-
Notifications
You must be signed in to change notification settings - Fork 17.9k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
net: Buffers.WriteTo is prone to memory leaks #45163
Comments
Change https://golang.org/cl/303829 mentions this issue: |
It looks to me like the writev implementation manipulates the net.Buffers value directly. Should these two implementations be the same? Lines 731 to 742 in f58c78a
Lines 69 to 79 in f58c78a
|
@cbandy Yes, they should. Want to send a patch for 1.19? |
Change https://golang.org/cl/373374 mentions this issue: |
Isn't this a breaking change? For example code like and does not work correctly anymore since Go 1.17 because it expects the underlying array to not be modified. I have tried searching for usages of net.Buffers on GitHub. Most of the time, the net.Buffers were allocated temporarily just before calling cleared the memory already. Other uses tried to cache the underlying buffers, so it is not clear that zeroing the elements in the underlying array is better than not touching them. After the change, it is also not possible to reuse the net.Buffers underlying data to write to multiple writers without allocating a copy of the net.Buffers (e.g. to retry on another connection), but I haven't found any usages that would do so. |
I also forgot to mention https://github.com/kiwicom/gocql/blob/354a9342c24f61f448e0eff351eda4438f8d7b55/conn.go#L1031-L1033 which is another instance where not modifying the backing array would be helpful, although this piece of code could be rewritten to not need the underlying array. |
Thanks. That's interesting. This change already went out in the Go 1.17 release. So the question now is whether we should roll it back for 1.18, or just document it. Given that it has already gone out, and given that the |
My understanding is that these examples were incorrect before Go 1.17. I had similar code in one of my projects. Both copies of
🤔 I forget how I learned that it modified its receiver. I'm surprised that there is no mention of it on the type or method! These perhaps? |
I see, thanks for pointing this out! So we just need to add documentation for net.Buffers. |
Change https://go.dev/cl/387434 mentions this issue: |
There is code in the wild that copies the Buffers slice, but not the contents. Let's document explicitly that it is not safe to do so. Updates #45163 Change-Id: Id45e27b93037d4e9f2bfde2558e7869983b60bcf Reviewed-on: https://go-review.googlesource.com/c/go/+/387434 Reviewed-by: Ian Lance Taylor <iant@golang.org> Run-TryBot: Ian Lance Taylor <iant@golang.org> TryBot-Result: Gopher Robot <gobot@golang.org> Reviewed-by: Damien Neil <dneil@google.com>
Updates #45163 Change-Id: I73a6f22715550e0e8b83fbd3ebec72ef019f153f Reviewed-on: https://go-review.googlesource.com/c/go/+/373374 Run-TryBot: Lee Baokun <bk@golangcn.org> Run-TryBot: Ian Lance Taylor <iant@google.com> TryBot-Result: Gopher Robot <gobot@golang.org> Auto-Submit: Ian Lance Taylor <iant@google.com> Reviewed-by: Carlos Amedee <carlos@golang.org> Reviewed-by: Ian Lance Taylor <iant@google.com>
Buffers.WriteTo
modifies its receiver (insideconsume
), leaving part of the backing array inaccessible. But it can still contain references that pin potentially large buffers into memory, so if the client code continues to hold the remainder of the slice for further use, it may have much higher memory consumption than expected.The fix is simply to set
(v*)[0]
to nil before advancing.The text was updated successfully, but these errors were encountered: