github.com/bakjos/protoreflect@v1.9.2/desc/protoparse/options.go (about)

     1  package protoparse
     2  
     3  import (
     4  	"bytes"
     5  	"fmt"
     6  	"math"
     7  
     8  	"github.com/golang/protobuf/proto"
     9  	dpb "github.com/golang/protobuf/protoc-gen-go/descriptor"
    10  
    11  	"github.com/bakjos/protoreflect/desc"
    12  	"github.com/bakjos/protoreflect/desc/internal"
    13  	"github.com/bakjos/protoreflect/desc/protoparse/ast"
    14  	"github.com/bakjos/protoreflect/dynamic"
    15  )
    16  
    17  // NB: To process options, we need descriptors, but we may not have rich
    18  // descriptors when trying to interpret options for unlinked parsed files.
    19  // So we define minimal interfaces that can be backed by both rich descriptors
    20  // as well as their poorer cousins, plain ol' descriptor protos.
    21  
    22  type descriptorish interface {
    23  	GetFile() fileDescriptorish
    24  	GetFullyQualifiedName() string
    25  	AsProto() proto.Message
    26  }
    27  
    28  type fileDescriptorish interface {
    29  	descriptorish
    30  	GetFileOptions() *dpb.FileOptions
    31  	GetPackage() string
    32  	FindSymbol(name string) desc.Descriptor
    33  	GetPublicDependencies() []fileDescriptorish
    34  	GetDependencies() []fileDescriptorish
    35  	GetMessageTypes() []msgDescriptorish
    36  	GetExtensions() []fldDescriptorish
    37  	GetEnumTypes() []enumDescriptorish
    38  	GetServices() []svcDescriptorish
    39  }
    40  
    41  type msgDescriptorish interface {
    42  	descriptorish
    43  	GetMessageOptions() *dpb.MessageOptions
    44  	GetFields() []fldDescriptorish
    45  	GetOneOfs() []oneofDescriptorish
    46  	GetExtensionRanges() []extRangeDescriptorish
    47  	GetNestedMessageTypes() []msgDescriptorish
    48  	GetNestedExtensions() []fldDescriptorish
    49  	GetNestedEnumTypes() []enumDescriptorish
    50  }
    51  
    52  type fldDescriptorish interface {
    53  	descriptorish
    54  	GetFieldOptions() *dpb.FieldOptions
    55  	GetMessageType() *desc.MessageDescriptor
    56  	GetEnumType() *desc.EnumDescriptor
    57  	AsFieldDescriptorProto() *dpb.FieldDescriptorProto
    58  }
    59  
    60  type oneofDescriptorish interface {
    61  	descriptorish
    62  	GetOneOfOptions() *dpb.OneofOptions
    63  }
    64  
    65  type enumDescriptorish interface {
    66  	descriptorish
    67  	GetEnumOptions() *dpb.EnumOptions
    68  	GetValues() []enumValDescriptorish
    69  }
    70  
    71  type enumValDescriptorish interface {
    72  	descriptorish
    73  	GetEnumValueOptions() *dpb.EnumValueOptions
    74  }
    75  
    76  type svcDescriptorish interface {
    77  	descriptorish
    78  	GetServiceOptions() *dpb.ServiceOptions
    79  	GetMethods() []methodDescriptorish
    80  }
    81  
    82  type methodDescriptorish interface {
    83  	descriptorish
    84  	GetMethodOptions() *dpb.MethodOptions
    85  }
    86  
    87  // The hierarchy of descriptorish implementations backed by
    88  // rich descriptors:
    89  
    90  type richFileDescriptorish struct {
    91  	*desc.FileDescriptor
    92  }
    93  
    94  func (d richFileDescriptorish) GetFile() fileDescriptorish {
    95  	return d
    96  }
    97  
    98  func (d richFileDescriptorish) GetPublicDependencies() []fileDescriptorish {
    99  	deps := d.FileDescriptor.GetPublicDependencies()
   100  	ret := make([]fileDescriptorish, len(deps))
   101  	for i, d := range deps {
   102  		ret[i] = richFileDescriptorish{FileDescriptor: d}
   103  	}
   104  	return ret
   105  }
   106  
   107  func (d richFileDescriptorish) GetDependencies() []fileDescriptorish {
   108  	deps := d.FileDescriptor.GetDependencies()
   109  	ret := make([]fileDescriptorish, len(deps))
   110  	for i, d := range deps {
   111  		ret[i] = richFileDescriptorish{FileDescriptor: d}
   112  	}
   113  	return ret
   114  }
   115  
   116  func (d richFileDescriptorish) GetMessageTypes() []msgDescriptorish {
   117  	msgs := d.FileDescriptor.GetMessageTypes()
   118  	ret := make([]msgDescriptorish, len(msgs))
   119  	for i, m := range msgs {
   120  		ret[i] = richMsgDescriptorish{MessageDescriptor: m}
   121  	}
   122  	return ret
   123  }
   124  
   125  func (d richFileDescriptorish) GetExtensions() []fldDescriptorish {
   126  	flds := d.FileDescriptor.GetExtensions()
   127  	ret := make([]fldDescriptorish, len(flds))
   128  	for i, f := range flds {
   129  		ret[i] = richFldDescriptorish{FieldDescriptor: f}
   130  	}
   131  	return ret
   132  }
   133  
   134  func (d richFileDescriptorish) GetEnumTypes() []enumDescriptorish {
   135  	ens := d.FileDescriptor.GetEnumTypes()
   136  	ret := make([]enumDescriptorish, len(ens))
   137  	for i, en := range ens {
   138  		ret[i] = richEnumDescriptorish{EnumDescriptor: en}
   139  	}
   140  	return ret
   141  }
   142  
   143  func (d richFileDescriptorish) GetServices() []svcDescriptorish {
   144  	svcs := d.FileDescriptor.GetServices()
   145  	ret := make([]svcDescriptorish, len(svcs))
   146  	for i, s := range svcs {
   147  		ret[i] = richSvcDescriptorish{ServiceDescriptor: s}
   148  	}
   149  	return ret
   150  }
   151  
   152  type richMsgDescriptorish struct {
   153  	*desc.MessageDescriptor
   154  }
   155  
   156  func (d richMsgDescriptorish) GetFile() fileDescriptorish {
   157  	return richFileDescriptorish{FileDescriptor: d.MessageDescriptor.GetFile()}
   158  }
   159  
   160  func (d richMsgDescriptorish) GetFields() []fldDescriptorish {
   161  	flds := d.MessageDescriptor.GetFields()
   162  	ret := make([]fldDescriptorish, len(flds))
   163  	for i, f := range flds {
   164  		ret[i] = richFldDescriptorish{FieldDescriptor: f}
   165  	}
   166  	return ret
   167  }
   168  
   169  func (d richMsgDescriptorish) GetOneOfs() []oneofDescriptorish {
   170  	oos := d.MessageDescriptor.GetOneOfs()
   171  	ret := make([]oneofDescriptorish, len(oos))
   172  	for i, oo := range oos {
   173  		ret[i] = richOneOfDescriptorish{OneOfDescriptor: oo}
   174  	}
   175  	return ret
   176  }
   177  
   178  func (d richMsgDescriptorish) GetExtensionRanges() []extRangeDescriptorish {
   179  	md := d.MessageDescriptor
   180  	mdFqn := md.GetFullyQualifiedName()
   181  	extrs := md.AsDescriptorProto().GetExtensionRange()
   182  	ret := make([]extRangeDescriptorish, len(extrs))
   183  	for i, extr := range extrs {
   184  		ret[i] = extRangeDescriptorish{
   185  			er:   extr,
   186  			qual: mdFqn,
   187  			file: richFileDescriptorish{FileDescriptor: md.GetFile()},
   188  		}
   189  	}
   190  	return ret
   191  }
   192  
   193  func (d richMsgDescriptorish) GetNestedMessageTypes() []msgDescriptorish {
   194  	msgs := d.MessageDescriptor.GetNestedMessageTypes()
   195  	ret := make([]msgDescriptorish, len(msgs))
   196  	for i, m := range msgs {
   197  		ret[i] = richMsgDescriptorish{MessageDescriptor: m}
   198  	}
   199  	return ret
   200  }
   201  
   202  func (d richMsgDescriptorish) GetNestedExtensions() []fldDescriptorish {
   203  	flds := d.MessageDescriptor.GetNestedExtensions()
   204  	ret := make([]fldDescriptorish, len(flds))
   205  	for i, f := range flds {
   206  		ret[i] = richFldDescriptorish{FieldDescriptor: f}
   207  	}
   208  	return ret
   209  }
   210  
   211  func (d richMsgDescriptorish) GetNestedEnumTypes() []enumDescriptorish {
   212  	ens := d.MessageDescriptor.GetNestedEnumTypes()
   213  	ret := make([]enumDescriptorish, len(ens))
   214  	for i, en := range ens {
   215  		ret[i] = richEnumDescriptorish{EnumDescriptor: en}
   216  	}
   217  	return ret
   218  }
   219  
   220  type richFldDescriptorish struct {
   221  	*desc.FieldDescriptor
   222  }
   223  
   224  func (d richFldDescriptorish) GetFile() fileDescriptorish {
   225  	return richFileDescriptorish{FileDescriptor: d.FieldDescriptor.GetFile()}
   226  }
   227  
   228  func (d richFldDescriptorish) AsFieldDescriptorProto() *dpb.FieldDescriptorProto {
   229  	return d.FieldDescriptor.AsFieldDescriptorProto()
   230  }
   231  
   232  type richOneOfDescriptorish struct {
   233  	*desc.OneOfDescriptor
   234  }
   235  
   236  func (d richOneOfDescriptorish) GetFile() fileDescriptorish {
   237  	return richFileDescriptorish{FileDescriptor: d.OneOfDescriptor.GetFile()}
   238  }
   239  
   240  type richEnumDescriptorish struct {
   241  	*desc.EnumDescriptor
   242  }
   243  
   244  func (d richEnumDescriptorish) GetFile() fileDescriptorish {
   245  	return richFileDescriptorish{FileDescriptor: d.EnumDescriptor.GetFile()}
   246  }
   247  
   248  func (d richEnumDescriptorish) GetValues() []enumValDescriptorish {
   249  	vals := d.EnumDescriptor.GetValues()
   250  	ret := make([]enumValDescriptorish, len(vals))
   251  	for i, val := range vals {
   252  		ret[i] = richEnumValDescriptorish{EnumValueDescriptor: val}
   253  	}
   254  	return ret
   255  }
   256  
   257  type richEnumValDescriptorish struct {
   258  	*desc.EnumValueDescriptor
   259  }
   260  
   261  func (d richEnumValDescriptorish) GetFile() fileDescriptorish {
   262  	return richFileDescriptorish{FileDescriptor: d.EnumValueDescriptor.GetFile()}
   263  }
   264  
   265  type richSvcDescriptorish struct {
   266  	*desc.ServiceDescriptor
   267  }
   268  
   269  func (d richSvcDescriptorish) GetFile() fileDescriptorish {
   270  	return richFileDescriptorish{FileDescriptor: d.ServiceDescriptor.GetFile()}
   271  }
   272  
   273  func (d richSvcDescriptorish) GetMethods() []methodDescriptorish {
   274  	mtds := d.ServiceDescriptor.GetMethods()
   275  	ret := make([]methodDescriptorish, len(mtds))
   276  	for i, mtd := range mtds {
   277  		ret[i] = richMethodDescriptorish{MethodDescriptor: mtd}
   278  	}
   279  	return ret
   280  }
   281  
   282  type richMethodDescriptorish struct {
   283  	*desc.MethodDescriptor
   284  }
   285  
   286  func (d richMethodDescriptorish) GetFile() fileDescriptorish {
   287  	return richFileDescriptorish{FileDescriptor: d.MethodDescriptor.GetFile()}
   288  }
   289  
   290  // The hierarchy of descriptorish implementations backed by
   291  // plain descriptor protos:
   292  
   293  type poorFileDescriptorish struct {
   294  	*dpb.FileDescriptorProto
   295  }
   296  
   297  func (d poorFileDescriptorish) GetFile() fileDescriptorish {
   298  	return d
   299  }
   300  
   301  func (d poorFileDescriptorish) GetFullyQualifiedName() string {
   302  	return d.FileDescriptorProto.GetName()
   303  }
   304  
   305  func (d poorFileDescriptorish) AsProto() proto.Message {
   306  	return d.FileDescriptorProto
   307  }
   308  
   309  func (d poorFileDescriptorish) GetFileOptions() *dpb.FileOptions {
   310  	return d.FileDescriptorProto.GetOptions()
   311  }
   312  
   313  func (d poorFileDescriptorish) FindSymbol(name string) desc.Descriptor {
   314  	return nil
   315  }
   316  
   317  func (d poorFileDescriptorish) GetPublicDependencies() []fileDescriptorish {
   318  	return nil
   319  }
   320  
   321  func (d poorFileDescriptorish) GetDependencies() []fileDescriptorish {
   322  	return nil
   323  }
   324  
   325  func (d poorFileDescriptorish) GetMessageTypes() []msgDescriptorish {
   326  	msgs := d.FileDescriptorProto.GetMessageType()
   327  	pkg := d.FileDescriptorProto.GetPackage()
   328  	ret := make([]msgDescriptorish, len(msgs))
   329  	for i, m := range msgs {
   330  		ret[i] = poorMsgDescriptorish{
   331  			DescriptorProto: m,
   332  			qual:            pkg,
   333  			file:            d,
   334  		}
   335  	}
   336  	return ret
   337  }
   338  
   339  func (d poorFileDescriptorish) GetExtensions() []fldDescriptorish {
   340  	exts := d.FileDescriptorProto.GetExtension()
   341  	pkg := d.FileDescriptorProto.GetPackage()
   342  	ret := make([]fldDescriptorish, len(exts))
   343  	for i, e := range exts {
   344  		ret[i] = poorFldDescriptorish{
   345  			FieldDescriptorProto: e,
   346  			qual:                 pkg,
   347  			file:                 d,
   348  		}
   349  	}
   350  	return ret
   351  }
   352  
   353  func (d poorFileDescriptorish) GetEnumTypes() []enumDescriptorish {
   354  	ens := d.FileDescriptorProto.GetEnumType()
   355  	pkg := d.FileDescriptorProto.GetPackage()
   356  	ret := make([]enumDescriptorish, len(ens))
   357  	for i, e := range ens {
   358  		ret[i] = poorEnumDescriptorish{
   359  			EnumDescriptorProto: e,
   360  			qual:                pkg,
   361  			file:                d,
   362  		}
   363  	}
   364  	return ret
   365  }
   366  
   367  func (d poorFileDescriptorish) GetServices() []svcDescriptorish {
   368  	svcs := d.FileDescriptorProto.GetService()
   369  	pkg := d.FileDescriptorProto.GetPackage()
   370  	ret := make([]svcDescriptorish, len(svcs))
   371  	for i, s := range svcs {
   372  		ret[i] = poorSvcDescriptorish{
   373  			ServiceDescriptorProto: s,
   374  			qual:                   pkg,
   375  			file:                   d,
   376  		}
   377  	}
   378  	return ret
   379  }
   380  
   381  type poorMsgDescriptorish struct {
   382  	*dpb.DescriptorProto
   383  	qual string
   384  	file fileDescriptorish
   385  }
   386  
   387  func (d poorMsgDescriptorish) GetFile() fileDescriptorish {
   388  	return d.file
   389  }
   390  
   391  func (d poorMsgDescriptorish) GetFullyQualifiedName() string {
   392  	return qualify(d.qual, d.DescriptorProto.GetName())
   393  }
   394  
   395  func qualify(qual, name string) string {
   396  	if qual == "" {
   397  		return name
   398  	} else {
   399  		return fmt.Sprintf("%s.%s", qual, name)
   400  	}
   401  }
   402  
   403  func (d poorMsgDescriptorish) AsProto() proto.Message {
   404  	return d.DescriptorProto
   405  }
   406  
   407  func (d poorMsgDescriptorish) GetMessageOptions() *dpb.MessageOptions {
   408  	return d.DescriptorProto.GetOptions()
   409  }
   410  
   411  func (d poorMsgDescriptorish) GetFields() []fldDescriptorish {
   412  	flds := d.DescriptorProto.GetField()
   413  	ret := make([]fldDescriptorish, len(flds))
   414  	for i, f := range flds {
   415  		ret[i] = poorFldDescriptorish{
   416  			FieldDescriptorProto: f,
   417  			qual:                 d.GetFullyQualifiedName(),
   418  			file:                 d.file,
   419  		}
   420  	}
   421  	return ret
   422  }
   423  
   424  func (d poorMsgDescriptorish) GetOneOfs() []oneofDescriptorish {
   425  	oos := d.DescriptorProto.GetOneofDecl()
   426  	ret := make([]oneofDescriptorish, len(oos))
   427  	for i, oo := range oos {
   428  		ret[i] = poorOneOfDescriptorish{
   429  			OneofDescriptorProto: oo,
   430  			qual:                 d.GetFullyQualifiedName(),
   431  			file:                 d.file,
   432  		}
   433  	}
   434  	return ret
   435  }
   436  
   437  func (d poorMsgDescriptorish) GetExtensionRanges() []extRangeDescriptorish {
   438  	mdFqn := d.GetFullyQualifiedName()
   439  	extrs := d.DescriptorProto.GetExtensionRange()
   440  	ret := make([]extRangeDescriptorish, len(extrs))
   441  	for i, extr := range extrs {
   442  		ret[i] = extRangeDescriptorish{
   443  			er:   extr,
   444  			qual: mdFqn,
   445  			file: d.file,
   446  		}
   447  	}
   448  	return ret
   449  }
   450  
   451  func (d poorMsgDescriptorish) GetNestedMessageTypes() []msgDescriptorish {
   452  	msgs := d.DescriptorProto.GetNestedType()
   453  	ret := make([]msgDescriptorish, len(msgs))
   454  	for i, m := range msgs {
   455  		ret[i] = poorMsgDescriptorish{
   456  			DescriptorProto: m,
   457  			qual:            d.GetFullyQualifiedName(),
   458  			file:            d.file,
   459  		}
   460  	}
   461  	return ret
   462  }
   463  
   464  func (d poorMsgDescriptorish) GetNestedExtensions() []fldDescriptorish {
   465  	flds := d.DescriptorProto.GetExtension()
   466  	ret := make([]fldDescriptorish, len(flds))
   467  	for i, f := range flds {
   468  		ret[i] = poorFldDescriptorish{
   469  			FieldDescriptorProto: f,
   470  			qual:                 d.GetFullyQualifiedName(),
   471  			file:                 d.file,
   472  		}
   473  	}
   474  	return ret
   475  }
   476  
   477  func (d poorMsgDescriptorish) GetNestedEnumTypes() []enumDescriptorish {
   478  	ens := d.DescriptorProto.GetEnumType()
   479  	ret := make([]enumDescriptorish, len(ens))
   480  	for i, en := range ens {
   481  		ret[i] = poorEnumDescriptorish{
   482  			EnumDescriptorProto: en,
   483  			qual:                d.GetFullyQualifiedName(),
   484  			file:                d.file,
   485  		}
   486  	}
   487  	return ret
   488  }
   489  
   490  type poorFldDescriptorish struct {
   491  	*dpb.FieldDescriptorProto
   492  	qual string
   493  	file fileDescriptorish
   494  }
   495  
   496  func (d poorFldDescriptorish) GetFile() fileDescriptorish {
   497  	return d.file
   498  }
   499  
   500  func (d poorFldDescriptorish) GetFullyQualifiedName() string {
   501  	return qualify(d.qual, d.FieldDescriptorProto.GetName())
   502  }
   503  
   504  func (d poorFldDescriptorish) AsProto() proto.Message {
   505  	return d.FieldDescriptorProto
   506  }
   507  
   508  func (d poorFldDescriptorish) GetFieldOptions() *dpb.FieldOptions {
   509  	return d.FieldDescriptorProto.GetOptions()
   510  }
   511  
   512  func (d poorFldDescriptorish) GetMessageType() *desc.MessageDescriptor {
   513  	return nil
   514  }
   515  
   516  func (d poorFldDescriptorish) GetEnumType() *desc.EnumDescriptor {
   517  	return nil
   518  }
   519  
   520  type poorOneOfDescriptorish struct {
   521  	*dpb.OneofDescriptorProto
   522  	qual string
   523  	file fileDescriptorish
   524  }
   525  
   526  func (d poorOneOfDescriptorish) GetFile() fileDescriptorish {
   527  	return d.file
   528  }
   529  
   530  func (d poorOneOfDescriptorish) GetFullyQualifiedName() string {
   531  	return qualify(d.qual, d.OneofDescriptorProto.GetName())
   532  }
   533  
   534  func (d poorOneOfDescriptorish) AsProto() proto.Message {
   535  	return d.OneofDescriptorProto
   536  }
   537  
   538  func (d poorOneOfDescriptorish) GetOneOfOptions() *dpb.OneofOptions {
   539  	return d.OneofDescriptorProto.GetOptions()
   540  }
   541  
   542  func (d poorFldDescriptorish) AsFieldDescriptorProto() *dpb.FieldDescriptorProto {
   543  	return d.FieldDescriptorProto
   544  }
   545  
   546  type poorEnumDescriptorish struct {
   547  	*dpb.EnumDescriptorProto
   548  	qual string
   549  	file fileDescriptorish
   550  }
   551  
   552  func (d poorEnumDescriptorish) GetFile() fileDescriptorish {
   553  	return d.file
   554  }
   555  
   556  func (d poorEnumDescriptorish) GetFullyQualifiedName() string {
   557  	return qualify(d.qual, d.EnumDescriptorProto.GetName())
   558  }
   559  
   560  func (d poorEnumDescriptorish) AsProto() proto.Message {
   561  	return d.EnumDescriptorProto
   562  }
   563  
   564  func (d poorEnumDescriptorish) GetEnumOptions() *dpb.EnumOptions {
   565  	return d.EnumDescriptorProto.GetOptions()
   566  }
   567  
   568  func (d poorEnumDescriptorish) GetValues() []enumValDescriptorish {
   569  	vals := d.EnumDescriptorProto.GetValue()
   570  	ret := make([]enumValDescriptorish, len(vals))
   571  	for i, v := range vals {
   572  		ret[i] = poorEnumValDescriptorish{
   573  			EnumValueDescriptorProto: v,
   574  			qual:                     d.GetFullyQualifiedName(),
   575  			file:                     d.file,
   576  		}
   577  	}
   578  	return ret
   579  }
   580  
   581  type poorEnumValDescriptorish struct {
   582  	*dpb.EnumValueDescriptorProto
   583  	qual string
   584  	file fileDescriptorish
   585  }
   586  
   587  func (d poorEnumValDescriptorish) GetFile() fileDescriptorish {
   588  	return d.file
   589  }
   590  
   591  func (d poorEnumValDescriptorish) GetFullyQualifiedName() string {
   592  	return qualify(d.qual, d.EnumValueDescriptorProto.GetName())
   593  }
   594  
   595  func (d poorEnumValDescriptorish) AsProto() proto.Message {
   596  	return d.EnumValueDescriptorProto
   597  }
   598  
   599  func (d poorEnumValDescriptorish) GetEnumValueOptions() *dpb.EnumValueOptions {
   600  	return d.EnumValueDescriptorProto.GetOptions()
   601  }
   602  
   603  type poorSvcDescriptorish struct {
   604  	*dpb.ServiceDescriptorProto
   605  	qual string
   606  	file fileDescriptorish
   607  }
   608  
   609  func (d poorSvcDescriptorish) GetFile() fileDescriptorish {
   610  	return d.file
   611  }
   612  
   613  func (d poorSvcDescriptorish) GetFullyQualifiedName() string {
   614  	return qualify(d.qual, d.ServiceDescriptorProto.GetName())
   615  }
   616  
   617  func (d poorSvcDescriptorish) AsProto() proto.Message {
   618  	return d.ServiceDescriptorProto
   619  }
   620  
   621  func (d poorSvcDescriptorish) GetServiceOptions() *dpb.ServiceOptions {
   622  	return d.ServiceDescriptorProto.GetOptions()
   623  }
   624  
   625  func (d poorSvcDescriptorish) GetMethods() []methodDescriptorish {
   626  	mtds := d.ServiceDescriptorProto.GetMethod()
   627  	ret := make([]methodDescriptorish, len(mtds))
   628  	for i, m := range mtds {
   629  		ret[i] = poorMethodDescriptorish{
   630  			MethodDescriptorProto: m,
   631  			qual:                  d.GetFullyQualifiedName(),
   632  			file:                  d.file,
   633  		}
   634  	}
   635  	return ret
   636  }
   637  
   638  type poorMethodDescriptorish struct {
   639  	*dpb.MethodDescriptorProto
   640  	qual string
   641  	file fileDescriptorish
   642  }
   643  
   644  func (d poorMethodDescriptorish) GetFile() fileDescriptorish {
   645  	return d.file
   646  }
   647  
   648  func (d poorMethodDescriptorish) GetFullyQualifiedName() string {
   649  	return qualify(d.qual, d.MethodDescriptorProto.GetName())
   650  }
   651  
   652  func (d poorMethodDescriptorish) AsProto() proto.Message {
   653  	return d.MethodDescriptorProto
   654  }
   655  
   656  func (d poorMethodDescriptorish) GetMethodOptions() *dpb.MethodOptions {
   657  	return d.MethodDescriptorProto.GetOptions()
   658  }
   659  
   660  type extRangeDescriptorish struct {
   661  	er   *dpb.DescriptorProto_ExtensionRange
   662  	qual string
   663  	file fileDescriptorish
   664  }
   665  
   666  func (er extRangeDescriptorish) GetFile() fileDescriptorish {
   667  	return er.file
   668  }
   669  
   670  func (er extRangeDescriptorish) GetFullyQualifiedName() string {
   671  	return qualify(er.qual, fmt.Sprintf("%d-%d", er.er.GetStart(), er.er.GetEnd()-1))
   672  }
   673  
   674  func (er extRangeDescriptorish) AsProto() proto.Message {
   675  	return er.er
   676  }
   677  
   678  func (er extRangeDescriptorish) GetExtensionRangeOptions() *dpb.ExtensionRangeOptions {
   679  	return er.er.GetOptions()
   680  }
   681  
   682  func interpretFileOptions(l *linker, r *parseResult, fd fileDescriptorish) error {
   683  	opts := fd.GetFileOptions()
   684  	if opts != nil {
   685  		if len(opts.UninterpretedOption) > 0 {
   686  			if remain, err := interpretOptions(l, r, fd, opts, opts.UninterpretedOption); err != nil {
   687  				return err
   688  			} else {
   689  				opts.UninterpretedOption = remain
   690  			}
   691  		}
   692  	}
   693  	for _, md := range fd.GetMessageTypes() {
   694  		if err := interpretMessageOptions(l, r, md); err != nil {
   695  			return err
   696  		}
   697  	}
   698  	for _, fld := range fd.GetExtensions() {
   699  		if err := interpretFieldOptions(l, r, fld); err != nil {
   700  			return err
   701  		}
   702  	}
   703  	for _, ed := range fd.GetEnumTypes() {
   704  		if err := interpretEnumOptions(l, r, ed); err != nil {
   705  			return err
   706  		}
   707  	}
   708  	for _, sd := range fd.GetServices() {
   709  		opts := sd.GetServiceOptions()
   710  		if len(opts.GetUninterpretedOption()) > 0 {
   711  			if remain, err := interpretOptions(l, r, sd, opts, opts.UninterpretedOption); err != nil {
   712  				return err
   713  			} else {
   714  				opts.UninterpretedOption = remain
   715  			}
   716  		}
   717  		for _, mtd := range sd.GetMethods() {
   718  			opts := mtd.GetMethodOptions()
   719  			if len(opts.GetUninterpretedOption()) > 0 {
   720  				if remain, err := interpretOptions(l, r, mtd, opts, opts.UninterpretedOption); err != nil {
   721  					return err
   722  				} else {
   723  					opts.UninterpretedOption = remain
   724  				}
   725  			}
   726  		}
   727  	}
   728  	return nil
   729  }
   730  
   731  func interpretMessageOptions(l *linker, r *parseResult, md msgDescriptorish) error {
   732  	opts := md.GetMessageOptions()
   733  	if opts != nil {
   734  		if len(opts.UninterpretedOption) > 0 {
   735  			if remain, err := interpretOptions(l, r, md, opts, opts.UninterpretedOption); err != nil {
   736  				return err
   737  			} else {
   738  				opts.UninterpretedOption = remain
   739  			}
   740  		}
   741  	}
   742  	for _, fld := range md.GetFields() {
   743  		if err := interpretFieldOptions(l, r, fld); err != nil {
   744  			return err
   745  		}
   746  	}
   747  	for _, ood := range md.GetOneOfs() {
   748  		opts := ood.GetOneOfOptions()
   749  		if len(opts.GetUninterpretedOption()) > 0 {
   750  			if remain, err := interpretOptions(l, r, ood, opts, opts.UninterpretedOption); err != nil {
   751  				return err
   752  			} else {
   753  				opts.UninterpretedOption = remain
   754  			}
   755  		}
   756  	}
   757  	for _, fld := range md.GetNestedExtensions() {
   758  		if err := interpretFieldOptions(l, r, fld); err != nil {
   759  			return err
   760  		}
   761  	}
   762  	for _, er := range md.GetExtensionRanges() {
   763  		opts := er.GetExtensionRangeOptions()
   764  		if len(opts.GetUninterpretedOption()) > 0 {
   765  			if remain, err := interpretOptions(l, r, er, opts, opts.UninterpretedOption); err != nil {
   766  				return err
   767  			} else {
   768  				opts.UninterpretedOption = remain
   769  			}
   770  		}
   771  	}
   772  	for _, nmd := range md.GetNestedMessageTypes() {
   773  		if err := interpretMessageOptions(l, r, nmd); err != nil {
   774  			return err
   775  		}
   776  	}
   777  	for _, ed := range md.GetNestedEnumTypes() {
   778  		if err := interpretEnumOptions(l, r, ed); err != nil {
   779  			return err
   780  		}
   781  	}
   782  	return nil
   783  }
   784  
   785  func interpretFieldOptions(l *linker, r *parseResult, fld fldDescriptorish) error {
   786  	opts := fld.GetFieldOptions()
   787  	if len(opts.GetUninterpretedOption()) > 0 {
   788  		uo := opts.UninterpretedOption
   789  		scope := fmt.Sprintf("field %s", fld.GetFullyQualifiedName())
   790  
   791  		// process json_name pseudo-option
   792  		if index, err := findOption(r, scope, uo, "json_name"); err != nil && !r.lenient {
   793  			return err
   794  		} else if index >= 0 {
   795  			opt := uo[index]
   796  			optNode := r.getOptionNode(opt)
   797  
   798  			// attribute source code info
   799  			if on, ok := optNode.(*ast.OptionNode); ok {
   800  				r.interpretedOptions[on] = []int32{-1, internal.Field_jsonNameTag}
   801  			}
   802  			uo = removeOption(uo, index)
   803  			if opt.StringValue == nil {
   804  				if err := r.errs.handleErrorWithPos(optNode.GetValue().Start(), "%s: expecting string value for json_name option", scope); err != nil {
   805  					return err
   806  				}
   807  			} else {
   808  				fld.AsFieldDescriptorProto().JsonName = proto.String(string(opt.StringValue))
   809  			}
   810  		}
   811  
   812  		// and process default pseudo-option
   813  		if index, err := processDefaultOption(r, scope, fld, uo); err != nil && !r.lenient {
   814  			return err
   815  		} else if index >= 0 {
   816  			// attribute source code info
   817  			optNode := r.getOptionNode(uo[index])
   818  			if on, ok := optNode.(*ast.OptionNode); ok {
   819  				r.interpretedOptions[on] = []int32{-1, internal.Field_defaultTag}
   820  			}
   821  			uo = removeOption(uo, index)
   822  		}
   823  
   824  		if len(uo) == 0 {
   825  			// no real options, only pseudo-options above? clear out options
   826  			fld.AsFieldDescriptorProto().Options = nil
   827  		} else if remain, err := interpretOptions(l, r, fld, opts, uo); err != nil {
   828  			return err
   829  		} else {
   830  			opts.UninterpretedOption = remain
   831  		}
   832  	}
   833  	return nil
   834  }
   835  
   836  func processDefaultOption(res *parseResult, scope string, fld fldDescriptorish, uos []*dpb.UninterpretedOption) (defaultIndex int, err error) {
   837  	found, err := findOption(res, scope, uos, "default")
   838  	if err != nil || found == -1 {
   839  		return -1, err
   840  	}
   841  	opt := uos[found]
   842  	optNode := res.getOptionNode(opt)
   843  	fdp := fld.AsFieldDescriptorProto()
   844  	if fdp.GetLabel() == dpb.FieldDescriptorProto_LABEL_REPEATED {
   845  		return -1, res.errs.handleErrorWithPos(optNode.GetName().Start(), "%s: default value cannot be set because field is repeated", scope)
   846  	}
   847  	if fdp.GetType() == dpb.FieldDescriptorProto_TYPE_GROUP || fdp.GetType() == dpb.FieldDescriptorProto_TYPE_MESSAGE {
   848  		return -1, res.errs.handleErrorWithPos(optNode.GetName().Start(), "%s: default value cannot be set because field is a message", scope)
   849  	}
   850  	val := optNode.GetValue()
   851  	if _, ok := val.(*ast.MessageLiteralNode); ok {
   852  		return -1, res.errs.handleErrorWithPos(val.Start(), "%s: default value cannot be a message", scope)
   853  	}
   854  	mc := &messageContext{
   855  		res:         res,
   856  		file:        fld.GetFile(),
   857  		elementName: fld.GetFullyQualifiedName(),
   858  		elementType: descriptorType(fld.AsProto()),
   859  		option:      opt,
   860  	}
   861  	v, err := fieldValue(res, mc, fld, val, true)
   862  	if err != nil {
   863  		return -1, res.errs.handleError(err)
   864  	}
   865  	if str, ok := v.(string); ok {
   866  		fld.AsFieldDescriptorProto().DefaultValue = proto.String(str)
   867  	} else if b, ok := v.([]byte); ok {
   868  		fld.AsFieldDescriptorProto().DefaultValue = proto.String(encodeDefaultBytes(b))
   869  	} else {
   870  		var flt float64
   871  		var ok bool
   872  		if flt, ok = v.(float64); !ok {
   873  			var flt32 float32
   874  			if flt32, ok = v.(float32); ok {
   875  				flt = float64(flt32)
   876  			}
   877  		}
   878  		if ok {
   879  			if math.IsInf(flt, 1) {
   880  				fld.AsFieldDescriptorProto().DefaultValue = proto.String("inf")
   881  			} else if ok && math.IsInf(flt, -1) {
   882  				fld.AsFieldDescriptorProto().DefaultValue = proto.String("-inf")
   883  			} else if ok && math.IsNaN(flt) {
   884  				fld.AsFieldDescriptorProto().DefaultValue = proto.String("nan")
   885  			} else {
   886  				fld.AsFieldDescriptorProto().DefaultValue = proto.String(fmt.Sprintf("%v", v))
   887  			}
   888  		} else {
   889  			fld.AsFieldDescriptorProto().DefaultValue = proto.String(fmt.Sprintf("%v", v))
   890  		}
   891  	}
   892  	return found, nil
   893  }
   894  
   895  func encodeDefaultBytes(b []byte) string {
   896  	var buf bytes.Buffer
   897  	writeEscapedBytes(&buf, b)
   898  	return buf.String()
   899  }
   900  
   901  func interpretEnumOptions(l *linker, r *parseResult, ed enumDescriptorish) error {
   902  	opts := ed.GetEnumOptions()
   903  	if opts != nil {
   904  		if len(opts.UninterpretedOption) > 0 {
   905  			if remain, err := interpretOptions(l, r, ed, opts, opts.UninterpretedOption); err != nil {
   906  				return err
   907  			} else {
   908  				opts.UninterpretedOption = remain
   909  			}
   910  		}
   911  	}
   912  	for _, evd := range ed.GetValues() {
   913  		opts := evd.GetEnumValueOptions()
   914  		if len(opts.GetUninterpretedOption()) > 0 {
   915  			if remain, err := interpretOptions(l, r, evd, opts, opts.UninterpretedOption); err != nil {
   916  				return err
   917  			} else {
   918  				opts.UninterpretedOption = remain
   919  			}
   920  		}
   921  	}
   922  	return nil
   923  }
   924  
   925  func interpretOptions(l *linker, res *parseResult, element descriptorish, opts proto.Message, uninterpreted []*dpb.UninterpretedOption) ([]*dpb.UninterpretedOption, error) {
   926  	optsd, err := loadMessageDescriptorForOptions(l, element.GetFile(), opts)
   927  	if err != nil {
   928  		if res.lenient {
   929  			return uninterpreted, nil
   930  		}
   931  		return nil, res.errs.handleError(err)
   932  	}
   933  	dm := dynamic.NewMessage(optsd)
   934  	err = dm.ConvertFrom(opts)
   935  	if err != nil {
   936  		if res.lenient {
   937  			return uninterpreted, nil
   938  		}
   939  		node := res.nodes[element.AsProto()]
   940  		return nil, res.errs.handleError(ErrorWithSourcePos{Pos: node.Start(), Underlying: err})
   941  	}
   942  
   943  	mc := &messageContext{res: res, file: element.GetFile(), elementName: element.GetFullyQualifiedName(), elementType: descriptorType(element.AsProto())}
   944  	var remain []*dpb.UninterpretedOption
   945  	for _, uo := range uninterpreted {
   946  		node := res.getOptionNode(uo)
   947  		if !uo.Name[0].GetIsExtension() && uo.Name[0].GetNamePart() == "uninterpreted_option" {
   948  			if res.lenient {
   949  				remain = append(remain, uo)
   950  				continue
   951  			}
   952  			// uninterpreted_option might be found reflectively, but is not actually valid for use
   953  			if err := res.errs.handleErrorWithPos(node.GetName().Start(), "%vinvalid option 'uninterpreted_option'", mc); err != nil {
   954  				return nil, err
   955  			}
   956  		}
   957  		mc.option = uo
   958  		path, err := interpretField(res, mc, element, dm, uo, 0, nil)
   959  		if err != nil {
   960  			if res.lenient {
   961  				remain = append(remain, uo)
   962  				continue
   963  			}
   964  			return nil, err
   965  		}
   966  		if optn, ok := node.(*ast.OptionNode); ok {
   967  			res.interpretedOptions[optn] = path
   968  		}
   969  	}
   970  
   971  	if res.lenient {
   972  		// If we're lenient, then we don't want to clobber the passed in message
   973  		// and leave it partially populated. So we convert into a copy first
   974  		optsClone := proto.Clone(opts)
   975  		if err := dm.ConvertToDeterministic(optsClone); err != nil {
   976  			// TODO: do this in a more granular way, so we can convert individual
   977  			// fields and leave bad ones uninterpreted instead of skipping all of
   978  			// the work we've done so far.
   979  			return uninterpreted, nil
   980  		}
   981  		// conversion from dynamic message above worked, so now
   982  		// it is safe to overwrite the passed in message
   983  		opts.Reset()
   984  		proto.Merge(opts, optsClone)
   985  
   986  		return remain, nil
   987  	}
   988  
   989  	if err := dm.ValidateRecursive(); err != nil {
   990  		node := res.nodes[element.AsProto()]
   991  		if err := res.errs.handleErrorWithPos(node.Start(), "error in %s options: %v", descriptorType(element.AsProto()), err); err != nil {
   992  			return nil, err
   993  		}
   994  	}
   995  
   996  	// now try to convert into the passed in message and fail if not successful
   997  	if err := dm.ConvertToDeterministic(opts); err != nil {
   998  		node := res.nodes[element.AsProto()]
   999  		return nil, res.errs.handleError(ErrorWithSourcePos{Pos: node.Start(), Underlying: err})
  1000  	}
  1001  
  1002  	return nil, nil
  1003  }
  1004  
  1005  func loadMessageDescriptorForOptions(l *linker, fd fileDescriptorish, opts proto.Message) (*desc.MessageDescriptor, error) {
  1006  	// see if the file imports a custom version of descriptor.proto
  1007  	fqn := proto.MessageName(opts)
  1008  	d := findMessageDescriptorForOptions(l, fd, fqn)
  1009  	if d != nil {
  1010  		return d, nil
  1011  	}
  1012  	// fall back to built-in options descriptors
  1013  	return desc.LoadMessageDescriptorForMessage(opts)
  1014  }
  1015  
  1016  func findMessageDescriptorForOptions(l *linker, fd fileDescriptorish, messageName string) *desc.MessageDescriptor {
  1017  	d := fd.FindSymbol(messageName)
  1018  	if d != nil {
  1019  		md, _ := d.(*desc.MessageDescriptor)
  1020  		return md
  1021  	}
  1022  
  1023  	// TODO: should this support public imports and be recursive?
  1024  	for _, dep := range fd.GetDependencies() {
  1025  		d := dep.FindSymbol(messageName)
  1026  		if d != nil {
  1027  			if l != nil {
  1028  				l.markUsed(fd.AsProto().(*dpb.FileDescriptorProto), d.GetFile().AsFileDescriptorProto())
  1029  			}
  1030  			md, _ := d.(*desc.MessageDescriptor)
  1031  			return md
  1032  		}
  1033  	}
  1034  
  1035  	return nil
  1036  }
  1037  
  1038  func interpretField(res *parseResult, mc *messageContext, element descriptorish, dm *dynamic.Message, opt *dpb.UninterpretedOption, nameIndex int, pathPrefix []int32) (path []int32, err error) {
  1039  	var fld *desc.FieldDescriptor
  1040  	nm := opt.GetName()[nameIndex]
  1041  	node := res.getOptionNamePartNode(nm)
  1042  	if nm.GetIsExtension() {
  1043  		extName := nm.GetNamePart()
  1044  		if extName[0] == '.' {
  1045  			extName = extName[1:] /* skip leading dot */
  1046  		}
  1047  		fld = findExtension(element.GetFile(), extName, false, map[fileDescriptorish]struct{}{})
  1048  		if fld == nil {
  1049  			return nil, res.errs.handleErrorWithPos(node.Start(),
  1050  				"%vunrecognized extension %s of %s",
  1051  				mc, extName, dm.GetMessageDescriptor().GetFullyQualifiedName())
  1052  		}
  1053  		if fld.GetOwner().GetFullyQualifiedName() != dm.GetMessageDescriptor().GetFullyQualifiedName() {
  1054  			return nil, res.errs.handleErrorWithPos(node.Start(),
  1055  				"%vextension %s should extend %s but instead extends %s",
  1056  				mc, extName, dm.GetMessageDescriptor().GetFullyQualifiedName(), fld.GetOwner().GetFullyQualifiedName())
  1057  		}
  1058  	} else {
  1059  		fld = dm.GetMessageDescriptor().FindFieldByName(nm.GetNamePart())
  1060  		if fld == nil {
  1061  			return nil, res.errs.handleErrorWithPos(node.Start(),
  1062  				"%vfield %s of %s does not exist",
  1063  				mc, nm.GetNamePart(), dm.GetMessageDescriptor().GetFullyQualifiedName())
  1064  		}
  1065  	}
  1066  
  1067  	path = append(pathPrefix, fld.GetNumber())
  1068  
  1069  	if len(opt.GetName()) > nameIndex+1 {
  1070  		nextnm := opt.GetName()[nameIndex+1]
  1071  		nextnode := res.getOptionNamePartNode(nextnm)
  1072  		if fld.GetType() != dpb.FieldDescriptorProto_TYPE_MESSAGE {
  1073  			return nil, res.errs.handleErrorWithPos(nextnode.Start(),
  1074  				"%vcannot set field %s because %s is not a message",
  1075  				mc, nextnm.GetNamePart(), nm.GetNamePart())
  1076  		}
  1077  		if fld.IsRepeated() {
  1078  			return nil, res.errs.handleErrorWithPos(nextnode.Start(),
  1079  				"%vcannot set field %s because %s is repeated (must use an aggregate)",
  1080  				mc, nextnm.GetNamePart(), nm.GetNamePart())
  1081  		}
  1082  		var fdm *dynamic.Message
  1083  		var err error
  1084  		if dm.HasField(fld) {
  1085  			var v interface{}
  1086  			v, err = dm.TryGetField(fld)
  1087  			fdm, _ = v.(*dynamic.Message)
  1088  		} else {
  1089  			fdm = dynamic.NewMessage(fld.GetMessageType())
  1090  			err = dm.TrySetField(fld, fdm)
  1091  		}
  1092  		if err != nil {
  1093  			return nil, res.errs.handleError(ErrorWithSourcePos{Pos: node.Start(), Underlying: err})
  1094  		}
  1095  		// recurse to set next part of name
  1096  		return interpretField(res, mc, element, fdm, opt, nameIndex+1, path)
  1097  	}
  1098  
  1099  	optNode := res.getOptionNode(opt)
  1100  	if err := setOptionField(res, mc, dm, fld, node, optNode.GetValue()); err != nil {
  1101  		return nil, res.errs.handleError(err)
  1102  	}
  1103  	if fld.IsRepeated() {
  1104  		path = append(path, int32(dm.FieldLength(fld))-1)
  1105  	}
  1106  	return path, nil
  1107  }
  1108  
  1109  func findExtension(fd fileDescriptorish, name string, public bool, checked map[fileDescriptorish]struct{}) *desc.FieldDescriptor {
  1110  	if _, ok := checked[fd]; ok {
  1111  		return nil
  1112  	}
  1113  	checked[fd] = struct{}{}
  1114  	d := fd.FindSymbol(name)
  1115  	if d != nil {
  1116  		if fld, ok := d.(*desc.FieldDescriptor); ok {
  1117  			return fld
  1118  		}
  1119  		return nil
  1120  	}
  1121  
  1122  	// When public = false, we are searching only directly imported symbols. But we
  1123  	// also need to search transitive public imports due to semantics of public imports.
  1124  	if public {
  1125  		for _, dep := range fd.GetPublicDependencies() {
  1126  			d := findExtension(dep, name, true, checked)
  1127  			if d != nil {
  1128  				return d
  1129  			}
  1130  		}
  1131  	} else {
  1132  		for _, dep := range fd.GetDependencies() {
  1133  			d := findExtension(dep, name, true, checked)
  1134  			if d != nil {
  1135  				return d
  1136  			}
  1137  		}
  1138  	}
  1139  	return nil
  1140  }
  1141  
  1142  func setOptionField(res *parseResult, mc *messageContext, dm *dynamic.Message, fld *desc.FieldDescriptor, name ast.Node, val ast.ValueNode) error {
  1143  	v := val.Value()
  1144  	if sl, ok := v.([]ast.ValueNode); ok {
  1145  		// handle slices a little differently than the others
  1146  		if !fld.IsRepeated() {
  1147  			return errorWithPos(val.Start(), "%vvalue is an array but field is not repeated", mc)
  1148  		}
  1149  		origPath := mc.optAggPath
  1150  		defer func() {
  1151  			mc.optAggPath = origPath
  1152  		}()
  1153  		for index, item := range sl {
  1154  			mc.optAggPath = fmt.Sprintf("%s[%d]", origPath, index)
  1155  			if v, err := fieldValue(res, mc, richFldDescriptorish{FieldDescriptor: fld}, item, false); err != nil {
  1156  				return err
  1157  			} else if err = dm.TryAddRepeatedField(fld, v); err != nil {
  1158  				return errorWithPos(val.Start(), "%verror setting value: %s", mc, err)
  1159  			}
  1160  		}
  1161  		return nil
  1162  	}
  1163  
  1164  	v, err := fieldValue(res, mc, richFldDescriptorish{FieldDescriptor: fld}, val, false)
  1165  	if err != nil {
  1166  		return err
  1167  	}
  1168  	if fld.IsRepeated() {
  1169  		err = dm.TryAddRepeatedField(fld, v)
  1170  	} else {
  1171  		if dm.HasField(fld) {
  1172  			return errorWithPos(name.Start(), "%vnon-repeated option field %s already set", mc, fieldName(fld))
  1173  		}
  1174  		err = dm.TrySetField(fld, v)
  1175  	}
  1176  	if err != nil {
  1177  		return errorWithPos(val.Start(), "%verror setting value: %s", mc, err)
  1178  	}
  1179  
  1180  	return nil
  1181  }
  1182  
  1183  func findOption(res *parseResult, scope string, opts []*dpb.UninterpretedOption, name string) (int, error) {
  1184  	found := -1
  1185  	for i, opt := range opts {
  1186  		if len(opt.Name) != 1 {
  1187  			continue
  1188  		}
  1189  		if opt.Name[0].GetIsExtension() || opt.Name[0].GetNamePart() != name {
  1190  			continue
  1191  		}
  1192  		if found >= 0 {
  1193  			optNode := res.getOptionNode(opt)
  1194  			return -1, res.errs.handleErrorWithPos(optNode.GetName().Start(), "%s: option %s cannot be defined more than once", scope, name)
  1195  		}
  1196  		found = i
  1197  	}
  1198  	return found, nil
  1199  }
  1200  
  1201  func removeOption(uo []*dpb.UninterpretedOption, indexToRemove int) []*dpb.UninterpretedOption {
  1202  	if indexToRemove == 0 {
  1203  		return uo[1:]
  1204  	} else if int(indexToRemove) == len(uo)-1 {
  1205  		return uo[:len(uo)-1]
  1206  	} else {
  1207  		return append(uo[:indexToRemove], uo[indexToRemove+1:]...)
  1208  	}
  1209  }
  1210  
  1211  type messageContext struct {
  1212  	res         *parseResult
  1213  	file        fileDescriptorish
  1214  	elementType string
  1215  	elementName string
  1216  	option      *dpb.UninterpretedOption
  1217  	optAggPath  string
  1218  }
  1219  
  1220  func (c *messageContext) String() string {
  1221  	var ctx bytes.Buffer
  1222  	if c.elementType != "file" {
  1223  		_, _ = fmt.Fprintf(&ctx, "%s %s: ", c.elementType, c.elementName)
  1224  	}
  1225  	if c.option != nil && c.option.Name != nil {
  1226  		ctx.WriteString("option ")
  1227  		writeOptionName(&ctx, c.option.Name)
  1228  		if c.res.nodes == nil {
  1229  			// if we have no source position info, try to provide as much context
  1230  			// as possible (if nodes != nil, we don't need this because any errors
  1231  			// will actually have file and line numbers)
  1232  			if c.optAggPath != "" {
  1233  				_, _ = fmt.Fprintf(&ctx, " at %s", c.optAggPath)
  1234  			}
  1235  		}
  1236  		ctx.WriteString(": ")
  1237  	}
  1238  	return ctx.String()
  1239  }
  1240  
  1241  func writeOptionName(buf *bytes.Buffer, parts []*dpb.UninterpretedOption_NamePart) {
  1242  	first := true
  1243  	for _, p := range parts {
  1244  		if first {
  1245  			first = false
  1246  		} else {
  1247  			buf.WriteByte('.')
  1248  		}
  1249  		nm := p.GetNamePart()
  1250  		if nm[0] == '.' {
  1251  			// skip leading dot
  1252  			nm = nm[1:]
  1253  		}
  1254  		if p.GetIsExtension() {
  1255  			buf.WriteByte('(')
  1256  			buf.WriteString(nm)
  1257  			buf.WriteByte(')')
  1258  		} else {
  1259  			buf.WriteString(nm)
  1260  		}
  1261  	}
  1262  }
  1263  
  1264  func fieldName(fld *desc.FieldDescriptor) string {
  1265  	if fld.IsExtension() {
  1266  		return fld.GetFullyQualifiedName()
  1267  	} else {
  1268  		return fld.GetName()
  1269  	}
  1270  }
  1271  
  1272  func valueKind(val interface{}) string {
  1273  	switch val := val.(type) {
  1274  	case ast.Identifier:
  1275  		return "identifier"
  1276  	case bool:
  1277  		return "bool"
  1278  	case int64:
  1279  		if val < 0 {
  1280  			return "negative integer"
  1281  		}
  1282  		return "integer"
  1283  	case uint64:
  1284  		return "integer"
  1285  	case float64:
  1286  		return "double"
  1287  	case string, []byte:
  1288  		return "string"
  1289  	case []*ast.MessageFieldNode:
  1290  		return "message"
  1291  	case []ast.ValueNode:
  1292  		return "array"
  1293  	default:
  1294  		return fmt.Sprintf("%T", val)
  1295  	}
  1296  }
  1297  
  1298  func fieldValue(res *parseResult, mc *messageContext, fld fldDescriptorish, val ast.ValueNode, enumAsString bool) (interface{}, error) {
  1299  	v := val.Value()
  1300  	t := fld.AsFieldDescriptorProto().GetType()
  1301  	switch t {
  1302  	case dpb.FieldDescriptorProto_TYPE_ENUM:
  1303  		if id, ok := v.(ast.Identifier); ok {
  1304  			ev := fld.GetEnumType().FindValueByName(string(id))
  1305  			if ev == nil {
  1306  				return nil, errorWithPos(val.Start(), "%venum %s has no value named %s", mc, fld.GetEnumType().GetFullyQualifiedName(), id)
  1307  			}
  1308  			if enumAsString {
  1309  				return ev.GetName(), nil
  1310  			} else {
  1311  				return ev.GetNumber(), nil
  1312  			}
  1313  		} else if str, ok := v.(string); ok {
  1314  			ev := fld.GetEnumType().FindValueByName(str)
  1315  			if ev == nil {
  1316  				return nil, errorWithPos(val.Start(), "%venum %s has no value named %s", mc, fld.GetEnumType().GetFullyQualifiedName(), id)
  1317  			}
  1318  			if enumAsString {
  1319  				return ev.GetName(), nil
  1320  			} else {
  1321  				return ev.GetNumber(), nil
  1322  			}
  1323  		}
  1324  		return nil, errorWithPos(val.Start(), "%vexpecting enum, got %s", mc, valueKind(v))
  1325  	case dpb.FieldDescriptorProto_TYPE_MESSAGE, dpb.FieldDescriptorProto_TYPE_GROUP:
  1326  		if aggs, ok := v.([]*ast.MessageFieldNode); ok {
  1327  			fmd := fld.GetMessageType()
  1328  			fdm := dynamic.NewMessage(fmd)
  1329  			origPath := mc.optAggPath
  1330  			defer func() {
  1331  				mc.optAggPath = origPath
  1332  			}()
  1333  			for _, a := range aggs {
  1334  				if origPath == "" {
  1335  					mc.optAggPath = a.Name.Value()
  1336  				} else {
  1337  					mc.optAggPath = origPath + "." + a.Name.Value()
  1338  				}
  1339  				var ffld *desc.FieldDescriptor
  1340  				if a.Name.IsExtension() {
  1341  					n := string(a.Name.Name.AsIdentifier())
  1342  					ffld = findExtension(mc.file, n, false, map[fileDescriptorish]struct{}{})
  1343  					if ffld == nil {
  1344  						// may need to qualify with package name
  1345  						pkg := mc.file.GetPackage()
  1346  						if pkg != "" {
  1347  							ffld = findExtension(mc.file, pkg+"."+n, false, map[fileDescriptorish]struct{}{})
  1348  						}
  1349  					}
  1350  				} else {
  1351  					ffld = fmd.FindFieldByName(a.Name.Value())
  1352  				}
  1353  				if ffld == nil {
  1354  					return nil, errorWithPos(val.Start(), "%vfield %s not found", mc, string(a.Name.Name.AsIdentifier()))
  1355  				}
  1356  				if err := setOptionField(res, mc, fdm, ffld, a.Name, a.Val); err != nil {
  1357  					return nil, err
  1358  				}
  1359  			}
  1360  			return fdm, nil
  1361  		}
  1362  		return nil, errorWithPos(val.Start(), "%vexpecting message, got %s", mc, valueKind(v))
  1363  	case dpb.FieldDescriptorProto_TYPE_BOOL:
  1364  		if b, ok := v.(bool); ok {
  1365  			return b, nil
  1366  		}
  1367  		return nil, errorWithPos(val.Start(), "%vexpecting bool, got %s", mc, valueKind(v))
  1368  	case dpb.FieldDescriptorProto_TYPE_BYTES:
  1369  		if str, ok := v.(string); ok {
  1370  			return []byte(str), nil
  1371  		}
  1372  		return nil, errorWithPos(val.Start(), "%vexpecting bytes, got %s", mc, valueKind(v))
  1373  	case dpb.FieldDescriptorProto_TYPE_STRING:
  1374  		if str, ok := v.(string); ok {
  1375  			return str, nil
  1376  		}
  1377  		return nil, errorWithPos(val.Start(), "%vexpecting string, got %s", mc, valueKind(v))
  1378  	case dpb.FieldDescriptorProto_TYPE_INT32, dpb.FieldDescriptorProto_TYPE_SINT32, dpb.FieldDescriptorProto_TYPE_SFIXED32:
  1379  		if i, ok := v.(int64); ok {
  1380  			if i > math.MaxInt32 || i < math.MinInt32 {
  1381  				return nil, errorWithPos(val.Start(), "%vvalue %d is out of range for int32", mc, i)
  1382  			}
  1383  			return int32(i), nil
  1384  		}
  1385  		if ui, ok := v.(uint64); ok {
  1386  			if ui > math.MaxInt32 {
  1387  				return nil, errorWithPos(val.Start(), "%vvalue %d is out of range for int32", mc, ui)
  1388  			}
  1389  			return int32(ui), nil
  1390  		}
  1391  		return nil, errorWithPos(val.Start(), "%vexpecting int32, got %s", mc, valueKind(v))
  1392  	case dpb.FieldDescriptorProto_TYPE_UINT32, dpb.FieldDescriptorProto_TYPE_FIXED32:
  1393  		if i, ok := v.(int64); ok {
  1394  			if i > math.MaxUint32 || i < 0 {
  1395  				return nil, errorWithPos(val.Start(), "%vvalue %d is out of range for uint32", mc, i)
  1396  			}
  1397  			return uint32(i), nil
  1398  		}
  1399  		if ui, ok := v.(uint64); ok {
  1400  			if ui > math.MaxUint32 {
  1401  				return nil, errorWithPos(val.Start(), "%vvalue %d is out of range for uint32", mc, ui)
  1402  			}
  1403  			return uint32(ui), nil
  1404  		}
  1405  		return nil, errorWithPos(val.Start(), "%vexpecting uint32, got %s", mc, valueKind(v))
  1406  	case dpb.FieldDescriptorProto_TYPE_INT64, dpb.FieldDescriptorProto_TYPE_SINT64, dpb.FieldDescriptorProto_TYPE_SFIXED64:
  1407  		if i, ok := v.(int64); ok {
  1408  			return i, nil
  1409  		}
  1410  		if ui, ok := v.(uint64); ok {
  1411  			if ui > math.MaxInt64 {
  1412  				return nil, errorWithPos(val.Start(), "%vvalue %d is out of range for int64", mc, ui)
  1413  			}
  1414  			return int64(ui), nil
  1415  		}
  1416  		return nil, errorWithPos(val.Start(), "%vexpecting int64, got %s", mc, valueKind(v))
  1417  	case dpb.FieldDescriptorProto_TYPE_UINT64, dpb.FieldDescriptorProto_TYPE_FIXED64:
  1418  		if i, ok := v.(int64); ok {
  1419  			if i < 0 {
  1420  				return nil, errorWithPos(val.Start(), "%vvalue %d is out of range for uint64", mc, i)
  1421  			}
  1422  			return uint64(i), nil
  1423  		}
  1424  		if ui, ok := v.(uint64); ok {
  1425  			return ui, nil
  1426  		}
  1427  		return nil, errorWithPos(val.Start(), "%vexpecting uint64, got %s", mc, valueKind(v))
  1428  	case dpb.FieldDescriptorProto_TYPE_DOUBLE:
  1429  		if d, ok := v.(float64); ok {
  1430  			return d, nil
  1431  		}
  1432  		if i, ok := v.(int64); ok {
  1433  			return float64(i), nil
  1434  		}
  1435  		if u, ok := v.(uint64); ok {
  1436  			return float64(u), nil
  1437  		}
  1438  		return nil, errorWithPos(val.Start(), "%vexpecting double, got %s", mc, valueKind(v))
  1439  	case dpb.FieldDescriptorProto_TYPE_FLOAT:
  1440  		if d, ok := v.(float64); ok {
  1441  			if (d > math.MaxFloat32 || d < -math.MaxFloat32) && !math.IsInf(d, 1) && !math.IsInf(d, -1) && !math.IsNaN(d) {
  1442  				return nil, errorWithPos(val.Start(), "%vvalue %f is out of range for float", mc, d)
  1443  			}
  1444  			return float32(d), nil
  1445  		}
  1446  		if i, ok := v.(int64); ok {
  1447  			return float32(i), nil
  1448  		}
  1449  		if u, ok := v.(uint64); ok {
  1450  			return float32(u), nil
  1451  		}
  1452  		return nil, errorWithPos(val.Start(), "%vexpecting float, got %s", mc, valueKind(v))
  1453  	default:
  1454  		return nil, errorWithPos(val.Start(), "%vunrecognized field type: %s", mc, t)
  1455  	}
  1456  }