1
2
3
4
5 package gob
6
7 import (
8 "fmt"
9 "os"
10 "reflect"
11 "sync"
12 "unicode"
13 "utf8"
14 )
15
16
17
18
19 type userTypeInfo struct {
20 user reflect.Type
21 base reflect.Type
22 indir int
23 isGobEncoder bool
24 isGobDecoder bool
25 encIndir int8
26 decIndir int8
27 }
28
29 var (
30
31
32 userTypeLock sync.RWMutex
33 userTypeCache = make(map[reflect.Type]*userTypeInfo)
34 )
35
36
37
38
39 func validUserType(rt reflect.Type) (ut *userTypeInfo, err os.Error) {
40 userTypeLock.RLock()
41 ut = userTypeCache[rt]
42 userTypeLock.RUnlock()
43 if ut != nil {
44 return
45 }
46
47 userTypeLock.Lock()
48 defer userTypeLock.Unlock()
49 if ut = userTypeCache[rt]; ut != nil {
50
51 return
52 }
53 ut = new(userTypeInfo)
54 ut.base = rt
55 ut.user = rt
56
57
58
59
60
61 slowpoke := ut.base
62 for {
63 pt := ut.base
64 if pt.Kind() != reflect.Ptr {
65 break
66 }
67 ut.base = pt.Elem()
68 if ut.base == slowpoke {
69
70 return nil, os.NewError("can't represent recursive pointer type " + ut.base.String())
71 }
72 if ut.indir%2 == 0 {
73 slowpoke = slowpoke.Elem()
74 }
75 ut.indir++
76 }
77 ut.isGobEncoder, ut.encIndir = implementsInterface(ut.user, gobEncoderInterfaceType)
78 ut.isGobDecoder, ut.decIndir = implementsInterface(ut.user, gobDecoderInterfaceType)
79 userTypeCache[rt] = ut
80 return
81 }
82
83 var (
84 gobEncoderInterfaceType = reflect.TypeOf((*GobEncoder)(nil)).Elem()
85 gobDecoderInterfaceType = reflect.TypeOf((*GobDecoder)(nil)).Elem()
86 )
87
88
89
90
91
92 func implementsInterface(typ, gobEncDecType reflect.Type) (success bool, indir int8) {
93 if typ == nil {
94 return
95 }
96 rt := typ
97
98
99 for {
100 if rt.Implements(gobEncDecType) {
101 return true, indir
102 }
103 if p := rt; p.Kind() == reflect.Ptr {
104 indir++
105 if indir > 100 {
106 return false, 0
107 }
108 rt = p.Elem()
109 continue
110 }
111 break
112 }
113
114 if typ.Kind() != reflect.Ptr {
115
116 if reflect.PtrTo(typ).Implements(gobEncDecType) {
117 return true, -1
118 }
119 }
120 return false, 0
121 }
122
123
124
125 func userType(rt reflect.Type) *userTypeInfo {
126 ut, err := validUserType(rt)
127 if err != nil {
128 error(err)
129 }
130 return ut
131 }
132
133
134 type typeId int32
135
136 var nextId typeId
137 var typeLock sync.Mutex
138 const firstUserId = 64
139
140 type gobType interface {
141 id() typeId
142 setId(id typeId)
143 name() string
144 string() string
145 safeString(seen map[typeId]bool) string
146 }
147
148 var types = make(map[reflect.Type]gobType)
149 var idToType = make(map[typeId]gobType)
150 var builtinIdToType map[typeId]gobType
151
152 func setTypeId(typ gobType) {
153 nextId++
154 typ.setId(nextId)
155 idToType[nextId] = typ
156 }
157
158 func (t typeId) gobType() gobType {
159 if t == 0 {
160 return nil
161 }
162 return idToType[t]
163 }
164
165
166 func (t typeId) string() string {
167 if t.gobType() == nil {
168 return "<nil>"
169 }
170 return t.gobType().string()
171 }
172
173
174 func (t typeId) name() string {
175 if t.gobType() == nil {
176 return "<nil>"
177 }
178 return t.gobType().name()
179 }
180
181
182 type CommonType struct {
183 Name string
184 Id typeId
185 }
186
187 func (t *CommonType) id() typeId { return t.Id }
188
189 func (t *CommonType) setId(id typeId) { t.Id = id }
190
191 func (t *CommonType) string() string { return t.Name }
192
193 func (t *CommonType) safeString(seen map[typeId]bool) string {
194 return t.Name
195 }
196
197 func (t *CommonType) name() string { return t.Name }
198
199
200
201
202 var (
203
204
205
206 tBool = bootstrapType("bool", (*bool)(nil), 1)
207 tInt = bootstrapType("int", (*int)(nil), 2)
208 tUint = bootstrapType("uint", (*uint)(nil), 3)
209 tFloat = bootstrapType("float", (*float64)(nil), 4)
210 tBytes = bootstrapType("bytes", (*[]byte)(nil), 5)
211 tString = bootstrapType("string", (*string)(nil), 6)
212 tComplex = bootstrapType("complex", (*complex128)(nil), 7)
213 tInterface = bootstrapType("interface", (*interface{})(nil), 8)
214
215 tReserved7 = bootstrapType("_reserved1", (*struct{ r7 int })(nil), 9)
216 tReserved6 = bootstrapType("_reserved1", (*struct{ r6 int })(nil), 10)
217 tReserved5 = bootstrapType("_reserved1", (*struct{ r5 int })(nil), 11)
218 tReserved4 = bootstrapType("_reserved1", (*struct{ r4 int })(nil), 12)
219 tReserved3 = bootstrapType("_reserved1", (*struct{ r3 int })(nil), 13)
220 tReserved2 = bootstrapType("_reserved1", (*struct{ r2 int })(nil), 14)
221 tReserved1 = bootstrapType("_reserved1", (*struct{ r1 int })(nil), 15)
222 )
223
224
225 var tWireType = mustGetTypeInfo(reflect.TypeOf(wireType{})).id
226 var wireTypeUserInfo *userTypeInfo
227
228 func init() {
229
230 checkId(16, tWireType)
231 checkId(17, mustGetTypeInfo(reflect.TypeOf(arrayType{})).id)
232 checkId(18, mustGetTypeInfo(reflect.TypeOf(CommonType{})).id)
233 checkId(19, mustGetTypeInfo(reflect.TypeOf(sliceType{})).id)
234 checkId(20, mustGetTypeInfo(reflect.TypeOf(structType{})).id)
235 checkId(21, mustGetTypeInfo(reflect.TypeOf(fieldType{})).id)
236 checkId(23, mustGetTypeInfo(reflect.TypeOf(mapType{})).id)
237
238 builtinIdToType = make(map[typeId]gobType)
239 for k, v := range idToType {
240 builtinIdToType[k] = v
241 }
242
243
244
245 if nextId > firstUserId {
246 panic(fmt.Sprintln("nextId too large:", nextId))
247 }
248 nextId = firstUserId
249 registerBasics()
250 wireTypeUserInfo = userType(reflect.TypeOf((*wireType)(nil)))
251 }
252
253
254 type arrayType struct {
255 CommonType
256 Elem typeId
257 Len int
258 }
259
260 func newArrayType(name string) *arrayType {
261 a := &arrayType{CommonType{Name: name}, 0, 0}
262 return a
263 }
264
265 func (a *arrayType) init(elem gobType, len int) {
266
267 setTypeId(a)
268 a.Elem = elem.id()
269 a.Len = len
270 }
271
272 func (a *arrayType) safeString(seen map[typeId]bool) string {
273 if seen[a.Id] {
274 return a.Name
275 }
276 seen[a.Id] = true
277 return fmt.Sprintf("[%d]%s", a.Len, a.Elem.gobType().safeString(seen))
278 }
279
280 func (a *arrayType) string() string { return a.safeString(make(map[typeId]bool)) }
281
282
283 type gobEncoderType struct {
284 CommonType
285 }
286
287 func newGobEncoderType(name string) *gobEncoderType {
288 g := &gobEncoderType{CommonType{Name: name}}
289 setTypeId(g)
290 return g
291 }
292
293 func (g *gobEncoderType) safeString(seen map[typeId]bool) string {
294 return g.Name
295 }
296
297 func (g *gobEncoderType) string() string { return g.Name }
298
299
300 type mapType struct {
301 CommonType
302 Key typeId
303 Elem typeId
304 }
305
306 func newMapType(name string) *mapType {
307 m := &mapType{CommonType{Name: name}, 0, 0}
308 return m
309 }
310
311 func (m *mapType) init(key, elem gobType) {
312
313 setTypeId(m)
314 m.Key = key.id()
315 m.Elem = elem.id()
316 }
317
318 func (m *mapType) safeString(seen map[typeId]bool) string {
319 if seen[m.Id] {
320 return m.Name
321 }
322 seen[m.Id] = true
323 key := m.Key.gobType().safeString(seen)
324 elem := m.Elem.gobType().safeString(seen)
325 return fmt.Sprintf("map[%s]%s", key, elem)
326 }
327
328 func (m *mapType) string() string { return m.safeString(make(map[typeId]bool)) }
329
330
331 type sliceType struct {
332 CommonType
333 Elem typeId
334 }
335
336 func newSliceType(name string) *sliceType {
337 s := &sliceType{CommonType{Name: name}, 0}
338 return s
339 }
340
341 func (s *sliceType) init(elem gobType) {
342
343 setTypeId(s)
344 s.Elem = elem.id()
345 }
346
347 func (s *sliceType) safeString(seen map[typeId]bool) string {
348 if seen[s.Id] {
349 return s.Name
350 }
351 seen[s.Id] = true
352 return fmt.Sprintf("[]%s", s.Elem.gobType().safeString(seen))
353 }
354
355 func (s *sliceType) string() string { return s.safeString(make(map[typeId]bool)) }
356
357
358 type fieldType struct {
359 Name string
360 Id typeId
361 }
362
363 type structType struct {
364 CommonType
365 Field []*fieldType
366 }
367
368 func (s *structType) safeString(seen map[typeId]bool) string {
369 if s == nil {
370 return "<nil>"
371 }
372 if _, ok := seen[s.Id]; ok {
373 return s.Name
374 }
375 seen[s.Id] = true
376 str := s.Name + " = struct { "
377 for _, f := range s.Field {
378 str += fmt.Sprintf("%s %s; ", f.Name, f.Id.gobType().safeString(seen))
379 }
380 str += "}"
381 return str
382 }
383
384 func (s *structType) string() string { return s.safeString(make(map[typeId]bool)) }
385
386 func newStructType(name string) *structType {
387 s := &structType{CommonType{Name: name}, nil}
388
389
390 setTypeId(s)
391 return s
392 }
393
394
395
396
397
398
399 func newTypeObject(name string, ut *userTypeInfo, rt reflect.Type) (gobType, os.Error) {
400
401 if ut.isGobEncoder {
402 return newGobEncoderType(name), nil
403 }
404 var err os.Error
405 var type0, type1 gobType
406 defer func() {
407 if err != nil {
408 types[rt] = nil, false
409 }
410 }()
411
412
413 switch t := rt; t.Kind() {
414
415 case reflect.Bool:
416 return tBool.gobType(), nil
417
418 case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64:
419 return tInt.gobType(), nil
420
421 case reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Uintptr:
422 return tUint.gobType(), nil
423
424 case reflect.Float32, reflect.Float64:
425 return tFloat.gobType(), nil
426
427 case reflect.Complex64, reflect.Complex128:
428 return tComplex.gobType(), nil
429
430 case reflect.String:
431 return tString.gobType(), nil
432
433 case reflect.Interface:
434 return tInterface.gobType(), nil
435
436 case reflect.Array:
437 at := newArrayType(name)
438 types[rt] = at
439 type0, err = getBaseType("", t.Elem())
440 if err != nil {
441 return nil, err
442 }
443
444
445
446
447
448
449
450
451 at.init(type0, t.Len())
452 return at, nil
453
454 case reflect.Map:
455 mt := newMapType(name)
456 types[rt] = mt
457 type0, err = getBaseType("", t.Key())
458 if err != nil {
459 return nil, err
460 }
461 type1, err = getBaseType("", t.Elem())
462 if err != nil {
463 return nil, err
464 }
465 mt.init(type0, type1)
466 return mt, nil
467
468 case reflect.Slice:
469
470 if t.Elem().Kind() == reflect.Uint8 {
471 return tBytes.gobType(), nil
472 }
473 st := newSliceType(name)
474 types[rt] = st
475 type0, err = getBaseType(t.Elem().Name(), t.Elem())
476 if err != nil {
477 return nil, err
478 }
479 st.init(type0)
480 return st, nil
481
482 case reflect.Struct:
483 st := newStructType(name)
484 types[rt] = st
485 idToType[st.id()] = st
486 for i := 0; i < t.NumField(); i++ {
487 f := t.Field(i)
488 if !isExported(f.Name) {
489 continue
490 }
491 typ := userType(f.Type).base
492 tname := typ.Name()
493 if tname == "" {
494 t := userType(f.Type).base
495 tname = t.String()
496 }
497 gt, err := getBaseType(tname, f.Type)
498 if err != nil {
499 return nil, err
500 }
501 st.Field = append(st.Field, &fieldType{f.Name, gt.id()})
502 }
503 return st, nil
504
505 default:
506 return nil, os.NewError("gob NewTypeObject can't handle type: " + rt.String())
507 }
508 return nil, nil
509 }
510
511
512 func isExported(name string) bool {
513 rune, _ := utf8.DecodeRuneInString(name)
514 return unicode.IsUpper(rune)
515 }
516
517
518
519 func getBaseType(name string, rt reflect.Type) (gobType, os.Error) {
520 ut := userType(rt)
521 return getType(name, ut, ut.base)
522 }
523
524
525
526
527
528
529 func getType(name string, ut *userTypeInfo, rt reflect.Type) (gobType, os.Error) {
530 typ, present := types[rt]
531 if present {
532 return typ, nil
533 }
534 typ, err := newTypeObject(name, ut, rt)
535 if err == nil {
536 types[rt] = typ
537 }
538 return typ, err
539 }
540
541 func checkId(want, got typeId) {
542 if want != got {
543 fmt.Fprintf(os.Stderr, "checkId: %d should be %d\n", int(got), int(want))
544 panic("bootstrap type wrong id: " + got.name() + " " + got.string() + " not " + want.string())
545 }
546 }
547
548
549
550 func bootstrapType(name string, e interface{}, expect typeId) typeId {
551 rt := reflect.TypeOf(e).Elem()
552 _, present := types[rt]
553 if present {
554 panic("bootstrap type already present: " + name + ", " + rt.String())
555 }
556 typ := &CommonType{Name: name}
557 types[rt] = typ
558 setTypeId(typ)
559 checkId(expect, nextId)
560 userType(rt)
561 return nextId
562 }
563
564
565
566
567
568
569
570
571
572
573
574
575 type wireType struct {
576 ArrayT *arrayType
577 SliceT *sliceType
578 StructT *structType
579 MapT *mapType
580 GobEncoderT *gobEncoderType
581 }
582
583 func (w *wireType) string() string {
584 const unknown = "unknown type"
585 if w == nil {
586 return unknown
587 }
588 switch {
589 case w.ArrayT != nil:
590 return w.ArrayT.Name
591 case w.SliceT != nil:
592 return w.SliceT.Name
593 case w.StructT != nil:
594 return w.StructT.Name
595 case w.MapT != nil:
596 return w.MapT.Name
597 case w.GobEncoderT != nil:
598 return w.GobEncoderT.Name
599 }
600 return unknown
601 }
602
603 type typeInfo struct {
604 id typeId
605 encoder *encEngine
606 wire *wireType
607 }
608
609 var typeInfoMap = make(map[reflect.Type]*typeInfo)
610
611
612 func getTypeInfo(ut *userTypeInfo) (*typeInfo, os.Error) {
613 rt := ut.base
614 if ut.isGobEncoder {
615
616 rt = ut.user
617 }
618 info, ok := typeInfoMap[rt]
619 if ok {
620 return info, nil
621 }
622 info = new(typeInfo)
623 gt, err := getBaseType(rt.Name(), rt)
624 if err != nil {
625 return nil, err
626 }
627 info.id = gt.id()
628
629 if ut.isGobEncoder {
630 userType, err := getType(rt.Name(), ut, rt)
631 if err != nil {
632 return nil, err
633 }
634 info.wire = &wireType{GobEncoderT: userType.id().gobType().(*gobEncoderType)}
635 typeInfoMap[ut.user] = info
636 return info, nil
637 }
638
639 t := info.id.gobType()
640 switch typ := rt; typ.Kind() {
641 case reflect.Array:
642 info.wire = &wireType{ArrayT: t.(*arrayType)}
643 case reflect.Map:
644 info.wire = &wireType{MapT: t.(*mapType)}
645 case reflect.Slice:
646
647 if typ.Elem().Kind() != reflect.Uint8 {
648 info.wire = &wireType{SliceT: t.(*sliceType)}
649 }
650 case reflect.Struct:
651 info.wire = &wireType{StructT: t.(*structType)}
652 }
653 typeInfoMap[rt] = info
654 return info, nil
655 }
656
657
658 func mustGetTypeInfo(rt reflect.Type) *typeInfo {
659 t, err := getTypeInfo(userType(rt))
660 if err != nil {
661 panic("getTypeInfo: " + err.String())
662 }
663 return t
664 }
665
666
667
668
669
670
671
672
673
674
675
676
677 type GobEncoder interface {
678
679
680
681 GobEncode() ([]byte, os.Error)
682 }
683
684
685
686 type GobDecoder interface {
687
688
689
690 GobDecode([]byte) os.Error
691 }
692
693 var (
694 nameToConcreteType = make(map[string]reflect.Type)
695 concreteTypeToName = make(map[reflect.Type]string)
696 )
697
698
699
700 func RegisterName(name string, value interface{}) {
701 if name == "" {
702
703 panic("attempt to register empty name")
704 }
705 base := userType(reflect.TypeOf(value)).base
706
707 if t, ok := nameToConcreteType[name]; ok && t != base {
708 panic("gob: registering duplicate types for " + name)
709 }
710 if n, ok := concreteTypeToName[base]; ok && n != name {
711 panic("gob: registering duplicate names for " + base.String())
712 }
713
714 nameToConcreteType[name] = reflect.TypeOf(value)
715
716 concreteTypeToName[base] = name
717 }
718
719
720
721
722
723
724
725 func Register(value interface{}) {
726
727 rt := reflect.TypeOf(value)
728 name := rt.String()
729
730
731
732 star := ""
733 if rt.Name() == "" {
734 if pt := rt; pt.Kind() == reflect.Ptr {
735 star = "*"
736 rt = pt
737 }
738 }
739 if rt.Name() != "" {
740 if rt.PkgPath() == "" {
741 name = star + rt.Name()
742 } else {
743 name = star + rt.PkgPath() + "." + rt.Name()
744 }
745 }
746
747 RegisterName(name, value)
748 }
749
750 func registerBasics() {
751 Register(int(0))
752 Register(int8(0))
753 Register(int16(0))
754 Register(int32(0))
755 Register(int64(0))
756 Register(uint(0))
757 Register(uint8(0))
758 Register(uint16(0))
759 Register(uint32(0))
760 Register(uint64(0))
761 Register(float32(0))
762 Register(float64(0))
763 Register(complex64(0i))
764 Register(complex128(0i))
765 Register(uintptr(0))
766 Register(false)
767 Register("")
768 Register([]byte(nil))
769 Register([]int(nil))
770 Register([]int8(nil))
771 Register([]int16(nil))
772 Register([]int32(nil))
773 Register([]int64(nil))
774 Register([]uint(nil))
775 Register([]uint8(nil))
776 Register([]uint16(nil))
777 Register([]uint32(nil))
778 Register([]uint64(nil))
779 Register([]float32(nil))
780 Register([]float64(nil))
781 Register([]complex64(nil))
782 Register([]complex128(nil))
783 Register([]uintptr(nil))
784 Register([]bool(nil))
785 Register([]string(nil))
786 }