1
2
3
4
5
6
7 package gcimporter
8
9 import (
10 "fmt"
11 "go/token"
12 "go/types"
13 "sort"
14 "strings"
15
16 "golang.org/x/tools/internal/aliases"
17 "golang.org/x/tools/internal/pkgbits"
18 "golang.org/x/tools/internal/typesinternal"
19 )
20
21
22
23 type pkgReader struct {
24 pkgbits.PkgDecoder
25
26 fake fakeFileSet
27
28 ctxt *types.Context
29 imports map[string]*types.Package
30
31
32
33 posBases []string
34 pkgs []*types.Package
35 typs []types.Type
36
37
38
39
40
41
42
43 laterFns []func()
44
45 laterFors map[types.Type]int
46
47
48
49 ifaces []*types.Interface
50 }
51
52
53 func (pr *pkgReader) later(fn func()) {
54 pr.laterFns = append(pr.laterFns, fn)
55 }
56
57
58 type derivedInfo struct {
59 idx pkgbits.Index
60 }
61
62
63 type typeInfo struct {
64 idx pkgbits.Index
65 derived bool
66 }
67
68 func UImportData(fset *token.FileSet, imports map[string]*types.Package, data []byte, path string) (_ int, pkg *types.Package, err error) {
69 if !debug {
70 defer func() {
71 if x := recover(); x != nil {
72 err = fmt.Errorf("internal error in importing %q (%v); please report an issue", path, x)
73 }
74 }()
75 }
76
77 s := string(data)
78 input := pkgbits.NewPkgDecoder(path, s)
79 pkg = readUnifiedPackage(fset, nil, imports, input)
80 return
81 }
82
83
84 func (pr *pkgReader) laterFor(t types.Type, fn func()) {
85 if pr.laterFors == nil {
86 pr.laterFors = make(map[types.Type]int)
87 }
88 pr.laterFors[t] = len(pr.laterFns)
89 pr.laterFns = append(pr.laterFns, fn)
90 }
91
92
93
94 func readUnifiedPackage(fset *token.FileSet, ctxt *types.Context, imports map[string]*types.Package, input pkgbits.PkgDecoder) *types.Package {
95 pr := pkgReader{
96 PkgDecoder: input,
97
98 fake: fakeFileSet{
99 fset: fset,
100 files: make(map[string]*fileInfo),
101 },
102
103 ctxt: ctxt,
104 imports: imports,
105
106 posBases: make([]string, input.NumElems(pkgbits.RelocPosBase)),
107 pkgs: make([]*types.Package, input.NumElems(pkgbits.RelocPkg)),
108 typs: make([]types.Type, input.NumElems(pkgbits.RelocType)),
109 }
110 defer pr.fake.setLines()
111
112 r := pr.newReader(pkgbits.RelocMeta, pkgbits.PublicRootIdx, pkgbits.SyncPublic)
113 pkg := r.pkg()
114 if r.Version().Has(pkgbits.HasInit) {
115 r.Bool()
116 }
117
118 for i, n := 0, r.Len(); i < n; i++ {
119
120
121 r.Sync(pkgbits.SyncObject)
122 if r.Version().Has(pkgbits.DerivedFuncInstance) {
123 assert(!r.Bool())
124 }
125 r.p.objIdx(r.Reloc(pkgbits.RelocObj))
126 assert(r.Len() == 0)
127 }
128
129 r.Sync(pkgbits.SyncEOF)
130
131 for _, fn := range pr.laterFns {
132 fn()
133 }
134
135 for _, iface := range pr.ifaces {
136 iface.Complete()
137 }
138
139
140 var imps []*types.Package
141 for _, imp := range pr.pkgs {
142 if imp != nil && imp != pkg {
143 imps = append(imps, imp)
144 }
145 }
146 sort.Sort(byPath(imps))
147 pkg.SetImports(imps)
148
149 pkg.MarkComplete()
150 return pkg
151 }
152
153
154
155 type reader struct {
156 pkgbits.Decoder
157
158 p *pkgReader
159
160 dict *readerDict
161 }
162
163
164
165 type readerDict struct {
166 rtbounds []typeInfo
167 rtparams []*types.TypeParam
168
169 tbounds []typeInfo
170 tparams []*types.TypeParam
171
172
173
174 derived []derivedInfo
175 derivedTypes []types.Type
176 }
177
178 func (pr *pkgReader) newReader(k pkgbits.RelocKind, idx pkgbits.Index, marker pkgbits.SyncMarker) *reader {
179 return &reader{
180 Decoder: pr.NewDecoder(k, idx, marker),
181 p: pr,
182 }
183 }
184
185 func (pr *pkgReader) tempReader(k pkgbits.RelocKind, idx pkgbits.Index, marker pkgbits.SyncMarker) *reader {
186 return &reader{
187 Decoder: pr.TempDecoder(k, idx, marker),
188 p: pr,
189 }
190 }
191
192 func (pr *pkgReader) retireReader(r *reader) {
193 pr.RetireDecoder(&r.Decoder)
194 }
195
196
197
198 func (r *reader) pos() token.Pos {
199 r.Sync(pkgbits.SyncPos)
200 if !r.Bool() {
201 return token.NoPos
202 }
203
204
205 posBase := r.posBase()
206 line := r.Uint()
207 col := r.Uint()
208 return r.p.fake.pos(posBase, int(line), int(col))
209 }
210
211 func (r *reader) posBase() string {
212 return r.p.posBaseIdx(r.Reloc(pkgbits.RelocPosBase))
213 }
214
215 func (pr *pkgReader) posBaseIdx(idx pkgbits.Index) string {
216 if b := pr.posBases[idx]; b != "" {
217 return b
218 }
219
220 var filename string
221 {
222 r := pr.tempReader(pkgbits.RelocPosBase, idx, pkgbits.SyncPosBase)
223
224
225
226
227
228
229 filename = r.String()
230
231 if r.Bool() {
232
233 } else {
234 pos := r.pos()
235 line := r.Uint()
236 col := r.Uint()
237
238
239 _, _, _ = pos, line, col
240 }
241 pr.retireReader(r)
242 }
243 b := filename
244 pr.posBases[idx] = b
245 return b
246 }
247
248
249
250 func (r *reader) pkg() *types.Package {
251 r.Sync(pkgbits.SyncPkg)
252 return r.p.pkgIdx(r.Reloc(pkgbits.RelocPkg))
253 }
254
255 func (pr *pkgReader) pkgIdx(idx pkgbits.Index) *types.Package {
256
257
258 if pkg := pr.pkgs[idx]; pkg != nil {
259 return pkg
260 }
261
262 pkg := pr.newReader(pkgbits.RelocPkg, idx, pkgbits.SyncPkgDef).doPkg()
263 pr.pkgs[idx] = pkg
264 return pkg
265 }
266
267 func (r *reader) doPkg() *types.Package {
268 path := r.String()
269 switch path {
270
271
272
273
274
275 case "", "main":
276 path = r.p.PkgPath()
277 case "builtin":
278 return nil
279 case "unsafe":
280 return types.Unsafe
281 }
282
283 if pkg := r.p.imports[path]; pkg != nil {
284 return pkg
285 }
286
287 name := r.String()
288
289 pkg := types.NewPackage(path, name)
290 r.p.imports[path] = pkg
291
292 return pkg
293 }
294
295
296
297 func (r *reader) typ() types.Type {
298 return r.p.typIdx(r.typInfo(), r.dict)
299 }
300
301 func (r *reader) typInfo() typeInfo {
302 r.Sync(pkgbits.SyncType)
303 if r.Bool() {
304 return typeInfo{idx: pkgbits.Index(r.Len()), derived: true}
305 }
306 return typeInfo{idx: r.Reloc(pkgbits.RelocType), derived: false}
307 }
308
309 func (pr *pkgReader) typIdx(info typeInfo, dict *readerDict) types.Type {
310 idx := info.idx
311 var where *types.Type
312 if info.derived {
313 where = &dict.derivedTypes[idx]
314 idx = dict.derived[idx].idx
315 } else {
316 where = &pr.typs[idx]
317 }
318
319 if typ := *where; typ != nil {
320 return typ
321 }
322
323 var typ types.Type
324 {
325 r := pr.tempReader(pkgbits.RelocType, idx, pkgbits.SyncTypeIdx)
326 r.dict = dict
327
328 typ = r.doTyp()
329 assert(typ != nil)
330 pr.retireReader(r)
331 }
332
333 if prev := *where; prev != nil {
334 return prev
335 }
336
337 *where = typ
338 return typ
339 }
340
341 func (r *reader) doTyp() (res types.Type) {
342 switch tag := pkgbits.CodeType(r.Code(pkgbits.SyncType)); tag {
343 default:
344 errorf("unhandled type tag: %v", tag)
345 panic("unreachable")
346
347 case pkgbits.TypeBasic:
348 return types.Typ[r.Len()]
349
350 case pkgbits.TypeNamed:
351 obj, targs := r.obj()
352 name := obj.(*types.TypeName)
353 if len(targs) != 0 {
354 t, _ := types.Instantiate(r.p.ctxt, name.Type(), targs, false)
355 return t
356 }
357 return name.Type()
358
359 case pkgbits.TypeTypeParam:
360 n := r.Len()
361 if n < len(r.dict.rtbounds) {
362 return r.dict.rtparams[n]
363 }
364 return r.dict.tparams[n-len(r.dict.rtbounds)]
365
366 case pkgbits.TypeArray:
367 len := int64(r.Uint64())
368 return types.NewArray(r.typ(), len)
369 case pkgbits.TypeChan:
370 dir := types.ChanDir(r.Len())
371 return types.NewChan(dir, r.typ())
372 case pkgbits.TypeMap:
373 return types.NewMap(r.typ(), r.typ())
374 case pkgbits.TypePointer:
375 return types.NewPointer(r.typ())
376 case pkgbits.TypeSignature:
377 return r.signature(nil, nil, nil)
378 case pkgbits.TypeSlice:
379 return types.NewSlice(r.typ())
380 case pkgbits.TypeStruct:
381 return r.structType()
382 case pkgbits.TypeInterface:
383 return r.interfaceType()
384 case pkgbits.TypeUnion:
385 return r.unionType()
386 }
387 }
388
389 func (r *reader) structType() *types.Struct {
390 fields := make([]*types.Var, r.Len())
391 var tags []string
392 for i := range fields {
393 pos := r.pos()
394 pkg, name := r.selector()
395 ftyp := r.typ()
396 tag := r.String()
397 embedded := r.Bool()
398
399 fields[i] = types.NewField(pos, pkg, name, ftyp, embedded)
400 if tag != "" {
401 for len(tags) < i {
402 tags = append(tags, "")
403 }
404 tags = append(tags, tag)
405 }
406 }
407 return types.NewStruct(fields, tags)
408 }
409
410 func (r *reader) unionType() *types.Union {
411 terms := make([]*types.Term, r.Len())
412 for i := range terms {
413 terms[i] = types.NewTerm(r.Bool(), r.typ())
414 }
415 return types.NewUnion(terms)
416 }
417
418 func (r *reader) interfaceType() *types.Interface {
419 methods := make([]*types.Func, r.Len())
420 embeddeds := make([]types.Type, r.Len())
421 implicit := len(methods) == 0 && len(embeddeds) == 1 && r.Bool()
422
423 for i := range methods {
424 pos := r.pos()
425 pkg, name := r.selector()
426 mtyp := r.signature(nil, nil, nil)
427 methods[i] = types.NewFunc(pos, pkg, name, mtyp)
428 }
429
430 for i := range embeddeds {
431 embeddeds[i] = r.typ()
432 }
433
434 iface := types.NewInterfaceType(methods, embeddeds)
435 if implicit {
436 iface.MarkImplicit()
437 }
438
439
440
441
442
443
444
445
446 r.p.ifaces = append(r.p.ifaces, iface)
447
448 return iface
449 }
450
451 func (r *reader) signature(recv *types.Var, rtparams, tparams []*types.TypeParam) *types.Signature {
452 r.Sync(pkgbits.SyncSignature)
453
454 params := r.params()
455 results := r.params()
456 variadic := r.Bool()
457
458 return types.NewSignatureType(recv, rtparams, tparams, params, results, variadic)
459 }
460
461 func (r *reader) params() *types.Tuple {
462 r.Sync(pkgbits.SyncParams)
463
464 params := make([]*types.Var, r.Len())
465 for i := range params {
466 params[i] = r.param()
467 }
468
469 return types.NewTuple(params...)
470 }
471
472 func (r *reader) param() *types.Var {
473 r.Sync(pkgbits.SyncParam)
474
475 pos := r.pos()
476 pkg, name := r.localIdent()
477 typ := r.typ()
478
479 return types.NewParam(pos, pkg, name, typ)
480 }
481
482
483
484 func (r *reader) obj() (types.Object, []types.Type) {
485 r.Sync(pkgbits.SyncObject)
486
487 if r.Version().Has(pkgbits.DerivedFuncInstance) {
488 assert(!r.Bool())
489 }
490
491 pkg, name := r.p.objIdx(r.Reloc(pkgbits.RelocObj))
492 obj := pkgScope(pkg).Lookup(name)
493
494 targs := make([]types.Type, r.Len())
495 for i := range targs {
496 targs[i] = r.typ()
497 }
498
499 return obj, targs
500 }
501
502 func (pr *pkgReader) objIdx(idx pkgbits.Index) (*types.Package, string) {
503
504 var objPkg *types.Package
505 var objName string
506 var tag pkgbits.CodeObj
507 {
508 rname := pr.tempReader(pkgbits.RelocName, idx, pkgbits.SyncObject1)
509
510 objPkg, objName = rname.qualifiedIdent()
511 assert(objName != "")
512
513 tag = pkgbits.CodeObj(rname.Code(pkgbits.SyncCodeObj))
514 pr.retireReader(rname)
515 }
516
517 if tag == pkgbits.ObjStub {
518 assert(objPkg == nil || objPkg == types.Unsafe)
519 return objPkg, objName
520 }
521
522
523 if _, suffix := splitVargenSuffix(objName); suffix != "" {
524 return objPkg, objName
525 }
526
527
528
529 if strings.Contains(objName, ".") {
530 return objPkg, objName
531 }
532
533 if objPkg.Scope().Lookup(objName) == nil {
534 dict := pr.objDictIdx(idx)
535
536 r := pr.newReader(pkgbits.RelocObj, idx, pkgbits.SyncObject1)
537 r.dict = dict
538
539 declare := func(obj types.Object) {
540 objPkg.Scope().Insert(obj)
541 }
542
543 switch tag {
544 default:
545 panic("weird")
546
547 case pkgbits.ObjAlias:
548 pos := r.pos()
549 var tparams []*types.TypeParam
550 if r.Version().Has(pkgbits.AliasTypeParamNames) {
551 tparams = r.typeParamNames(false)
552 }
553 typ := r.typ()
554 declare(aliases.New(pos, objPkg, objName, typ, tparams))
555
556 case pkgbits.ObjConst:
557 pos := r.pos()
558 typ := r.typ()
559 val := r.Value()
560 declare(types.NewConst(pos, objPkg, objName, typ, val))
561
562 case pkgbits.ObjFunc:
563 pos := r.pos()
564 if r.Version().Has(pkgbits.GenericMethods) {
565 assert(!r.Bool())
566 }
567 tparams := r.typeParamNames(false)
568 sig := r.signature(nil, nil, tparams)
569 declare(types.NewFunc(pos, objPkg, objName, sig))
570
571 case pkgbits.ObjType:
572 pos := r.pos()
573
574 obj := types.NewTypeName(pos, objPkg, objName, nil)
575 named := types.NewNamed(obj, nil, nil)
576 declare(obj)
577
578 named.SetTypeParams(r.typeParamNames(false))
579
580 setUnderlying := func(underlying types.Type) {
581
582
583
584 if iface, ok := types.Unalias(underlying).(*types.Interface); ok && iface.NumExplicitMethods() != 0 {
585 methods := make([]*types.Func, iface.NumExplicitMethods())
586 for i := range methods {
587 fn := iface.ExplicitMethod(i)
588 sig := fn.Type().(*types.Signature)
589
590 recv := types.NewVar(fn.Pos(), fn.Pkg(), "", named)
591 typesinternal.SetVarKind(recv, typesinternal.RecvVar)
592 methods[i] = types.NewFunc(fn.Pos(), fn.Pkg(), fn.Name(), types.NewSignatureType(recv, nil, nil, sig.Params(), sig.Results(), sig.Variadic()))
593 }
594
595 embeds := make([]types.Type, iface.NumEmbeddeds())
596 for i := range embeds {
597 embeds[i] = iface.EmbeddedType(i)
598 }
599
600 newIface := types.NewInterfaceType(methods, embeds)
601 r.p.ifaces = append(r.p.ifaces, newIface)
602 underlying = newIface
603 }
604
605 named.SetUnderlying(underlying)
606 }
607
608
609
610
611
612
613
614
615 rhs := r.typ()
616 if underlying := rhs.Underlying(); underlying != nil {
617 setUnderlying(underlying)
618 } else {
619 pk := r.p
620 pk.laterFor(named, func() {
621
622 delete(pk.laterFors, named)
623 if i, ok := pk.laterFors[rhs]; ok {
624 f := pk.laterFns[i]
625 pk.laterFns[i] = func() {}
626 f()
627 }
628 setUnderlying(rhs.Underlying())
629 })
630 }
631
632 for i, n := 0, r.Len(); i < n; i++ {
633 named.AddMethod(r.method())
634 }
635
636 if r.Version().Has(pkgbits.GenericMethods) {
637 for range r.Len() {
638
639
640
641 idx := r.Reloc(pkgbits.RelocObj)
642
643 r := pr.tempReader(pkgbits.RelocObj, idx, pkgbits.SyncObject1)
644 r.dict = pr.objDictIdx(idx)
645
646 pos := r.pos()
647 assert(r.Bool())
648 pkg, name := r.selector()
649 rtparams := r.typeParamNames(true)
650 recv := r.param()
651 tparams := r.typeParamNames(false)
652 sig := r.signature(recv, rtparams, tparams)
653
654 pr.retireReader(r)
655 named.AddMethod(types.NewFunc(pos, pkg, name, sig))
656 }
657 }
658
659 case pkgbits.ObjVar:
660 pos := r.pos()
661 typ := r.typ()
662 v := types.NewVar(pos, objPkg, objName, typ)
663 typesinternal.SetVarKind(v, typesinternal.PackageVar)
664 declare(v)
665 }
666 }
667
668 return objPkg, objName
669 }
670
671 func (pr *pkgReader) objDictIdx(idx pkgbits.Index) *readerDict {
672
673 var dict readerDict
674
675 {
676 r := pr.tempReader(pkgbits.RelocObjDict, idx, pkgbits.SyncObject1)
677 if implicits := r.Len(); implicits != 0 {
678 errorf("unexpected object with %v implicit type parameter(s)", implicits)
679 }
680
681 nreceivers := 0
682 if r.Version().Has(pkgbits.GenericMethods) {
683 nreceivers = r.Len()
684 }
685 nexplicits := r.Len()
686
687 dict.rtbounds = make([]typeInfo, nreceivers)
688 for i := range dict.rtbounds {
689 dict.rtbounds[i] = r.typInfo()
690 }
691
692 dict.tbounds = make([]typeInfo, nexplicits)
693 for i := range dict.tbounds {
694 dict.tbounds[i] = r.typInfo()
695 }
696
697 dict.derived = make([]derivedInfo, r.Len())
698 dict.derivedTypes = make([]types.Type, len(dict.derived))
699 for i := range dict.derived {
700 dict.derived[i] = derivedInfo{idx: r.Reloc(pkgbits.RelocType)}
701 if r.Version().Has(pkgbits.DerivedInfoNeeded) {
702 assert(!r.Bool())
703 }
704 }
705
706 pr.retireReader(r)
707 }
708
709
710 return &dict
711 }
712
713 func (r *reader) typeParamNames(isGenMeth bool) []*types.TypeParam {
714 r.Sync(pkgbits.SyncTypeParamNames)
715
716
717
718
719
720 var in []typeInfo
721 var out *[]*types.TypeParam
722 if isGenMeth {
723 in = r.dict.rtbounds
724 out = &r.dict.rtparams
725 } else {
726 in = r.dict.tbounds
727 out = &r.dict.tparams
728 }
729
730 if len(in) == 0 {
731 return nil
732 }
733
734
735
736
737
738
739
740
741 tparams := make([]*types.TypeParam, len(in))
742 *out = tparams
743
744 for i := range in {
745 pos := r.pos()
746 pkg, name := r.localIdent()
747
748 tname := types.NewTypeName(pos, pkg, name, nil)
749 tparams[i] = types.NewTypeParam(tname, nil)
750 }
751
752
753
754 types := make([]types.Type, len(in))
755 for i, info := range in {
756 types[i] = r.p.typIdx(info, r.dict)
757 }
758
759
760 r.p.later(func() {
761 for i, typ := range types {
762 tparams[i].SetConstraint(typ)
763 }
764 })
765
766 return tparams
767 }
768
769 func (r *reader) method() *types.Func {
770 r.Sync(pkgbits.SyncMethod)
771 pos := r.pos()
772 pkg, name := r.selector()
773
774 rparams := r.typeParamNames(false)
775 sig := r.signature(r.param(), rparams, nil)
776
777 _ = r.pos()
778 return types.NewFunc(pos, pkg, name, sig)
779 }
780
781 func (r *reader) qualifiedIdent() (*types.Package, string) { return r.ident(pkgbits.SyncSym) }
782 func (r *reader) localIdent() (*types.Package, string) { return r.ident(pkgbits.SyncLocalIdent) }
783 func (r *reader) selector() (*types.Package, string) { return r.ident(pkgbits.SyncSelector) }
784
785 func (r *reader) ident(marker pkgbits.SyncMarker) (*types.Package, string) {
786 r.Sync(marker)
787 return r.pkg(), r.String()
788 }
789
790
791
792
793
794 func pkgScope(pkg *types.Package) *types.Scope {
795 if pkg != nil {
796 return pkg.Scope()
797 }
798 return types.Universe
799 }
800
801
802 func splitVargenSuffix(name string) (base, suffix string) {
803 i := len(name)
804 for i > 0 && name[i-1] >= '0' && name[i-1] <= '9' {
805 i--
806 }
807 const dot = "ยท"
808 if i >= len(dot) && name[i-len(dot):i] == dot {
809 i -= len(dot)
810 return name[:i], name[i:]
811 }
812 return name, ""
813 }
814
View as plain text