This is an automated email from the ASF dual-hosted git repository.

zeroshade pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/arrow-go.git


The following commit(s) were added to refs/heads/main by this push:
     new 8126a1bb fix(memory): handle zero-length checked reallocations (#1132)
8126a1bb is described below

commit 8126a1bbfdcff297488a43cc69f2edc4f47f2c23
Author: Minh Vu <[email protected]>
AuthorDate: Wed Aug 12 19:51:55 2026 +0200

    fix(memory): handle zero-length checked reallocations (#1132)
    
    ### Rationale for this change
    
    CheckedAllocator.Reallocate panics when called with nil, and zero-size
    reallocations leave stale entries in the leak-tracking map.
    
    ### What changes are included in this PR?
    
    Handle nil input buffers and remove the old allocation record when a
    reallocation reduces the size to zero. Add coverage for both paths.
    
    ### Are these changes tested?
    
    - `go test ./arrow/memory`
    
    ### Are there any user-facing changes?
    
    CheckedAllocator no longer panics or reports a false allocation leak for
    these reallocation paths. The allocator interface is unchanged.
---
 arrow/memory/buffer_test.go       | 11 +++++++++++
 arrow/memory/checked_allocator.go |  9 +++++++--
 2 files changed, 18 insertions(+), 2 deletions(-)

diff --git a/arrow/memory/buffer_test.go b/arrow/memory/buffer_test.go
index 549d57c4..7b413ec1 100644
--- a/arrow/memory/buffer_test.go
+++ b/arrow/memory/buffer_test.go
@@ -58,6 +58,17 @@ func TestNewResizableBuffer(t *testing.T) {
        assert.Zero(t, buf.Len())
 }
 
+func TestCheckedAllocatorReallocate(t *testing.T) {
+       mem := memory.NewCheckedAllocator(memory.NewGoAllocator())
+       defer mem.AssertSize(t, 0)
+
+       buf := mem.Reallocate(16, nil)
+       assert.Len(t, buf, 16)
+
+       buf = mem.Reallocate(0, buf)
+       assert.Empty(t, buf)
+}
+
 func TestBufferReset(t *testing.T) {
        mem := memory.NewCheckedAllocator(memory.NewGoAllocator())
        defer mem.AssertSize(t, 0)
diff --git a/arrow/memory/checked_allocator.go 
b/arrow/memory/checked_allocator.go
index 2c3726d2..95ac8d5e 100644
--- a/arrow/memory/checked_allocator.go
+++ b/arrow/memory/checked_allocator.go
@@ -68,14 +68,19 @@ func (a *CheckedAllocator) Allocate(size int) []byte {
 func (a *CheckedAllocator) Reallocate(size int, b []byte) []byte {
        a.sz.Add(int64(size - len(b)))
 
-       oldptr := uintptr(unsafe.Pointer(&b[0]))
+       var oldptr uintptr
+       if len(b) > 0 {
+               oldptr = uintptr(unsafe.Pointer(unsafe.SliceData(b)))
+       }
        out := a.mem.Reallocate(size, b)
+       if oldptr != 0 {
+               a.allocs.Delete(oldptr)
+       }
        if size == 0 {
                return out
        }
 
        newptr := uintptr(unsafe.Pointer(&out[0]))
-       a.allocs.Delete(oldptr)
        pcs := make([]uintptr, maxRetainedFrames)
 
        // For historical reasons the meaning of the skip argument

Reply via email to