@@ -149,34 +149,33 @@ extension _ArrayBufferProtocol {
149
149
elementsOf newValues: __owned C
150
150
) where C: Collection , C. Element == Element {
151
151
_internalInvariant ( startIndex == 0 , " _SliceBuffer should override this function. " )
152
- let oldCount = self . count
153
- let eraseCount = subrange. count
154
-
155
- let growth = newCount - eraseCount
156
- // This check will prevent storing a 0 count to the empty array singleton.
157
- if growth != 0 {
158
- self . count = oldCount + growth
159
- }
160
-
161
152
let elements = self . firstElementAddress
162
153
163
154
// erase all the elements we're replacing to create a hole
164
155
let holeStart = elements + subrange. lowerBound
165
156
let holeEnd = holeStart + newCount
166
-
167
- // directly forwards to Builtin.destroyArray
168
- // TODO: should we branch here or does the compiler branch implicitly?
157
+ let eraseCount = subrange. count
169
158
holeStart. deinitialize ( count: eraseCount)
170
159
171
- // resize the hole to make it the correct size
172
- // safe to always call, moveInitialize to the same location is a no-op
173
- let tailStart = elements + subrange. upperBound
174
- let tailCount = oldCount - subrange. upperBound
175
- holeEnd. moveInitialize ( from: tailStart, count: tailCount)
160
+ let growth = newCount - eraseCount
161
+
162
+ if growth != 0 {
163
+ let tailStart = elements + subrange. upperBound
164
+ let tailCount = oldCount - subrange. upperBound
165
+ holeEnd. moveInitialize ( from: tailStart, count: tailCount)
166
+ self . count += growth
167
+ }
176
168
177
- // place the values into the hole we created
169
+ // don't use UnsafeMutableBufferPointer.initialize(fromContentsOf:)
170
+ // since it behaves differently on collections that misreport count,
171
+ // and breaks validation tests for those usecases / potentially
172
+ // breaks ABI guarantees.
178
173
if newCount > 0 {
179
174
let done : Void ? = newValues. withContiguousStorageIfAvailable {
175
+ _precondition (
176
+ $0. count == newCount,
177
+ " invalid Collection: count differed in successive traversals "
178
+ )
180
179
holeStart. initialize ( from: $0. baseAddress!, count: newCount)
181
180
}
182
181
if done == nil {
0 commit comments