15f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#################### View.MemoryView #################### 25f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 35f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# This utility provides cython.array and cython.view.memoryview 45f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 55f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)import cython 65f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 75f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# from cpython cimport ... 85f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef extern from "Python.h": 95f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) int PyIndex_Check "__Pyx_PyIndex_Check" (object) 105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) object PyLong_FromVoidPtr(void *) 115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef extern from "pythread.h": 135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) ctypedef void *PyThread_type_lock 145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) PyThread_type_lock PyThread_allocate_lock() 165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) void PyThread_free_lock(PyThread_type_lock) 175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) int PyThread_acquire_lock(PyThread_type_lock, int mode) nogil 185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) void PyThread_release_lock(PyThread_type_lock) nogil 195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef extern from "string.h": 215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) void *memset(void *b, int c, size_t len) 225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef extern from *: 245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) int __Pyx_GetBuffer(object, Py_buffer *, int) except -1 255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) void __Pyx_ReleaseBuffer(Py_buffer *) 265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) ctypedef struct PyObject 285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) ctypedef Py_ssize_t Py_intptr_t 295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) void Py_INCREF(PyObject *) 305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) void Py_DECREF(PyObject *) 315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) void* PyMem_Malloc(size_t n) 335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) void PyMem_Free(void *p) 345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef struct __pyx_memoryview "__pyx_memoryview_obj": 365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) Py_buffer view 375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) PyObject *obj 385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) __Pyx_TypeInfo *typeinfo 395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) ctypedef struct {{memviewslice_name}}: 415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) __pyx_memoryview *memview 425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) char *data 435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) Py_ssize_t shape[{{max_dims}}] 445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) Py_ssize_t strides[{{max_dims}}] 455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) Py_ssize_t suboffsets[{{max_dims}}] 465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) void __PYX_INC_MEMVIEW({{memviewslice_name}} *memslice, int have_gil) 485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) void __PYX_XDEC_MEMVIEW({{memviewslice_name}} *memslice, int have_gil) 495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) ctypedef struct __pyx_buffer "Py_buffer": 515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) PyObject *obj 525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) PyObject *Py_None 545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef enum: 565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) PyBUF_C_CONTIGUOUS, 575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) PyBUF_F_CONTIGUOUS, 585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) PyBUF_ANY_CONTIGUOUS 595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) PyBUF_FORMAT 605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) PyBUF_WRITABLE 615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) PyBUF_STRIDES 625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) PyBUF_INDIRECT 635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) PyBUF_RECORDS 645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) ctypedef struct __Pyx_TypeInfo: 665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) pass 675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef object capsule "__pyx_capsule_create" (void *p, char *sig) 695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef int __pyx_array_getbuffer(PyObject *obj, Py_buffer view, int flags) 705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef int __pyx_memoryview_getbuffer(PyObject *obj, Py_buffer view, int flags) 715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef extern from *: 735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) ctypedef int __pyx_atomic_int 745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) {{memviewslice_name}} slice_copy_contig "__pyx_memoryview_copy_new_contig"( 755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) __Pyx_memviewslice *from_mvs, 765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) char *mode, int ndim, 775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) size_t sizeof_dtype, int contig_flag, 785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) bint dtype_is_object) nogil except * 795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) bint slice_is_contig "__pyx_memviewslice_is_contig" ( 805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) {{memviewslice_name}} *mvs, char order, int ndim) nogil 815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) bint slices_overlap "__pyx_slices_overlap" ({{memviewslice_name}} *slice1, 825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) {{memviewslice_name}} *slice2, 835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) int ndim, size_t itemsize) nogil 845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef extern from "stdlib.h": 875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) void *malloc(size_t) nogil 885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) void free(void *) nogil 895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) void *memcpy(void *dest, void *src, size_t n) nogil 905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# 955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)### cython.array class 965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# 975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)@cname("__pyx_array") 995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef class array: 1005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 1015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef: 1025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) char *data 1035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) Py_ssize_t len 1045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) char *format 1055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) int ndim 1065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) Py_ssize_t *_shape 1075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) Py_ssize_t *_strides 1085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) Py_ssize_t itemsize 1095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) unicode mode # FIXME: this should have been a simple 'char' 1105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) bytes _format 1115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) void (*callback_free_data)(void *data) 1125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # cdef object _memview 1135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef bint free_data 1145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef bint dtype_is_object 1155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 1165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) def __cinit__(array self, tuple shape, Py_ssize_t itemsize, format not None, 1175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) mode="c", bint allocate_buffer=True): 1185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 1195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef int idx 1205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef Py_ssize_t i, dim 1215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef PyObject **p 1225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 1235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) self.ndim = <int> len(shape) 1245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) self.itemsize = itemsize 1255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 1265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if not self.ndim: 1275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) raise ValueError("Empty shape tuple for cython.array") 1285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 1295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if itemsize <= 0: 1305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) raise ValueError("itemsize <= 0 for cython.array") 1315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 1325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if isinstance(format, unicode): 1335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) format = (<unicode>format).encode('ASCII') 1345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) self._format = format # keep a reference to the byte string 1355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) self.format = self._format 1365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 1375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # use single malloc() for both shape and strides 1385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) self._shape = <Py_ssize_t *> PyMem_Malloc(sizeof(Py_ssize_t)*self.ndim*2) 1395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) self._strides = self._shape + self.ndim 1405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 1415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if not self._shape: 1425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) raise MemoryError("unable to allocate shape and strides.") 1435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 1445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # cdef Py_ssize_t dim, stride 1455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) for idx, dim in enumerate(shape): 1465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if dim <= 0: 1475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) raise ValueError("Invalid shape in axis %d: %d." % (idx, dim)) 1485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) self._shape[idx] = dim 1495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 1505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef char order 1515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if mode == 'fortran': 1525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) order = b'F' 1535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) self.mode = u'fortran' 1545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) elif mode == 'c': 1555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) order = b'C' 1565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) self.mode = u'c' 1575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 1585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) raise ValueError("Invalid mode, expected 'c' or 'fortran', got %s" % mode) 1595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 1605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) self.len = fill_contig_strides_array(self._shape, self._strides, 1615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) itemsize, self.ndim, order) 1625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 1635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) self.free_data = allocate_buffer 1645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) self.dtype_is_object = format == b'O' 1655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if allocate_buffer: 1665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # use malloc() for backwards compatibility 1675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # in case external code wants to change the data pointer 1685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) self.data = <char *>malloc(self.len) 1695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if not self.data: 1705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) raise MemoryError("unable to allocate array data.") 1715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 1725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if self.dtype_is_object: 1735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) p = <PyObject **> self.data 1745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) for i in range(self.len / itemsize): 1755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) p[i] = Py_None 1765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) Py_INCREF(Py_None) 1775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 1785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) @cname('getbuffer') 1795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) def __getbuffer__(self, Py_buffer *info, int flags): 1805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef int bufmode = -1 1815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if self.mode == u"c": 1825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) bufmode = PyBUF_C_CONTIGUOUS | PyBUF_ANY_CONTIGUOUS 1835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) elif self.mode == u"fortran": 1845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) bufmode = PyBUF_F_CONTIGUOUS | PyBUF_ANY_CONTIGUOUS 1855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if not (flags & bufmode): 1865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) raise ValueError("Can only create a buffer that is contiguous in memory.") 1875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) info.buf = self.data 1885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) info.len = self.len 1895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) info.ndim = self.ndim 1905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) info.shape = self._shape 1915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) info.strides = self._strides 1925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) info.suboffsets = NULL 1935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) info.itemsize = self.itemsize 1945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) info.readonly = 0 1955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 1965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if flags & PyBUF_FORMAT: 1975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) info.format = self.format 1985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 1995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) info.format = NULL 2005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 2015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) info.obj = self 2025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 2035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) __pyx_getbuffer = capsule(<void *> &__pyx_array_getbuffer, "getbuffer(obj, view, flags)") 2045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 2055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) def __dealloc__(array self): 2065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if self.callback_free_data != NULL: 2075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) self.callback_free_data(self.data) 2085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) elif self.free_data: 2095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if self.dtype_is_object: 2105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) refcount_objects_in_slice(self.data, self._shape, 2115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) self._strides, self.ndim, False) 2125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) free(self.data) 2135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) PyMem_Free(self._shape) 2145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 2155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) property memview: 2165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) @cname('get_memview') 2175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) def __get__(self): 2185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # Make this a property as 'self.data' may be set after instantiation 2195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) flags = PyBUF_ANY_CONTIGUOUS|PyBUF_FORMAT|PyBUF_WRITABLE 2205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return memoryview(self, flags, self.dtype_is_object) 2215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 2225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 2235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) def __getattr__(self, attr): 2245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return getattr(self.memview, attr) 2255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 2265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) def __getitem__(self, item): 2275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return self.memview[item] 2285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 2295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) def __setitem__(self, item, value): 2305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) self.memview[item] = value 2315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 2325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 2335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)@cname("__pyx_array_new") 2345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef array array_cwrapper(tuple shape, Py_ssize_t itemsize, char *format, 2355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) char *mode, char *buf): 2365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef array result 2375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 2385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if buf == NULL: 2395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) result = array(shape, itemsize, format, mode.decode('ASCII')) 2405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 2415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) result = array(shape, itemsize, format, mode.decode('ASCII'), 2425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) allocate_buffer=False) 2435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) result.data = buf 2445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 2455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return result 2465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 2475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 2485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# 2495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)### Memoryview constants and cython.view.memoryview class 2505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# 2515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 2525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# Disable generic_contiguous, as it makes trouble verifying contiguity: 2535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# - 'contiguous' or '::1' means the dimension is contiguous with dtype 2545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# - 'indirect_contiguous' means a contiguous list of pointers 2555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# - dtype contiguous must be contiguous in the first or last dimension 2565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# from the start, or from the dimension following the last indirect dimension 2575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# 2585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# e.g. 2595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# int[::indirect_contiguous, ::contiguous, :] 2605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# 2615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# is valid (list of pointers to 2d fortran-contiguous array), but 2625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# 2635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# int[::generic_contiguous, ::contiguous, :] 2645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# 2655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# would mean you'd have assert dimension 0 to be indirect (and pointer contiguous) at runtime. 2665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# So it doesn't bring any performance benefit, and it's only confusing. 2675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 2685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)@cname('__pyx_MemviewEnum') 2695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef class Enum(object): 2705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef object name 2715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) def __init__(self, name): 2725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) self.name = name 2735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) def __repr__(self): 2745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return self.name 2755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 2765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef generic = Enum("<strided and direct or indirect>") 2775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef strided = Enum("<strided and direct>") # default 2785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef indirect = Enum("<strided and indirect>") 2795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# Disable generic_contiguous, as it is a troublemaker 2805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)#cdef generic_contiguous = Enum("<contiguous and direct or indirect>") 2815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef contiguous = Enum("<contiguous and direct>") 2825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef indirect_contiguous = Enum("<contiguous and indirect>") 2835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 2845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# 'follow' is implied when the first or last axis is ::1 2855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 2865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 2875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)@cname('__pyx_align_pointer') 2885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef void *align_pointer(void *memory, size_t alignment) nogil: 2895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) "Align pointer memory on a given boundary" 2905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef Py_intptr_t aligned_p = <Py_intptr_t> memory 2915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef size_t offset 2925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 2935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) with cython.cdivision(True): 2945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) offset = aligned_p % alignment 2955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 2965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if offset > 0: 2975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) aligned_p += alignment - offset 2985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 2995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return <void *> aligned_p 3005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 3015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)@cname('__pyx_memoryview') 3025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef class memoryview(object): 3035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 3045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef object obj 3055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef object _size 3065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef object _array_interface 3075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef PyThread_type_lock lock 3085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # the following array will contain a single __pyx_atomic int with 3095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # suitable alignment 3105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef __pyx_atomic_int acquisition_count[2] 3115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef __pyx_atomic_int *acquisition_count_aligned_p 3125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef Py_buffer view 3135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef int flags 3145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef bint dtype_is_object 3155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef __Pyx_TypeInfo *typeinfo 3165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 3175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) def __cinit__(memoryview self, object obj, int flags, bint dtype_is_object=False): 3185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) self.obj = obj 3195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) self.flags = flags 3205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if type(self) is memoryview or obj is not None: 3215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) __Pyx_GetBuffer(obj, &self.view, flags) 3225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if <PyObject *> self.view.obj == NULL: 3235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) (<__pyx_buffer *> &self.view).obj = Py_None 3245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) Py_INCREF(Py_None) 3255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 3265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) self.lock = PyThread_allocate_lock() 3275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if self.lock == NULL: 3285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) raise MemoryError 3295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 3305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if flags & PyBUF_FORMAT: 3315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) self.dtype_is_object = self.view.format == b'O' 3325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 3335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) self.dtype_is_object = dtype_is_object 3345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 3355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) self.acquisition_count_aligned_p = <__pyx_atomic_int *> align_pointer( 3365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) <void *> &self.acquisition_count[0], sizeof(__pyx_atomic_int)) 3375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) self.typeinfo = NULL 3385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 3395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) def __dealloc__(memoryview self): 3405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if self.obj is not None: 3415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) __Pyx_ReleaseBuffer(&self.view) 3425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 3435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if self.lock != NULL: 3445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) PyThread_free_lock(self.lock) 3455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 3465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef char *get_item_pointer(memoryview self, object index) except NULL: 3475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef Py_ssize_t dim 3485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef char *itemp = <char *> self.view.buf 3495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 3505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) for dim, idx in enumerate(index): 3515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) itemp = pybuffer_index(&self.view, itemp, idx, dim) 3525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 3535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return itemp 3545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 3555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) #@cname('__pyx_memoryview_getitem') 3565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) def __getitem__(memoryview self, object index): 3575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if index is Ellipsis: 3585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return self 3595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 3605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) have_slices, indices = _unellipsify(index, self.view.ndim) 3615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 3625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef char *itemp 3635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if have_slices: 3645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return memview_slice(self, indices) 3655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 3665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) itemp = self.get_item_pointer(indices) 3675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return self.convert_item_to_object(itemp) 3685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 3695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) def __setitem__(memoryview self, object index, object value): 3705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) have_slices, index = _unellipsify(index, self.view.ndim) 3715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 3725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if have_slices: 3735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) obj = self.is_slice(value) 3745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if obj: 3755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) self.setitem_slice_assignment(self[index], obj) 3765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 3775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) self.setitem_slice_assign_scalar(self[index], value) 3785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 3795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) self.setitem_indexed(index, value) 3805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 3815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef is_slice(self, obj): 3825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if not isinstance(obj, memoryview): 3835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) try: 3845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) obj = memoryview(obj, self.flags|PyBUF_ANY_CONTIGUOUS, 3855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) self.dtype_is_object) 3865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) except TypeError: 3875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return None 3885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 3895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return obj 3905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 3915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef setitem_slice_assignment(self, dst, src): 3925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef {{memviewslice_name}} dst_slice 3935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef {{memviewslice_name}} src_slice 3945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 3955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) memoryview_copy_contents(get_slice_from_memview(src, &src_slice)[0], 3965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) get_slice_from_memview(dst, &dst_slice)[0], 3975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) src.ndim, dst.ndim, self.dtype_is_object) 3985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 3995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef setitem_slice_assign_scalar(self, memoryview dst, value): 4005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef int array[128] 4015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef void *tmp = NULL 4025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef void *item 4035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 4045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef {{memviewslice_name}} *dst_slice 4055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef {{memviewslice_name}} tmp_slice 4065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) dst_slice = get_slice_from_memview(dst, &tmp_slice) 4075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 4085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if <size_t>self.view.itemsize > sizeof(array): 4095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) tmp = PyMem_Malloc(self.view.itemsize) 4105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if tmp == NULL: 4115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) raise MemoryError 4125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) item = tmp 4135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 4145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) item = <void *> array 4155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 4165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) try: 4175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if self.dtype_is_object: 4185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) (<PyObject **> item)[0] = <PyObject *> value 4195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 4205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) self.assign_item_from_object(<char *> item, value) 4215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 4225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # It would be easy to support indirect dimensions, but it's easier 4235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # to disallow :) 4245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if self.view.suboffsets != NULL: 4255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) assert_direct_dimensions(self.view.suboffsets, self.view.ndim) 4265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) slice_assign_scalar(dst_slice, dst.view.ndim, self.view.itemsize, 4275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) item, self.dtype_is_object) 4285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) finally: 4295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) PyMem_Free(tmp) 4305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 4315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef setitem_indexed(self, index, value): 4325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef char *itemp = self.get_item_pointer(index) 4335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) self.assign_item_from_object(itemp, value) 4345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 4355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef convert_item_to_object(self, char *itemp): 4365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) """Only used if instantiated manually by the user, or if Cython doesn't 4375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) know how to convert the type""" 4385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) import struct 4395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef bytes bytesitem 4405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # Do a manual and complete check here instead of this easy hack 4415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) bytesitem = itemp[:self.view.itemsize] 4425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) try: 4435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) result = struct.unpack(self.view.format, bytesitem) 4445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) except struct.error: 4455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) raise ValueError("Unable to convert item to object") 4465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 4475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if len(self.view.format) == 1: 4485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return result[0] 4495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return result 4505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 4515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef assign_item_from_object(self, char *itemp, object value): 4525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) """Only used if instantiated manually by the user, or if Cython doesn't 4535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) know how to convert the type""" 4545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) import struct 4555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef char c 4565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef bytes bytesvalue 4575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef Py_ssize_t i 4585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 4595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if isinstance(value, tuple): 4605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) bytesvalue = struct.pack(self.view.format, *value) 4615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 4625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) bytesvalue = struct.pack(self.view.format, value) 4635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 4645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) for i, c in enumerate(bytesvalue): 4655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) itemp[i] = c 4665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 4675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) @cname('getbuffer') 4685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) def __getbuffer__(self, Py_buffer *info, int flags): 4695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if flags & PyBUF_STRIDES: 4705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) info.shape = self.view.shape 4715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 4725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) info.shape = NULL 4735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 4745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if flags & PyBUF_STRIDES: 4755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) info.strides = self.view.strides 4765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 4775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) info.strides = NULL 4785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 4795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if flags & PyBUF_INDIRECT: 4805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) info.suboffsets = self.view.suboffsets 4815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 4825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) info.suboffsets = NULL 4835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 4845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if flags & PyBUF_FORMAT: 4855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) info.format = self.view.format 4865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 4875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) info.format = NULL 4885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 4895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) info.buf = self.view.buf 4905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) info.ndim = self.view.ndim 4915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) info.itemsize = self.view.itemsize 4925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) info.len = self.view.len 4935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) info.readonly = 0 4945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) info.obj = self 4955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 4965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) __pyx_getbuffer = capsule(<void *> &__pyx_memoryview_getbuffer, "getbuffer(obj, view, flags)") 4975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 4985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # Some properties that have the same sematics as in NumPy 4995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) property T: 5005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) @cname('__pyx_memoryview_transpose') 5015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) def __get__(self): 5025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef _memoryviewslice result = memoryview_copy(self) 5035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) transpose_memslice(&result.from_slice) 5045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return result 5055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 5065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) property base: 5075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) @cname('__pyx_memoryview__get__base') 5085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) def __get__(self): 5095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return self.obj 5105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 5115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) property shape: 5125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) @cname('__pyx_memoryview_get_shape') 5135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) def __get__(self): 5145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return tuple([self.view.shape[i] for i in xrange(self.view.ndim)]) 5155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 5165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) property strides: 5175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) @cname('__pyx_memoryview_get_strides') 5185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) def __get__(self): 5195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if self.view.strides == NULL: 5205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # Note: we always ask for strides, so if this is not set it's a bug 5215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) raise ValueError("Buffer view does not expose strides") 5225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 5235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return tuple([self.view.strides[i] for i in xrange(self.view.ndim)]) 5245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 5255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) property suboffsets: 5265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) @cname('__pyx_memoryview_get_suboffsets') 5275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) def __get__(self): 5285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if self.view.suboffsets == NULL: 5295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return [-1] * self.view.ndim 5305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 5315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return tuple([self.view.suboffsets[i] for i in xrange(self.view.ndim)]) 5325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 5335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) property ndim: 5345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) @cname('__pyx_memoryview_get_ndim') 5355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) def __get__(self): 5365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return self.view.ndim 5375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 5385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) property itemsize: 5395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) @cname('__pyx_memoryview_get_itemsize') 5405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) def __get__(self): 5415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return self.view.itemsize 5425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 5435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) property nbytes: 5445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) @cname('__pyx_memoryview_get_nbytes') 5455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) def __get__(self): 5465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return self.size * self.view.itemsize 5475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 5485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) property size: 5495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) @cname('__pyx_memoryview_get_size') 5505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) def __get__(self): 5515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if self._size is None: 5525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) result = 1 5535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 5545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) for length in self.shape: 5555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) result *= length 5565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 5575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) self._size = result 5585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 5595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return self._size 5605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 5615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) def __len__(self): 5625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if self.view.ndim >= 1: 5635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return self.view.shape[0] 5645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 5655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return 0 5665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 5675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) def __repr__(self): 5685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return "<MemoryView of %r at 0x%x>" % (self.base.__class__.__name__, 5695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) id(self)) 5705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 5715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) def __str__(self): 5725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return "<MemoryView of %r object>" % (self.base.__class__.__name__,) 5735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 5745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # Support the same attributes as memoryview slices 5755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) def is_c_contig(self): 5765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef {{memviewslice_name}} *mslice 5775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef {{memviewslice_name}} tmp 5785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) mslice = get_slice_from_memview(self, &tmp) 5795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return slice_is_contig(mslice, 'C', self.view.ndim) 5805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 5815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) def is_f_contig(self): 5825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef {{memviewslice_name}} *mslice 5835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef {{memviewslice_name}} tmp 5845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) mslice = get_slice_from_memview(self, &tmp) 5855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return slice_is_contig(mslice, 'F', self.view.ndim) 5865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 5875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) def copy(self): 5885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef {{memviewslice_name}} mslice 5895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef int flags = self.flags & ~PyBUF_F_CONTIGUOUS 5905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 5915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) slice_copy(self, &mslice) 5925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) mslice = slice_copy_contig(&mslice, "c", self.view.ndim, 5935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) self.view.itemsize, 5945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) flags|PyBUF_C_CONTIGUOUS, 5955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) self.dtype_is_object) 5965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 5975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return memoryview_copy_from_slice(self, &mslice) 5985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 5995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) def copy_fortran(self): 6005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef {{memviewslice_name}} src, dst 6015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef int flags = self.flags & ~PyBUF_C_CONTIGUOUS 6025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 6035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) slice_copy(self, &src) 6045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) dst = slice_copy_contig(&src, "fortran", self.view.ndim, 6055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) self.view.itemsize, 6065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) flags|PyBUF_F_CONTIGUOUS, 6075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) self.dtype_is_object) 6085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 6095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return memoryview_copy_from_slice(self, &dst) 6105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 6115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 6125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)@cname('__pyx_memoryview_new') 6135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef memoryview_cwrapper(object o, int flags, bint dtype_is_object, __Pyx_TypeInfo *typeinfo): 6145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef memoryview result = memoryview(o, flags, dtype_is_object) 6155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) result.typeinfo = typeinfo 6165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return result 6175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 6185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)@cname('__pyx_memoryview_check') 6195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef inline bint memoryview_check(object o): 6205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return isinstance(o, memoryview) 6215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 6225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef tuple _unellipsify(object index, int ndim): 6235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) """ 6245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) Replace all ellipses with full slices and fill incomplete indices with 6255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) full slices. 6265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) """ 6275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if not isinstance(index, tuple): 6285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) tup = (index,) 6295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 6305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) tup = index 6315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 6325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) result = [] 6335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) have_slices = False 6345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) seen_ellipsis = False 6355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) for idx, item in enumerate(tup): 6365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if item is Ellipsis: 6375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if not seen_ellipsis: 6385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) result.extend([slice(None)] * (ndim - len(tup) + 1)) 6395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) seen_ellipsis = True 6405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 6415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) result.append(slice(None)) 6425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) have_slices = True 6435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 6445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if not isinstance(item, slice) and not PyIndex_Check(item): 6455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) raise TypeError("Cannot index with type '%s'" % type(item)) 6465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 6475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) have_slices = have_slices or isinstance(item, slice) 6485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) result.append(item) 6495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 6505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) nslices = ndim - len(result) 6515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if nslices: 6525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) result.extend([slice(None)] * nslices) 6535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 6545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return have_slices or nslices, tuple(result) 6555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 6565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef assert_direct_dimensions(Py_ssize_t *suboffsets, int ndim): 6575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef int i 6585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) for i in range(ndim): 6595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if suboffsets[i] >= 0: 6605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) raise ValueError("Indirect dimensions not supported") 6615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 6625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# 6635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)### Slicing a memoryview 6645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# 6655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 6665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)@cname('__pyx_memview_slice') 6675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef memoryview memview_slice(memoryview memview, object indices): 6685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef int new_ndim = 0, suboffset_dim = -1, dim 6695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef bint negative_step 6705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef {{memviewslice_name}} src, dst 6715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef {{memviewslice_name}} *p_src 6725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 6735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # dst is copied by value in memoryview_fromslice -- initialize it 6745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # src is never copied 6755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) memset(&dst, 0, sizeof(dst)) 6765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 6775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef _memoryviewslice memviewsliceobj 6785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 6795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) assert memview.view.ndim > 0 6805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 6815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if isinstance(memview, _memoryviewslice): 6825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) memviewsliceobj = memview 6835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) p_src = &memviewsliceobj.from_slice 6845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 6855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) slice_copy(memview, &src) 6865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) p_src = &src 6875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 6885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # Note: don't use variable src at this point 6895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # SubNote: we should be able to declare variables in blocks... 6905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 6915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # memoryview_fromslice() will inc our dst slice 6925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) dst.memview = p_src.memview 6935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) dst.data = p_src.data 6945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 6955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # Put everything in temps to avoid this bloody warning: 6965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # "Argument evaluation order in C function call is undefined and 6975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # may not be as expected" 6985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef {{memviewslice_name}} *p_dst = &dst 6995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef int *p_suboffset_dim = &suboffset_dim 7005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef Py_ssize_t start, stop, step 7015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef bint have_start, have_stop, have_step 7025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 7035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) for dim, index in enumerate(indices): 7045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if PyIndex_Check(index): 7055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) slice_memviewslice( 7065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) p_dst, p_src.shape[dim], p_src.strides[dim], p_src.suboffsets[dim], 7075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) dim, new_ndim, p_suboffset_dim, 7085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) index, 0, 0, # start, stop, step 7095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 0, 0, 0, # have_{start,stop,step} 7105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) False) 7115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) elif index is None: 7125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) p_dst.shape[new_ndim] = 1 7135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) p_dst.strides[new_ndim] = 0 7145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) p_dst.suboffsets[new_ndim] = -1 7155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) new_ndim += 1 7165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 7175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) start = index.start or 0 7185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) stop = index.stop or 0 7195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) step = index.step or 0 7205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 7215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) have_start = index.start is not None 7225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) have_stop = index.stop is not None 7235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) have_step = index.step is not None 7245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 7255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) slice_memviewslice( 7265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) p_dst, p_src.shape[dim], p_src.strides[dim], p_src.suboffsets[dim], 7275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) dim, new_ndim, p_suboffset_dim, 7285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) start, stop, step, 7295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) have_start, have_stop, have_step, 7305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) True) 7315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) new_ndim += 1 7325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 7335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if isinstance(memview, _memoryviewslice): 7345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return memoryview_fromslice(dst, new_ndim, 7355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) memviewsliceobj.to_object_func, 7365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) memviewsliceobj.to_dtype_func, 7375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) memview.dtype_is_object) 7385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 7395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return memoryview_fromslice(dst, new_ndim, NULL, NULL, 7405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) memview.dtype_is_object) 7415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 7425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 7435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# 7445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)### Slicing in a single dimension of a memoryviewslice 7455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# 7465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 7475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef extern from "stdlib.h": 7485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) void abort() nogil 7495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) void printf(char *s, ...) nogil 7505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 7515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef extern from "stdio.h": 7525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) ctypedef struct FILE 7535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) FILE *stderr 7545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) int fputs(char *s, FILE *stream) 7555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 7565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef extern from "pystate.h": 7575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) void PyThreadState_Get() nogil 7585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 7595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # These are not actually nogil, but we check for the GIL before calling them 7605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) void PyErr_SetString(PyObject *type, char *msg) nogil 7615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) PyObject *PyErr_Format(PyObject *exc, char *msg, ...) nogil 7625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 7635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)@cname('__pyx_memoryview_slice_memviewslice') 7645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef int slice_memviewslice( 7655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) {{memviewslice_name}} *dst, 7665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) Py_ssize_t shape, Py_ssize_t stride, Py_ssize_t suboffset, 7675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) int dim, int new_ndim, int *suboffset_dim, 7685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) Py_ssize_t start, Py_ssize_t stop, Py_ssize_t step, 7695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) int have_start, int have_stop, int have_step, 7705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) bint is_slice) nogil except -1: 7715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) """ 7725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) Create a new slice dst given slice src. 7735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 7745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) dim - the current src dimension (indexing will make dimensions 7755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) disappear) 7765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) new_dim - the new dst dimension 7775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) suboffset_dim - pointer to a single int initialized to -1 to keep track of 7785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) where slicing offsets should be added 7795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) """ 7805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 7815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef Py_ssize_t new_shape 7825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef bint negative_step 7835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 7845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if not is_slice: 7855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # index is a normal integer-like index 7865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if start < 0: 7875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) start += shape 7885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if not 0 <= start < shape: 7895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) _err_dim(IndexError, "Index out of bounds (axis %d)", dim) 7905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 7915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # index is a slice 7925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) negative_step = have_step != 0 and step < 0 7935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 7945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if have_step and step == 0: 7955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) _err_dim(ValueError, "Step may not be zero (axis %d)", dim) 7965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 7975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # check our bounds and set defaults 7985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if have_start: 7995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if start < 0: 8005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) start += shape 8015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if start < 0: 8025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) start = 0 8035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) elif start >= shape: 8045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if negative_step: 8055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) start = shape - 1 8065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 8075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) start = shape 8085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 8095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if negative_step: 8105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) start = shape - 1 8115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 8125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) start = 0 8135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 8145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if have_stop: 8155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if stop < 0: 8165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) stop += shape 8175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if stop < 0: 8185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) stop = 0 8195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) elif stop > shape: 8205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) stop = shape 8215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 8225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if negative_step: 8235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) stop = -1 8245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 8255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) stop = shape 8265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 8275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if not have_step: 8285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) step = 1 8295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 8305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # len = ceil( (stop - start) / step ) 8315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) with cython.cdivision(True): 8325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) new_shape = (stop - start) // step 8335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 8345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if (stop - start) - step * new_shape: 8355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) new_shape += 1 8365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 8375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if new_shape < 0: 8385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) new_shape = 0 8395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 8405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # shape/strides/suboffsets 8415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) dst.strides[new_ndim] = stride * step 8425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) dst.shape[new_ndim] = new_shape 8435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) dst.suboffsets[new_ndim] = suboffset 8445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 8455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # Add the slicing or idexing offsets to the right suboffset or base data * 8465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if suboffset_dim[0] < 0: 8475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) dst.data += start * stride 8485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 8495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) dst.suboffsets[suboffset_dim[0]] += start * stride 8505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 8515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if suboffset >= 0: 8525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if not is_slice: 8535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if new_ndim == 0: 8545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) dst.data = (<char **> dst.data)[0] + suboffset 8555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 8565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) _err_dim(IndexError, "All dimensions preceding dimension %d " 8575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) "must be indexed and not sliced", dim) 8585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 8595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) suboffset_dim[0] = new_ndim 8605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 8615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return 0 8625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 8635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# 8645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)### Index a memoryview 8655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# 8665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)@cname('__pyx_pybuffer_index') 8675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef char *pybuffer_index(Py_buffer *view, char *bufp, Py_ssize_t index, 8685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) Py_ssize_t dim) except NULL: 8695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef Py_ssize_t shape, stride, suboffset = -1 8705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef Py_ssize_t itemsize = view.itemsize 8715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef char *resultp 8725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 8735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if view.ndim == 0: 8745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) shape = view.len / itemsize 8755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) stride = itemsize 8765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 8775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) shape = view.shape[dim] 8785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) stride = view.strides[dim] 8795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if view.suboffsets != NULL: 8805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) suboffset = view.suboffsets[dim] 8815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 8825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if index < 0: 8835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) index += view.shape[dim] 8845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if index < 0: 8855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) raise IndexError("Out of bounds on buffer access (axis %d)" % dim) 8865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 8875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if index >= shape: 8885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) raise IndexError("Out of bounds on buffer access (axis %d)" % dim) 8895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 8905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) resultp = bufp + index * stride 8915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if suboffset >= 0: 8925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) resultp = (<char **> resultp)[0] + suboffset 8935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 8945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return resultp 8955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 8965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# 8975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)### Transposing a memoryviewslice 8985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# 8995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)@cname('__pyx_memslice_transpose') 9005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef int transpose_memslice({{memviewslice_name}} *memslice) nogil except 0: 9015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef int ndim = memslice.memview.view.ndim 9025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 9035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef Py_ssize_t *shape = memslice.shape 9045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef Py_ssize_t *strides = memslice.strides 9055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 9065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # reverse strides and shape 9075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef int i, j 9085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) for i in range(ndim / 2): 9095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) j = ndim - 1 - i 9105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) strides[i], strides[j] = strides[j], strides[i] 9115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) shape[i], shape[j] = shape[j], shape[i] 9125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 9135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if memslice.suboffsets[i] >= 0 or memslice.suboffsets[j] >= 0: 9145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) _err(ValueError, "Cannot transpose memoryview with indirect dimensions") 9155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 9165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return 1 9175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 9185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# 9195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)### Creating new memoryview objects from slices and memoryviews 9205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# 9215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)@cname('__pyx_memoryviewslice') 9225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef class _memoryviewslice(memoryview): 9235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) "Internal class for passing memoryview slices to Python" 9245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 9255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # We need this to keep our shape/strides/suboffset pointers valid 9265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef {{memviewslice_name}} from_slice 9275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # We need this only to print it's class' name 9285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef object from_object 9295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 9305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef object (*to_object_func)(char *) 9315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef int (*to_dtype_func)(char *, object) except 0 9325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 9335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) def __dealloc__(self): 9345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) __PYX_XDEC_MEMVIEW(&self.from_slice, 1) 9355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 9365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef convert_item_to_object(self, char *itemp): 9375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if self.to_object_func != NULL: 9385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return self.to_object_func(itemp) 9395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 9405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return memoryview.convert_item_to_object(self, itemp) 9415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 9425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef assign_item_from_object(self, char *itemp, object value): 9435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if self.to_dtype_func != NULL: 9445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) self.to_dtype_func(itemp, value) 9455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 9465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) memoryview.assign_item_from_object(self, itemp, value) 9475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 9485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) property base: 9495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) @cname('__pyx_memoryviewslice__get__base') 9505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) def __get__(self): 9515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return self.from_object 9525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 9535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) __pyx_getbuffer = capsule(<void *> &__pyx_memoryview_getbuffer, "getbuffer(obj, view, flags)") 9545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 9555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 9565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)@cname('__pyx_memoryview_fromslice') 9575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef memoryview_fromslice({{memviewslice_name}} memviewslice, 9585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) int ndim, 9595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) object (*to_object_func)(char *), 9605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) int (*to_dtype_func)(char *, object) except 0, 9615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) bint dtype_is_object): 9625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 9635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef _memoryviewslice result 9645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef int i 9655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 9665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if <PyObject *> memviewslice.memview == Py_None: 9675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return None 9685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 9695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # assert 0 < ndim <= memviewslice.memview.view.ndim, ( 9705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # ndim, memviewslice.memview.view.ndim) 9715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 9725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) result = _memoryviewslice(None, 0, dtype_is_object) 9735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 9745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) result.from_slice = memviewslice 9755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) __PYX_INC_MEMVIEW(&memviewslice, 1) 9765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 9775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) result.from_object = (<memoryview> memviewslice.memview).base 9785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) result.typeinfo = memviewslice.memview.typeinfo 9795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 9805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) result.view = memviewslice.memview.view 9815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) result.view.buf = <void *> memviewslice.data 9825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) result.view.ndim = ndim 9835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) (<__pyx_buffer *> &result.view).obj = Py_None 9845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) Py_INCREF(Py_None) 9855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 9865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) result.flags = PyBUF_RECORDS 9875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 9885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) result.view.shape = <Py_ssize_t *> result.from_slice.shape 9895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) result.view.strides = <Py_ssize_t *> result.from_slice.strides 9905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) result.view.suboffsets = <Py_ssize_t *> result.from_slice.suboffsets 9915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 9925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) result.view.len = result.view.itemsize 9935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) for i in range(ndim): 9945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) result.view.len *= result.view.shape[i] 9955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 9965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) result.to_object_func = to_object_func 9975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) result.to_dtype_func = to_dtype_func 9985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 9995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return result 10005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 10015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)@cname('__pyx_memoryview_get_slice_from_memoryview') 10025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef {{memviewslice_name}} *get_slice_from_memview(memoryview memview, 10035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) {{memviewslice_name}} *mslice): 10045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef _memoryviewslice obj 10055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if isinstance(memview, _memoryviewslice): 10065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) obj = memview 10075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return &obj.from_slice 10085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 10095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) slice_copy(memview, mslice) 10105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return mslice 10115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 10125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)@cname('__pyx_memoryview_slice_copy') 10135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef void slice_copy(memoryview memview, {{memviewslice_name}} *dst): 10145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef int dim 10155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef (Py_ssize_t*) shape, strides, suboffsets 10165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 10175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) shape = memview.view.shape 10185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) strides = memview.view.strides 10195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) suboffsets = memview.view.suboffsets 10205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 10215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) dst.memview = <__pyx_memoryview *> memview 10225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) dst.data = <char *> memview.view.buf 10235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 10245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) for dim in range(memview.view.ndim): 10255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) dst.shape[dim] = shape[dim] 10265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) dst.strides[dim] = strides[dim] 10275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if suboffsets == NULL: 10285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) dst.suboffsets[dim] = -1 10295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 10305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) dst.suboffsets[dim] = suboffsets[dim] 10315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 10325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)@cname('__pyx_memoryview_copy_object') 10335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef memoryview_copy(memoryview memview): 10345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) "Create a new memoryview object" 10355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef {{memviewslice_name}} memviewslice 10365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) slice_copy(memview, &memviewslice) 10375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return memoryview_copy_from_slice(memview, &memviewslice) 10385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 10395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)@cname('__pyx_memoryview_copy_object_from_slice') 10405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef memoryview_copy_from_slice(memoryview memview, {{memviewslice_name}} *memviewslice): 10415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) """ 10425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) Create a new memoryview object from a given memoryview object and slice. 10435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) """ 10445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef object (*to_object_func)(char *) 10455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef int (*to_dtype_func)(char *, object) except 0 10465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 10475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if isinstance(memview, _memoryviewslice): 10485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) to_object_func = (<_memoryviewslice> memview).to_object_func 10495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) to_dtype_func = (<_memoryviewslice> memview).to_dtype_func 10505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 10515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) to_object_func = NULL 10525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) to_dtype_func = NULL 10535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 10545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return memoryview_fromslice(memviewslice[0], memview.view.ndim, 10555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) to_object_func, to_dtype_func, 10565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) memview.dtype_is_object) 10575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 10585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 10595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# 10605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)### Copy the contents of a memoryview slices 10615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# 10625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef Py_ssize_t abs_py_ssize_t(Py_ssize_t arg) nogil: 10635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if arg < 0: 10645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return -arg 10655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 10665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return arg 10675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 10685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)@cname('__pyx_get_best_slice_order') 10695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef char get_best_order({{memviewslice_name}} *mslice, int ndim) nogil: 10705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) """ 10715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) Figure out the best memory access order for a given slice. 10725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) """ 10735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef int i 10745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef Py_ssize_t c_stride = 0 10755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef Py_ssize_t f_stride = 0 10765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 10775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) for i in range(ndim - 1, -1, -1): 10785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if mslice.shape[i] > 1: 10795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) c_stride = mslice.strides[i] 10805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) break 10815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 10825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) for i in range(ndim): 10835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if mslice.shape[i] > 1: 10845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) f_stride = mslice.strides[i] 10855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) break 10865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 10875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if abs_py_ssize_t(c_stride) <= abs_py_ssize_t(f_stride): 10885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return 'C' 10895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 10905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return 'F' 10915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 10925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)@cython.cdivision(True) 10935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef void _copy_strided_to_strided(char *src_data, Py_ssize_t *src_strides, 10945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) char *dst_data, Py_ssize_t *dst_strides, 10955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) Py_ssize_t *src_shape, Py_ssize_t *dst_shape, 10965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) int ndim, size_t itemsize) nogil: 10975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # Note: src_extent is 1 if we're broadcasting 10985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # dst_extent always >= src_extent as we don't do reductions 10995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef Py_ssize_t i 11005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef Py_ssize_t src_extent = src_shape[0] 11015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef Py_ssize_t dst_extent = dst_shape[0] 11025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef Py_ssize_t src_stride = src_strides[0] 11035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef Py_ssize_t dst_stride = dst_strides[0] 11045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 11055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if ndim == 1: 11065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if (src_stride > 0 and dst_stride > 0 and 11075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) <size_t> src_stride == itemsize == <size_t> dst_stride): 11085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) memcpy(dst_data, src_data, itemsize * dst_extent) 11095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 11105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) for i in range(dst_extent): 11115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) memcpy(dst_data, src_data, itemsize) 11125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) src_data += src_stride 11135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) dst_data += dst_stride 11145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 11155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) for i in range(dst_extent): 11165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) _copy_strided_to_strided(src_data, src_strides + 1, 11175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) dst_data, dst_strides + 1, 11185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) src_shape + 1, dst_shape + 1, 11195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) ndim - 1, itemsize) 11205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) src_data += src_stride 11215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) dst_data += dst_stride 11225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 11235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef void copy_strided_to_strided({{memviewslice_name}} *src, 11245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) {{memviewslice_name}} *dst, 11255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) int ndim, size_t itemsize) nogil: 11265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) _copy_strided_to_strided(src.data, src.strides, dst.data, dst.strides, 11275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) src.shape, dst.shape, ndim, itemsize) 11285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 11295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)@cname('__pyx_memoryview_slice_get_size') 11305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef Py_ssize_t slice_get_size({{memviewslice_name}} *src, int ndim) nogil: 11315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) "Return the size of the memory occupied by the slice in number of bytes" 11325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef int i 11335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef Py_ssize_t size = src.memview.view.itemsize 11345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 11355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) for i in range(ndim): 11365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) size *= src.shape[i] 11375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 11385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return size 11395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 11405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)@cname('__pyx_fill_contig_strides_array') 11415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef Py_ssize_t fill_contig_strides_array( 11425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) Py_ssize_t *shape, Py_ssize_t *strides, Py_ssize_t stride, 11435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) int ndim, char order) nogil: 11445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) """ 11455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) Fill the strides array for a slice with C or F contiguous strides. 11465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) This is like PyBuffer_FillContiguousStrides, but compatible with py < 2.6 11475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) """ 11485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef int idx 11495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 11505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if order == 'F': 11515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) for idx in range(ndim): 11525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) strides[idx] = stride 11535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) stride = stride * shape[idx] 11545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 11555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) for idx in range(ndim - 1, -1, -1): 11565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) strides[idx] = stride 11575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) stride = stride * shape[idx] 11585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 11595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return stride 11605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 11615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)@cname('__pyx_memoryview_copy_data_to_temp') 11625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef void *copy_data_to_temp({{memviewslice_name}} *src, 11635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) {{memviewslice_name}} *tmpslice, 11645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) char order, 11655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) int ndim) nogil except NULL: 11665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) """ 11675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) Copy a direct slice to temporary contiguous memory. The caller should free 11685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) the result when done. 11695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) """ 11705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef int i 11715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef void *result 11725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 11735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef size_t itemsize = src.memview.view.itemsize 11745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef size_t size = slice_get_size(src, ndim) 11755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 11765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) result = malloc(size) 11775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if not result: 11785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) _err(MemoryError, NULL) 11795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 11805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # tmpslice[0] = src 11815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) tmpslice.data = <char *> result 11825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) tmpslice.memview = src.memview 11835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) for i in range(ndim): 11845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) tmpslice.shape[i] = src.shape[i] 11855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) tmpslice.suboffsets[i] = -1 11865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 11875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) fill_contig_strides_array(&tmpslice.shape[0], &tmpslice.strides[0], itemsize, 11885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) ndim, order) 11895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 11905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # We need to broadcast strides again 11915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) for i in range(ndim): 11925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if tmpslice.shape[i] == 1: 11935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) tmpslice.strides[i] = 0 11945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 11955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if slice_is_contig(src, order, ndim): 11965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) memcpy(result, src.data, size) 11975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 11985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) copy_strided_to_strided(src, tmpslice, ndim, itemsize) 11995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 12005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return result 12015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 12025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# Use 'with gil' functions and avoid 'with gil' blocks, as the code within the blocks 12035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# has temporaries that need the GIL to clean up 12045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)@cname('__pyx_memoryview_err_extents') 12055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef int _err_extents(int i, Py_ssize_t extent1, 12065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) Py_ssize_t extent2) except -1 with gil: 12075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) raise ValueError("got differing extents in dimension %d (got %d and %d)" % 12085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) (i, extent1, extent2)) 12095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 12105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)@cname('__pyx_memoryview_err_dim') 12115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef int _err_dim(object error, char *msg, int dim) except -1 with gil: 12125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) raise error(msg.decode('ascii') % dim) 12135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 12145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)@cname('__pyx_memoryview_err') 12155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef int _err(object error, char *msg) except -1 with gil: 12165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if msg != NULL: 12175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) raise error(msg.decode('ascii')) 12185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 12195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) raise error 12205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 12215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)@cname('__pyx_memoryview_copy_contents') 12225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef int memoryview_copy_contents({{memviewslice_name}} src, 12235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) {{memviewslice_name}} dst, 12245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) int src_ndim, int dst_ndim, 12255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) bint dtype_is_object) nogil except -1: 12265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) """ 12275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) Copy memory from slice src to slice dst. 12285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) Check for overlapping memory and verify the shapes. 12295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) """ 12305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef void *tmpdata = NULL 12315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef size_t itemsize = src.memview.view.itemsize 12325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef int i 12335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef char order = get_best_order(&src, src_ndim) 12345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef bint broadcasting = False 12355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef bint direct_copy = False 12365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef {{memviewslice_name}} tmp 12375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 12385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if src_ndim < dst_ndim: 12395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) broadcast_leading(&src, src_ndim, dst_ndim) 12405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) elif dst_ndim < src_ndim: 12415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) broadcast_leading(&dst, dst_ndim, src_ndim) 12425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 12435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef int ndim = max(src_ndim, dst_ndim) 12445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 12455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) for i in range(ndim): 12465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if src.shape[i] != dst.shape[i]: 12475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if src.shape[i] == 1: 12485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) broadcasting = True 12495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) src.strides[i] = 0 12505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 12515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) _err_extents(i, dst.shape[i], src.shape[i]) 12525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 12535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if src.suboffsets[i] >= 0: 12545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) _err_dim(ValueError, "Dimension %d is not direct", i) 12555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 12565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if slices_overlap(&src, &dst, ndim, itemsize): 12575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # slices overlap, copy to temp, copy temp to dst 12585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if not slice_is_contig(&src, order, ndim): 12595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) order = get_best_order(&dst, ndim) 12605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 12615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) tmpdata = copy_data_to_temp(&src, &tmp, order, ndim) 12625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) src = tmp 12635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 12645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if not broadcasting: 12655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # See if both slices have equal contiguity, in that case perform a 12665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # direct copy. This only works when we are not broadcasting. 12675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if slice_is_contig(&src, 'C', ndim): 12685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) direct_copy = slice_is_contig(&dst, 'C', ndim) 12695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) elif slice_is_contig(&src, 'F', ndim): 12705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) direct_copy = slice_is_contig(&dst, 'F', ndim) 12715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 12725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if direct_copy: 12735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # Contiguous slices with same order 12745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) refcount_copying(&dst, dtype_is_object, ndim, False) 12755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) memcpy(dst.data, src.data, slice_get_size(&src, ndim)) 12765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) refcount_copying(&dst, dtype_is_object, ndim, True) 12775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) free(tmpdata) 12785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return 0 12795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 12805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if order == 'F' == get_best_order(&dst, ndim): 12815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # see if both slices have Fortran order, transpose them to match our 12825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # C-style indexing order 12835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) transpose_memslice(&src) 12845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) transpose_memslice(&dst) 12855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 12865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) refcount_copying(&dst, dtype_is_object, ndim, False) 12875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) copy_strided_to_strided(&src, &dst, ndim, itemsize) 12885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) refcount_copying(&dst, dtype_is_object, ndim, True) 12895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 12905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) free(tmpdata) 12915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return 0 12925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 12935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)@cname('__pyx_memoryview_broadcast_leading') 12945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef void broadcast_leading({{memviewslice_name}} *slice, 12955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) int ndim, 12965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) int ndim_other) nogil: 12975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef int i 12985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef int offset = ndim_other - ndim 12995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 13005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) for i in range(ndim - 1, -1, -1): 13015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) slice.shape[i + offset] = slice.shape[i] 13025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) slice.strides[i + offset] = slice.strides[i] 13035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) slice.suboffsets[i + offset] = slice.suboffsets[i] 13045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 13055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) for i in range(offset): 13065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) slice.shape[i] = 1 13075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) slice.strides[i] = slice.strides[0] 13085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) slice.suboffsets[i] = -1 13095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 13105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# 13115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)### Take care of refcounting the objects in slices. Do this seperately from any copying, 13125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)### to minimize acquiring the GIL 13135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# 13145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 13155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)@cname('__pyx_memoryview_refcount_copying') 13165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef void refcount_copying({{memviewslice_name}} *dst, bint dtype_is_object, 13175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) int ndim, bint inc) nogil: 13185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # incref or decref the objects in the destination slice if the dtype is 13195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # object 13205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if dtype_is_object: 13215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) refcount_objects_in_slice_with_gil(dst.data, dst.shape, 13225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) dst.strides, ndim, inc) 13235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 13245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)@cname('__pyx_memoryview_refcount_objects_in_slice_with_gil') 13255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef void refcount_objects_in_slice_with_gil(char *data, Py_ssize_t *shape, 13265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) Py_ssize_t *strides, int ndim, 13275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) bint inc) with gil: 13285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) refcount_objects_in_slice(data, shape, strides, ndim, inc) 13295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 13305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)@cname('__pyx_memoryview_refcount_objects_in_slice') 13315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef void refcount_objects_in_slice(char *data, Py_ssize_t *shape, 13325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) Py_ssize_t *strides, int ndim, bint inc): 13335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef Py_ssize_t i 13345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 13355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) for i in range(shape[0]): 13365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if ndim == 1: 13375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if inc: 13385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) Py_INCREF((<PyObject **> data)[0]) 13395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 13405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) Py_DECREF((<PyObject **> data)[0]) 13415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 13425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) refcount_objects_in_slice(data, shape + 1, strides + 1, 13435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) ndim - 1, inc) 13445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 13455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) data += strides[0] 13465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 13475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# 13485f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)### Scalar to slice assignment 13495f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)# 13505f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)@cname('__pyx_memoryview_slice_assign_scalar') 13515f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef void slice_assign_scalar({{memviewslice_name}} *dst, int ndim, 13525f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) size_t itemsize, void *item, 13535f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) bint dtype_is_object) nogil: 13545f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) refcount_copying(dst, dtype_is_object, ndim, False) 13555f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) _slice_assign_scalar(dst.data, dst.shape, dst.strides, ndim, 13565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) itemsize, item) 13575f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) refcount_copying(dst, dtype_is_object, ndim, True) 13585f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 13595f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 13605f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)@cname('__pyx_memoryview__slice_assign_scalar') 13615f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef void _slice_assign_scalar(char *data, Py_ssize_t *shape, 13625f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) Py_ssize_t *strides, int ndim, 13635f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) size_t itemsize, void *item) nogil: 13645f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef Py_ssize_t i 13655f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef Py_ssize_t stride = strides[0] 13665f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef Py_ssize_t extent = shape[0] 13675f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 13685f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if ndim == 1: 13695f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) for i in range(extent): 13705f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) memcpy(data, item, itemsize) 13715f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) data += stride 13725f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 13735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) for i in range(extent): 13745f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) _slice_assign_scalar(data, shape + 1, strides + 1, 13755f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) ndim - 1, itemsize, item) 13765f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) data += stride 13775f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 13785f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 13795f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)############### BufferFormatFromTypeInfo ############### 13805f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef extern from *: 13815f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) ctypedef struct __Pyx_StructField 13825f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 13835f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef enum: 13845f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) __PYX_BUF_FLAGS_PACKED_STRUCT 13855f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) __PYX_BUF_FLAGS_INTEGER_COMPLEX 13865f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 13875f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) ctypedef struct __Pyx_TypeInfo: 13885f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) char* name 13895f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) __Pyx_StructField* fields 13905f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) size_t size 13915f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) size_t arraysize[8] 13925f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) int ndim 13935f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) char typegroup 13945f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) char is_unsigned 13955f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) int flags 13965f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 13975f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) ctypedef struct __Pyx_StructField: 13985f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) __Pyx_TypeInfo* type 13995f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) char* name 14005f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) size_t offset 14015f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 14025f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) ctypedef struct __Pyx_BufFmt_StackElem: 14035f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) __Pyx_StructField* field 14045f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) size_t parent_offset 14055f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 14065f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) #ctypedef struct __Pyx_BufFmt_Context: 14075f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) # __Pyx_StructField root 14085f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) __Pyx_BufFmt_StackElem* head 14095f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 14105f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) struct __pyx_typeinfo_string: 14115f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) char string[3] 14125f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 14135f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) __pyx_typeinfo_string __Pyx_TypeInfoToFormat(__Pyx_TypeInfo *) 14145f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 14155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 14165f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)@cname('__pyx_format_from_typeinfo') 14175f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)cdef bytes format_from_typeinfo(__Pyx_TypeInfo *type): 14185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef __Pyx_StructField *field 14195f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef __pyx_typeinfo_string fmt 14205f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) cdef bytes part, result 14215f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 14225f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if type.typegroup == 'S': 14235f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) assert type.fields != NULL and type.fields.type != NULL 14245f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 14255f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if type.flags & __PYX_BUF_FLAGS_PACKED_STRUCT: 14265f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) alignment = b'^' 14275f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 14285f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) alignment = b'' 14295f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 14305f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) parts = [b"T{"] 14315f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) field = type.fields 14325f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 14335f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) while field.type: 14345f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) part = format_from_typeinfo(field.type) 14355f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) parts.append(part + b':' + field.name + b':') 14365f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) field += 1 14375f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 14385f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) result = alignment.join(parts) + b'}' 14395f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 14405f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) fmt = __Pyx_TypeInfoToFormat(type) 14415f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) if type.arraysize[0]: 14425f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) extents = [unicode(type.arraysize[i]) for i in range(type.ndim)] 14435f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) result = (u"(%s)" % u','.join(extents)).encode('ascii') + fmt.string 14445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else: 14455f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) result = fmt.string 14465f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) 14475f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) return result 1448