That seems like a wasted opportunity to me. Let’s break down your example.
You have 3 meshes in the original buffer: A, B and C, in that order and tightly packed. Now, you want to add mesh D, but there’s not enough space for it. So you need a reallocation.
But “at the same time”, you independently decide that B is no longer needed.
The correct way to do this is to copy A, copy C, and copy D, so that the new buffer contains A, C, and D.
If you do it this way, you won’t have a B-shaped hole in the middle of your mesh data. Or more specifically, a
sizeof(D) - sizeof(B) shaped hole. It’s all nice and compact, just like it was when you started.
Now, doing this if you’re just deleting B is a bad idea; it’s faster to just leave the hole there. And if you’ve already deleted B, and D will fit into B’s former storage, it’s faster to just copy D over B’s data.
But once you decide that you need to do reallocation, it’s best to get rid of any holes in your storage. You’re already having to pay the cost of waiting on a memory transfer operation, so it makes sense to take a little extra time and optimize your memory layout.
My main point is that, if you do things this way, there are no overlapping writes (that is, no attempts to write to the same memory). The copy of A doesn’t overlap with the copy of C, and neither overlap with the copy of D. You can do GPU-to-GPU copies of A and C, then update the memory for D via a staging buffer or just mapped memory writes. There are no data races.