mirror of
https://github.com/protocolbuffers/protobuf-go.git
synced 2025-01-29 18:32:46 +00:00
encoding/protojson, internal/encoding/json: handle missing object values
In internal/encoding/json, report an error when encountering a } when we are expecting an object field value. For example, the input `{"":}` now correctly results in an error at the closing } token. In encoding/protojson, check for an unexpected EOF token in skipJSONValue. This is redundant with the check in internal/encoding/json, but adds a bit more defense against any other similar bugs that might exist. Fixes CVE-2024-24786 Change-Id: I03d52512acb5091c8549e31ca74541d57e56c99d Reviewed-on: https://go-review.googlesource.com/c/protobuf/+/569356 TryBot-Bypass: Damien Neil <dneil@google.com> Reviewed-by: Roland Shoemaker <roland@golang.org> Commit-Queue: Damien Neil <dneil@google.com>
This commit is contained in:
parent
235ef28b75
commit
f01a588e58
@ -2770,6 +2770,23 @@ func TestUnmarshal(t *testing.T) {
|
||||
inputText: `{"foo":{"bar":[{"baz":[{}]]}}`,
|
||||
umo: protojson.UnmarshalOptions{RecursionLimit: 5, DiscardUnknown: true},
|
||||
wantErr: "exceeded max recursion depth",
|
||||
}, {
|
||||
desc: "Object missing value: no DiscardUnknown",
|
||||
inputMessage: &testpb.TestAllTypes{},
|
||||
inputText: `{"":}`,
|
||||
umo: protojson.UnmarshalOptions{RecursionLimit: 5, DiscardUnknown: false},
|
||||
wantErr: `(line 1:2): unknown field ""`,
|
||||
}, {
|
||||
desc: "Object missing value: DiscardUnknown",
|
||||
inputMessage: &testpb.TestAllTypes{},
|
||||
inputText: `{"":}`,
|
||||
umo: protojson.UnmarshalOptions{RecursionLimit: 5, DiscardUnknown: true},
|
||||
wantErr: `(line 1:5): unexpected token`,
|
||||
}, {
|
||||
desc: "Object missing value: Any",
|
||||
inputMessage: &anypb.Any{},
|
||||
inputText: `{"":}`,
|
||||
wantErr: `(line 1:5): unexpected token`,
|
||||
}}
|
||||
|
||||
for _, tt := range tests {
|
||||
|
@ -322,6 +322,10 @@ func (d decoder) skipJSONValue() error {
|
||||
if open > d.opts.RecursionLimit {
|
||||
return errors.New("exceeded max recursion depth")
|
||||
}
|
||||
case json.EOF:
|
||||
// This can only happen if there's a bug in Decoder.Read.
|
||||
// Avoid an infinite loop if this does happen.
|
||||
return errors.New("unexpected EOF")
|
||||
}
|
||||
if open == 0 {
|
||||
return nil
|
||||
|
@ -121,7 +121,7 @@ func (d *Decoder) Read() (Token, error) {
|
||||
|
||||
case ObjectClose:
|
||||
if len(d.openStack) == 0 ||
|
||||
d.lastToken.kind == comma ||
|
||||
d.lastToken.kind&(Name|comma) != 0 ||
|
||||
d.openStack[len(d.openStack)-1] != ObjectOpen {
|
||||
return Token{}, d.newSyntaxError(tok.pos, unexpectedFmt, tok.RawString())
|
||||
}
|
||||
|
@ -1193,6 +1193,21 @@ func TestDecoder(t *testing.T) {
|
||||
{E: errEOF},
|
||||
},
|
||||
},
|
||||
{
|
||||
in: `{""`,
|
||||
want: []R{
|
||||
{V: ObjectOpen},
|
||||
{E: errEOF},
|
||||
},
|
||||
},
|
||||
{
|
||||
in: `{"":`,
|
||||
want: []R{
|
||||
{V: ObjectOpen},
|
||||
{V: Name{""}},
|
||||
{E: errEOF},
|
||||
},
|
||||
},
|
||||
{
|
||||
in: `{"34":"89",}`,
|
||||
want: []R{
|
||||
|
Loading…
x
Reference in New Issue
Block a user