gtsocial-umbx

Unnamed repository; edit this file 'description' to name the repository.
Log | Files | Refs | README | LICENSE

decode.go (21218B)


      1 // Copyright 2018 The Go Authors. All rights reserved.
      2 // Use of this source code is governed by a BSD-style
      3 // license that can be found in the LICENSE file.
      4 
      5 package prototext
      6 
      7 import (
      8 	"fmt"
      9 	"unicode/utf8"
     10 
     11 	"google.golang.org/protobuf/internal/encoding/messageset"
     12 	"google.golang.org/protobuf/internal/encoding/text"
     13 	"google.golang.org/protobuf/internal/errors"
     14 	"google.golang.org/protobuf/internal/flags"
     15 	"google.golang.org/protobuf/internal/genid"
     16 	"google.golang.org/protobuf/internal/pragma"
     17 	"google.golang.org/protobuf/internal/set"
     18 	"google.golang.org/protobuf/internal/strs"
     19 	"google.golang.org/protobuf/proto"
     20 	"google.golang.org/protobuf/reflect/protoreflect"
     21 	"google.golang.org/protobuf/reflect/protoregistry"
     22 )
     23 
     24 // Unmarshal reads the given []byte into the given proto.Message.
     25 // The provided message must be mutable (e.g., a non-nil pointer to a message).
     26 func Unmarshal(b []byte, m proto.Message) error {
     27 	return UnmarshalOptions{}.Unmarshal(b, m)
     28 }
     29 
     30 // UnmarshalOptions is a configurable textproto format unmarshaler.
     31 type UnmarshalOptions struct {
     32 	pragma.NoUnkeyedLiterals
     33 
     34 	// AllowPartial accepts input for messages that will result in missing
     35 	// required fields. If AllowPartial is false (the default), Unmarshal will
     36 	// return error if there are any missing required fields.
     37 	AllowPartial bool
     38 
     39 	// DiscardUnknown specifies whether to ignore unknown fields when parsing.
     40 	// An unknown field is any field whose field name or field number does not
     41 	// resolve to any known or extension field in the message.
     42 	// By default, unmarshal rejects unknown fields as an error.
     43 	DiscardUnknown bool
     44 
     45 	// Resolver is used for looking up types when unmarshaling
     46 	// google.protobuf.Any messages or extension fields.
     47 	// If nil, this defaults to using protoregistry.GlobalTypes.
     48 	Resolver interface {
     49 		protoregistry.MessageTypeResolver
     50 		protoregistry.ExtensionTypeResolver
     51 	}
     52 }
     53 
     54 // Unmarshal reads the given []byte and populates the given proto.Message
     55 // using options in the UnmarshalOptions object.
     56 // The provided message must be mutable (e.g., a non-nil pointer to a message).
     57 func (o UnmarshalOptions) Unmarshal(b []byte, m proto.Message) error {
     58 	return o.unmarshal(b, m)
     59 }
     60 
     61 // unmarshal is a centralized function that all unmarshal operations go through.
     62 // For profiling purposes, avoid changing the name of this function or
     63 // introducing other code paths for unmarshal that do not go through this.
     64 func (o UnmarshalOptions) unmarshal(b []byte, m proto.Message) error {
     65 	proto.Reset(m)
     66 
     67 	if o.Resolver == nil {
     68 		o.Resolver = protoregistry.GlobalTypes
     69 	}
     70 
     71 	dec := decoder{text.NewDecoder(b), o}
     72 	if err := dec.unmarshalMessage(m.ProtoReflect(), false); err != nil {
     73 		return err
     74 	}
     75 	if o.AllowPartial {
     76 		return nil
     77 	}
     78 	return proto.CheckInitialized(m)
     79 }
     80 
     81 type decoder struct {
     82 	*text.Decoder
     83 	opts UnmarshalOptions
     84 }
     85 
     86 // newError returns an error object with position info.
     87 func (d decoder) newError(pos int, f string, x ...interface{}) error {
     88 	line, column := d.Position(pos)
     89 	head := fmt.Sprintf("(line %d:%d): ", line, column)
     90 	return errors.New(head+f, x...)
     91 }
     92 
     93 // unexpectedTokenError returns a syntax error for the given unexpected token.
     94 func (d decoder) unexpectedTokenError(tok text.Token) error {
     95 	return d.syntaxError(tok.Pos(), "unexpected token: %s", tok.RawString())
     96 }
     97 
     98 // syntaxError returns a syntax error for given position.
     99 func (d decoder) syntaxError(pos int, f string, x ...interface{}) error {
    100 	line, column := d.Position(pos)
    101 	head := fmt.Sprintf("syntax error (line %d:%d): ", line, column)
    102 	return errors.New(head+f, x...)
    103 }
    104 
    105 // unmarshalMessage unmarshals into the given protoreflect.Message.
    106 func (d decoder) unmarshalMessage(m protoreflect.Message, checkDelims bool) error {
    107 	messageDesc := m.Descriptor()
    108 	if !flags.ProtoLegacy && messageset.IsMessageSet(messageDesc) {
    109 		return errors.New("no support for proto1 MessageSets")
    110 	}
    111 
    112 	if messageDesc.FullName() == genid.Any_message_fullname {
    113 		return d.unmarshalAny(m, checkDelims)
    114 	}
    115 
    116 	if checkDelims {
    117 		tok, err := d.Read()
    118 		if err != nil {
    119 			return err
    120 		}
    121 
    122 		if tok.Kind() != text.MessageOpen {
    123 			return d.unexpectedTokenError(tok)
    124 		}
    125 	}
    126 
    127 	var seenNums set.Ints
    128 	var seenOneofs set.Ints
    129 	fieldDescs := messageDesc.Fields()
    130 
    131 	for {
    132 		// Read field name.
    133 		tok, err := d.Read()
    134 		if err != nil {
    135 			return err
    136 		}
    137 		switch typ := tok.Kind(); typ {
    138 		case text.Name:
    139 			// Continue below.
    140 		case text.EOF:
    141 			if checkDelims {
    142 				return text.ErrUnexpectedEOF
    143 			}
    144 			return nil
    145 		default:
    146 			if checkDelims && typ == text.MessageClose {
    147 				return nil
    148 			}
    149 			return d.unexpectedTokenError(tok)
    150 		}
    151 
    152 		// Resolve the field descriptor.
    153 		var name protoreflect.Name
    154 		var fd protoreflect.FieldDescriptor
    155 		var xt protoreflect.ExtensionType
    156 		var xtErr error
    157 		var isFieldNumberName bool
    158 
    159 		switch tok.NameKind() {
    160 		case text.IdentName:
    161 			name = protoreflect.Name(tok.IdentName())
    162 			fd = fieldDescs.ByTextName(string(name))
    163 
    164 		case text.TypeName:
    165 			// Handle extensions only. This code path is not for Any.
    166 			xt, xtErr = d.opts.Resolver.FindExtensionByName(protoreflect.FullName(tok.TypeName()))
    167 
    168 		case text.FieldNumber:
    169 			isFieldNumberName = true
    170 			num := protoreflect.FieldNumber(tok.FieldNumber())
    171 			if !num.IsValid() {
    172 				return d.newError(tok.Pos(), "invalid field number: %d", num)
    173 			}
    174 			fd = fieldDescs.ByNumber(num)
    175 			if fd == nil {
    176 				xt, xtErr = d.opts.Resolver.FindExtensionByNumber(messageDesc.FullName(), num)
    177 			}
    178 		}
    179 
    180 		if xt != nil {
    181 			fd = xt.TypeDescriptor()
    182 			if !messageDesc.ExtensionRanges().Has(fd.Number()) || fd.ContainingMessage().FullName() != messageDesc.FullName() {
    183 				return d.newError(tok.Pos(), "message %v cannot be extended by %v", messageDesc.FullName(), fd.FullName())
    184 			}
    185 		} else if xtErr != nil && xtErr != protoregistry.NotFound {
    186 			return d.newError(tok.Pos(), "unable to resolve [%s]: %v", tok.RawString(), xtErr)
    187 		}
    188 		if flags.ProtoLegacy {
    189 			if fd != nil && fd.IsWeak() && fd.Message().IsPlaceholder() {
    190 				fd = nil // reset since the weak reference is not linked in
    191 			}
    192 		}
    193 
    194 		// Handle unknown fields.
    195 		if fd == nil {
    196 			if d.opts.DiscardUnknown || messageDesc.ReservedNames().Has(name) {
    197 				d.skipValue()
    198 				continue
    199 			}
    200 			return d.newError(tok.Pos(), "unknown field: %v", tok.RawString())
    201 		}
    202 
    203 		// Handle fields identified by field number.
    204 		if isFieldNumberName {
    205 			// TODO: Add an option to permit parsing field numbers.
    206 			//
    207 			// This requires careful thought as the MarshalOptions.EmitUnknown
    208 			// option allows formatting unknown fields as the field number and the
    209 			// best-effort textual representation of the field value.  In that case,
    210 			// it may not be possible to unmarshal the value from a parser that does
    211 			// have information about the unknown field.
    212 			return d.newError(tok.Pos(), "cannot specify field by number: %v", tok.RawString())
    213 		}
    214 
    215 		switch {
    216 		case fd.IsList():
    217 			kind := fd.Kind()
    218 			if kind != protoreflect.MessageKind && kind != protoreflect.GroupKind && !tok.HasSeparator() {
    219 				return d.syntaxError(tok.Pos(), "missing field separator :")
    220 			}
    221 
    222 			list := m.Mutable(fd).List()
    223 			if err := d.unmarshalList(fd, list); err != nil {
    224 				return err
    225 			}
    226 
    227 		case fd.IsMap():
    228 			mmap := m.Mutable(fd).Map()
    229 			if err := d.unmarshalMap(fd, mmap); err != nil {
    230 				return err
    231 			}
    232 
    233 		default:
    234 			kind := fd.Kind()
    235 			if kind != protoreflect.MessageKind && kind != protoreflect.GroupKind && !tok.HasSeparator() {
    236 				return d.syntaxError(tok.Pos(), "missing field separator :")
    237 			}
    238 
    239 			// If field is a oneof, check if it has already been set.
    240 			if od := fd.ContainingOneof(); od != nil {
    241 				idx := uint64(od.Index())
    242 				if seenOneofs.Has(idx) {
    243 					return d.newError(tok.Pos(), "error parsing %q, oneof %v is already set", tok.RawString(), od.FullName())
    244 				}
    245 				seenOneofs.Set(idx)
    246 			}
    247 
    248 			num := uint64(fd.Number())
    249 			if seenNums.Has(num) {
    250 				return d.newError(tok.Pos(), "non-repeated field %q is repeated", tok.RawString())
    251 			}
    252 
    253 			if err := d.unmarshalSingular(fd, m); err != nil {
    254 				return err
    255 			}
    256 			seenNums.Set(num)
    257 		}
    258 	}
    259 
    260 	return nil
    261 }
    262 
    263 // unmarshalSingular unmarshals a non-repeated field value specified by the
    264 // given FieldDescriptor.
    265 func (d decoder) unmarshalSingular(fd protoreflect.FieldDescriptor, m protoreflect.Message) error {
    266 	var val protoreflect.Value
    267 	var err error
    268 	switch fd.Kind() {
    269 	case protoreflect.MessageKind, protoreflect.GroupKind:
    270 		val = m.NewField(fd)
    271 		err = d.unmarshalMessage(val.Message(), true)
    272 	default:
    273 		val, err = d.unmarshalScalar(fd)
    274 	}
    275 	if err == nil {
    276 		m.Set(fd, val)
    277 	}
    278 	return err
    279 }
    280 
    281 // unmarshalScalar unmarshals a scalar/enum protoreflect.Value specified by the
    282 // given FieldDescriptor.
    283 func (d decoder) unmarshalScalar(fd protoreflect.FieldDescriptor) (protoreflect.Value, error) {
    284 	tok, err := d.Read()
    285 	if err != nil {
    286 		return protoreflect.Value{}, err
    287 	}
    288 
    289 	if tok.Kind() != text.Scalar {
    290 		return protoreflect.Value{}, d.unexpectedTokenError(tok)
    291 	}
    292 
    293 	kind := fd.Kind()
    294 	switch kind {
    295 	case protoreflect.BoolKind:
    296 		if b, ok := tok.Bool(); ok {
    297 			return protoreflect.ValueOfBool(b), nil
    298 		}
    299 
    300 	case protoreflect.Int32Kind, protoreflect.Sint32Kind, protoreflect.Sfixed32Kind:
    301 		if n, ok := tok.Int32(); ok {
    302 			return protoreflect.ValueOfInt32(n), nil
    303 		}
    304 
    305 	case protoreflect.Int64Kind, protoreflect.Sint64Kind, protoreflect.Sfixed64Kind:
    306 		if n, ok := tok.Int64(); ok {
    307 			return protoreflect.ValueOfInt64(n), nil
    308 		}
    309 
    310 	case protoreflect.Uint32Kind, protoreflect.Fixed32Kind:
    311 		if n, ok := tok.Uint32(); ok {
    312 			return protoreflect.ValueOfUint32(n), nil
    313 		}
    314 
    315 	case protoreflect.Uint64Kind, protoreflect.Fixed64Kind:
    316 		if n, ok := tok.Uint64(); ok {
    317 			return protoreflect.ValueOfUint64(n), nil
    318 		}
    319 
    320 	case protoreflect.FloatKind:
    321 		if n, ok := tok.Float32(); ok {
    322 			return protoreflect.ValueOfFloat32(n), nil
    323 		}
    324 
    325 	case protoreflect.DoubleKind:
    326 		if n, ok := tok.Float64(); ok {
    327 			return protoreflect.ValueOfFloat64(n), nil
    328 		}
    329 
    330 	case protoreflect.StringKind:
    331 		if s, ok := tok.String(); ok {
    332 			if strs.EnforceUTF8(fd) && !utf8.ValidString(s) {
    333 				return protoreflect.Value{}, d.newError(tok.Pos(), "contains invalid UTF-8")
    334 			}
    335 			return protoreflect.ValueOfString(s), nil
    336 		}
    337 
    338 	case protoreflect.BytesKind:
    339 		if b, ok := tok.String(); ok {
    340 			return protoreflect.ValueOfBytes([]byte(b)), nil
    341 		}
    342 
    343 	case protoreflect.EnumKind:
    344 		if lit, ok := tok.Enum(); ok {
    345 			// Lookup EnumNumber based on name.
    346 			if enumVal := fd.Enum().Values().ByName(protoreflect.Name(lit)); enumVal != nil {
    347 				return protoreflect.ValueOfEnum(enumVal.Number()), nil
    348 			}
    349 		}
    350 		if num, ok := tok.Int32(); ok {
    351 			return protoreflect.ValueOfEnum(protoreflect.EnumNumber(num)), nil
    352 		}
    353 
    354 	default:
    355 		panic(fmt.Sprintf("invalid scalar kind %v", kind))
    356 	}
    357 
    358 	return protoreflect.Value{}, d.newError(tok.Pos(), "invalid value for %v type: %v", kind, tok.RawString())
    359 }
    360 
    361 // unmarshalList unmarshals into given protoreflect.List. A list value can
    362 // either be in [] syntax or simply just a single scalar/message value.
    363 func (d decoder) unmarshalList(fd protoreflect.FieldDescriptor, list protoreflect.List) error {
    364 	tok, err := d.Peek()
    365 	if err != nil {
    366 		return err
    367 	}
    368 
    369 	switch fd.Kind() {
    370 	case protoreflect.MessageKind, protoreflect.GroupKind:
    371 		switch tok.Kind() {
    372 		case text.ListOpen:
    373 			d.Read()
    374 			for {
    375 				tok, err := d.Peek()
    376 				if err != nil {
    377 					return err
    378 				}
    379 
    380 				switch tok.Kind() {
    381 				case text.ListClose:
    382 					d.Read()
    383 					return nil
    384 				case text.MessageOpen:
    385 					pval := list.NewElement()
    386 					if err := d.unmarshalMessage(pval.Message(), true); err != nil {
    387 						return err
    388 					}
    389 					list.Append(pval)
    390 				default:
    391 					return d.unexpectedTokenError(tok)
    392 				}
    393 			}
    394 
    395 		case text.MessageOpen:
    396 			pval := list.NewElement()
    397 			if err := d.unmarshalMessage(pval.Message(), true); err != nil {
    398 				return err
    399 			}
    400 			list.Append(pval)
    401 			return nil
    402 		}
    403 
    404 	default:
    405 		switch tok.Kind() {
    406 		case text.ListOpen:
    407 			d.Read()
    408 			for {
    409 				tok, err := d.Peek()
    410 				if err != nil {
    411 					return err
    412 				}
    413 
    414 				switch tok.Kind() {
    415 				case text.ListClose:
    416 					d.Read()
    417 					return nil
    418 				case text.Scalar:
    419 					pval, err := d.unmarshalScalar(fd)
    420 					if err != nil {
    421 						return err
    422 					}
    423 					list.Append(pval)
    424 				default:
    425 					return d.unexpectedTokenError(tok)
    426 				}
    427 			}
    428 
    429 		case text.Scalar:
    430 			pval, err := d.unmarshalScalar(fd)
    431 			if err != nil {
    432 				return err
    433 			}
    434 			list.Append(pval)
    435 			return nil
    436 		}
    437 	}
    438 
    439 	return d.unexpectedTokenError(tok)
    440 }
    441 
    442 // unmarshalMap unmarshals into given protoreflect.Map. A map value is a
    443 // textproto message containing {key: <kvalue>, value: <mvalue>}.
    444 func (d decoder) unmarshalMap(fd protoreflect.FieldDescriptor, mmap protoreflect.Map) error {
    445 	// Determine ahead whether map entry is a scalar type or a message type in
    446 	// order to call the appropriate unmarshalMapValue func inside
    447 	// unmarshalMapEntry.
    448 	var unmarshalMapValue func() (protoreflect.Value, error)
    449 	switch fd.MapValue().Kind() {
    450 	case protoreflect.MessageKind, protoreflect.GroupKind:
    451 		unmarshalMapValue = func() (protoreflect.Value, error) {
    452 			pval := mmap.NewValue()
    453 			if err := d.unmarshalMessage(pval.Message(), true); err != nil {
    454 				return protoreflect.Value{}, err
    455 			}
    456 			return pval, nil
    457 		}
    458 	default:
    459 		unmarshalMapValue = func() (protoreflect.Value, error) {
    460 			return d.unmarshalScalar(fd.MapValue())
    461 		}
    462 	}
    463 
    464 	tok, err := d.Read()
    465 	if err != nil {
    466 		return err
    467 	}
    468 	switch tok.Kind() {
    469 	case text.MessageOpen:
    470 		return d.unmarshalMapEntry(fd, mmap, unmarshalMapValue)
    471 
    472 	case text.ListOpen:
    473 		for {
    474 			tok, err := d.Read()
    475 			if err != nil {
    476 				return err
    477 			}
    478 			switch tok.Kind() {
    479 			case text.ListClose:
    480 				return nil
    481 			case text.MessageOpen:
    482 				if err := d.unmarshalMapEntry(fd, mmap, unmarshalMapValue); err != nil {
    483 					return err
    484 				}
    485 			default:
    486 				return d.unexpectedTokenError(tok)
    487 			}
    488 		}
    489 
    490 	default:
    491 		return d.unexpectedTokenError(tok)
    492 	}
    493 }
    494 
    495 // unmarshalMap unmarshals into given protoreflect.Map. A map value is a
    496 // textproto message containing {key: <kvalue>, value: <mvalue>}.
    497 func (d decoder) unmarshalMapEntry(fd protoreflect.FieldDescriptor, mmap protoreflect.Map, unmarshalMapValue func() (protoreflect.Value, error)) error {
    498 	var key protoreflect.MapKey
    499 	var pval protoreflect.Value
    500 Loop:
    501 	for {
    502 		// Read field name.
    503 		tok, err := d.Read()
    504 		if err != nil {
    505 			return err
    506 		}
    507 		switch tok.Kind() {
    508 		case text.Name:
    509 			if tok.NameKind() != text.IdentName {
    510 				if !d.opts.DiscardUnknown {
    511 					return d.newError(tok.Pos(), "unknown map entry field %q", tok.RawString())
    512 				}
    513 				d.skipValue()
    514 				continue Loop
    515 			}
    516 			// Continue below.
    517 		case text.MessageClose:
    518 			break Loop
    519 		default:
    520 			return d.unexpectedTokenError(tok)
    521 		}
    522 
    523 		switch name := protoreflect.Name(tok.IdentName()); name {
    524 		case genid.MapEntry_Key_field_name:
    525 			if !tok.HasSeparator() {
    526 				return d.syntaxError(tok.Pos(), "missing field separator :")
    527 			}
    528 			if key.IsValid() {
    529 				return d.newError(tok.Pos(), "map entry %q cannot be repeated", name)
    530 			}
    531 			val, err := d.unmarshalScalar(fd.MapKey())
    532 			if err != nil {
    533 				return err
    534 			}
    535 			key = val.MapKey()
    536 
    537 		case genid.MapEntry_Value_field_name:
    538 			if kind := fd.MapValue().Kind(); (kind != protoreflect.MessageKind) && (kind != protoreflect.GroupKind) {
    539 				if !tok.HasSeparator() {
    540 					return d.syntaxError(tok.Pos(), "missing field separator :")
    541 				}
    542 			}
    543 			if pval.IsValid() {
    544 				return d.newError(tok.Pos(), "map entry %q cannot be repeated", name)
    545 			}
    546 			pval, err = unmarshalMapValue()
    547 			if err != nil {
    548 				return err
    549 			}
    550 
    551 		default:
    552 			if !d.opts.DiscardUnknown {
    553 				return d.newError(tok.Pos(), "unknown map entry field %q", name)
    554 			}
    555 			d.skipValue()
    556 		}
    557 	}
    558 
    559 	if !key.IsValid() {
    560 		key = fd.MapKey().Default().MapKey()
    561 	}
    562 	if !pval.IsValid() {
    563 		switch fd.MapValue().Kind() {
    564 		case protoreflect.MessageKind, protoreflect.GroupKind:
    565 			// If value field is not set for message/group types, construct an
    566 			// empty one as default.
    567 			pval = mmap.NewValue()
    568 		default:
    569 			pval = fd.MapValue().Default()
    570 		}
    571 	}
    572 	mmap.Set(key, pval)
    573 	return nil
    574 }
    575 
    576 // unmarshalAny unmarshals an Any textproto. It can either be in expanded form
    577 // or non-expanded form.
    578 func (d decoder) unmarshalAny(m protoreflect.Message, checkDelims bool) error {
    579 	var typeURL string
    580 	var bValue []byte
    581 	var seenTypeUrl bool
    582 	var seenValue bool
    583 	var isExpanded bool
    584 
    585 	if checkDelims {
    586 		tok, err := d.Read()
    587 		if err != nil {
    588 			return err
    589 		}
    590 
    591 		if tok.Kind() != text.MessageOpen {
    592 			return d.unexpectedTokenError(tok)
    593 		}
    594 	}
    595 
    596 Loop:
    597 	for {
    598 		// Read field name. Can only have 3 possible field names, i.e. type_url,
    599 		// value and type URL name inside [].
    600 		tok, err := d.Read()
    601 		if err != nil {
    602 			return err
    603 		}
    604 		if typ := tok.Kind(); typ != text.Name {
    605 			if checkDelims {
    606 				if typ == text.MessageClose {
    607 					break Loop
    608 				}
    609 			} else if typ == text.EOF {
    610 				break Loop
    611 			}
    612 			return d.unexpectedTokenError(tok)
    613 		}
    614 
    615 		switch tok.NameKind() {
    616 		case text.IdentName:
    617 			// Both type_url and value fields require field separator :.
    618 			if !tok.HasSeparator() {
    619 				return d.syntaxError(tok.Pos(), "missing field separator :")
    620 			}
    621 
    622 			switch name := protoreflect.Name(tok.IdentName()); name {
    623 			case genid.Any_TypeUrl_field_name:
    624 				if seenTypeUrl {
    625 					return d.newError(tok.Pos(), "duplicate %v field", genid.Any_TypeUrl_field_fullname)
    626 				}
    627 				if isExpanded {
    628 					return d.newError(tok.Pos(), "conflict with [%s] field", typeURL)
    629 				}
    630 				tok, err := d.Read()
    631 				if err != nil {
    632 					return err
    633 				}
    634 				var ok bool
    635 				typeURL, ok = tok.String()
    636 				if !ok {
    637 					return d.newError(tok.Pos(), "invalid %v field value: %v", genid.Any_TypeUrl_field_fullname, tok.RawString())
    638 				}
    639 				seenTypeUrl = true
    640 
    641 			case genid.Any_Value_field_name:
    642 				if seenValue {
    643 					return d.newError(tok.Pos(), "duplicate %v field", genid.Any_Value_field_fullname)
    644 				}
    645 				if isExpanded {
    646 					return d.newError(tok.Pos(), "conflict with [%s] field", typeURL)
    647 				}
    648 				tok, err := d.Read()
    649 				if err != nil {
    650 					return err
    651 				}
    652 				s, ok := tok.String()
    653 				if !ok {
    654 					return d.newError(tok.Pos(), "invalid %v field value: %v", genid.Any_Value_field_fullname, tok.RawString())
    655 				}
    656 				bValue = []byte(s)
    657 				seenValue = true
    658 
    659 			default:
    660 				if !d.opts.DiscardUnknown {
    661 					return d.newError(tok.Pos(), "invalid field name %q in %v message", tok.RawString(), genid.Any_message_fullname)
    662 				}
    663 			}
    664 
    665 		case text.TypeName:
    666 			if isExpanded {
    667 				return d.newError(tok.Pos(), "cannot have more than one type")
    668 			}
    669 			if seenTypeUrl {
    670 				return d.newError(tok.Pos(), "conflict with type_url field")
    671 			}
    672 			typeURL = tok.TypeName()
    673 			var err error
    674 			bValue, err = d.unmarshalExpandedAny(typeURL, tok.Pos())
    675 			if err != nil {
    676 				return err
    677 			}
    678 			isExpanded = true
    679 
    680 		default:
    681 			if !d.opts.DiscardUnknown {
    682 				return d.newError(tok.Pos(), "invalid field name %q in %v message", tok.RawString(), genid.Any_message_fullname)
    683 			}
    684 		}
    685 	}
    686 
    687 	fds := m.Descriptor().Fields()
    688 	if len(typeURL) > 0 {
    689 		m.Set(fds.ByNumber(genid.Any_TypeUrl_field_number), protoreflect.ValueOfString(typeURL))
    690 	}
    691 	if len(bValue) > 0 {
    692 		m.Set(fds.ByNumber(genid.Any_Value_field_number), protoreflect.ValueOfBytes(bValue))
    693 	}
    694 	return nil
    695 }
    696 
    697 func (d decoder) unmarshalExpandedAny(typeURL string, pos int) ([]byte, error) {
    698 	mt, err := d.opts.Resolver.FindMessageByURL(typeURL)
    699 	if err != nil {
    700 		return nil, d.newError(pos, "unable to resolve message [%v]: %v", typeURL, err)
    701 	}
    702 	// Create new message for the embedded message type and unmarshal the value
    703 	// field into it.
    704 	m := mt.New()
    705 	if err := d.unmarshalMessage(m, true); err != nil {
    706 		return nil, err
    707 	}
    708 	// Serialize the embedded message and return the resulting bytes.
    709 	b, err := proto.MarshalOptions{
    710 		AllowPartial:  true, // Never check required fields inside an Any.
    711 		Deterministic: true,
    712 	}.Marshal(m.Interface())
    713 	if err != nil {
    714 		return nil, d.newError(pos, "error in marshaling message into Any.value: %v", err)
    715 	}
    716 	return b, nil
    717 }
    718 
    719 // skipValue makes the decoder parse a field value in order to advance the read
    720 // to the next field. It relies on Read returning an error if the types are not
    721 // in valid sequence.
    722 func (d decoder) skipValue() error {
    723 	tok, err := d.Read()
    724 	if err != nil {
    725 		return err
    726 	}
    727 	// Only need to continue reading for messages and lists.
    728 	switch tok.Kind() {
    729 	case text.MessageOpen:
    730 		return d.skipMessageValue()
    731 
    732 	case text.ListOpen:
    733 		for {
    734 			tok, err := d.Read()
    735 			if err != nil {
    736 				return err
    737 			}
    738 			switch tok.Kind() {
    739 			case text.ListClose:
    740 				return nil
    741 			case text.MessageOpen:
    742 				return d.skipMessageValue()
    743 			default:
    744 				// Skip items. This will not validate whether skipped values are
    745 				// of the same type or not, same behavior as C++
    746 				// TextFormat::Parser::AllowUnknownField(true) version 3.8.0.
    747 			}
    748 		}
    749 	}
    750 	return nil
    751 }
    752 
    753 // skipMessageValue makes the decoder parse and skip over all fields in a
    754 // message. It assumes that the previous read type is MessageOpen.
    755 func (d decoder) skipMessageValue() error {
    756 	for {
    757 		tok, err := d.Read()
    758 		if err != nil {
    759 			return err
    760 		}
    761 		switch tok.Kind() {
    762 		case text.MessageClose:
    763 			return nil
    764 		case text.Name:
    765 			if err := d.skipValue(); err != nil {
    766 				return err
    767 			}
    768 		}
    769 	}
    770 }