github.com/ader1990/go@v0.0.0-20140630135419-8c24447fa791/src/pkg/encoding/gob/type.go (about)

     1  // Copyright 2009 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 gob
     6  
     7  import (
     8  	"encoding"
     9  	"errors"
    10  	"fmt"
    11  	"os"
    12  	"reflect"
    13  	"sync"
    14  	"unicode"
    15  	"unicode/utf8"
    16  )
    17  
    18  // userTypeInfo stores the information associated with a type the user has handed
    19  // to the package.  It's computed once and stored in a map keyed by reflection
    20  // type.
    21  type userTypeInfo struct {
    22  	user        reflect.Type // the type the user handed us
    23  	base        reflect.Type // the base type after all indirections
    24  	indir       int          // number of indirections to reach the base type
    25  	externalEnc int          // xGob, xBinary, or xText
    26  	externalDec int          // xGob, xBinary or xText
    27  	encIndir    int8         // number of indirections to reach the receiver type; may be negative
    28  	decIndir    int8         // number of indirections to reach the receiver type; may be negative
    29  }
    30  
    31  // externalEncoding bits
    32  const (
    33  	xGob    = 1 + iota // GobEncoder or GobDecoder
    34  	xBinary            // encoding.BinaryMarshaler or encoding.BinaryUnmarshaler
    35  	xText              // encoding.TextMarshaler or encoding.TextUnmarshaler
    36  )
    37  
    38  var (
    39  	// Protected by an RWMutex because we read it a lot and write
    40  	// it only when we see a new type, typically when compiling.
    41  	userTypeLock  sync.RWMutex
    42  	userTypeCache = make(map[reflect.Type]*userTypeInfo)
    43  )
    44  
    45  // validType returns, and saves, the information associated with user-provided type rt.
    46  // If the user type is not valid, err will be non-nil.  To be used when the error handler
    47  // is not set up.
    48  func validUserType(rt reflect.Type) (ut *userTypeInfo, err error) {
    49  	userTypeLock.RLock()
    50  	ut = userTypeCache[rt]
    51  	userTypeLock.RUnlock()
    52  	if ut != nil {
    53  		return
    54  	}
    55  	// Now set the value under the write lock.
    56  	userTypeLock.Lock()
    57  	defer userTypeLock.Unlock()
    58  	if ut = userTypeCache[rt]; ut != nil {
    59  		// Lost the race; not a problem.
    60  		return
    61  	}
    62  	ut = new(userTypeInfo)
    63  	ut.base = rt
    64  	ut.user = rt
    65  	// A type that is just a cycle of pointers (such as type T *T) cannot
    66  	// be represented in gobs, which need some concrete data.  We use a
    67  	// cycle detection algorithm from Knuth, Vol 2, Section 3.1, Ex 6,
    68  	// pp 539-540.  As we step through indirections, run another type at
    69  	// half speed. If they meet up, there's a cycle.
    70  	slowpoke := ut.base // walks half as fast as ut.base
    71  	for {
    72  		pt := ut.base
    73  		if pt.Kind() != reflect.Ptr {
    74  			break
    75  		}
    76  		ut.base = pt.Elem()
    77  		if ut.base == slowpoke { // ut.base lapped slowpoke
    78  			// recursive pointer type.
    79  			return nil, errors.New("can't represent recursive pointer type " + ut.base.String())
    80  		}
    81  		if ut.indir%2 == 0 {
    82  			slowpoke = slowpoke.Elem()
    83  		}
    84  		ut.indir++
    85  	}
    86  
    87  	if ok, indir := implementsInterface(ut.user, gobEncoderInterfaceType); ok {
    88  		ut.externalEnc, ut.encIndir = xGob, indir
    89  	} else if ok, indir := implementsInterface(ut.user, binaryMarshalerInterfaceType); ok {
    90  		ut.externalEnc, ut.encIndir = xBinary, indir
    91  	}
    92  
    93  	// NOTE(rsc): Would like to allow MarshalText here, but results in incompatibility
    94  	// with older encodings for net.IP. See golang.org/issue/6760.
    95  	// } else if ok, indir := implementsInterface(ut.user, textMarshalerInterfaceType); ok {
    96  	// 	ut.externalEnc, ut.encIndir = xText, indir
    97  	// }
    98  
    99  	if ok, indir := implementsInterface(ut.user, gobDecoderInterfaceType); ok {
   100  		ut.externalDec, ut.decIndir = xGob, indir
   101  	} else if ok, indir := implementsInterface(ut.user, binaryUnmarshalerInterfaceType); ok {
   102  		ut.externalDec, ut.decIndir = xBinary, indir
   103  	}
   104  
   105  	// See note above.
   106  	// } else if ok, indir := implementsInterface(ut.user, textUnmarshalerInterfaceType); ok {
   107  	// 	ut.externalDec, ut.decIndir = xText, indir
   108  	// }
   109  
   110  	userTypeCache[rt] = ut
   111  	return
   112  }
   113  
   114  var (
   115  	gobEncoderInterfaceType        = reflect.TypeOf((*GobEncoder)(nil)).Elem()
   116  	gobDecoderInterfaceType        = reflect.TypeOf((*GobDecoder)(nil)).Elem()
   117  	binaryMarshalerInterfaceType   = reflect.TypeOf((*encoding.BinaryMarshaler)(nil)).Elem()
   118  	binaryUnmarshalerInterfaceType = reflect.TypeOf((*encoding.BinaryUnmarshaler)(nil)).Elem()
   119  	textMarshalerInterfaceType     = reflect.TypeOf((*encoding.TextMarshaler)(nil)).Elem()
   120  	textUnmarshalerInterfaceType   = reflect.TypeOf((*encoding.TextUnmarshaler)(nil)).Elem()
   121  )
   122  
   123  // implementsInterface reports whether the type implements the
   124  // gobEncoder/gobDecoder interface.
   125  // It also returns the number of indirections required to get to the
   126  // implementation.
   127  func implementsInterface(typ, gobEncDecType reflect.Type) (success bool, indir int8) {
   128  	if typ == nil {
   129  		return
   130  	}
   131  	rt := typ
   132  	// The type might be a pointer and we need to keep
   133  	// dereferencing to the base type until we find an implementation.
   134  	for {
   135  		if rt.Implements(gobEncDecType) {
   136  			return true, indir
   137  		}
   138  		if p := rt; p.Kind() == reflect.Ptr {
   139  			indir++
   140  			if indir > 100 { // insane number of indirections
   141  				return false, 0
   142  			}
   143  			rt = p.Elem()
   144  			continue
   145  		}
   146  		break
   147  	}
   148  	// No luck yet, but if this is a base type (non-pointer), the pointer might satisfy.
   149  	if typ.Kind() != reflect.Ptr {
   150  		// Not a pointer, but does the pointer work?
   151  		if reflect.PtrTo(typ).Implements(gobEncDecType) {
   152  			return true, -1
   153  		}
   154  	}
   155  	return false, 0
   156  }
   157  
   158  // userType returns, and saves, the information associated with user-provided type rt.
   159  // If the user type is not valid, it calls error.
   160  func userType(rt reflect.Type) *userTypeInfo {
   161  	ut, err := validUserType(rt)
   162  	if err != nil {
   163  		error_(err)
   164  	}
   165  	return ut
   166  }
   167  
   168  // A typeId represents a gob Type as an integer that can be passed on the wire.
   169  // Internally, typeIds are used as keys to a map to recover the underlying type info.
   170  type typeId int32
   171  
   172  var nextId typeId       // incremented for each new type we build
   173  var typeLock sync.Mutex // set while building a type
   174  const firstUserId = 64  // lowest id number granted to user
   175  
   176  type gobType interface {
   177  	id() typeId
   178  	setId(id typeId)
   179  	name() string
   180  	string() string // not public; only for debugging
   181  	safeString(seen map[typeId]bool) string
   182  }
   183  
   184  var types = make(map[reflect.Type]gobType)
   185  var idToType = make(map[typeId]gobType)
   186  var builtinIdToType map[typeId]gobType // set in init() after builtins are established
   187  
   188  func setTypeId(typ gobType) {
   189  	// When building recursive types, someone may get there before us.
   190  	if typ.id() != 0 {
   191  		return
   192  	}
   193  	nextId++
   194  	typ.setId(nextId)
   195  	idToType[nextId] = typ
   196  }
   197  
   198  func (t typeId) gobType() gobType {
   199  	if t == 0 {
   200  		return nil
   201  	}
   202  	return idToType[t]
   203  }
   204  
   205  // string returns the string representation of the type associated with the typeId.
   206  func (t typeId) string() string {
   207  	if t.gobType() == nil {
   208  		return "<nil>"
   209  	}
   210  	return t.gobType().string()
   211  }
   212  
   213  // Name returns the name of the type associated with the typeId.
   214  func (t typeId) name() string {
   215  	if t.gobType() == nil {
   216  		return "<nil>"
   217  	}
   218  	return t.gobType().name()
   219  }
   220  
   221  // CommonType holds elements of all types.
   222  // It is a historical artifact, kept for binary compatibility and exported
   223  // only for the benefit of the package's encoding of type descriptors. It is
   224  // not intended for direct use by clients.
   225  type CommonType struct {
   226  	Name string
   227  	Id   typeId
   228  }
   229  
   230  func (t *CommonType) id() typeId { return t.Id }
   231  
   232  func (t *CommonType) setId(id typeId) { t.Id = id }
   233  
   234  func (t *CommonType) string() string { return t.Name }
   235  
   236  func (t *CommonType) safeString(seen map[typeId]bool) string {
   237  	return t.Name
   238  }
   239  
   240  func (t *CommonType) name() string { return t.Name }
   241  
   242  // Create and check predefined types
   243  // The string for tBytes is "bytes" not "[]byte" to signify its specialness.
   244  
   245  var (
   246  	// Primordial types, needed during initialization.
   247  	// Always passed as pointers so the interface{} type
   248  	// goes through without losing its interfaceness.
   249  	tBool      = bootstrapType("bool", (*bool)(nil), 1)
   250  	tInt       = bootstrapType("int", (*int)(nil), 2)
   251  	tUint      = bootstrapType("uint", (*uint)(nil), 3)
   252  	tFloat     = bootstrapType("float", (*float64)(nil), 4)
   253  	tBytes     = bootstrapType("bytes", (*[]byte)(nil), 5)
   254  	tString    = bootstrapType("string", (*string)(nil), 6)
   255  	tComplex   = bootstrapType("complex", (*complex128)(nil), 7)
   256  	tInterface = bootstrapType("interface", (*interface{})(nil), 8)
   257  	// Reserve some Ids for compatible expansion
   258  	tReserved7 = bootstrapType("_reserved1", (*struct{ r7 int })(nil), 9)
   259  	tReserved6 = bootstrapType("_reserved1", (*struct{ r6 int })(nil), 10)
   260  	tReserved5 = bootstrapType("_reserved1", (*struct{ r5 int })(nil), 11)
   261  	tReserved4 = bootstrapType("_reserved1", (*struct{ r4 int })(nil), 12)
   262  	tReserved3 = bootstrapType("_reserved1", (*struct{ r3 int })(nil), 13)
   263  	tReserved2 = bootstrapType("_reserved1", (*struct{ r2 int })(nil), 14)
   264  	tReserved1 = bootstrapType("_reserved1", (*struct{ r1 int })(nil), 15)
   265  )
   266  
   267  // Predefined because it's needed by the Decoder
   268  var tWireType = mustGetTypeInfo(reflect.TypeOf(wireType{})).id
   269  var wireTypeUserInfo *userTypeInfo // userTypeInfo of (*wireType)
   270  
   271  func init() {
   272  	// Some magic numbers to make sure there are no surprises.
   273  	checkId(16, tWireType)
   274  	checkId(17, mustGetTypeInfo(reflect.TypeOf(arrayType{})).id)
   275  	checkId(18, mustGetTypeInfo(reflect.TypeOf(CommonType{})).id)
   276  	checkId(19, mustGetTypeInfo(reflect.TypeOf(sliceType{})).id)
   277  	checkId(20, mustGetTypeInfo(reflect.TypeOf(structType{})).id)
   278  	checkId(21, mustGetTypeInfo(reflect.TypeOf(fieldType{})).id)
   279  	checkId(23, mustGetTypeInfo(reflect.TypeOf(mapType{})).id)
   280  
   281  	builtinIdToType = make(map[typeId]gobType)
   282  	for k, v := range idToType {
   283  		builtinIdToType[k] = v
   284  	}
   285  
   286  	// Move the id space upwards to allow for growth in the predefined world
   287  	// without breaking existing files.
   288  	if nextId > firstUserId {
   289  		panic(fmt.Sprintln("nextId too large:", nextId))
   290  	}
   291  	nextId = firstUserId
   292  	registerBasics()
   293  	wireTypeUserInfo = userType(reflect.TypeOf((*wireType)(nil)))
   294  }
   295  
   296  // Array type
   297  type arrayType struct {
   298  	CommonType
   299  	Elem typeId
   300  	Len  int
   301  }
   302  
   303  func newArrayType(name string) *arrayType {
   304  	a := &arrayType{CommonType{Name: name}, 0, 0}
   305  	return a
   306  }
   307  
   308  func (a *arrayType) init(elem gobType, len int) {
   309  	// Set our type id before evaluating the element's, in case it's our own.
   310  	setTypeId(a)
   311  	a.Elem = elem.id()
   312  	a.Len = len
   313  }
   314  
   315  func (a *arrayType) safeString(seen map[typeId]bool) string {
   316  	if seen[a.Id] {
   317  		return a.Name
   318  	}
   319  	seen[a.Id] = true
   320  	return fmt.Sprintf("[%d]%s", a.Len, a.Elem.gobType().safeString(seen))
   321  }
   322  
   323  func (a *arrayType) string() string { return a.safeString(make(map[typeId]bool)) }
   324  
   325  // GobEncoder type (something that implements the GobEncoder interface)
   326  type gobEncoderType struct {
   327  	CommonType
   328  }
   329  
   330  func newGobEncoderType(name string) *gobEncoderType {
   331  	g := &gobEncoderType{CommonType{Name: name}}
   332  	setTypeId(g)
   333  	return g
   334  }
   335  
   336  func (g *gobEncoderType) safeString(seen map[typeId]bool) string {
   337  	return g.Name
   338  }
   339  
   340  func (g *gobEncoderType) string() string { return g.Name }
   341  
   342  // Map type
   343  type mapType struct {
   344  	CommonType
   345  	Key  typeId
   346  	Elem typeId
   347  }
   348  
   349  func newMapType(name string) *mapType {
   350  	m := &mapType{CommonType{Name: name}, 0, 0}
   351  	return m
   352  }
   353  
   354  func (m *mapType) init(key, elem gobType) {
   355  	// Set our type id before evaluating the element's, in case it's our own.
   356  	setTypeId(m)
   357  	m.Key = key.id()
   358  	m.Elem = elem.id()
   359  }
   360  
   361  func (m *mapType) safeString(seen map[typeId]bool) string {
   362  	if seen[m.Id] {
   363  		return m.Name
   364  	}
   365  	seen[m.Id] = true
   366  	key := m.Key.gobType().safeString(seen)
   367  	elem := m.Elem.gobType().safeString(seen)
   368  	return fmt.Sprintf("map[%s]%s", key, elem)
   369  }
   370  
   371  func (m *mapType) string() string { return m.safeString(make(map[typeId]bool)) }
   372  
   373  // Slice type
   374  type sliceType struct {
   375  	CommonType
   376  	Elem typeId
   377  }
   378  
   379  func newSliceType(name string) *sliceType {
   380  	s := &sliceType{CommonType{Name: name}, 0}
   381  	return s
   382  }
   383  
   384  func (s *sliceType) init(elem gobType) {
   385  	// Set our type id before evaluating the element's, in case it's our own.
   386  	setTypeId(s)
   387  	// See the comments about ids in newTypeObject. Only slices and
   388  	// structs have mutual recursion.
   389  	if elem.id() == 0 {
   390  		setTypeId(elem)
   391  	}
   392  	s.Elem = elem.id()
   393  }
   394  
   395  func (s *sliceType) safeString(seen map[typeId]bool) string {
   396  	if seen[s.Id] {
   397  		return s.Name
   398  	}
   399  	seen[s.Id] = true
   400  	return fmt.Sprintf("[]%s", s.Elem.gobType().safeString(seen))
   401  }
   402  
   403  func (s *sliceType) string() string { return s.safeString(make(map[typeId]bool)) }
   404  
   405  // Struct type
   406  type fieldType struct {
   407  	Name string
   408  	Id   typeId
   409  }
   410  
   411  type structType struct {
   412  	CommonType
   413  	Field []*fieldType
   414  }
   415  
   416  func (s *structType) safeString(seen map[typeId]bool) string {
   417  	if s == nil {
   418  		return "<nil>"
   419  	}
   420  	if _, ok := seen[s.Id]; ok {
   421  		return s.Name
   422  	}
   423  	seen[s.Id] = true
   424  	str := s.Name + " = struct { "
   425  	for _, f := range s.Field {
   426  		str += fmt.Sprintf("%s %s; ", f.Name, f.Id.gobType().safeString(seen))
   427  	}
   428  	str += "}"
   429  	return str
   430  }
   431  
   432  func (s *structType) string() string { return s.safeString(make(map[typeId]bool)) }
   433  
   434  func newStructType(name string) *structType {
   435  	s := &structType{CommonType{Name: name}, nil}
   436  	// For historical reasons we set the id here rather than init.
   437  	// See the comment in newTypeObject for details.
   438  	setTypeId(s)
   439  	return s
   440  }
   441  
   442  // newTypeObject allocates a gobType for the reflection type rt.
   443  // Unless ut represents a GobEncoder, rt should be the base type
   444  // of ut.
   445  // This is only called from the encoding side. The decoding side
   446  // works through typeIds and userTypeInfos alone.
   447  func newTypeObject(name string, ut *userTypeInfo, rt reflect.Type) (gobType, error) {
   448  	// Does this type implement GobEncoder?
   449  	if ut.externalEnc != 0 {
   450  		return newGobEncoderType(name), nil
   451  	}
   452  	var err error
   453  	var type0, type1 gobType
   454  	defer func() {
   455  		if err != nil {
   456  			delete(types, rt)
   457  		}
   458  	}()
   459  	// Install the top-level type before the subtypes (e.g. struct before
   460  	// fields) so recursive types can be constructed safely.
   461  	switch t := rt; t.Kind() {
   462  	// All basic types are easy: they are predefined.
   463  	case reflect.Bool:
   464  		return tBool.gobType(), nil
   465  
   466  	case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64:
   467  		return tInt.gobType(), nil
   468  
   469  	case reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Uintptr:
   470  		return tUint.gobType(), nil
   471  
   472  	case reflect.Float32, reflect.Float64:
   473  		return tFloat.gobType(), nil
   474  
   475  	case reflect.Complex64, reflect.Complex128:
   476  		return tComplex.gobType(), nil
   477  
   478  	case reflect.String:
   479  		return tString.gobType(), nil
   480  
   481  	case reflect.Interface:
   482  		return tInterface.gobType(), nil
   483  
   484  	case reflect.Array:
   485  		at := newArrayType(name)
   486  		types[rt] = at
   487  		type0, err = getBaseType("", t.Elem())
   488  		if err != nil {
   489  			return nil, err
   490  		}
   491  		// Historical aside:
   492  		// For arrays, maps, and slices, we set the type id after the elements
   493  		// are constructed. This is to retain the order of type id allocation after
   494  		// a fix made to handle recursive types, which changed the order in
   495  		// which types are built.  Delaying the setting in this way preserves
   496  		// type ids while allowing recursive types to be described. Structs,
   497  		// done below, were already handling recursion correctly so they
   498  		// assign the top-level id before those of the field.
   499  		at.init(type0, t.Len())
   500  		return at, nil
   501  
   502  	case reflect.Map:
   503  		mt := newMapType(name)
   504  		types[rt] = mt
   505  		type0, err = getBaseType("", t.Key())
   506  		if err != nil {
   507  			return nil, err
   508  		}
   509  		type1, err = getBaseType("", t.Elem())
   510  		if err != nil {
   511  			return nil, err
   512  		}
   513  		mt.init(type0, type1)
   514  		return mt, nil
   515  
   516  	case reflect.Slice:
   517  		// []byte == []uint8 is a special case
   518  		if t.Elem().Kind() == reflect.Uint8 {
   519  			return tBytes.gobType(), nil
   520  		}
   521  		st := newSliceType(name)
   522  		types[rt] = st
   523  		type0, err = getBaseType(t.Elem().Name(), t.Elem())
   524  		if err != nil {
   525  			return nil, err
   526  		}
   527  		st.init(type0)
   528  		return st, nil
   529  
   530  	case reflect.Struct:
   531  		st := newStructType(name)
   532  		types[rt] = st
   533  		idToType[st.id()] = st
   534  		for i := 0; i < t.NumField(); i++ {
   535  			f := t.Field(i)
   536  			if !isSent(&f) {
   537  				continue
   538  			}
   539  			typ := userType(f.Type).base
   540  			tname := typ.Name()
   541  			if tname == "" {
   542  				t := userType(f.Type).base
   543  				tname = t.String()
   544  			}
   545  			gt, err := getBaseType(tname, f.Type)
   546  			if err != nil {
   547  				return nil, err
   548  			}
   549  			// Some mutually recursive types can cause us to be here while
   550  			// still defining the element. Fix the element type id here.
   551  			// We could do this more neatly by setting the id at the start of
   552  			// building every type, but that would break binary compatibility.
   553  			if gt.id() == 0 {
   554  				setTypeId(gt)
   555  			}
   556  			st.Field = append(st.Field, &fieldType{f.Name, gt.id()})
   557  		}
   558  		return st, nil
   559  
   560  	default:
   561  		return nil, errors.New("gob NewTypeObject can't handle type: " + rt.String())
   562  	}
   563  }
   564  
   565  // isExported reports whether this is an exported - upper case - name.
   566  func isExported(name string) bool {
   567  	rune, _ := utf8.DecodeRuneInString(name)
   568  	return unicode.IsUpper(rune)
   569  }
   570  
   571  // isSent reports whether this struct field is to be transmitted.
   572  // It will be transmitted only if it is exported and not a chan or func field
   573  // or pointer to chan or func.
   574  func isSent(field *reflect.StructField) bool {
   575  	if !isExported(field.Name) {
   576  		return false
   577  	}
   578  	// If the field is a chan or func or pointer thereto, don't send it.
   579  	// That is, treat it like an unexported field.
   580  	typ := field.Type
   581  	for typ.Kind() == reflect.Ptr {
   582  		typ = typ.Elem()
   583  	}
   584  	if typ.Kind() == reflect.Chan || typ.Kind() == reflect.Func {
   585  		return false
   586  	}
   587  	return true
   588  }
   589  
   590  // getBaseType returns the Gob type describing the given reflect.Type's base type.
   591  // typeLock must be held.
   592  func getBaseType(name string, rt reflect.Type) (gobType, error) {
   593  	ut := userType(rt)
   594  	return getType(name, ut, ut.base)
   595  }
   596  
   597  // getType returns the Gob type describing the given reflect.Type.
   598  // Should be called only when handling GobEncoders/Decoders,
   599  // which may be pointers.  All other types are handled through the
   600  // base type, never a pointer.
   601  // typeLock must be held.
   602  func getType(name string, ut *userTypeInfo, rt reflect.Type) (gobType, error) {
   603  	typ, present := types[rt]
   604  	if present {
   605  		return typ, nil
   606  	}
   607  	typ, err := newTypeObject(name, ut, rt)
   608  	if err == nil {
   609  		types[rt] = typ
   610  	}
   611  	return typ, err
   612  }
   613  
   614  func checkId(want, got typeId) {
   615  	if want != got {
   616  		fmt.Fprintf(os.Stderr, "checkId: %d should be %d\n", int(got), int(want))
   617  		panic("bootstrap type wrong id: " + got.name() + " " + got.string() + " not " + want.string())
   618  	}
   619  }
   620  
   621  // used for building the basic types; called only from init().  the incoming
   622  // interface always refers to a pointer.
   623  func bootstrapType(name string, e interface{}, expect typeId) typeId {
   624  	rt := reflect.TypeOf(e).Elem()
   625  	_, present := types[rt]
   626  	if present {
   627  		panic("bootstrap type already present: " + name + ", " + rt.String())
   628  	}
   629  	typ := &CommonType{Name: name}
   630  	types[rt] = typ
   631  	setTypeId(typ)
   632  	checkId(expect, nextId)
   633  	userType(rt) // might as well cache it now
   634  	return nextId
   635  }
   636  
   637  // Representation of the information we send and receive about this type.
   638  // Each value we send is preceded by its type definition: an encoded int.
   639  // However, the very first time we send the value, we first send the pair
   640  // (-id, wireType).
   641  // For bootstrapping purposes, we assume that the recipient knows how
   642  // to decode a wireType; it is exactly the wireType struct here, interpreted
   643  // using the gob rules for sending a structure, except that we assume the
   644  // ids for wireType and structType etc. are known.  The relevant pieces
   645  // are built in encode.go's init() function.
   646  // To maintain binary compatibility, if you extend this type, always put
   647  // the new fields last.
   648  type wireType struct {
   649  	ArrayT           *arrayType
   650  	SliceT           *sliceType
   651  	StructT          *structType
   652  	MapT             *mapType
   653  	GobEncoderT      *gobEncoderType
   654  	BinaryMarshalerT *gobEncoderType
   655  	TextMarshalerT   *gobEncoderType
   656  }
   657  
   658  func (w *wireType) string() string {
   659  	const unknown = "unknown type"
   660  	if w == nil {
   661  		return unknown
   662  	}
   663  	switch {
   664  	case w.ArrayT != nil:
   665  		return w.ArrayT.Name
   666  	case w.SliceT != nil:
   667  		return w.SliceT.Name
   668  	case w.StructT != nil:
   669  		return w.StructT.Name
   670  	case w.MapT != nil:
   671  		return w.MapT.Name
   672  	case w.GobEncoderT != nil:
   673  		return w.GobEncoderT.Name
   674  	case w.BinaryMarshalerT != nil:
   675  		return w.BinaryMarshalerT.Name
   676  	case w.TextMarshalerT != nil:
   677  		return w.TextMarshalerT.Name
   678  	}
   679  	return unknown
   680  }
   681  
   682  type typeInfo struct {
   683  	id      typeId
   684  	encoder *encEngine
   685  	wire    *wireType
   686  }
   687  
   688  var typeInfoMap = make(map[reflect.Type]*typeInfo) // protected by typeLock
   689  
   690  // typeLock must be held.
   691  func getTypeInfo(ut *userTypeInfo) (*typeInfo, error) {
   692  	rt := ut.base
   693  	if ut.externalEnc != 0 {
   694  		// We want the user type, not the base type.
   695  		rt = ut.user
   696  	}
   697  	info, ok := typeInfoMap[rt]
   698  	if ok {
   699  		return info, nil
   700  	}
   701  	info = new(typeInfo)
   702  	gt, err := getBaseType(rt.Name(), rt)
   703  	if err != nil {
   704  		return nil, err
   705  	}
   706  	info.id = gt.id()
   707  
   708  	if ut.externalEnc != 0 {
   709  		userType, err := getType(rt.Name(), ut, rt)
   710  		if err != nil {
   711  			return nil, err
   712  		}
   713  		gt := userType.id().gobType().(*gobEncoderType)
   714  		switch ut.externalEnc {
   715  		case xGob:
   716  			info.wire = &wireType{GobEncoderT: gt}
   717  		case xBinary:
   718  			info.wire = &wireType{BinaryMarshalerT: gt}
   719  		case xText:
   720  			info.wire = &wireType{TextMarshalerT: gt}
   721  		}
   722  		typeInfoMap[ut.user] = info
   723  		return info, nil
   724  	}
   725  
   726  	t := info.id.gobType()
   727  	switch typ := rt; typ.Kind() {
   728  	case reflect.Array:
   729  		info.wire = &wireType{ArrayT: t.(*arrayType)}
   730  	case reflect.Map:
   731  		info.wire = &wireType{MapT: t.(*mapType)}
   732  	case reflect.Slice:
   733  		// []byte == []uint8 is a special case handled separately
   734  		if typ.Elem().Kind() != reflect.Uint8 {
   735  			info.wire = &wireType{SliceT: t.(*sliceType)}
   736  		}
   737  	case reflect.Struct:
   738  		info.wire = &wireType{StructT: t.(*structType)}
   739  	}
   740  	typeInfoMap[rt] = info
   741  	return info, nil
   742  }
   743  
   744  // Called only when a panic is acceptable and unexpected.
   745  func mustGetTypeInfo(rt reflect.Type) *typeInfo {
   746  	t, err := getTypeInfo(userType(rt))
   747  	if err != nil {
   748  		panic("getTypeInfo: " + err.Error())
   749  	}
   750  	return t
   751  }
   752  
   753  // GobEncoder is the interface describing data that provides its own
   754  // representation for encoding values for transmission to a GobDecoder.
   755  // A type that implements GobEncoder and GobDecoder has complete
   756  // control over the representation of its data and may therefore
   757  // contain things such as private fields, channels, and functions,
   758  // which are not usually transmissible in gob streams.
   759  //
   760  // Note: Since gobs can be stored permanently, It is good design
   761  // to guarantee the encoding used by a GobEncoder is stable as the
   762  // software evolves.  For instance, it might make sense for GobEncode
   763  // to include a version number in the encoding.
   764  type GobEncoder interface {
   765  	// GobEncode returns a byte slice representing the encoding of the
   766  	// receiver for transmission to a GobDecoder, usually of the same
   767  	// concrete type.
   768  	GobEncode() ([]byte, error)
   769  }
   770  
   771  // GobDecoder is the interface describing data that provides its own
   772  // routine for decoding transmitted values sent by a GobEncoder.
   773  type GobDecoder interface {
   774  	// GobDecode overwrites the receiver, which must be a pointer,
   775  	// with the value represented by the byte slice, which was written
   776  	// by GobEncode, usually for the same concrete type.
   777  	GobDecode([]byte) error
   778  }
   779  
   780  var (
   781  	registerLock       sync.RWMutex
   782  	nameToConcreteType = make(map[string]reflect.Type)
   783  	concreteTypeToName = make(map[reflect.Type]string)
   784  )
   785  
   786  // RegisterName is like Register but uses the provided name rather than the
   787  // type's default.
   788  func RegisterName(name string, value interface{}) {
   789  	if name == "" {
   790  		// reserved for nil
   791  		panic("attempt to register empty name")
   792  	}
   793  	registerLock.Lock()
   794  	defer registerLock.Unlock()
   795  	ut := userType(reflect.TypeOf(value))
   796  	// Check for incompatible duplicates. The name must refer to the
   797  	// same user type, and vice versa.
   798  	if t, ok := nameToConcreteType[name]; ok && t != ut.user {
   799  		panic(fmt.Sprintf("gob: registering duplicate types for %q: %s != %s", name, t, ut.user))
   800  	}
   801  	if n, ok := concreteTypeToName[ut.base]; ok && n != name {
   802  		panic(fmt.Sprintf("gob: registering duplicate names for %s: %q != %q", ut.user, n, name))
   803  	}
   804  	// Store the name and type provided by the user....
   805  	nameToConcreteType[name] = reflect.TypeOf(value)
   806  	// but the flattened type in the type table, since that's what decode needs.
   807  	concreteTypeToName[ut.base] = name
   808  }
   809  
   810  // Register records a type, identified by a value for that type, under its
   811  // internal type name.  That name will identify the concrete type of a value
   812  // sent or received as an interface variable.  Only types that will be
   813  // transferred as implementations of interface values need to be registered.
   814  // Expecting to be used only during initialization, it panics if the mapping
   815  // between types and names is not a bijection.
   816  func Register(value interface{}) {
   817  	// Default to printed representation for unnamed types
   818  	rt := reflect.TypeOf(value)
   819  	name := rt.String()
   820  
   821  	// But for named types (or pointers to them), qualify with import path (but see inner comment).
   822  	// Dereference one pointer looking for a named type.
   823  	star := ""
   824  	if rt.Name() == "" {
   825  		if pt := rt; pt.Kind() == reflect.Ptr {
   826  			star = "*"
   827  			// NOTE: The following line should be rt = pt.Elem() to implement
   828  			// what the comment above claims, but fixing it would break compatibility
   829  			// with existing gobs.
   830  			//
   831  			// Given package p imported as "full/p" with these definitions:
   832  			//     package p
   833  			//     type T1 struct { ... }
   834  			// this table shows the intended and actual strings used by gob to
   835  			// name the types:
   836  			//
   837  			// Type      Correct string     Actual string
   838  			//
   839  			// T1        full/p.T1          full/p.T1
   840  			// *T1       *full/p.T1         *p.T1
   841  			//
   842  			// The missing full path cannot be fixed without breaking existing gob decoders.
   843  			rt = pt
   844  		}
   845  	}
   846  	if rt.Name() != "" {
   847  		if rt.PkgPath() == "" {
   848  			name = star + rt.Name()
   849  		} else {
   850  			name = star + rt.PkgPath() + "." + rt.Name()
   851  		}
   852  	}
   853  
   854  	RegisterName(name, value)
   855  }
   856  
   857  func registerBasics() {
   858  	Register(int(0))
   859  	Register(int8(0))
   860  	Register(int16(0))
   861  	Register(int32(0))
   862  	Register(int64(0))
   863  	Register(uint(0))
   864  	Register(uint8(0))
   865  	Register(uint16(0))
   866  	Register(uint32(0))
   867  	Register(uint64(0))
   868  	Register(float32(0))
   869  	Register(float64(0))
   870  	Register(complex64(0i))
   871  	Register(complex128(0i))
   872  	Register(uintptr(0))
   873  	Register(false)
   874  	Register("")
   875  	Register([]byte(nil))
   876  	Register([]int(nil))
   877  	Register([]int8(nil))
   878  	Register([]int16(nil))
   879  	Register([]int32(nil))
   880  	Register([]int64(nil))
   881  	Register([]uint(nil))
   882  	Register([]uint8(nil))
   883  	Register([]uint16(nil))
   884  	Register([]uint32(nil))
   885  	Register([]uint64(nil))
   886  	Register([]float32(nil))
   887  	Register([]float64(nil))
   888  	Register([]complex64(nil))
   889  	Register([]complex128(nil))
   890  	Register([]uintptr(nil))
   891  	Register([]bool(nil))
   892  	Register([]string(nil))
   893  }