From 32065c07e27a46d1dce42272082e7bb9aa6e6c52 Mon Sep 17 00:00:00 2001 From: MilesCranmer Date: Mon, 30 Jun 2025 00:23:48 +0100 Subject: [PATCH 1/3] only set array size when safe to do so --- base/array.jl | 14 ++++++++++---- 1 file changed, 10 insertions(+), 4 deletions(-) diff --git a/base/array.jl b/base/array.jl index 61a3c39ca2bb7..a90b9a4285001 100644 --- a/base/array.jl +++ b/base/array.jl @@ -1117,12 +1117,13 @@ function _growbeg!(a::Vector, delta::Integer) len = length(a) offset = memoryrefoffset(ref) newlen = len + delta - setfield!(a, :size, (newlen,)) # if offset is far enough advanced to fit data in existing memory without copying if delta <= offset - 1 setfield!(a, :ref, @inbounds memoryref(ref, 1 - delta)) + setfield!(a, :size, (newlen,)) else @noinline _growbeg_internal!(a, delta, len) + setfield!(a, :size, (newlen,)) end return end @@ -1172,10 +1173,10 @@ function _growend!(a::Vector, delta::Integer) len = length(a) newlen = len + delta offset = memoryrefoffset(ref) - setfield!(a, :size, (newlen,)) newmemlen = offset + newlen - 1 if memlen < newmemlen @noinline _growend_internal!(a, delta, len) + setfield!(a, :size, (newlen,)) end return end @@ -1194,7 +1195,6 @@ function _growat!(a::Vector, i::Integer, delta::Integer) memlen = length(mem) newlen = len + delta offset = memoryrefoffset(ref) - setfield!(a, :size, (newlen,)) newmemlen = offset + newlen - 1 # which side would we rather grow into? @@ -1204,11 +1204,13 @@ function _growat!(a::Vector, i::Integer, delta::Integer) newref = @inbounds memoryref(mem, offset - delta) unsafe_copyto!(newref, ref, i) setfield!(a, :ref, newref) + setfield!(a, :size, (newlen,)) for j in i:i+delta-1 @inbounds _unsetindex!(a, j) end elseif !prefer_start && memlen >= newmemlen unsafe_copyto!(mem, offset - 1 + delta + i, mem, offset - 1 + i, len - i + 1) + setfield!(a, :size, (newlen,)) for j in i:i+delta-1 @inbounds _unsetindex!(a, j) end @@ -1222,6 +1224,10 @@ function _growat!(a::Vector, i::Integer, delta::Integer) unsafe_copyto!(newref, ref, i-1) unsafe_copyto!(newmem, newoffset + delta + i - 1, mem, offset + i - 1, len - i + 1) setfield!(a, :ref, newref) + setfield!(a, :size, (newlen,)) + for j in i:i+delta-1 + @inbounds _unsetindex!(a, j) + end end end @@ -1234,11 +1240,11 @@ function _deletebeg!(a::Vector, delta::Integer) @inbounds _unsetindex!(a, i) end newlen = len - delta + setfield!(a, :size, (newlen,)) if newlen != 0 # if newlen==0 we could accidentally index past the memory newref = @inbounds memoryref(a.ref, delta + 1) setfield!(a, :ref, newref) end - setfield!(a, :size, (newlen,)) return end function _deleteend!(a::Vector, delta::Integer) From 6006cddc7be6f31d116562e2aeac87ebb2d017e3 Mon Sep 17 00:00:00 2001 From: MilesCranmer Date: Mon, 30 Jun 2025 00:35:16 +0100 Subject: [PATCH 2/3] fix: remove unneccessary unsetindex --- base/array.jl | 3 --- 1 file changed, 3 deletions(-) diff --git a/base/array.jl b/base/array.jl index a90b9a4285001..602d60c9026a6 100644 --- a/base/array.jl +++ b/base/array.jl @@ -1225,9 +1225,6 @@ function _growat!(a::Vector, i::Integer, delta::Integer) unsafe_copyto!(newmem, newoffset + delta + i - 1, mem, offset + i - 1, len - i + 1) setfield!(a, :ref, newref) setfield!(a, :size, (newlen,)) - for j in i:i+delta-1 - @inbounds _unsetindex!(a, j) - end end end From 87c7cdb5dbd171107b5ac7da8ad09fc8ac51e638 Mon Sep 17 00:00:00 2001 From: Miles Cranmer Date: Tue, 1 Jul 2025 04:55:44 +0900 Subject: [PATCH 3/3] ensure newlen is set --- base/array.jl | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/base/array.jl b/base/array.jl index 602d60c9026a6..df79d7aa96261 100644 --- a/base/array.jl +++ b/base/array.jl @@ -1176,8 +1176,8 @@ function _growend!(a::Vector, delta::Integer) newmemlen = offset + newlen - 1 if memlen < newmemlen @noinline _growend_internal!(a, delta, len) - setfield!(a, :size, (newlen,)) end + setfield!(a, :size, (newlen,)) return end