12 #include "detail/common.h"
14 PYBIND11_NAMESPACE_BEGIN(PYBIND11_NAMESPACE)
16 PYBIND11_NAMESPACE_BEGIN(detail)
19 inline std::vector<ssize_t> c_strides(const std::vector<ssize_t> &shape, ssize_t itemsize) {
20 auto ndim = shape.size();
21 std::vector<ssize_t> strides(ndim, itemsize);
23 for (
size_t i = ndim - 1; i > 0; --i)
24 strides[i - 1] = strides[i] * shape[i];
29 inline std::vector<ssize_t> f_strides(
const std::vector<ssize_t> &shape, ssize_t itemsize) {
30 auto ndim = shape.size();
31 std::vector<ssize_t> strides(ndim, itemsize);
32 for (
size_t i = 1; i < ndim; ++i)
33 strides[i] = strides[i - 1] * shape[i - 1];
37 PYBIND11_NAMESPACE_END(detail)
46 std::vector<ssize_t> shape;
47 std::vector<ssize_t> strides;
48 bool readonly =
false;
50 buffer_info() =
default;
52 buffer_info(
void *ptr, ssize_t itemsize,
const std::string &format, ssize_t ndim,
53 detail::any_container<ssize_t> shape_in, detail::any_container<ssize_t> strides_in,
bool readonly=
false)
54 : ptr(ptr), itemsize(itemsize), size(1), format(format), ndim(ndim),
55 shape(std::move(shape_in)), strides(std::move(strides_in)), readonly(readonly) {
56 if (ndim != (ssize_t) shape.size() || ndim != (ssize_t) strides.size())
57 pybind11_fail(
"buffer_info: ndim doesn't match shape and/or strides length");
58 for (
size_t i = 0; i < (size_t) ndim; ++i)
63 buffer_info(T *ptr, detail::any_container<ssize_t> shape_in, detail::any_container<ssize_t> strides_in,
bool readonly=
false)
66 buffer_info(
void *ptr, ssize_t itemsize,
const std::string &format, ssize_t size,
bool readonly=
false)
67 : buffer_info(ptr, itemsize, format, 1, {size}, {itemsize}, readonly) { }
70 buffer_info(T *ptr, ssize_t size,
bool readonly=
false)
74 buffer_info(
const T *ptr, ssize_t size,
bool readonly=
true)
77 explicit buffer_info(Py_buffer *view,
bool ownview =
true)
78 : buffer_info(view->buf, view->itemsize, view->format, view->ndim,
79 {view->shape, view->shape + view->ndim},
84 ? std::vector<ssize_t>(view->strides, view->strides + view->ndim)
85 : detail::c_strides({view->shape, view->shape + view->ndim}, view->itemsize),
88 this->ownview = ownview;
95 (*this) = std::move(other);
100 itemsize = rhs.itemsize;
102 format = std::move(rhs.format);
104 shape = std::move(rhs.shape);
105 strides = std::move(rhs.strides);
106 std::swap(m_view, rhs.m_view);
107 std::swap(ownview, rhs.ownview);
108 readonly = rhs.readonly;
113 if (m_view && ownview) { PyBuffer_Release(m_view);
delete m_view; }
116 Py_buffer *view()
const {
return m_view; }
117 Py_buffer *&view() {
return m_view; }
122 detail::any_container<ssize_t> &&shape_in, detail::any_container<ssize_t> &&strides_in,
bool readonly)
123 :
buffer_info(ptr, itemsize, format, ndim, std::move(shape_in), std::move(strides_in), readonly) { }
125 Py_buffer *m_view =
nullptr;
126 bool ownview =
false;
129 PYBIND11_NAMESPACE_BEGIN(detail)
140 ((
sizeof(T) ==
sizeof(
long)) && b.format == (std::is_unsigned<T>::value ?
"L" :
"l")) ||
141 ((
sizeof(T) ==
sizeof(
size_t)) && b.format == (std::is_unsigned<T>::value ?
"N" :
"n")));
145 PYBIND11_NAMESPACE_END(detail)
146 PYBIND11_NAMESPACE_END(PYBIND11_NAMESPACE)
Information record describing a Python buffer object.