You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@arrow.apache.org by we...@apache.org on 2018/09/16 00:43:10 UTC
[arrow] branch master updated: ARROW-3228: [Python] Do not allow
PyObject_GetBuffer to obtain non-readonly Py_buffer when pyarrow Buffer is
not mutable
This is an automated email from the ASF dual-hosted git repository.
wesm pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/arrow.git
The following commit(s) were added to refs/heads/master by this push:
new 4121c5a ARROW-3228: [Python] Do not allow PyObject_GetBuffer to obtain non-readonly Py_buffer when pyarrow Buffer is not mutable
4121c5a is described below
commit 4121c5abe9e5ff852bc738b46c04d99132bced62
Author: Wes McKinney <we...@apache.org>
AuthorDate: Sat Sep 15 20:42:59 2018 -0400
ARROW-3228: [Python] Do not allow PyObject_GetBuffer to obtain non-readonly Py_buffer when pyarrow Buffer is not mutable
NumPy tries to obtain a writable buffer to determine mutability. This was passing silently:
https://github.com/numpy/numpy/blob/e8d177f74adbe5c7630721a4ab3f20f58839ac99/numpy/core/src/multiarray/ctors.c#L3711
Author: Wes McKinney <we...@apache.org>
Closes #2567 from wesm/ARROW-3228 and squashes the following commits:
95287e6ea <Wes McKinney> Raise exception when writable buffer requested by PyObject_GetBuffer when pyarrow.Buffer is not writable
---
python/pyarrow/io.pxi | 11 +++++++----
python/pyarrow/tests/test_io.py | 11 +++++++++++
2 files changed, 18 insertions(+), 4 deletions(-)
diff --git a/python/pyarrow/io.pxi b/python/pyarrow/io.pxi
index e240b23..8414f07 100644
--- a/python/pyarrow/io.pxi
+++ b/python/pyarrow/io.pxi
@@ -821,6 +821,13 @@ cdef class Buffer:
self.buffer.get().size())
def __getbuffer__(self, cp.Py_buffer* buffer, int flags):
+ if self.buffer.get().is_mutable():
+ buffer.readonly = 0
+ else:
+ if flags & cp.PyBUF_WRITABLE:
+ raise BufferError("Writable buffer requested but Arrow "
+ "buffer was not mutable")
+ buffer.readonly = 1
buffer.buf = <char *>self.buffer.get().data()
buffer.format = 'b'
buffer.internal = NULL
@@ -828,10 +835,6 @@ cdef class Buffer:
buffer.len = self.size
buffer.ndim = 1
buffer.obj = self
- if self.buffer.get().is_mutable():
- buffer.readonly = 0
- else:
- buffer.readonly = 1
buffer.shape = self.shape
buffer.strides = self.strides
buffer.suboffsets = NULL
diff --git a/python/pyarrow/tests/test_io.py b/python/pyarrow/tests/test_io.py
index 547dee3..c1a210d 100644
--- a/python/pyarrow/tests/test_io.py
+++ b/python/pyarrow/tests/test_io.py
@@ -450,6 +450,17 @@ def test_buffer_hashing():
hash(pa.py_buffer(b'123'))
+def test_buffer_protocol_respects_immutability():
+ # ARROW-3228; NumPy's frombuffer ctor determines whether a buffer-like
+ # object is mutable by first attempting to get a mutable buffer using
+ # PyObject_FromBuffer. If that fails, it assumes that the object is
+ # immutable
+ a = b'12345'
+ arrow_ref = pa.py_buffer(a)
+ numpy_ref = np.frombuffer(arrow_ref, dtype=np.uint8)
+ assert not numpy_ref.flags.writeable
+
+
def test_foreign_buffer():
obj = np.array([1, 2], dtype=np.int32)
addr = obj.__array_interface__["data"][0]