-
Notifications
You must be signed in to change notification settings - Fork 17.7k
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
encoding/gob: excessive memory consumption #10490
Comments
This input is probably a dup, but please test separately.
|
@robpike, ping. This is the last one for gob. |
No need to ping. The milestone is sufficient. |
The later this bug is fixed the later in the release cycle the rest of the bugs will be discovered. |
I investigated this a bit, but need to stop for now. What I found is that when I turn on encoding/gob/debug.go, and then call Debug(bytes.NewReader("...the hex...")) the variable numFields in debug.go gets set to a too big number, undoubtedly due to the corrupted gob input. I have not yet worked backwards to find out if there's a way that gob can tell that the number of fields it is being asked to keep track of is too big. |
We know input size. If claimed number of entries is N and minimum entry size is S, can't we check that N*S <= DATA_SIZE? |
Working as intended, if somewhat unfortunate. The slices falsely encoded in these data are just under the cutoff for "too big". If they were slightly larger, they would be rejected outright. In general, we can't compare the data length against the buffer size because the stream may contain type definitions, which mean some of the data will be in a second, as yet unread, message. We could put in a really complicated test for those cases that are guaranteed to be in this message, but since the goal here is hardening, that's pointless: other data types can still trigger the big allocation |
The data claims to contain a type definition with 117507149 fields, the type should be followed by 117507149 field definitions, each field definition takes non-zero number of bytes, a 92-byte data can't possibly contain that. |
That's not true in general. A slice can be stored in many messages, depending on its contents. Please leave this closed. |
@robpike How is it possible that a slice is stored in several messages? The code seems to just read in all slice elements from the provided buffer. I don't understand why it does not make sense to sanity check claimed data size against real data size. If we have N elements with minimal wire size S, input data must be at least N*S bytes. Please elaborate. |
Because the slice may contain interface fields that require a type definition. |
Is it answer to the first question (slice stored in several messages) or to the second (checking of data size)? |
A slice can in general require as many messages as there are elements. Therefore it is not easy to say, this message is too short for the slice data. As I said above, it's feasible to check for certain slice types but not all, so I don't believe it's worth doing at all since it can't be done properly. |
Rob, have you already commented somewhere on the question, "how can I
|
I have not. |
go version devel +8ea2438 Fri Apr 17 13:44:30 2015 +0300 linux/amd64
with https://go-review.googlesource.com/#/c/8942/ appled.
The following program consumes 2GB while the input is few bytes. I suspect it is possible to modify the input to force the program to allocate arbitrary amount of memory and run for arbitrary period of time.
Allocations happen while receiving a wire type (encoding/gob.(*Decoder).recvType).
The text was updated successfully, but these errors were encountered: