1
2
3
4
5 package gccgoimporter
6
7 import (
8 "errors"
9 "fmt"
10 "go/constant"
11 "go/token"
12 "go/types"
13 "io"
14 "strconv"
15 "strings"
16 "text/scanner"
17 "unicode/utf8"
18 )
19
20 type parser struct {
21 scanner *scanner.Scanner
22 version string
23 tok rune
24 lit string
25 pkgpath string
26 pkgname string
27 pkg *types.Package
28 imports map[string]*types.Package
29 typeList []types.Type
30 typeData []string
31 fixups []fixupRecord
32 initdata InitData
33 aliases map[int]string
34 }
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51 type fixupRecord struct {
52 toUpdate *types.Named
53 target types.Type
54 }
55
56 func (p *parser) init(filename string, src io.Reader, imports map[string]*types.Package) {
57 p.scanner = new(scanner.Scanner)
58 p.initScanner(filename, src)
59 p.imports = imports
60 p.aliases = make(map[int]string)
61 p.typeList = make([]types.Type, 1 , 16)
62 }
63
64 func (p *parser) initScanner(filename string, src io.Reader) {
65 p.scanner.Init(src)
66 p.scanner.Error = func(_ *scanner.Scanner, msg string) { p.error(msg) }
67 p.scanner.Mode = scanner.ScanIdents | scanner.ScanInts | scanner.ScanFloats | scanner.ScanStrings
68 p.scanner.Whitespace = 1<<'\t' | 1<<' '
69 p.scanner.Filename = filename
70 p.next()
71 }
72
73 type importError struct {
74 pos scanner.Position
75 err error
76 }
77
78 func (e importError) Error() string {
79 return fmt.Sprintf("import error %s (byte offset = %d): %s", e.pos, e.pos.Offset, e.err)
80 }
81
82 func (p *parser) error(err any) {
83 if s, ok := err.(string); ok {
84 err = errors.New(s)
85 }
86
87 panic(importError{p.scanner.Pos(), err.(error)})
88 }
89
90 func (p *parser) errorf(format string, args ...any) {
91 p.error(fmt.Errorf(format, args...))
92 }
93
94 func (p *parser) expect(tok rune) string {
95 lit := p.lit
96 if p.tok != tok {
97 p.errorf("expected %s, got %s (%s)", scanner.TokenString(tok), scanner.TokenString(p.tok), lit)
98 }
99 p.next()
100 return lit
101 }
102
103 func (p *parser) expectEOL() {
104 if p.version == "v1" || p.version == "v2" {
105 p.expect(';')
106 }
107 p.expect('\n')
108 }
109
110 func (p *parser) expectKeyword(keyword string) {
111 lit := p.expect(scanner.Ident)
112 if lit != keyword {
113 p.errorf("expected keyword %s, got %q", keyword, lit)
114 }
115 }
116
117 func (p *parser) parseString() string {
118 str, err := strconv.Unquote(p.expect(scanner.String))
119 if err != nil {
120 p.error(err)
121 }
122 return str
123 }
124
125
126
127 func (p *parser) parseUnquotedString() string {
128 if p.tok == scanner.EOF {
129 p.error("unexpected EOF")
130 }
131 var b strings.Builder
132 b.WriteString(p.scanner.TokenText())
133
134
135 for ch := p.scanner.Peek(); ch != '\n' && ch != ';' && ch != scanner.EOF && p.scanner.Whitespace&(1<<uint(ch)) == 0; ch = p.scanner.Peek() {
136 b.WriteRune(ch)
137 p.scanner.Next()
138 }
139 p.next()
140 return b.String()
141 }
142
143 func (p *parser) next() {
144 p.tok = p.scanner.Scan()
145 switch p.tok {
146 case scanner.Ident, scanner.Int, scanner.Float, scanner.String, 'ยท':
147 p.lit = p.scanner.TokenText()
148 default:
149 p.lit = ""
150 }
151 }
152
153 func (p *parser) parseQualifiedName() (path, name string) {
154 return p.parseQualifiedNameStr(p.parseString())
155 }
156
157 func (p *parser) parseUnquotedQualifiedName() (path, name string) {
158 return p.parseQualifiedNameStr(p.parseUnquotedString())
159 }
160
161
162
163
164 func (p *parser) parseQualifiedNameStr(unquotedName string) (pkgpath, name string) {
165 parts := strings.Split(unquotedName, ".")
166 if parts[0] == "" {
167 parts = parts[1:]
168 }
169
170 switch len(parts) {
171 case 0:
172 p.errorf("malformed qualified name: %q", unquotedName)
173 case 1:
174
175 pkgpath = p.pkgpath
176 name = parts[0]
177 default:
178
179 pkgpath = strings.Join(parts[0:len(parts)-1], ".")
180 name = parts[len(parts)-1]
181 }
182
183 return
184 }
185
186
187
188
189 func (p *parser) getPkg(pkgpath, name string) *types.Package {
190
191 if pkgpath == "unsafe" {
192 return types.Unsafe
193 }
194 pkg := p.imports[pkgpath]
195 if pkg == nil && name != "" {
196 pkg = types.NewPackage(pkgpath, name)
197 p.imports[pkgpath] = pkg
198 }
199 return pkg
200 }
201
202
203
204
205
206 func (p *parser) parseExportedName() (pkg *types.Package, name string) {
207 path, name := p.parseQualifiedName()
208 var pkgname string
209 if p.tok == scanner.String {
210 pkgname = p.parseString()
211 }
212 pkg = p.getPkg(path, pkgname)
213 if pkg == nil {
214 p.errorf("package %s (path = %q) not found", name, path)
215 }
216 return
217 }
218
219
220 func (p *parser) parseName() string {
221 if p.tok == '?' {
222
223 p.next()
224 return ""
225 }
226
227 _, name := p.parseUnquotedQualifiedName()
228 return name
229 }
230
231 func deref(typ types.Type) types.Type {
232 if p, _ := typ.(*types.Pointer); p != nil {
233 typ = p.Elem()
234 }
235 return typ
236 }
237
238
239 func (p *parser) parseField(pkg *types.Package) (field *types.Var, tag string) {
240 name := p.parseName()
241 typ, n := p.parseTypeExtended(pkg)
242 anon := false
243 if name == "" {
244 anon = true
245
246 if aname, ok := p.aliases[n]; ok {
247 name = aname
248 } else {
249 switch typ := deref(typ).(type) {
250 case *types.Basic:
251 name = typ.Name()
252 case *types.Named:
253 name = typ.Obj().Name()
254 default:
255 p.error("embedded field expected")
256 }
257 }
258 }
259 field = types.NewField(token.NoPos, pkg, name, typ, anon)
260 if p.tok == scanner.String {
261 tag = p.parseString()
262 }
263 return
264 }
265
266
267 func (p *parser) parseParam(pkg *types.Package) (param *types.Var, isVariadic bool) {
268 name := p.parseName()
269
270 if strings.HasPrefix(name, "p.") || strings.HasPrefix(name, "r.") || strings.HasPrefix(name, "$ret") {
271 name = ""
272 }
273 if p.tok == '<' && p.scanner.Peek() == 'e' {
274
275 p.next()
276 p.expectKeyword("esc")
277 p.expect(':')
278 p.expect(scanner.Int)
279 p.expect('>')
280 }
281 if p.tok == '.' {
282 p.next()
283 p.expect('.')
284 p.expect('.')
285 isVariadic = true
286 }
287 typ := p.parseType(pkg)
288 if isVariadic {
289 typ = types.NewSlice(typ)
290 }
291 param = types.NewParam(token.NoPos, pkg, name, typ)
292 return
293 }
294
295
296 func (p *parser) parseVar(pkg *types.Package) *types.Var {
297 name := p.parseName()
298 v := types.NewVar(token.NoPos, pkg, name, p.parseType(pkg))
299 if name[0] == '.' || name[0] == '<' {
300
301
302
303 return nil
304 }
305 return v
306 }
307
308
309 func (p *parser) parseConversion(pkg *types.Package) (val constant.Value, typ types.Type) {
310 p.expectKeyword("convert")
311 p.expect('(')
312 typ = p.parseType(pkg)
313 p.expect(',')
314 val, _ = p.parseConstValue(pkg)
315 p.expect(')')
316 return
317 }
318
319
320
321 func (p *parser) parseConstValue(pkg *types.Package) (val constant.Value, typ types.Type) {
322
323
324 if p.tok == '$' {
325 p.next()
326 if p.tok != scanner.Ident {
327 p.errorf("expected identifier after '$', got %s (%q)", scanner.TokenString(p.tok), p.lit)
328 }
329 }
330
331 switch p.tok {
332 case scanner.String:
333 str := p.parseString()
334 val = constant.MakeString(str)
335 typ = types.Typ[types.UntypedString]
336 return
337
338 case scanner.Ident:
339 b := false
340 switch p.lit {
341 case "false":
342 case "true":
343 b = true
344
345 case "convert":
346 return p.parseConversion(pkg)
347
348 default:
349 p.errorf("expected const value, got %s (%q)", scanner.TokenString(p.tok), p.lit)
350 }
351
352 p.next()
353 val = constant.MakeBool(b)
354 typ = types.Typ[types.UntypedBool]
355 return
356 }
357
358 sign := ""
359 if p.tok == '-' {
360 p.next()
361 sign = "-"
362 }
363
364 switch p.tok {
365 case scanner.Int:
366 val = constant.MakeFromLiteral(sign+p.lit, token.INT, 0)
367 if val == nil {
368 p.error("could not parse integer literal")
369 }
370
371 p.next()
372 if p.tok == '\'' {
373 p.next()
374 typ = types.Typ[types.UntypedRune]
375 } else {
376 typ = types.Typ[types.UntypedInt]
377 }
378
379 case scanner.Float:
380 re := sign + p.lit
381 p.next()
382
383 var im string
384 switch p.tok {
385 case '+':
386 p.next()
387 im = p.expect(scanner.Float)
388
389 case '-':
390 p.next()
391 im = "-" + p.expect(scanner.Float)
392
393 case scanner.Ident:
394
395 im = re
396 re = "0"
397
398 default:
399 val = constant.MakeFromLiteral(re, token.FLOAT, 0)
400 if val == nil {
401 p.error("could not parse float literal")
402 }
403 typ = types.Typ[types.UntypedFloat]
404 return
405 }
406
407 p.expectKeyword("i")
408 reval := constant.MakeFromLiteral(re, token.FLOAT, 0)
409 if reval == nil {
410 p.error("could not parse real component of complex literal")
411 }
412 imval := constant.MakeFromLiteral(im+"i", token.IMAG, 0)
413 if imval == nil {
414 p.error("could not parse imag component of complex literal")
415 }
416 val = constant.BinaryOp(reval, token.ADD, imval)
417 typ = types.Typ[types.UntypedComplex]
418
419 default:
420 p.errorf("expected const value, got %s (%q)", scanner.TokenString(p.tok), p.lit)
421 }
422
423 return
424 }
425
426
427 func (p *parser) parseConst(pkg *types.Package) *types.Const {
428 name := p.parseName()
429 var typ types.Type
430 if p.tok == '<' {
431 typ = p.parseType(pkg)
432 }
433 p.expect('=')
434 val, vtyp := p.parseConstValue(pkg)
435 if typ == nil {
436 typ = vtyp
437 }
438 return types.NewConst(token.NoPos, pkg, name, typ, val)
439 }
440
441
442
443
444
445
446 var reserved = new(struct{ types.Type })
447
448
449 func (p *parser) reserve(n int) {
450
451
452
453
454
455
456
457 if len(p.typeData) == 0 {
458 if n != len(p.typeList) {
459 p.errorf("invalid type number %d (out of sync)", n)
460 }
461 p.typeList = append(p.typeList, reserved)
462 } else {
463 if p.typeList[n] != nil {
464 p.errorf("previously visited type number %d", n)
465 }
466 p.typeList[n] = reserved
467 }
468 }
469
470
471
472
473
474
475 func (p *parser) update(t types.Type, nlist []any) {
476 if t == reserved {
477 p.errorf("internal error: update(%v) invoked on reserved", nlist)
478 }
479 if t == nil {
480 p.errorf("internal error: update(%v) invoked on nil", nlist)
481 }
482 for _, n := range nlist {
483 switch n := n.(type) {
484 case int:
485 if p.typeList[n] == t {
486 continue
487 }
488 if p.typeList[n] != reserved {
489 p.errorf("internal error: update(%v): %d not reserved", nlist, n)
490 }
491 p.typeList[n] = t
492 case *types.Pointer:
493 if *n != (types.Pointer{}) {
494 elem := n.Elem()
495 if elem == t {
496 continue
497 }
498 p.errorf("internal error: update: pointer already set to %v, expected %v", elem, t)
499 }
500 *n = *types.NewPointer(t)
501 default:
502 p.errorf("internal error: %T on nlist", n)
503 }
504 }
505 }
506
507
508
509
510 func (p *parser) parseNamedType(nlist []any) types.Type {
511 pkg, name := p.parseExportedName()
512 scope := pkg.Scope()
513 obj := scope.Lookup(name)
514 if obj != nil && obj.Type() == nil {
515 p.errorf("%v has nil type", obj)
516 }
517
518 if p.tok == scanner.Ident && p.lit == "notinheap" {
519 p.next()
520
521
522
523 }
524
525
526 if p.tok == '=' {
527 p.next()
528 p.aliases[nlist[len(nlist)-1].(int)] = name
529 if obj != nil {
530
531 t := obj.Type()
532 p.update(t, nlist)
533 p.parseType(pkg)
534 return t
535 }
536 t := p.parseType(pkg, nlist...)
537 obj = types.NewTypeName(token.NoPos, pkg, name, t)
538 scope.Insert(obj)
539 return t
540 }
541
542
543 if obj == nil {
544
545
546 tname := types.NewTypeName(token.NoPos, pkg, name, nil)
547 types.NewNamed(tname, nil, nil)
548 scope.Insert(tname)
549 obj = tname
550 }
551
552
553 t := obj.Type()
554 p.update(t, nlist)
555
556 nt, ok := t.(*types.Named)
557 if !ok {
558
559 pt := p.parseType(pkg)
560 if pt != t {
561 p.error("unexpected underlying type for non-named TypeName")
562 }
563 return t
564 }
565
566 underlying := p.parseType(pkg)
567 if nt.Underlying() == nil {
568 if underlying.Underlying() == nil {
569 fix := fixupRecord{toUpdate: nt, target: underlying}
570 p.fixups = append(p.fixups, fix)
571 } else {
572 nt.SetUnderlying(underlying.Underlying())
573 }
574 }
575
576 if p.tok == '\n' {
577 p.next()
578
579 for p.tok == scanner.Ident {
580 p.expectKeyword("func")
581 if p.tok == '/' {
582
583 p.expect('/')
584 p.expect('*')
585 if p.expect(scanner.Ident) == "asm" {
586 p.parseUnquotedString()
587 }
588 p.expect('*')
589 p.expect('/')
590 }
591 p.expect('(')
592 receiver, _ := p.parseParam(pkg)
593 p.expect(')')
594 name := p.parseName()
595 params, isVariadic := p.parseParamList(pkg)
596 results := p.parseResultList(pkg)
597 p.skipInlineBody()
598 p.expectEOL()
599
600 sig := types.NewSignatureType(receiver, nil, nil, params, results, isVariadic)
601 nt.AddMethod(types.NewFunc(token.NoPos, pkg, name, sig))
602 }
603 }
604
605 return nt
606 }
607
608 func (p *parser) parseInt64() int64 {
609 lit := p.expect(scanner.Int)
610 n, err := strconv.ParseInt(lit, 10, 64)
611 if err != nil {
612 p.error(err)
613 }
614 return n
615 }
616
617 func (p *parser) parseInt() int {
618 lit := p.expect(scanner.Int)
619 n, err := strconv.ParseInt(lit, 10, 0 )
620 if err != nil {
621 p.error(err)
622 }
623 return int(n)
624 }
625
626
627 func (p *parser) parseArrayOrSliceType(pkg *types.Package, nlist []any) types.Type {
628 p.expect('[')
629 if p.tok == ']' {
630 p.next()
631
632 t := new(types.Slice)
633 p.update(t, nlist)
634
635 *t = *types.NewSlice(p.parseType(pkg))
636 return t
637 }
638
639 t := new(types.Array)
640 p.update(t, nlist)
641
642 len := p.parseInt64()
643 p.expect(']')
644
645 *t = *types.NewArray(p.parseType(pkg), len)
646 return t
647 }
648
649
650 func (p *parser) parseMapType(pkg *types.Package, nlist []any) types.Type {
651 p.expectKeyword("map")
652
653 t := new(types.Map)
654 p.update(t, nlist)
655
656 p.expect('[')
657 key := p.parseType(pkg)
658 p.expect(']')
659 elem := p.parseType(pkg)
660
661 *t = *types.NewMap(key, elem)
662 return t
663 }
664
665
666 func (p *parser) parseChanType(pkg *types.Package, nlist []any) types.Type {
667 p.expectKeyword("chan")
668
669 t := new(types.Chan)
670 p.update(t, nlist)
671
672 dir := types.SendRecv
673 switch p.tok {
674 case '-':
675 p.next()
676 p.expect('<')
677 dir = types.SendOnly
678
679 case '<':
680
681 if p.scanner.Peek() == '-' {
682 p.next()
683 p.expect('-')
684 dir = types.RecvOnly
685 }
686 }
687
688 *t = *types.NewChan(dir, p.parseType(pkg))
689 return t
690 }
691
692
693 func (p *parser) parseStructType(pkg *types.Package, nlist []any) types.Type {
694 p.expectKeyword("struct")
695
696 t := new(types.Struct)
697 p.update(t, nlist)
698
699 var fields []*types.Var
700 var tags []string
701
702 p.expect('{')
703 for p.tok != '}' && p.tok != scanner.EOF {
704 field, tag := p.parseField(pkg)
705 p.expect(';')
706 fields = append(fields, field)
707 tags = append(tags, tag)
708 }
709 p.expect('}')
710
711 *t = *types.NewStruct(fields, tags)
712 return t
713 }
714
715
716 func (p *parser) parseParamList(pkg *types.Package) (*types.Tuple, bool) {
717 var list []*types.Var
718 isVariadic := false
719
720 p.expect('(')
721 for p.tok != ')' && p.tok != scanner.EOF {
722 if len(list) > 0 {
723 p.expect(',')
724 }
725 par, variadic := p.parseParam(pkg)
726 list = append(list, par)
727 if variadic {
728 if isVariadic {
729 p.error("... not on final argument")
730 }
731 isVariadic = true
732 }
733 }
734 p.expect(')')
735
736 return types.NewTuple(list...), isVariadic
737 }
738
739
740 func (p *parser) parseResultList(pkg *types.Package) *types.Tuple {
741 switch p.tok {
742 case '<':
743 p.next()
744 if p.tok == scanner.Ident && p.lit == "inl" {
745 return nil
746 }
747 taa, _ := p.parseTypeAfterAngle(pkg)
748 return types.NewTuple(types.NewParam(token.NoPos, pkg, "", taa))
749
750 case '(':
751 params, _ := p.parseParamList(pkg)
752 return params
753
754 default:
755 return nil
756 }
757 }
758
759
760 func (p *parser) parseFunctionType(pkg *types.Package, nlist []any) *types.Signature {
761 t := new(types.Signature)
762 p.update(t, nlist)
763
764 params, isVariadic := p.parseParamList(pkg)
765 results := p.parseResultList(pkg)
766
767 *t = *types.NewSignatureType(nil, nil, nil, params, results, isVariadic)
768 return t
769 }
770
771
772 func (p *parser) parseFunc(pkg *types.Package) *types.Func {
773 if p.tok == '/' {
774
775 p.expect('/')
776 p.expect('*')
777 if p.expect(scanner.Ident) == "asm" {
778 p.parseUnquotedString()
779 }
780 p.expect('*')
781 p.expect('/')
782 }
783
784 name := p.parseName()
785 f := types.NewFunc(token.NoPos, pkg, name, p.parseFunctionType(pkg, nil))
786 p.skipInlineBody()
787
788 if name[0] == '.' || name[0] == '<' || strings.ContainsRune(name, '$') {
789
790
791
792
793 return nil
794 }
795
796 return f
797 }
798
799
800 func (p *parser) parseInterfaceType(pkg *types.Package, nlist []any) types.Type {
801 p.expectKeyword("interface")
802
803 t := new(types.Interface)
804 p.update(t, nlist)
805
806 var methods []*types.Func
807 var embeddeds []types.Type
808
809 p.expect('{')
810 for p.tok != '}' && p.tok != scanner.EOF {
811 if p.tok == '?' {
812 p.next()
813 embeddeds = append(embeddeds, p.parseType(pkg))
814 } else {
815 method := p.parseFunc(pkg)
816 if method != nil {
817 methods = append(methods, method)
818 }
819 }
820 p.expect(';')
821 }
822 p.expect('}')
823
824 *t = *types.NewInterfaceType(methods, embeddeds)
825 return t
826 }
827
828
829 func (p *parser) parsePointerType(pkg *types.Package, nlist []any) types.Type {
830 p.expect('*')
831 if p.tok == scanner.Ident {
832 p.expectKeyword("any")
833 t := types.Typ[types.UnsafePointer]
834 p.update(t, nlist)
835 return t
836 }
837
838 t := new(types.Pointer)
839 p.update(t, nlist)
840
841 *t = *types.NewPointer(p.parseType(pkg, t))
842
843 return t
844 }
845
846
847 func (p *parser) parseTypeSpec(pkg *types.Package, nlist []any) types.Type {
848 switch p.tok {
849 case scanner.String:
850 return p.parseNamedType(nlist)
851
852 case scanner.Ident:
853 switch p.lit {
854 case "map":
855 return p.parseMapType(pkg, nlist)
856
857 case "chan":
858 return p.parseChanType(pkg, nlist)
859
860 case "struct":
861 return p.parseStructType(pkg, nlist)
862
863 case "interface":
864 return p.parseInterfaceType(pkg, nlist)
865 }
866
867 case '*':
868 return p.parsePointerType(pkg, nlist)
869
870 case '[':
871 return p.parseArrayOrSliceType(pkg, nlist)
872
873 case '(':
874 return p.parseFunctionType(pkg, nlist)
875 }
876
877 p.errorf("expected type name or literal, got %s", scanner.TokenString(p.tok))
878 return nil
879 }
880
881 const (
882
883
884
885 gccgoBuiltinINT8 = 1
886 gccgoBuiltinINT16 = 2
887 gccgoBuiltinINT32 = 3
888 gccgoBuiltinINT64 = 4
889 gccgoBuiltinUINT8 = 5
890 gccgoBuiltinUINT16 = 6
891 gccgoBuiltinUINT32 = 7
892 gccgoBuiltinUINT64 = 8
893 gccgoBuiltinFLOAT32 = 9
894 gccgoBuiltinFLOAT64 = 10
895 gccgoBuiltinINT = 11
896 gccgoBuiltinUINT = 12
897 gccgoBuiltinUINTPTR = 13
898 gccgoBuiltinBOOL = 15
899 gccgoBuiltinSTRING = 16
900 gccgoBuiltinCOMPLEX64 = 17
901 gccgoBuiltinCOMPLEX128 = 18
902 gccgoBuiltinERROR = 19
903 gccgoBuiltinBYTE = 20
904 gccgoBuiltinRUNE = 21
905 gccgoBuiltinANY = 22
906 )
907
908 func lookupBuiltinType(typ int) types.Type {
909 return [...]types.Type{
910 gccgoBuiltinINT8: types.Typ[types.Int8],
911 gccgoBuiltinINT16: types.Typ[types.Int16],
912 gccgoBuiltinINT32: types.Typ[types.Int32],
913 gccgoBuiltinINT64: types.Typ[types.Int64],
914 gccgoBuiltinUINT8: types.Typ[types.Uint8],
915 gccgoBuiltinUINT16: types.Typ[types.Uint16],
916 gccgoBuiltinUINT32: types.Typ[types.Uint32],
917 gccgoBuiltinUINT64: types.Typ[types.Uint64],
918 gccgoBuiltinFLOAT32: types.Typ[types.Float32],
919 gccgoBuiltinFLOAT64: types.Typ[types.Float64],
920 gccgoBuiltinINT: types.Typ[types.Int],
921 gccgoBuiltinUINT: types.Typ[types.Uint],
922 gccgoBuiltinUINTPTR: types.Typ[types.Uintptr],
923 gccgoBuiltinBOOL: types.Typ[types.Bool],
924 gccgoBuiltinSTRING: types.Typ[types.String],
925 gccgoBuiltinCOMPLEX64: types.Typ[types.Complex64],
926 gccgoBuiltinCOMPLEX128: types.Typ[types.Complex128],
927 gccgoBuiltinERROR: types.Universe.Lookup("error").Type(),
928 gccgoBuiltinBYTE: types.Universe.Lookup("byte").Type(),
929 gccgoBuiltinRUNE: types.Universe.Lookup("rune").Type(),
930 gccgoBuiltinANY: types.Universe.Lookup("any").Type(),
931 }[typ]
932 }
933
934
935
936
937 func (p *parser) parseType(pkg *types.Package, n ...any) types.Type {
938 p.expect('<')
939 t, _ := p.parseTypeAfterAngle(pkg, n...)
940 return t
941 }
942
943
944 func (p *parser) parseTypeAfterAngle(pkg *types.Package, n ...any) (t types.Type, n1 int) {
945 p.expectKeyword("type")
946
947 n1 = 0
948 switch p.tok {
949 case scanner.Int:
950 n1 = p.parseInt()
951 if p.tok == '>' {
952 if len(p.typeData) > 0 && p.typeList[n1] == nil {
953 p.parseSavedType(pkg, n1, n)
954 }
955 t = p.typeList[n1]
956 if len(p.typeData) == 0 && t == reserved {
957 p.errorf("invalid type cycle, type %d not yet defined (nlist=%v)", n1, n)
958 }
959 p.update(t, n)
960 } else {
961 p.reserve(n1)
962 t = p.parseTypeSpec(pkg, append(n, n1))
963 }
964
965 case '-':
966 p.next()
967 n1 := p.parseInt()
968 t = lookupBuiltinType(n1)
969 p.update(t, n)
970
971 default:
972 p.errorf("expected type number, got %s (%q)", scanner.TokenString(p.tok), p.lit)
973 return nil, 0
974 }
975
976 if t == nil || t == reserved {
977 p.errorf("internal error: bad return from parseType(%v)", n)
978 }
979
980 p.expect('>')
981 return
982 }
983
984
985
986
987 func (p *parser) parseTypeExtended(pkg *types.Package, n ...any) (t types.Type, n1 int) {
988 p.expect('<')
989 t, n1 = p.parseTypeAfterAngle(pkg, n...)
990 return
991 }
992
993
994
995 func (p *parser) skipInlineBody() {
996
997
998 if p.tok == '<' {
999 p.next()
1000 p.expectKeyword("inl")
1001 } else if p.tok != scanner.Ident || p.lit != "inl" {
1002 return
1003 } else {
1004 p.next()
1005 }
1006
1007 p.expect(':')
1008 want := p.parseInt()
1009 p.expect('>')
1010
1011 defer func(w uint64) {
1012 p.scanner.Whitespace = w
1013 }(p.scanner.Whitespace)
1014 p.scanner.Whitespace = 0
1015
1016 got := 0
1017 for got < want {
1018 r := p.scanner.Next()
1019 if r == scanner.EOF {
1020 p.error("unexpected EOF")
1021 }
1022 got += utf8.RuneLen(r)
1023 }
1024 }
1025
1026
1027 func (p *parser) parseTypes(pkg *types.Package) {
1028 maxp1 := p.parseInt()
1029 exportedp1 := p.parseInt()
1030 p.typeList = make([]types.Type, maxp1, maxp1)
1031
1032 type typeOffset struct {
1033 offset int
1034 length int
1035 }
1036 var typeOffsets []typeOffset
1037
1038 total := 0
1039 for i := 1; i < maxp1; i++ {
1040 len := p.parseInt()
1041 typeOffsets = append(typeOffsets, typeOffset{total, len})
1042 total += len
1043 }
1044
1045 defer func(w uint64) {
1046 p.scanner.Whitespace = w
1047 }(p.scanner.Whitespace)
1048 p.scanner.Whitespace = 0
1049
1050
1051
1052
1053 var sb strings.Builder
1054 for sb.Len() < total {
1055 r := p.scanner.Next()
1056 if r == scanner.EOF {
1057 p.error("unexpected EOF")
1058 }
1059 sb.WriteRune(r)
1060 }
1061 allTypeData := sb.String()
1062
1063 p.typeData = []string{""}
1064 for _, to := range typeOffsets {
1065 p.typeData = append(p.typeData, allTypeData[to.offset:to.offset+to.length])
1066 }
1067
1068 for i := 1; i < exportedp1; i++ {
1069 p.parseSavedType(pkg, i, nil)
1070 }
1071 }
1072
1073
1074 func (p *parser) parseSavedType(pkg *types.Package, i int, nlist []any) {
1075 defer func(s *scanner.Scanner, tok rune, lit string) {
1076 p.scanner = s
1077 p.tok = tok
1078 p.lit = lit
1079 }(p.scanner, p.tok, p.lit)
1080
1081 p.scanner = new(scanner.Scanner)
1082 p.initScanner(p.scanner.Filename, strings.NewReader(p.typeData[i]))
1083 p.expectKeyword("type")
1084 id := p.parseInt()
1085 if id != i {
1086 p.errorf("type ID mismatch: got %d, want %d", id, i)
1087 }
1088 if p.typeList[i] == reserved {
1089 p.errorf("internal error: %d already reserved in parseSavedType", i)
1090 }
1091 if p.typeList[i] == nil {
1092 p.reserve(i)
1093 p.parseTypeSpec(pkg, append(nlist, i))
1094 }
1095 if p.typeList[i] == nil || p.typeList[i] == reserved {
1096 p.errorf("internal error: parseSavedType(%d,%v) reserved/nil", i, nlist)
1097 }
1098 }
1099
1100
1101 func (p *parser) parsePackageInit() PackageInit {
1102 name := p.parseUnquotedString()
1103 initfunc := p.parseUnquotedString()
1104 priority := -1
1105 if p.version == "v1" {
1106 priority = p.parseInt()
1107 }
1108 return PackageInit{Name: name, InitFunc: initfunc, Priority: priority}
1109 }
1110
1111
1112 func (p *parser) maybeCreatePackage() {
1113 if p.pkgname != "" && p.pkgpath != "" {
1114 p.pkg = p.getPkg(p.pkgpath, p.pkgname)
1115 }
1116 }
1117
1118
1119
1120
1121
1122
1123 func (p *parser) parseInitDataDirective() {
1124 if p.tok != scanner.Ident {
1125
1126 p.expect(scanner.Ident)
1127 }
1128
1129 switch p.lit {
1130 case "v1", "v2", "v3":
1131 p.version = p.lit
1132 p.next()
1133 p.expect(';')
1134 p.expect('\n')
1135
1136 case "priority":
1137 p.next()
1138 p.initdata.Priority = p.parseInt()
1139 p.expectEOL()
1140
1141 case "init":
1142 p.next()
1143 for p.tok != '\n' && p.tok != ';' && p.tok != scanner.EOF {
1144 p.initdata.Inits = append(p.initdata.Inits, p.parsePackageInit())
1145 }
1146 p.expectEOL()
1147
1148 case "init_graph":
1149 p.next()
1150
1151 for p.tok != '\n' && p.tok != ';' && p.tok != scanner.EOF {
1152 p.parseInt64()
1153 p.parseInt64()
1154 }
1155 p.expectEOL()
1156
1157 case "checksum":
1158
1159 defer func(mode uint) {
1160 p.scanner.Mode = mode
1161 }(p.scanner.Mode)
1162 p.scanner.Mode &^= scanner.ScanInts | scanner.ScanFloats
1163 p.next()
1164 p.parseUnquotedString()
1165 p.expectEOL()
1166
1167 default:
1168 p.errorf("unexpected identifier: %q", p.lit)
1169 }
1170 }
1171
1172
1173
1174
1175
1176
1177
1178
1179
1180
1181
1182
1183 func (p *parser) parseDirective() {
1184 if p.tok != scanner.Ident {
1185
1186 p.expect(scanner.Ident)
1187 }
1188
1189 switch p.lit {
1190 case "v1", "v2", "v3", "priority", "init", "init_graph", "checksum":
1191 p.parseInitDataDirective()
1192
1193 case "package":
1194 p.next()
1195 p.pkgname = p.parseUnquotedString()
1196 p.maybeCreatePackage()
1197 if p.version != "v1" && p.tok != '\n' && p.tok != ';' {
1198 p.parseUnquotedString()
1199 p.parseUnquotedString()
1200 }
1201 p.expectEOL()
1202
1203 case "pkgpath":
1204 p.next()
1205 p.pkgpath = p.parseUnquotedString()
1206 p.maybeCreatePackage()
1207 p.expectEOL()
1208
1209 case "prefix":
1210 p.next()
1211 p.pkgpath = p.parseUnquotedString()
1212 p.expectEOL()
1213
1214 case "import":
1215 p.next()
1216 pkgname := p.parseUnquotedString()
1217 pkgpath := p.parseUnquotedString()
1218 p.getPkg(pkgpath, pkgname)
1219 p.parseString()
1220 p.expectEOL()
1221
1222 case "indirectimport":
1223 p.next()
1224 pkgname := p.parseUnquotedString()
1225 pkgpath := p.parseUnquotedString()
1226 p.getPkg(pkgpath, pkgname)
1227 p.expectEOL()
1228
1229 case "types":
1230 p.next()
1231 p.parseTypes(p.pkg)
1232 p.expectEOL()
1233
1234 case "func":
1235 p.next()
1236 fun := p.parseFunc(p.pkg)
1237 if fun != nil {
1238 p.pkg.Scope().Insert(fun)
1239 }
1240 p.expectEOL()
1241
1242 case "type":
1243 p.next()
1244 p.parseType(p.pkg)
1245 p.expectEOL()
1246
1247 case "var":
1248 p.next()
1249 v := p.parseVar(p.pkg)
1250 if v != nil {
1251 p.pkg.Scope().Insert(v)
1252 }
1253 p.expectEOL()
1254
1255 case "const":
1256 p.next()
1257 c := p.parseConst(p.pkg)
1258 p.pkg.Scope().Insert(c)
1259 p.expectEOL()
1260
1261 default:
1262 p.errorf("unexpected identifier: %q", p.lit)
1263 }
1264 }
1265
1266
1267 func (p *parser) parsePackage() *types.Package {
1268 for p.tok != scanner.EOF {
1269 p.parseDirective()
1270 }
1271 for _, f := range p.fixups {
1272 if f.target.Underlying() == nil {
1273 p.errorf("internal error: fixup can't be applied, loop required")
1274 }
1275 f.toUpdate.SetUnderlying(f.target.Underlying())
1276 }
1277 p.fixups = nil
1278 for _, typ := range p.typeList {
1279 if it, ok := typ.(*types.Interface); ok {
1280 it.Complete()
1281 }
1282 }
1283 p.pkg.MarkComplete()
1284 return p.pkg
1285 }
1286
View as plain text