github.com/traefik/yaegi@v0.15.1/interp/type.go (about) 1 package interp 2 3 import ( 4 "fmt" 5 "go/constant" 6 "path/filepath" 7 "reflect" 8 "strconv" 9 "strings" 10 11 "github.com/traefik/yaegi/internal/unsafe2" 12 ) 13 14 // tcat defines interpreter type categories. 15 type tcat uint 16 17 // Types for go language. 18 const ( 19 nilT tcat = iota 20 arrayT 21 binT 22 binPkgT 23 boolT 24 builtinT 25 chanT 26 chanSendT 27 chanRecvT 28 comparableT 29 complex64T 30 complex128T 31 constraintT 32 errorT 33 float32T 34 float64T 35 funcT 36 genericT 37 interfaceT 38 intT 39 int8T 40 int16T 41 int32T 42 int64T 43 linkedT 44 mapT 45 ptrT 46 sliceT 47 srcPkgT 48 stringT 49 structT 50 uintT 51 uint8T 52 uint16T 53 uint32T 54 uint64T 55 uintptrT 56 valueT 57 variadicT 58 maxT 59 ) 60 61 var cats = [...]string{ 62 nilT: "nilT", 63 arrayT: "arrayT", 64 binT: "binT", 65 binPkgT: "binPkgT", 66 boolT: "boolT", 67 builtinT: "builtinT", 68 chanT: "chanT", 69 comparableT: "comparableT", 70 complex64T: "complex64T", 71 complex128T: "complex128T", 72 constraintT: "constraintT", 73 errorT: "errorT", 74 float32T: "float32", 75 float64T: "float64T", 76 funcT: "funcT", 77 genericT: "genericT", 78 interfaceT: "interfaceT", 79 intT: "intT", 80 int8T: "int8T", 81 int16T: "int16T", 82 int32T: "int32T", 83 int64T: "int64T", 84 linkedT: "linkedT", 85 mapT: "mapT", 86 ptrT: "ptrT", 87 sliceT: "sliceT", 88 srcPkgT: "srcPkgT", 89 stringT: "stringT", 90 structT: "structT", 91 uintT: "uintT", 92 uint8T: "uint8T", 93 uint16T: "uint16T", 94 uint32T: "uint32T", 95 uint64T: "uint64T", 96 uintptrT: "uintptrT", 97 valueT: "valueT", 98 variadicT: "variadicT", 99 } 100 101 func (c tcat) String() string { 102 if c < tcat(len(cats)) { 103 return cats[c] 104 } 105 return "Cat(" + strconv.Itoa(int(c)) + ")" 106 } 107 108 // structField type defines a field in a struct. 109 type structField struct { 110 name string 111 tag string 112 embed bool 113 typ *itype 114 } 115 116 // itype defines the internal representation of types in the interpreter. 117 type itype struct { 118 cat tcat // Type category 119 field []structField // Array of struct fields if structT or interfaceT 120 key *itype // Type of key element if MapT or nil 121 val *itype // Type of value element if chanT, chanSendT, chanRecvT, mapT, ptrT, linkedT, arrayT, sliceT, variadicT or genericT 122 recv *itype // Receiver type for funcT or nil 123 arg []*itype // Argument types if funcT or nil 124 ret []*itype // Return types if funcT or nil 125 ptr *itype // Pointer to this type. Might be nil 126 method []*node // Associated methods or nil 127 constraint []*itype // For interfaceT: list of types part of interface set 128 ulconstraint []*itype // For interfaceT: list of underlying types part of interface set 129 instance []*itype // For genericT: list of instantiated types 130 name string // name of type within its package for a defined type 131 path string // for a defined type, the package import path 132 length int // length of array if ArrayT 133 rtype reflect.Type // Reflection type if ValueT, or nil 134 node *node // root AST node of type definition 135 scope *scope // type declaration scope (in case of re-parse incomplete type) 136 str string // String representation of the type 137 incomplete bool // true if type must be parsed again (out of order declarations) 138 untyped bool // true for a literal value (string or number) 139 isBinMethod bool // true if the type refers to a bin method function 140 } 141 142 type generic struct{} 143 144 func untypedBool(n *node) *itype { 145 return &itype{cat: boolT, name: "bool", untyped: true, str: "untyped bool", node: n} 146 } 147 148 func untypedString(n *node) *itype { 149 return &itype{cat: stringT, name: "string", untyped: true, str: "untyped string", node: n} 150 } 151 152 func untypedRune(n *node) *itype { 153 return &itype{cat: int32T, name: "int32", untyped: true, str: "untyped rune", node: n} 154 } 155 156 func untypedInt(n *node) *itype { 157 return &itype{cat: intT, name: "int", untyped: true, str: "untyped int", node: n} 158 } 159 160 func untypedFloat(n *node) *itype { 161 return &itype{cat: float64T, name: "float64", untyped: true, str: "untyped float", node: n} 162 } 163 164 func untypedComplex(n *node) *itype { 165 return &itype{cat: complex128T, name: "complex128", untyped: true, str: "untyped complex", node: n} 166 } 167 168 func errorMethodType(sc *scope) *itype { 169 return &itype{cat: funcT, ret: []*itype{sc.getType("string")}, str: "func() string"} 170 } 171 172 type itypeOption func(*itype) 173 174 func isBinMethod() itypeOption { 175 return func(t *itype) { 176 t.isBinMethod = true 177 } 178 } 179 180 func withRecv(typ *itype) itypeOption { 181 return func(t *itype) { 182 t.recv = typ 183 } 184 } 185 186 func withNode(n *node) itypeOption { 187 return func(t *itype) { 188 t.node = n 189 } 190 } 191 192 func withScope(sc *scope) itypeOption { 193 return func(t *itype) { 194 t.scope = sc 195 } 196 } 197 198 func withUntyped(b bool) itypeOption { 199 return func(t *itype) { 200 t.untyped = b 201 } 202 } 203 204 // valueTOf returns a valueT itype. 205 func valueTOf(rtype reflect.Type, opts ...itypeOption) *itype { 206 t := &itype{cat: valueT, rtype: rtype, str: rtype.String()} 207 for _, opt := range opts { 208 opt(t) 209 } 210 if t.untyped { 211 t.str = "untyped " + t.str 212 } 213 return t 214 } 215 216 // wrapperValueTOf returns a valueT itype wrapping an itype. 217 func wrapperValueTOf(rtype reflect.Type, val *itype, opts ...itypeOption) *itype { 218 t := &itype{cat: valueT, rtype: rtype, val: val, str: rtype.String()} 219 for _, opt := range opts { 220 opt(t) 221 } 222 return t 223 } 224 225 func variadicOf(val *itype, opts ...itypeOption) *itype { 226 t := &itype{cat: variadicT, val: val, str: "..." + val.str} 227 for _, opt := range opts { 228 opt(t) 229 } 230 return t 231 } 232 233 // ptrOf returns a pointer to t. 234 func ptrOf(val *itype, opts ...itypeOption) *itype { 235 if val.ptr != nil { 236 return val.ptr 237 } 238 t := &itype{cat: ptrT, val: val, str: "*" + val.str} 239 for _, opt := range opts { 240 opt(t) 241 } 242 val.ptr = t 243 return t 244 } 245 246 // namedOf returns a named type of val. 247 func namedOf(val *itype, path, name string, opts ...itypeOption) *itype { 248 str := name 249 if path != "" { 250 str = path + "." + name 251 } 252 t := &itype{cat: linkedT, val: val, path: path, name: name, str: str} 253 for _, opt := range opts { 254 opt(t) 255 } 256 return t 257 } 258 259 // funcOf returns a function type with the given args and returns. 260 func funcOf(args []*itype, ret []*itype, opts ...itypeOption) *itype { 261 b := []byte{} 262 b = append(b, "func("...) 263 b = append(b, paramsTypeString(args)...) 264 b = append(b, ')') 265 if len(ret) != 0 { 266 b = append(b, ' ') 267 if len(ret) > 1 { 268 b = append(b, '(') 269 } 270 b = append(b, paramsTypeString(ret)...) 271 if len(ret) > 1 { 272 b = append(b, ')') 273 } 274 } 275 276 t := &itype{cat: funcT, arg: args, ret: ret, str: string(b)} 277 for _, opt := range opts { 278 opt(t) 279 } 280 return t 281 } 282 283 type chanDir uint8 284 285 const ( 286 chanSendRecv chanDir = iota 287 chanSend 288 chanRecv 289 ) 290 291 // chanOf returns a channel of the underlying type val. 292 func chanOf(val *itype, dir chanDir, opts ...itypeOption) *itype { 293 cat := chanT 294 str := "chan " 295 switch dir { 296 case chanSend: 297 cat = chanSendT 298 str = "chan<- " 299 case chanRecv: 300 cat = chanRecvT 301 str = "<-chan " 302 } 303 t := &itype{cat: cat, val: val, str: str + val.str} 304 for _, opt := range opts { 305 opt(t) 306 } 307 return t 308 } 309 310 // arrayOf returns am array type of the underlying val with the given length. 311 func arrayOf(val *itype, l int, opts ...itypeOption) *itype { 312 lstr := strconv.Itoa(l) 313 t := &itype{cat: arrayT, val: val, length: l, str: "[" + lstr + "]" + val.str} 314 for _, opt := range opts { 315 opt(t) 316 } 317 return t 318 } 319 320 // sliceOf returns a slice type of the underlying val. 321 func sliceOf(val *itype, opts ...itypeOption) *itype { 322 t := &itype{cat: sliceT, val: val, str: "[]" + val.str} 323 for _, opt := range opts { 324 opt(t) 325 } 326 return t 327 } 328 329 // mapOf returns a map type of the underlying key and val. 330 func mapOf(key, val *itype, opts ...itypeOption) *itype { 331 t := &itype{cat: mapT, key: key, val: val, str: "map[" + key.str + "]" + val.str} 332 for _, opt := range opts { 333 opt(t) 334 } 335 return t 336 } 337 338 // interfaceOf returns an interface type with the given fields. 339 func interfaceOf(t *itype, fields []structField, constraint, ulconstraint []*itype, opts ...itypeOption) *itype { 340 str := "interface{}" 341 if len(fields) > 0 { 342 str = "interface { " + methodsTypeString(fields) + "}" 343 } 344 if t == nil { 345 t = &itype{} 346 } 347 t.cat = interfaceT 348 t.field = fields 349 t.constraint = constraint 350 t.ulconstraint = ulconstraint 351 t.str = str 352 for _, opt := range opts { 353 opt(t) 354 } 355 return t 356 } 357 358 // structOf returns a struct type with the given fields. 359 func structOf(t *itype, fields []structField, opts ...itypeOption) *itype { 360 str := "struct {}" 361 if len(fields) > 0 { 362 str = "struct { " + fieldsTypeString(fields) + "}" 363 } 364 if t == nil { 365 t = &itype{} 366 } 367 t.cat = structT 368 t.field = fields 369 t.str = str 370 for _, opt := range opts { 371 opt(t) 372 } 373 return t 374 } 375 376 // genericOf returns a generic type. 377 func genericOf(val *itype, name, path string, opts ...itypeOption) *itype { 378 t := &itype{cat: genericT, name: name, path: path, str: name, val: val} 379 for _, opt := range opts { 380 opt(t) 381 } 382 return t 383 } 384 385 // seenNode determines if a node has been seen. 386 // 387 // seenNode treats the slice of nodes as the path traveled down a node 388 // tree. 389 func seenNode(ns []*node, n *node) bool { 390 for _, nn := range ns { 391 if nn == n { 392 return true 393 } 394 } 395 return false 396 } 397 398 // nodeType returns a type definition for the corresponding AST subtree. 399 func nodeType(interp *Interpreter, sc *scope, n *node) (*itype, error) { 400 return nodeType2(interp, sc, n, nil) 401 } 402 403 func nodeType2(interp *Interpreter, sc *scope, n *node, seen []*node) (t *itype, err error) { 404 if n.typ != nil && !n.typ.incomplete { 405 return n.typ, nil 406 } 407 if sname := typeName(n); sname != "" { 408 sym, _, found := sc.lookup(sname) 409 if found && sym.kind == typeSym && sym.typ != nil { 410 if sym.typ.isComplete() { 411 return sym.typ, nil 412 } 413 if seenNode(seen, n) { 414 // We have seen this node in our tree, so it must be recursive. 415 sym.typ.incomplete = false 416 return sym.typ, nil 417 } 418 } 419 } 420 seen = append(seen, n) 421 defer func() { seen = seen[:len(seen)-1] }() 422 423 switch n.kind { 424 case addressExpr, starExpr: 425 val, err := nodeType2(interp, sc, n.child[0], seen) 426 if err != nil { 427 return nil, err 428 } 429 t = ptrOf(val, withNode(n), withScope(sc)) 430 t.incomplete = val.incomplete 431 432 case arrayType: 433 c0 := n.child[0] 434 if len(n.child) == 1 { 435 val, err := nodeType2(interp, sc, c0, seen) 436 if err != nil { 437 return nil, err 438 } 439 t = sliceOf(val, withNode(n), withScope(sc)) 440 t.incomplete = val.incomplete 441 break 442 } 443 // Array size is defined. 444 var ( 445 length int 446 incomplete bool 447 ) 448 switch v := c0.rval; { 449 case v.IsValid(): 450 // Size if defined by a constant literal value. 451 if isConstantValue(v.Type()) { 452 c := v.Interface().(constant.Value) 453 length = constToInt(c) 454 } else { 455 switch v.Type().Kind() { 456 case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64: 457 length = int(v.Int()) 458 case reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Uintptr: 459 length = int(v.Uint()) 460 default: 461 return nil, c0.cfgErrorf("non integer constant %v", v) 462 } 463 } 464 case c0.kind == ellipsisExpr: 465 // [...]T expression, get size from the length of composite array. 466 length, err = arrayTypeLen(n.anc, sc) 467 if err != nil { 468 incomplete = true 469 } 470 case c0.kind == identExpr: 471 sym, _, ok := sc.lookup(c0.ident) 472 if !ok { 473 incomplete = true 474 break 475 } 476 // Size is defined by a symbol which must be a constant integer. 477 if sym.kind != constSym { 478 return nil, c0.cfgErrorf("non-constant array bound %q", c0.ident) 479 } 480 if sym.typ == nil || !isInt(sym.typ.TypeOf()) || !sym.rval.IsValid() { 481 incomplete = true 482 break 483 } 484 length = int(vInt(sym.rval)) 485 default: 486 // Size is defined by a numeric constant expression. 487 if _, err := interp.cfg(c0, sc, sc.pkgID, sc.pkgName); err != nil { 488 if strings.Contains(err.Error(), " undefined: ") { 489 incomplete = true 490 break 491 } 492 return nil, err 493 } 494 v, ok := c0.rval.Interface().(constant.Value) 495 if !ok { 496 incomplete = true 497 break 498 } 499 length = constToInt(v) 500 } 501 val, err := nodeType2(interp, sc, n.child[1], seen) 502 if err != nil { 503 return nil, err 504 } 505 t = arrayOf(val, length, withNode(n), withScope(sc)) 506 t.incomplete = incomplete || val.incomplete 507 508 case basicLit: 509 switch v := n.rval.Interface().(type) { 510 case bool: 511 n.rval = reflect.ValueOf(constant.MakeBool(v)) 512 t = untypedBool(n) 513 case rune: 514 // It is impossible to work out rune const literals in AST 515 // with the correct type so we must make the const type here. 516 n.rval = reflect.ValueOf(constant.MakeInt64(int64(v))) 517 t = untypedRune(n) 518 case constant.Value: 519 switch v.Kind() { 520 case constant.Bool: 521 t = untypedBool(n) 522 case constant.String: 523 t = untypedString(n) 524 case constant.Int: 525 t = untypedInt(n) 526 case constant.Float: 527 t = untypedFloat(n) 528 case constant.Complex: 529 t = untypedComplex(n) 530 default: 531 err = n.cfgErrorf("missing support for type %v", n.rval) 532 } 533 default: 534 err = n.cfgErrorf("missing support for type %T: %v", v, n.rval) 535 } 536 537 case unaryExpr: 538 // In interfaceType, we process an underlying type constraint definition. 539 if isInInterfaceType(n) { 540 t1, err := nodeType2(interp, sc, n.child[0], seen) 541 if err != nil { 542 return nil, err 543 } 544 t = &itype{cat: constraintT, ulconstraint: []*itype{t1}} 545 break 546 } 547 t, err = nodeType2(interp, sc, n.child[0], seen) 548 549 case binaryExpr: 550 // In interfaceType, we process a type constraint union definition. 551 if isInInterfaceType(n) { 552 t = &itype{cat: constraintT, constraint: []*itype{}, ulconstraint: []*itype{}} 553 for _, c := range n.child { 554 t1, err := nodeType2(interp, sc, c, seen) 555 if err != nil { 556 return nil, err 557 } 558 switch t1.cat { 559 case constraintT: 560 t.constraint = append(t.constraint, t1.constraint...) 561 t.ulconstraint = append(t.ulconstraint, t1.ulconstraint...) 562 default: 563 t.constraint = append(t.constraint, t1) 564 } 565 } 566 break 567 } 568 // Get type of first operand. 569 if t, err = nodeType2(interp, sc, n.child[0], seen); err != nil { 570 return nil, err 571 } 572 // For operators other than shift, get the type from the 2nd operand if the first is untyped. 573 if t.untyped && !isShiftNode(n) { 574 var t1 *itype 575 t1, err = nodeType2(interp, sc, n.child[1], seen) 576 if !(t1.untyped && isInt(t1.TypeOf()) && isFloat(t.TypeOf())) { 577 t = t1 578 } 579 } 580 581 // If the node is to be assigned or returned, the node type is the destination type. 582 dt := t 583 584 switch a := n.anc; { 585 case a.kind == assignStmt && isEmptyInterface(a.child[0].typ): 586 // Because an empty interface concrete type "mutates" as different values are 587 // assigned to it, we need to make a new itype from scratch everytime a new 588 // assignment is made, and not let different nodes (of the same variable) share the 589 // same itype. Otherwise they would overwrite each other. 590 a.child[0].typ = &itype{cat: interfaceT, val: dt, str: "interface{}"} 591 592 case a.kind == defineStmt && len(a.child) > a.nleft+a.nright: 593 if dt, err = nodeType2(interp, sc, a.child[a.nleft], seen); err != nil { 594 return nil, err 595 } 596 597 case a.kind == returnStmt: 598 dt = sc.def.typ.ret[childPos(n)] 599 } 600 601 if isInterfaceSrc(dt) { 602 // Set a new interface type preserving the concrete type (.val field). 603 t2 := *dt 604 t2.val = t 605 dt = &t2 606 } 607 t = dt 608 609 case callExpr: 610 if isBuiltinCall(n, sc) { 611 // Builtin types are special and may depend from their input arguments. 612 switch n.child[0].ident { 613 case bltnComplex: 614 var nt0, nt1 *itype 615 if nt0, err = nodeType2(interp, sc, n.child[1], seen); err != nil { 616 return nil, err 617 } 618 if nt1, err = nodeType2(interp, sc, n.child[2], seen); err != nil { 619 return nil, err 620 } 621 if nt0.incomplete || nt1.incomplete { 622 t.incomplete = true 623 } else { 624 switch t0, t1 := nt0.TypeOf(), nt1.TypeOf(); { 625 case isFloat32(t0) && isFloat32(t1): 626 t = sc.getType("complex64") 627 case isFloat64(t0) && isFloat64(t1): 628 t = sc.getType("complex128") 629 case nt0.untyped && isNumber(t0) && nt1.untyped && isNumber(t1): 630 t = untypedComplex(n) 631 case nt0.untyped && isFloat32(t1) || nt1.untyped && isFloat32(t0): 632 t = sc.getType("complex64") 633 case nt0.untyped && isFloat64(t1) || nt1.untyped && isFloat64(t0): 634 t = sc.getType("complex128") 635 default: 636 err = n.cfgErrorf("invalid types %s and %s", t0.Kind(), t1.Kind()) 637 } 638 if nt0.untyped && nt1.untyped { 639 t = untypedComplex(n) 640 } 641 } 642 case bltnReal, bltnImag: 643 if t, err = nodeType2(interp, sc, n.child[1], seen); err != nil { 644 return nil, err 645 } 646 if !t.incomplete { 647 switch k := t.TypeOf().Kind(); { 648 case t.untyped && isNumber(t.TypeOf()): 649 t = untypedFloat(n) 650 case k == reflect.Complex64: 651 t = sc.getType("float32") 652 case k == reflect.Complex128: 653 t = sc.getType("float64") 654 default: 655 err = n.cfgErrorf("invalid complex type %s", k) 656 } 657 } 658 case bltnCap, bltnCopy, bltnLen: 659 t = sc.getType("int") 660 case bltnAppend, bltnMake: 661 t, err = nodeType2(interp, sc, n.child[1], seen) 662 case bltnNew: 663 t, err = nodeType2(interp, sc, n.child[1], seen) 664 incomplete := t.incomplete 665 t = ptrOf(t, withScope(sc)) 666 t.incomplete = incomplete 667 case bltnRecover: 668 t = sc.getType("interface{}") 669 default: 670 t = &itype{cat: builtinT} 671 } 672 if err != nil { 673 return nil, err 674 } 675 } else { 676 if t, err = nodeType2(interp, sc, n.child[0], seen); err != nil || t == nil { 677 return nil, err 678 } 679 switch t.cat { 680 case valueT: 681 if rt := t.rtype; rt.Kind() == reflect.Func && rt.NumOut() == 1 { 682 t = valueTOf(rt.Out(0), withScope(sc)) 683 } 684 default: 685 if len(t.ret) == 1 { 686 t = t.ret[0] 687 } 688 } 689 } 690 691 case compositeLitExpr: 692 t, err = nodeType2(interp, sc, n.child[0], seen) 693 694 case chanType, chanTypeRecv, chanTypeSend: 695 dir := chanSendRecv 696 switch n.kind { 697 case chanTypeRecv: 698 dir = chanRecv 699 case chanTypeSend: 700 dir = chanSend 701 } 702 val, err := nodeType2(interp, sc, n.child[0], seen) 703 if err != nil { 704 return nil, err 705 } 706 t = chanOf(val, dir, withNode(n), withScope(sc)) 707 t.incomplete = val.incomplete 708 709 case ellipsisExpr: 710 val, err := nodeType2(interp, sc, n.child[0], seen) 711 if err != nil { 712 return nil, err 713 } 714 t = variadicOf(val, withNode(n), withScope(sc)) 715 t.incomplete = t.val.incomplete 716 717 case funcLit: 718 t, err = nodeType2(interp, sc, n.child[2], seen) 719 720 case funcType: 721 var incomplete bool 722 723 // Handle type parameters. 724 for _, arg := range n.child[0].child { 725 cl := len(arg.child) - 1 726 typ, err := nodeType2(interp, sc, arg.child[cl], seen) 727 if err != nil { 728 return nil, err 729 } 730 for _, c := range arg.child[:cl] { 731 sc.sym[c.ident] = &symbol{index: -1, kind: varTypeSym, typ: typ} 732 } 733 incomplete = incomplete || typ.incomplete 734 } 735 736 // Handle input parameters. 737 args := make([]*itype, 0, len(n.child[1].child)) 738 for _, arg := range n.child[1].child { 739 cl := len(arg.child) - 1 740 typ, err := nodeType2(interp, sc, arg.child[cl], seen) 741 if err != nil { 742 return nil, err 743 } 744 args = append(args, typ) 745 // Several arguments may be factorized on the same field type. 746 for i := 1; i < cl; i++ { 747 args = append(args, typ) 748 } 749 incomplete = incomplete || typ.incomplete 750 } 751 752 // Handle returned values. 753 var rets []*itype 754 if len(n.child) == 3 { 755 for _, ret := range n.child[2].child { 756 cl := len(ret.child) - 1 757 typ, err := nodeType2(interp, sc, ret.child[cl], seen) 758 if err != nil { 759 return nil, err 760 } 761 rets = append(rets, typ) 762 // Several arguments may be factorized on the same field type. 763 for i := 1; i < cl; i++ { 764 rets = append(rets, typ) 765 } 766 incomplete = incomplete || typ.incomplete 767 } 768 } 769 t = funcOf(args, rets, withNode(n), withScope(sc)) 770 t.incomplete = incomplete 771 772 case identExpr: 773 sym, _, found := sc.lookup(n.ident) 774 if !found { 775 // retry with the filename, in case ident is a package name. 776 baseName := filepath.Base(interp.fset.Position(n.pos).Filename) 777 ident := filepath.Join(n.ident, baseName) 778 sym, _, found = sc.lookup(ident) 779 if !found { 780 t = &itype{name: n.ident, path: sc.pkgName, node: n, incomplete: true, scope: sc} 781 sc.sym[n.ident] = &symbol{kind: typeSym, typ: t} 782 break 783 } 784 } 785 if sym.kind == varTypeSym { 786 t = genericOf(sym.typ, n.ident, sc.pkgName, withNode(n), withScope(sc)) 787 } else { 788 t = sym.typ 789 } 790 if t == nil { 791 if t, err = nodeType2(interp, sc, sym.node, seen); err != nil { 792 return nil, err 793 } 794 } 795 if t.incomplete && t.cat == linkedT && t.val != nil && t.val.cat != nilT { 796 t.incomplete = false 797 } 798 if t.incomplete && t.node != n { 799 m := t.method 800 if t, err = nodeType2(interp, sc, t.node, seen); err != nil { 801 return nil, err 802 } 803 t.method = m 804 sym.typ = t 805 } 806 if t.node == nil { 807 t.node = n 808 } 809 810 case indexExpr: 811 var lt *itype 812 if lt, err = nodeType2(interp, sc, n.child[0], seen); err != nil { 813 return nil, err 814 } 815 if lt.incomplete { 816 if t == nil { 817 t = lt 818 } else { 819 t.incomplete = true 820 } 821 break 822 } 823 switch lt.cat { 824 case arrayT, mapT, sliceT, variadicT: 825 t = lt.val 826 case genericT: 827 t1, err := nodeType2(interp, sc, n.child[1], seen) 828 if err != nil { 829 return nil, err 830 } 831 if t1.cat == genericT || t1.incomplete { 832 t = lt 833 break 834 } 835 name := lt.id() + "[" + t1.id() + "]" 836 if sym, _, found := sc.lookup(name); found { 837 t = sym.typ 838 break 839 } 840 // A generic type is being instantiated. Generate it. 841 t, err = genType(interp, sc, name, lt, []*itype{t1}, seen) 842 if err != nil { 843 return nil, err 844 } 845 } 846 847 case indexListExpr: 848 // Similar to above indexExpr for generic types, but handle multiple type parameters. 849 var lt *itype 850 if lt, err = nodeType2(interp, sc, n.child[0], seen); err != nil { 851 return nil, err 852 } 853 if lt.incomplete { 854 if t == nil { 855 t = lt 856 } else { 857 t.incomplete = true 858 } 859 break 860 } 861 862 // Index list expressions can be used only in context of generic types. 863 if lt.cat != genericT { 864 err = n.cfgErrorf("not a generic type: %s", lt.id()) 865 return nil, err 866 } 867 name := lt.id() + "[" 868 out := false 869 types := []*itype{} 870 for _, c := range n.child[1:] { 871 t1, err := nodeType2(interp, sc, c, seen) 872 if err != nil { 873 return nil, err 874 } 875 if t1.cat == genericT || t1.incomplete { 876 t = lt 877 out = true 878 break 879 } 880 types = append(types, t1) 881 name += t1.id() + "," 882 } 883 if out { 884 break 885 } 886 name = strings.TrimSuffix(name, ",") + "]" 887 if sym, _, found := sc.lookup(name); found { 888 t = sym.typ 889 break 890 } 891 // A generic type is being instantiated. Generate it. 892 t, err = genType(interp, sc, name, lt, types, seen) 893 894 case interfaceType: 895 if sname := typeName(n); sname != "" { 896 if sym, _, found := sc.lookup(sname); found && sym.kind == typeSym { 897 t = interfaceOf(sym.typ, sym.typ.field, sym.typ.constraint, sym.typ.ulconstraint, withNode(n), withScope(sc)) 898 } 899 } 900 var incomplete bool 901 fields := []structField{} 902 constraint := []*itype{} 903 ulconstraint := []*itype{} 904 for _, c := range n.child[0].child { 905 c0 := c.child[0] 906 if len(c.child) == 1 { 907 if c0.ident == "error" { 908 // Unwrap error interface inplace rather than embedding it, because 909 // "error" is lower case which may cause problems with reflect for method lookup. 910 typ := errorMethodType(sc) 911 fields = append(fields, structField{name: "Error", typ: typ}) 912 continue 913 } 914 typ, err := nodeType2(interp, sc, c0, seen) 915 if err != nil { 916 return nil, err 917 } 918 incomplete = incomplete || typ.incomplete 919 if typ.cat == constraintT { 920 constraint = append(constraint, typ.constraint...) 921 ulconstraint = append(ulconstraint, typ.ulconstraint...) 922 continue 923 } 924 fields = append(fields, structField{name: fieldName(c0), embed: true, typ: typ}) 925 continue 926 } 927 typ, err := nodeType2(interp, sc, c.child[1], seen) 928 if err != nil { 929 return nil, err 930 } 931 fields = append(fields, structField{name: c0.ident, typ: typ}) 932 incomplete = incomplete || typ.incomplete 933 } 934 t = interfaceOf(t, fields, constraint, ulconstraint, withNode(n), withScope(sc)) 935 t.incomplete = incomplete 936 937 case landExpr, lorExpr: 938 t = sc.getType("bool") 939 940 case mapType: 941 key, err := nodeType2(interp, sc, n.child[0], seen) 942 if err != nil { 943 return nil, err 944 } 945 val, err := nodeType2(interp, sc, n.child[1], seen) 946 if err != nil { 947 return nil, err 948 } 949 t = mapOf(key, val, withNode(n), withScope(sc)) 950 t.incomplete = key.incomplete || val.incomplete 951 952 case parenExpr: 953 t, err = nodeType2(interp, sc, n.child[0], seen) 954 955 case selectorExpr: 956 // Resolve the left part of selector, then lookup the right part on it 957 var lt *itype 958 959 // Lookup the package symbol first if we are in a field expression as 960 // a previous parameter has the same name as the package, we need to 961 // prioritize the package type. 962 if n.anc.kind == fieldExpr { 963 lt = findPackageType(interp, sc, n.child[0]) 964 } 965 if lt == nil { 966 // No package was found or we are not in a field expression, we are looking for a variable. 967 if lt, err = nodeType2(interp, sc, n.child[0], seen); err != nil { 968 return nil, err 969 } 970 } 971 972 if lt.incomplete { 973 break 974 } 975 name := n.child[1].ident 976 switch lt.cat { 977 case binPkgT: 978 pkg := interp.binPkg[lt.path] 979 if v, ok := pkg[name]; ok { 980 rtype := v.Type() 981 if isBinType(v) { 982 // A bin type is encoded as a pointer on a typed nil value. 983 rtype = rtype.Elem() 984 } 985 t = valueTOf(rtype, withNode(n), withScope(sc)) 986 } else { 987 err = n.cfgErrorf("undefined selector %s.%s", lt.path, name) 988 } 989 case srcPkgT: 990 pkg := interp.srcPkg[lt.path] 991 if s, ok := pkg[name]; ok { 992 t = s.typ 993 } else { 994 err = n.cfgErrorf("undefined selector %s.%s", lt.path, name) 995 } 996 default: 997 if m, _ := lt.lookupMethod(name); m != nil { 998 t, err = nodeType2(interp, sc, m.child[2], seen) 999 } else if bm, _, _, ok := lt.lookupBinMethod(name); ok { 1000 t = valueTOf(bm.Type, isBinMethod(), withRecv(lt), withScope(sc)) 1001 } else if ti := lt.lookupField(name); len(ti) > 0 { 1002 t = lt.fieldSeq(ti) 1003 } else if bs, _, ok := lt.lookupBinField(name); ok { 1004 t = valueTOf(bs.Type, withScope(sc)) 1005 } else { 1006 err = lt.node.cfgErrorf("undefined selector %s", name) 1007 } 1008 } 1009 1010 case sliceExpr: 1011 t, err = nodeType2(interp, sc, n.child[0], seen) 1012 if err != nil { 1013 return nil, err 1014 } 1015 1016 if t.cat == valueT { 1017 switch t.rtype.Kind() { 1018 case reflect.Array, reflect.Ptr: 1019 t = valueTOf(reflect.SliceOf(t.rtype.Elem()), withScope(sc)) 1020 } 1021 break 1022 } 1023 if t.cat == ptrT { 1024 t = t.val 1025 } 1026 if t.cat == arrayT { 1027 incomplete := t.incomplete 1028 t = sliceOf(t.val, withNode(n), withScope(sc)) 1029 t.incomplete = incomplete 1030 } 1031 1032 case structType: 1033 var sym *symbol 1034 var found bool 1035 sname := structName(n) 1036 if sname != "" { 1037 sym, _, found = sc.lookup(sname) 1038 if found && sym.kind == typeSym && sym.typ != nil { 1039 t = structOf(sym.typ, sym.typ.field, withNode(n), withScope(sc)) 1040 } else { 1041 t = structOf(nil, nil, withNode(n), withScope(sc)) 1042 sc.sym[sname] = &symbol{index: -1, kind: typeSym, typ: t, node: n} 1043 } 1044 } 1045 var incomplete bool 1046 fields := make([]structField, 0, len(n.child[0].child)) 1047 for _, c := range n.child[0].child { 1048 switch { 1049 case len(c.child) == 1: 1050 typ, err := nodeType2(interp, sc, c.child[0], seen) 1051 if err != nil { 1052 return nil, err 1053 } 1054 fields = append(fields, structField{name: fieldName(c.child[0]), embed: true, typ: typ}) 1055 incomplete = incomplete || typ.incomplete 1056 case len(c.child) == 2 && c.child[1].kind == basicLit: 1057 tag := vString(c.child[1].rval) 1058 typ, err := nodeType2(interp, sc, c.child[0], seen) 1059 if err != nil { 1060 return nil, err 1061 } 1062 fields = append(fields, structField{name: fieldName(c.child[0]), embed: true, typ: typ, tag: tag}) 1063 incomplete = incomplete || typ.incomplete 1064 default: 1065 var tag string 1066 l := len(c.child) 1067 if c.lastChild().kind == basicLit { 1068 tag = vString(c.lastChild().rval) 1069 l-- 1070 } 1071 typ, err := nodeType2(interp, sc, c.child[l-1], seen) 1072 if err != nil { 1073 return nil, err 1074 } 1075 incomplete = incomplete || typ.incomplete 1076 for _, d := range c.child[:l-1] { 1077 fields = append(fields, structField{name: d.ident, typ: typ, tag: tag}) 1078 } 1079 } 1080 } 1081 t = structOf(t, fields, withNode(n), withScope(sc)) 1082 t.incomplete = incomplete 1083 if sname != "" { 1084 if sc.sym[sname] == nil { 1085 sc.sym[sname] = &symbol{index: -1, kind: typeSym, node: n} 1086 } 1087 sc.sym[sname].typ = t 1088 } 1089 1090 default: 1091 err = n.cfgErrorf("type definition not implemented: %s", n.kind) 1092 } 1093 1094 if err == nil && t != nil && t.cat == nilT && !t.incomplete { 1095 err = n.cfgErrorf("use of untyped nil %s", t.name) 1096 } 1097 1098 // The existing symbol data needs to be recovered, but not in the 1099 // case where we are aliasing another type. 1100 if n.anc.kind == typeSpec && n.kind != selectorExpr && n.kind != identExpr { 1101 name := n.anc.child[0].ident 1102 if sym := sc.sym[name]; sym != nil { 1103 t.path = sc.pkgName 1104 t.name = name 1105 } 1106 } 1107 1108 switch { 1109 case t == nil: 1110 case t.name != "" && t.path != "": 1111 t.str = t.path + "." + t.name 1112 case t.cat == nilT: 1113 t.str = "nil" 1114 } 1115 1116 return t, err 1117 } 1118 1119 func genType(interp *Interpreter, sc *scope, name string, lt *itype, types []*itype, seen []*node) (t *itype, err error) { 1120 // A generic type is being instantiated. Generate it. 1121 g, _, err := genAST(sc, lt.node.anc, types) 1122 if err != nil { 1123 return nil, err 1124 } 1125 t, err = nodeType2(interp, sc, g.lastChild(), seen) 1126 if err != nil { 1127 return nil, err 1128 } 1129 lt.instance = append(lt.instance, t) 1130 // Add generated symbol in the scope of generic source and user. 1131 sc.sym[name] = &symbol{index: -1, kind: typeSym, typ: t, node: g} 1132 if lt.scope.sym[name] == nil { 1133 lt.scope.sym[name] = sc.sym[name] 1134 } 1135 1136 for _, nod := range lt.method { 1137 if err := genMethod(interp, sc, t, nod, types); err != nil { 1138 return nil, err 1139 } 1140 } 1141 return t, err 1142 } 1143 1144 func genMethod(interp *Interpreter, sc *scope, t *itype, nod *node, types []*itype) error { 1145 gm, _, err := genAST(sc, nod, types) 1146 if err != nil { 1147 return err 1148 } 1149 if gm.typ, err = nodeType(interp, sc, gm.child[2]); err != nil { 1150 return err 1151 } 1152 t.addMethod(gm) 1153 1154 // If the receiver is a pointer to a generic type, generate also the pointer type. 1155 if rtn := gm.child[0].child[0].lastChild(); rtn != nil && rtn.kind == starExpr { 1156 pt := ptrOf(t, withNode(t.node), withScope(sc)) 1157 pt.addMethod(gm) 1158 rtn.typ = pt 1159 } 1160 1161 // Compile the method AST in the scope of the generic type. 1162 scop := nod.typ.scope 1163 if _, err = interp.cfg(gm, scop, scop.pkgID, scop.pkgName); err != nil { 1164 return err 1165 } 1166 1167 // Generate closures for function body. 1168 return genRun(gm) 1169 } 1170 1171 // findPackageType searches the top level scope for a package type. 1172 func findPackageType(interp *Interpreter, sc *scope, n *node) *itype { 1173 // Find the root scope, the package symbols will exist there. 1174 for { 1175 if sc.level == 0 { 1176 break 1177 } 1178 sc = sc.anc 1179 } 1180 1181 baseName := filepath.Base(interp.fset.Position(n.pos).Filename) 1182 sym, _, found := sc.lookup(filepath.Join(n.ident, baseName)) 1183 if !found || sym.typ == nil && sym.typ.cat != srcPkgT && sym.typ.cat != binPkgT { 1184 return nil 1185 } 1186 return sym.typ 1187 } 1188 1189 func isBuiltinCall(n *node, sc *scope) bool { 1190 if n.kind != callExpr { 1191 return false 1192 } 1193 s := n.child[0].sym 1194 if s == nil { 1195 if sym, _, found := sc.lookup(n.child[0].ident); found { 1196 s = sym 1197 } 1198 } 1199 return s != nil && s.kind == bltnSym 1200 } 1201 1202 // struct name returns the name of a struct type. 1203 func typeName(n *node) string { 1204 if n.anc.kind == typeSpec && len(n.anc.child) == 2 { 1205 return n.anc.child[0].ident 1206 } 1207 return "" 1208 } 1209 1210 func structName(n *node) string { 1211 if n.anc.kind == typeSpec { 1212 return n.anc.child[0].ident 1213 } 1214 return "" 1215 } 1216 1217 // fieldName returns an implicit struct field name according to node kind. 1218 func fieldName(n *node) string { 1219 switch n.kind { 1220 case selectorExpr: 1221 return fieldName(n.child[1]) 1222 case starExpr: 1223 return fieldName(n.child[0]) 1224 case identExpr: 1225 return n.ident 1226 default: 1227 return "" 1228 } 1229 } 1230 1231 var zeroValues [maxT]reflect.Value 1232 1233 func init() { 1234 zeroValues[boolT] = reflect.ValueOf(false) 1235 zeroValues[complex64T] = reflect.ValueOf(complex64(0)) 1236 zeroValues[complex128T] = reflect.ValueOf(complex128(0)) 1237 zeroValues[errorT] = reflect.ValueOf(new(error)).Elem() 1238 zeroValues[float32T] = reflect.ValueOf(float32(0)) 1239 zeroValues[float64T] = reflect.ValueOf(float64(0)) 1240 zeroValues[intT] = reflect.ValueOf(int(0)) 1241 zeroValues[int8T] = reflect.ValueOf(int8(0)) 1242 zeroValues[int16T] = reflect.ValueOf(int16(0)) 1243 zeroValues[int32T] = reflect.ValueOf(int32(0)) 1244 zeroValues[int64T] = reflect.ValueOf(int64(0)) 1245 zeroValues[stringT] = reflect.ValueOf("") 1246 zeroValues[uintT] = reflect.ValueOf(uint(0)) 1247 zeroValues[uint8T] = reflect.ValueOf(uint8(0)) 1248 zeroValues[uint16T] = reflect.ValueOf(uint16(0)) 1249 zeroValues[uint32T] = reflect.ValueOf(uint32(0)) 1250 zeroValues[uint64T] = reflect.ValueOf(uint64(0)) 1251 zeroValues[uintptrT] = reflect.ValueOf(uintptr(0)) 1252 } 1253 1254 // Finalize returns a type pointer and error. It reparses a type from the 1255 // partial AST if necessary (after missing dependecy data is available). 1256 // If error is nil, the type is guarranteed to be completely defined and 1257 // usable for CFG. 1258 func (t *itype) finalize() (*itype, error) { 1259 var err error 1260 if t.incomplete { 1261 sym, _, found := t.scope.lookup(t.name) 1262 if found && !sym.typ.incomplete { 1263 sym.typ.method = append(sym.typ.method, t.method...) 1264 t.method = sym.typ.method 1265 t.incomplete = false 1266 return sym.typ, nil 1267 } 1268 m := t.method 1269 if t, err = nodeType(t.node.interp, t.scope, t.node); err != nil { 1270 return nil, err 1271 } 1272 if t.incomplete { 1273 return nil, t.node.cfgErrorf("incomplete type %s", t.name) 1274 } 1275 t.method = m 1276 t.node.typ = t 1277 if sym != nil { 1278 sym.typ = t 1279 } 1280 } 1281 return t, err 1282 } 1283 1284 func (t *itype) addMethod(n *node) { 1285 for _, m := range t.method { 1286 if m == n { 1287 return 1288 } 1289 } 1290 t.method = append(t.method, n) 1291 } 1292 1293 func (t *itype) numIn() int { 1294 switch t.cat { 1295 case funcT: 1296 return len(t.arg) 1297 case valueT: 1298 if t.rtype.Kind() != reflect.Func { 1299 return 0 1300 } 1301 in := t.rtype.NumIn() 1302 if t.recv != nil { 1303 in-- 1304 } 1305 return in 1306 } 1307 return 0 1308 } 1309 1310 func (t *itype) in(i int) *itype { 1311 switch t.cat { 1312 case funcT: 1313 return t.arg[i] 1314 case valueT: 1315 if t.rtype.Kind() == reflect.Func { 1316 if t.recv != nil && !isInterface(t.recv) { 1317 i++ 1318 } 1319 if t.rtype.IsVariadic() && i == t.rtype.NumIn()-1 { 1320 val := valueTOf(t.rtype.In(i).Elem()) 1321 return &itype{cat: variadicT, val: val, str: "..." + val.str} 1322 } 1323 return valueTOf(t.rtype.In(i)) 1324 } 1325 } 1326 return nil 1327 } 1328 1329 func (t *itype) numOut() int { 1330 switch t.cat { 1331 case funcT: 1332 return len(t.ret) 1333 case valueT: 1334 if t.rtype.Kind() == reflect.Func { 1335 return t.rtype.NumOut() 1336 } 1337 case builtinT: 1338 switch t.name { 1339 case "append", "cap", "complex", "copy", "imag", "len", "make", "new", "real", "recover": 1340 return 1 1341 } 1342 } 1343 return 0 1344 } 1345 1346 func (t *itype) out(i int) *itype { 1347 switch t.cat { 1348 case funcT: 1349 return t.ret[i] 1350 case valueT: 1351 if t.rtype.Kind() == reflect.Func { 1352 return valueTOf(t.rtype.Out(i)) 1353 } 1354 } 1355 return nil 1356 } 1357 1358 func (t *itype) concrete() *itype { 1359 if isInterface(t) && t.val != nil { 1360 return t.val.concrete() 1361 } 1362 return t 1363 } 1364 1365 func (t *itype) underlying() *itype { 1366 if t.cat == linkedT { 1367 return t.val.underlying() 1368 } 1369 return t 1370 } 1371 1372 // typeDefined returns true if type t1 is defined from type t2 or t2 from t1. 1373 func typeDefined(t1, t2 *itype) bool { 1374 if t1.cat == linkedT && t1.val == t2 { 1375 return true 1376 } 1377 if t2.cat == linkedT && t2.val == t1 { 1378 return true 1379 } 1380 return false 1381 } 1382 1383 // isVariadic returns true if the function type is variadic. 1384 // If the type is not a function or is not variadic, it will 1385 // return false. 1386 func (t *itype) isVariadic() bool { 1387 switch t.cat { 1388 case funcT: 1389 return len(t.arg) > 0 && t.arg[len(t.arg)-1].cat == variadicT 1390 case valueT: 1391 if t.rtype.Kind() == reflect.Func { 1392 return t.rtype.IsVariadic() 1393 } 1394 } 1395 return false 1396 } 1397 1398 // isComplete returns true if type definition is complete. 1399 func (t *itype) isComplete() bool { return isComplete(t, map[string]bool{}) } 1400 1401 func isComplete(t *itype, visited map[string]bool) bool { 1402 if t.incomplete { 1403 return false 1404 } 1405 name := t.path + "/" + t.name 1406 if visited[name] { 1407 return true 1408 } 1409 if t.name != "" { 1410 visited[name] = true 1411 } 1412 switch t.cat { 1413 case linkedT: 1414 if t.val != nil && t.val.cat != nilT { 1415 // A type aliased to a partially defined type is considered complete, to allow recursivity. 1416 return true 1417 } 1418 fallthrough 1419 case arrayT, chanT, chanRecvT, chanSendT, ptrT, sliceT, variadicT: 1420 return isComplete(t.val, visited) 1421 case funcT: 1422 complete := true 1423 for _, a := range t.arg { 1424 complete = complete && isComplete(a, visited) 1425 } 1426 for _, a := range t.ret { 1427 complete = complete && isComplete(a, visited) 1428 } 1429 return complete 1430 case interfaceT, structT: 1431 complete := true 1432 for _, f := range t.field { 1433 // Field implicit type names must be marked as visited, to break false circles. 1434 visited[f.typ.path+"/"+f.typ.name] = true 1435 complete = complete && isComplete(f.typ, visited) 1436 } 1437 return complete 1438 case mapT: 1439 return isComplete(t.key, visited) && isComplete(t.val, visited) 1440 case nilT: 1441 return false 1442 } 1443 return true 1444 } 1445 1446 // comparable returns true if the type is comparable. 1447 func (t *itype) comparable() bool { 1448 typ := t.TypeOf() 1449 return t.cat == nilT || typ != nil && typ.Comparable() 1450 } 1451 1452 func (t *itype) assignableTo(o *itype) bool { 1453 if t.equals(o) { 1454 return true 1455 } 1456 1457 if t.cat == linkedT && o.cat == linkedT && (t.underlying().id() != o.underlying().id() || !typeDefined(t, o)) { 1458 return false 1459 } 1460 1461 if t.isNil() && o.hasNil() || o.isNil() && t.hasNil() { 1462 return true 1463 } 1464 1465 if t.TypeOf().AssignableTo(o.TypeOf()) { 1466 return true 1467 } 1468 1469 if isInterface(o) && t.implements(o) { 1470 return true 1471 } 1472 1473 if t.cat == sliceT && o.cat == sliceT { 1474 return t.val.assignableTo(o.val) 1475 } 1476 1477 if t.isBinMethod && isFunc(o) { 1478 // TODO (marc): check that t without receiver as first parameter is equivalent to o. 1479 return true 1480 } 1481 1482 if t.untyped && isNumber(t.TypeOf()) && isNumber(o.TypeOf()) { 1483 // Assignability depends on constant numeric value (overflow check), to be tested elsewhere. 1484 return true 1485 } 1486 1487 n := t.node 1488 if n == nil || !n.rval.IsValid() { 1489 return false 1490 } 1491 con, ok := n.rval.Interface().(constant.Value) 1492 if !ok { 1493 return false 1494 } 1495 if con == nil || !isConstType(o) { 1496 return false 1497 } 1498 return representableConst(con, o.TypeOf()) 1499 } 1500 1501 // convertibleTo returns true if t is convertible to o. 1502 func (t *itype) convertibleTo(o *itype) bool { 1503 if t.assignableTo(o) { 1504 return true 1505 } 1506 1507 // unsafe checks 1508 tt, ot := t.TypeOf(), o.TypeOf() 1509 if (tt.Kind() == reflect.Ptr || tt.Kind() == reflect.Uintptr) && ot.Kind() == reflect.UnsafePointer { 1510 return true 1511 } 1512 if tt.Kind() == reflect.UnsafePointer && (ot.Kind() == reflect.Ptr || ot.Kind() == reflect.Uintptr) { 1513 return true 1514 } 1515 1516 return t.TypeOf().ConvertibleTo(o.TypeOf()) 1517 } 1518 1519 // ordered returns true if the type is ordered. 1520 func (t *itype) ordered() bool { 1521 typ := t.TypeOf() 1522 return isInt(typ) || isFloat(typ) || isString(typ) 1523 } 1524 1525 // Equals returns true if the given type is identical to the receiver one. 1526 func (t *itype) equals(o *itype) bool { 1527 switch ti, oi := isInterface(t), isInterface(o); { 1528 case ti && oi: 1529 return t.methods().equals(o.methods()) 1530 case ti && !oi: 1531 return o.methods().contains(t.methods()) 1532 case oi && !ti: 1533 return t.methods().contains(o.methods()) 1534 default: 1535 return t.id() == o.id() 1536 } 1537 } 1538 1539 // MethodSet defines the set of methods signatures as strings, indexed per method name. 1540 type methodSet map[string]string 1541 1542 // Contains returns true if the method set m contains the method set n. 1543 func (m methodSet) contains(n methodSet) bool { 1544 for k, v := range n { 1545 if m[k] != v { 1546 return false 1547 } 1548 } 1549 return true 1550 } 1551 1552 // Equal returns true if the method set m is equal to the method set n. 1553 func (m methodSet) equals(n methodSet) bool { 1554 return m.contains(n) && n.contains(m) 1555 } 1556 1557 // Methods returns a map of method type strings, indexed by method names. 1558 func (t *itype) methods() methodSet { 1559 seen := map[*itype]bool{} 1560 var getMethods func(typ *itype) methodSet 1561 1562 getMethods = func(typ *itype) methodSet { 1563 res := make(methodSet) 1564 1565 if seen[typ] { 1566 // Stop the recursion, we have seen this type. 1567 return res 1568 } 1569 seen[typ] = true 1570 1571 switch typ.cat { 1572 case linkedT: 1573 for k, v := range getMethods(typ.val) { 1574 res[k] = v 1575 } 1576 case interfaceT: 1577 // Get methods from recursive analysis of interface fields. 1578 for _, f := range typ.field { 1579 if f.typ.cat == funcT { 1580 res[f.name] = f.typ.TypeOf().String() 1581 } else { 1582 for k, v := range getMethods(f.typ) { 1583 res[k] = v 1584 } 1585 } 1586 } 1587 case valueT, errorT: 1588 // Get method from corresponding reflect.Type. 1589 for i := typ.TypeOf().NumMethod() - 1; i >= 0; i-- { 1590 m := typ.rtype.Method(i) 1591 res[m.Name] = m.Type.String() 1592 } 1593 case ptrT: 1594 if typ.val.cat == valueT { 1595 // Ptr receiver methods need to be found with the ptr type. 1596 typ.TypeOf() // Ensure the rtype exists. 1597 for i := typ.rtype.NumMethod() - 1; i >= 0; i-- { 1598 m := typ.rtype.Method(i) 1599 res[m.Name] = m.Type.String() 1600 } 1601 } 1602 for k, v := range getMethods(typ.val) { 1603 res[k] = v 1604 } 1605 case structT: 1606 for _, f := range typ.field { 1607 if !f.embed { 1608 continue 1609 } 1610 for k, v := range getMethods(f.typ) { 1611 res[k] = v 1612 } 1613 } 1614 } 1615 // Get all methods defined on this type. 1616 for _, m := range typ.method { 1617 res[m.ident] = m.typ.TypeOf().String() 1618 } 1619 return res 1620 } 1621 1622 return getMethods(t) 1623 } 1624 1625 // id returns a unique type identificator string. 1626 func (t *itype) id() (res string) { 1627 // Prefer the wrapped type string over the rtype string. 1628 if t.cat == valueT && t.val != nil { 1629 return t.val.str 1630 } 1631 return t.str 1632 } 1633 1634 // fixPossibleConstType returns the input type if it not a constant value, 1635 // otherwise, it returns the default Go type corresponding to the 1636 // constant.Value. 1637 func fixPossibleConstType(t reflect.Type) (r reflect.Type) { 1638 cv, ok := reflect.New(t).Elem().Interface().(constant.Value) 1639 if !ok { 1640 return t 1641 } 1642 switch cv.Kind() { 1643 case constant.Bool: 1644 r = reflect.TypeOf(true) 1645 case constant.Int: 1646 r = reflect.TypeOf(0) 1647 case constant.String: 1648 r = reflect.TypeOf("") 1649 case constant.Float: 1650 r = reflect.TypeOf(float64(0)) 1651 case constant.Complex: 1652 r = reflect.TypeOf(complex128(0)) 1653 } 1654 return r 1655 } 1656 1657 // zero instantiates and return a zero value object for the given type during execution. 1658 func (t *itype) zero() (v reflect.Value, err error) { 1659 if t, err = t.finalize(); err != nil { 1660 return v, err 1661 } 1662 switch t.cat { 1663 case linkedT: 1664 v, err = t.val.zero() 1665 1666 case arrayT, ptrT, structT, sliceT: 1667 v = reflect.New(t.frameType()).Elem() 1668 1669 case valueT: 1670 v = reflect.New(t.rtype).Elem() 1671 1672 default: 1673 v = zeroValues[t.cat] 1674 } 1675 return v, err 1676 } 1677 1678 // fieldIndex returns the field index from name in a struct, or -1 if not found. 1679 func (t *itype) fieldIndex(name string) int { 1680 switch t.cat { 1681 case linkedT, ptrT: 1682 return t.val.fieldIndex(name) 1683 } 1684 for i, field := range t.field { 1685 if name == field.name { 1686 return i 1687 } 1688 } 1689 return -1 1690 } 1691 1692 // fieldSeq returns the field type from the list of field indexes. 1693 func (t *itype) fieldSeq(seq []int) *itype { 1694 ft := t 1695 for _, i := range seq { 1696 if ft.cat == ptrT { 1697 ft = ft.val 1698 } 1699 ft = ft.field[i].typ 1700 } 1701 return ft 1702 } 1703 1704 // lookupField returns a list of indices, i.e. a path to access a field in a struct object. 1705 func (t *itype) lookupField(name string) []int { 1706 seen := map[*itype]bool{} 1707 var lookup func(*itype) []int 1708 tias := isStruct(t) 1709 1710 lookup = func(typ *itype) []int { 1711 if seen[typ] { 1712 return nil 1713 } 1714 seen[typ] = true 1715 1716 switch typ.cat { 1717 case linkedT, ptrT: 1718 return lookup(typ.val) 1719 } 1720 if fi := typ.fieldIndex(name); fi >= 0 { 1721 return []int{fi} 1722 } 1723 1724 for i, f := range typ.field { 1725 switch f.typ.cat { 1726 case ptrT, structT, interfaceT, linkedT: 1727 if tias != isStruct(f.typ) { 1728 // Interface fields are not valid embedded struct fields. 1729 // Struct fields are not valid interface fields. 1730 break 1731 } 1732 if index2 := lookup(f.typ); len(index2) > 0 { 1733 return append([]int{i}, index2...) 1734 } 1735 } 1736 } 1737 1738 return nil 1739 } 1740 1741 return lookup(t) 1742 } 1743 1744 // lookupBinField returns a structfield and a path to access an embedded binary field in a struct object. 1745 func (t *itype) lookupBinField(name string) (s reflect.StructField, index []int, ok bool) { 1746 if t.cat == ptrT { 1747 return t.val.lookupBinField(name) 1748 } 1749 if !isStruct(t) { 1750 return 1751 } 1752 rt := t.TypeOf() 1753 for t.cat == valueT && rt.Kind() == reflect.Ptr { 1754 rt = rt.Elem() 1755 } 1756 if rt.Kind() != reflect.Struct { 1757 return 1758 } 1759 s, ok = rt.FieldByName(name) 1760 if !ok { 1761 for i, f := range t.field { 1762 if f.embed { 1763 if s2, index2, ok2 := f.typ.lookupBinField(name); ok2 { 1764 index = append([]int{i}, index2...) 1765 return s2, index, ok2 1766 } 1767 } 1768 } 1769 } 1770 return s, index, ok 1771 } 1772 1773 // MethodCallType returns a method function type without the receiver defined. 1774 // The input type must be a method function type with the receiver as the first input argument. 1775 func (t *itype) methodCallType() reflect.Type { 1776 it := []reflect.Type{} 1777 ni := t.rtype.NumIn() 1778 for i := 1; i < ni; i++ { 1779 it = append(it, t.rtype.In(i)) 1780 } 1781 ot := []reflect.Type{} 1782 no := t.rtype.NumOut() 1783 for i := 0; i < no; i++ { 1784 ot = append(ot, t.rtype.Out(i)) 1785 } 1786 return reflect.FuncOf(it, ot, t.rtype.IsVariadic()) 1787 } 1788 1789 func (t *itype) resolveAlias() *itype { 1790 for t.cat == linkedT { 1791 t = t.val 1792 } 1793 return t 1794 } 1795 1796 // GetMethod returns a pointer to the method definition. 1797 func (t *itype) getMethod(name string) *node { 1798 for _, m := range t.method { 1799 if name == m.ident { 1800 return m 1801 } 1802 } 1803 return nil 1804 } 1805 1806 // LookupMethod returns a pointer to method definition associated to type t 1807 // and the list of indices to access the right struct field, in case of an embedded method. 1808 func (t *itype) lookupMethod(name string) (*node, []int) { 1809 return t.lookupMethod2(name, nil) 1810 } 1811 1812 func (t *itype) lookupMethod2(name string, seen map[*itype]bool) (*node, []int) { 1813 if seen == nil { 1814 seen = map[*itype]bool{} 1815 } 1816 if seen[t] { 1817 return nil, nil 1818 } 1819 seen[t] = true 1820 if t.cat == ptrT { 1821 return t.val.lookupMethod2(name, seen) 1822 } 1823 var index []int 1824 m := t.getMethod(name) 1825 if m == nil { 1826 for i, f := range t.field { 1827 if f.embed { 1828 if n, index2 := f.typ.lookupMethod2(name, seen); n != nil { 1829 index = append([]int{i}, index2...) 1830 return n, index 1831 } 1832 } 1833 } 1834 if t.cat == linkedT || isInterfaceSrc(t) && t.val != nil { 1835 return t.val.lookupMethod2(name, seen) 1836 } 1837 } 1838 return m, index 1839 } 1840 1841 // interfaceMethod returns type of method matching an interface method name (not as a concrete method). 1842 func (t *itype) interfaceMethod(name string) *itype { 1843 return t.interfaceMethod2(name, nil) 1844 } 1845 1846 func (t *itype) interfaceMethod2(name string, seen map[*itype]bool) *itype { 1847 if seen == nil { 1848 seen = map[*itype]bool{} 1849 } 1850 if seen[t] { 1851 return nil 1852 } 1853 seen[t] = true 1854 if t.cat == ptrT { 1855 return t.val.interfaceMethod2(name, seen) 1856 } 1857 for _, f := range t.field { 1858 if f.name == name && isInterface(t) { 1859 return f.typ 1860 } 1861 if !f.embed { 1862 continue 1863 } 1864 if typ := f.typ.interfaceMethod2(name, seen); typ != nil { 1865 return typ 1866 } 1867 } 1868 if t.cat == linkedT || isInterfaceSrc(t) && t.val != nil { 1869 return t.val.interfaceMethod2(name, seen) 1870 } 1871 return nil 1872 } 1873 1874 // methodDepth returns a depth greater or equal to 0, or -1 if no match. 1875 func (t *itype) methodDepth(name string) int { 1876 if m, lint := t.lookupMethod(name); m != nil { 1877 return len(lint) 1878 } 1879 if _, lint, _, ok := t.lookupBinMethod(name); ok { 1880 return len(lint) 1881 } 1882 return -1 1883 } 1884 1885 // LookupBinMethod returns a method and a path to access a field in a struct object (the receiver). 1886 func (t *itype) lookupBinMethod(name string) (m reflect.Method, index []int, isPtr, ok bool) { 1887 return t.lookupBinMethod2(name, nil) 1888 } 1889 1890 func (t *itype) lookupBinMethod2(name string, seen map[*itype]bool) (m reflect.Method, index []int, isPtr, ok bool) { 1891 if seen == nil { 1892 seen = map[*itype]bool{} 1893 } 1894 if seen[t] { 1895 return 1896 } 1897 seen[t] = true 1898 if t.cat == ptrT { 1899 return t.val.lookupBinMethod2(name, seen) 1900 } 1901 for i, f := range t.field { 1902 if f.embed { 1903 if m2, index2, isPtr2, ok2 := f.typ.lookupBinMethod2(name, seen); ok2 { 1904 index = append([]int{i}, index2...) 1905 return m2, index, isPtr2, ok2 1906 } 1907 } 1908 } 1909 m, ok = t.TypeOf().MethodByName(name) 1910 if !ok { 1911 m, ok = reflect.PtrTo(t.TypeOf()).MethodByName(name) 1912 isPtr = ok 1913 } 1914 return m, index, isPtr, ok 1915 } 1916 1917 func lookupFieldOrMethod(t *itype, name string) *itype { 1918 switch { 1919 case t.cat == valueT || t.cat == ptrT && t.val.cat == valueT: 1920 m, _, isPtr, ok := t.lookupBinMethod(name) 1921 if !ok { 1922 return nil 1923 } 1924 var recv *itype 1925 if t.rtype.Kind() != reflect.Interface { 1926 recv = t 1927 if isPtr && t.cat != ptrT && t.rtype.Kind() != reflect.Ptr { 1928 recv = ptrOf(t) 1929 } 1930 } 1931 return valueTOf(m.Type, withRecv(recv)) 1932 case t.cat == interfaceT: 1933 seq := t.lookupField(name) 1934 if seq == nil { 1935 return nil 1936 } 1937 return t.fieldSeq(seq) 1938 default: 1939 n, _ := t.lookupMethod(name) 1940 if n == nil { 1941 return nil 1942 } 1943 return n.typ 1944 } 1945 } 1946 1947 func exportName(s string) string { 1948 if canExport(s) { 1949 return s 1950 } 1951 return "X" + s 1952 } 1953 1954 var ( 1955 // TODO(mpl): generators. 1956 emptyInterfaceType = reflect.TypeOf((*interface{})(nil)).Elem() 1957 valueInterfaceType = reflect.TypeOf((*valueInterface)(nil)).Elem() 1958 constVal = reflect.TypeOf((*constant.Value)(nil)).Elem() 1959 ) 1960 1961 type refTypeContext struct { 1962 defined map[string]*itype 1963 1964 // refs keeps track of all the places (in the same type recursion) where the 1965 // type name (as key) is used as a field of another (or possibly the same) struct 1966 // type. Each of these fields will then live as an unsafe2.dummy type until the 1967 // whole recursion is fully resolved, and the type is fixed. 1968 refs map[string][]*itype 1969 1970 // When we detect for the first time that we are in a recursive type (thanks to 1971 // defined), we keep track of the first occurrence of the type where the recursion 1972 // started, so we can restart the last step that fixes all the types from the same 1973 // "top-level" point. 1974 rect *itype 1975 rebuilding bool 1976 slevel int 1977 } 1978 1979 // Clone creates a copy of the ref type context. 1980 func (c *refTypeContext) Clone() *refTypeContext { 1981 return &refTypeContext{defined: c.defined, refs: c.refs, rebuilding: c.rebuilding} 1982 } 1983 1984 func (c *refTypeContext) isComplete() bool { 1985 for _, t := range c.defined { 1986 if t.rtype == nil { 1987 return false 1988 } 1989 } 1990 return true 1991 } 1992 1993 func (t *itype) fixDummy(typ reflect.Type) reflect.Type { 1994 if typ == unsafe2.DummyType { 1995 return t.rtype 1996 } 1997 switch typ.Kind() { 1998 case reflect.Array: 1999 return reflect.ArrayOf(typ.Len(), t.fixDummy(typ.Elem())) 2000 case reflect.Chan: 2001 return reflect.ChanOf(typ.ChanDir(), t.fixDummy(typ.Elem())) 2002 case reflect.Func: 2003 in := make([]reflect.Type, typ.NumIn()) 2004 for i := range in { 2005 in[i] = t.fixDummy(typ.In(i)) 2006 } 2007 out := make([]reflect.Type, typ.NumOut()) 2008 for i := range out { 2009 out[i] = t.fixDummy(typ.Out(i)) 2010 } 2011 return reflect.FuncOf(in, out, typ.IsVariadic()) 2012 case reflect.Map: 2013 return reflect.MapOf(t.fixDummy(typ.Key()), t.fixDummy(typ.Elem())) 2014 case reflect.Ptr: 2015 return reflect.PtrTo(t.fixDummy(typ.Elem())) 2016 case reflect.Slice: 2017 return reflect.SliceOf(t.fixDummy(typ.Elem())) 2018 case reflect.Struct: 2019 fields := make([]reflect.StructField, typ.NumField()) 2020 for i := range fields { 2021 fields[i] = typ.Field(i) 2022 fields[i].Type = t.fixDummy(fields[i].Type) 2023 } 2024 return reflect.StructOf(fields) 2025 } 2026 return typ 2027 } 2028 2029 // RefType returns a reflect.Type representation from an interpreter type. 2030 // In simple cases, reflect types are directly mapped from the interpreter 2031 // counterpart. 2032 // For recursive named struct or interfaces, as reflect does not permit to 2033 // create a recursive named struct, a dummy type is set temporarily for each recursive 2034 // field. When done, the dummy type fields are updated with the original reflect type 2035 // pointer using unsafe. We thus obtain a usable recursive type definition, except 2036 // for string representation, as created reflect types are still unnamed. 2037 func (t *itype) refType(ctx *refTypeContext) reflect.Type { 2038 if ctx == nil { 2039 ctx = &refTypeContext{ 2040 defined: map[string]*itype{}, 2041 refs: map[string][]*itype{}, 2042 } 2043 } 2044 if t.incomplete || t.cat == nilT { 2045 var err error 2046 if t, err = t.finalize(); err != nil { 2047 panic(err) 2048 } 2049 } 2050 name := t.path + "/" + t.name 2051 2052 if t.rtype != nil && !ctx.rebuilding { 2053 return t.rtype 2054 } 2055 if dt := ctx.defined[name]; dt != nil { 2056 // We get here when we are a struct field, and our type name has already been 2057 // seen at least once in one of our englobing structs. i.e. there's at least one 2058 // level of type recursion. 2059 if dt.rtype != nil { 2060 t.rtype = dt.rtype 2061 return dt.rtype 2062 } 2063 2064 // The recursion has not been fully resolved yet. 2065 // To indicate that a rebuild is needed on the englobing struct, 2066 // return a dummy field type and create an empty entry. 2067 flds := ctx.refs[name] 2068 ctx.rect = dt 2069 2070 // We know we are used as a field by someone, but we don't know by who 2071 // at this point in the code, so we just mark it as an empty *itype for now. 2072 // We'll complete the *itype in the caller. 2073 ctx.refs[name] = append(flds, (*itype)(nil)) 2074 return unsafe2.DummyType 2075 } 2076 if isGeneric(t) { 2077 return reflect.TypeOf((*generic)(nil)).Elem() 2078 } 2079 switch t.cat { 2080 case linkedT: 2081 t.rtype = t.val.refType(ctx) 2082 case arrayT: 2083 t.rtype = reflect.ArrayOf(t.length, t.val.refType(ctx)) 2084 case sliceT, variadicT: 2085 t.rtype = reflect.SliceOf(t.val.refType(ctx)) 2086 case chanT: 2087 t.rtype = reflect.ChanOf(reflect.BothDir, t.val.refType(ctx)) 2088 case chanRecvT: 2089 t.rtype = reflect.ChanOf(reflect.RecvDir, t.val.refType(ctx)) 2090 case chanSendT: 2091 t.rtype = reflect.ChanOf(reflect.SendDir, t.val.refType(ctx)) 2092 case errorT: 2093 t.rtype = reflect.TypeOf(new(error)).Elem() 2094 case funcT: 2095 variadic := false 2096 in := make([]reflect.Type, len(t.arg)) 2097 out := make([]reflect.Type, len(t.ret)) 2098 for i, v := range t.arg { 2099 in[i] = v.refType(ctx) 2100 variadic = v.cat == variadicT 2101 } 2102 for i, v := range t.ret { 2103 out[i] = v.refType(ctx) 2104 } 2105 t.rtype = reflect.FuncOf(in, out, variadic) 2106 case interfaceT: 2107 if len(t.field) == 0 { 2108 // empty interface, do not wrap it 2109 t.rtype = emptyInterfaceType 2110 break 2111 } 2112 t.rtype = valueInterfaceType 2113 case mapT: 2114 t.rtype = reflect.MapOf(t.key.refType(ctx), t.val.refType(ctx)) 2115 case ptrT: 2116 rt := t.val.refType(ctx) 2117 if rt == unsafe2.DummyType && ctx.slevel > 1 { 2118 // We have a pointer to a recursive struct which is not yet fully computed. 2119 // Return it but do not yet store it in rtype, so the complete version can 2120 // be stored in future. 2121 return reflect.PtrTo(rt) 2122 } 2123 t.rtype = reflect.PtrTo(rt) 2124 case structT: 2125 if t.name != "" { 2126 ctx.defined[name] = t 2127 } 2128 ctx.slevel++ 2129 var fields []reflect.StructField 2130 for _, f := range t.field { 2131 field := reflect.StructField{ 2132 Name: exportName(f.name), Type: f.typ.refType(ctx), 2133 Tag: reflect.StructTag(f.tag), Anonymous: f.embed, 2134 } 2135 fields = append(fields, field) 2136 // Find any nil type refs that indicates a rebuild is needed on this field. 2137 for _, flds := range ctx.refs { 2138 for j, fld := range flds { 2139 if fld == nil { 2140 flds[j] = t 2141 } 2142 } 2143 } 2144 } 2145 ctx.slevel-- 2146 type fixStructField struct { 2147 name string 2148 index int 2149 } 2150 fieldFix := []fixStructField{} // Slice of field indices to fix for recursivity. 2151 t.rtype = reflect.StructOf(fields) 2152 if ctx.isComplete() { 2153 for _, s := range ctx.defined { 2154 for i := 0; i < s.rtype.NumField(); i++ { 2155 f := s.rtype.Field(i) 2156 if strings.HasSuffix(f.Type.String(), "unsafe2.dummy") { 2157 unsafe2.SetFieldType(s.rtype, i, ctx.rect.fixDummy(s.rtype.Field(i).Type)) 2158 if name == s.path+"/"+s.name { 2159 fieldFix = append(fieldFix, fixStructField{s.name, i}) 2160 } 2161 continue 2162 } 2163 if f.Type.Kind() == reflect.Func && strings.Contains(f.Type.String(), "unsafe2.dummy") { 2164 fieldFix = append(fieldFix, fixStructField{s.name, i}) 2165 } 2166 } 2167 } 2168 } 2169 2170 // The rtype has now been built, we can go back and rebuild 2171 // all the recursive types that relied on this type. 2172 // However, as we are keyed by type name, if two or more (recursive) fields at 2173 // the same depth level are of the same type, or a "variation" of the same type 2174 // (slice of, map of, etc), they "mask" each other, and only one 2175 // of them is in ctx.refs. That is why the code around here is a bit convoluted, 2176 // and we need both the loop above, around all the struct fields, and the loop 2177 // below, around the ctx.refs. 2178 for _, f := range ctx.refs[name] { 2179 for _, ff := range fieldFix { 2180 if ff.name == f.name { 2181 ftyp := f.field[ff.index].typ.refType(&refTypeContext{defined: ctx.defined, rebuilding: true}) 2182 unsafe2.SetFieldType(f.rtype, ff.index, ftyp) 2183 } 2184 } 2185 } 2186 default: 2187 if z, _ := t.zero(); z.IsValid() { 2188 t.rtype = z.Type() 2189 } 2190 } 2191 return t.rtype 2192 } 2193 2194 // TypeOf returns the reflection type of dynamic interpreter type t. 2195 func (t *itype) TypeOf() reflect.Type { 2196 return t.refType(nil) 2197 } 2198 2199 func (t *itype) frameType() (r reflect.Type) { 2200 var err error 2201 if t, err = t.finalize(); err != nil { 2202 panic(err) 2203 } 2204 switch t.cat { 2205 case linkedT: 2206 r = t.val.frameType() 2207 case arrayT: 2208 r = reflect.ArrayOf(t.length, t.val.frameType()) 2209 case sliceT, variadicT: 2210 r = reflect.SliceOf(t.val.frameType()) 2211 case interfaceT: 2212 if len(t.field) == 0 { 2213 // empty interface, do not wrap it 2214 r = emptyInterfaceType 2215 break 2216 } 2217 r = valueInterfaceType 2218 case mapT: 2219 r = reflect.MapOf(t.key.frameType(), t.val.frameType()) 2220 case ptrT: 2221 r = reflect.PtrTo(t.val.frameType()) 2222 default: 2223 r = t.TypeOf() 2224 } 2225 return r 2226 } 2227 2228 func (t *itype) implements(it *itype) bool { 2229 if isBin(t) { 2230 // Note: in case of a valueInterfaceType, we 2231 // miss required data which will be available 2232 // later, so we optimistically return true to progress, 2233 // and additional checks will be hopefully performed at 2234 // runtime. 2235 if rt := it.TypeOf(); rt == valueInterfaceType { 2236 return true 2237 } 2238 return t.TypeOf().Implements(it.TypeOf()) 2239 } 2240 return t.methods().contains(it.methods()) 2241 } 2242 2243 // defaultType returns the default type of an untyped type. 2244 func (t *itype) defaultType(v reflect.Value, sc *scope) *itype { 2245 if !t.untyped { 2246 return t 2247 } 2248 2249 typ := t 2250 // The default type can also be derived from a constant value. 2251 if v.IsValid() && v.Type().Implements(constVal) { 2252 switch v.Interface().(constant.Value).Kind() { 2253 case constant.String: 2254 typ = sc.getType("string") 2255 case constant.Bool: 2256 typ = sc.getType("bool") 2257 case constant.Int: 2258 switch t.cat { 2259 case int32T: 2260 typ = sc.getType("int32") 2261 default: 2262 typ = sc.getType("int") 2263 } 2264 case constant.Float: 2265 typ = sc.getType("float64") 2266 case constant.Complex: 2267 typ = sc.getType("complex128") 2268 } 2269 } 2270 if typ.untyped { 2271 switch t.cat { 2272 case stringT: 2273 typ = sc.getType("string") 2274 case boolT: 2275 typ = sc.getType("bool") 2276 case intT: 2277 typ = sc.getType("int") 2278 case float64T: 2279 typ = sc.getType("float64") 2280 case complex128T: 2281 typ = sc.getType("complex128") 2282 default: 2283 *typ = *t 2284 typ.untyped = false 2285 } 2286 } 2287 return typ 2288 } 2289 2290 func (t *itype) isNil() bool { return t.cat == nilT } 2291 2292 func (t *itype) hasNil() bool { 2293 switch rt := t.TypeOf(); rt.Kind() { 2294 case reflect.UnsafePointer: 2295 return true 2296 case reflect.Slice, reflect.Ptr, reflect.Func, reflect.Interface, reflect.Map, reflect.Chan: 2297 return true 2298 case reflect.Struct: 2299 if rt == valueInterfaceType { 2300 return true 2301 } 2302 } 2303 return false 2304 } 2305 2306 func (t *itype) elem() *itype { 2307 if t.cat == valueT { 2308 return valueTOf(t.rtype.Elem()) 2309 } 2310 return t.val 2311 } 2312 2313 func hasElem(t reflect.Type) bool { 2314 switch t.Kind() { 2315 case reflect.Array, reflect.Chan, reflect.Map, reflect.Ptr, reflect.Slice: 2316 return true 2317 } 2318 return false 2319 } 2320 2321 func constToInt(c constant.Value) int { 2322 if constant.BitLen(c) > 64 { 2323 panic(fmt.Sprintf("constant %s overflows int64", c.ExactString())) 2324 } 2325 i, _ := constant.Int64Val(c) 2326 return int(i) 2327 } 2328 2329 func constToString(v reflect.Value) string { 2330 c := v.Interface().(constant.Value) 2331 return constant.StringVal(c) 2332 } 2333 2334 func wrappedType(n *node) *itype { 2335 if n.typ.cat != valueT { 2336 return nil 2337 } 2338 return n.typ.val 2339 } 2340 2341 func isShiftNode(n *node) bool { 2342 switch n.action { 2343 case aShl, aShr, aShlAssign, aShrAssign: 2344 return true 2345 } 2346 return false 2347 } 2348 2349 // chanElement returns the channel element type. 2350 func chanElement(t *itype) *itype { 2351 switch t.cat { 2352 case linkedT: 2353 return chanElement(t.val) 2354 case chanT, chanSendT, chanRecvT: 2355 return t.val 2356 case valueT: 2357 return valueTOf(t.rtype.Elem(), withNode(t.node), withScope(t.scope)) 2358 } 2359 return nil 2360 } 2361 2362 func isBool(t *itype) bool { return t.TypeOf().Kind() == reflect.Bool } 2363 func isChan(t *itype) bool { return t.TypeOf().Kind() == reflect.Chan } 2364 func isFunc(t *itype) bool { return t.TypeOf().Kind() == reflect.Func } 2365 func isMap(t *itype) bool { return t.TypeOf().Kind() == reflect.Map } 2366 func isPtr(t *itype) bool { return t.TypeOf().Kind() == reflect.Ptr } 2367 2368 func isEmptyInterface(t *itype) bool { 2369 return t.cat == interfaceT && len(t.field) == 0 2370 } 2371 2372 func isGeneric(t *itype) bool { 2373 return t.cat == funcT && t.node != nil && len(t.node.child) > 0 && len(t.node.child[0].child) > 0 2374 } 2375 2376 func isNamedFuncSrc(t *itype) bool { 2377 return isFuncSrc(t) && t.node.anc.kind == funcDecl 2378 } 2379 2380 func isFuncSrc(t *itype) bool { 2381 return t.cat == funcT || (t.cat == linkedT && isFuncSrc(t.val)) 2382 } 2383 2384 func isPtrSrc(t *itype) bool { 2385 return t.cat == ptrT || (t.cat == linkedT && isPtrSrc(t.val)) 2386 } 2387 2388 func isSendChan(t *itype) bool { 2389 rt := t.TypeOf() 2390 return rt.Kind() == reflect.Chan && rt.ChanDir() == reflect.SendDir 2391 } 2392 2393 func isArray(t *itype) bool { 2394 if t.cat == nilT { 2395 return false 2396 } 2397 k := t.TypeOf().Kind() 2398 return k == reflect.Array || k == reflect.Slice 2399 } 2400 2401 func isInterfaceSrc(t *itype) bool { 2402 return t.cat == interfaceT || (t.cat == linkedT && isInterfaceSrc(t.val)) 2403 } 2404 2405 func isInterfaceBin(t *itype) bool { 2406 return t.cat == valueT && t.rtype.Kind() == reflect.Interface || t.cat == errorT 2407 } 2408 2409 func isInterface(t *itype) bool { 2410 return isInterfaceSrc(t) || t.TypeOf() == valueInterfaceType || t.TypeOf() != nil && t.TypeOf().Kind() == reflect.Interface 2411 } 2412 2413 func isBin(t *itype) bool { 2414 switch t.cat { 2415 case valueT: 2416 return true 2417 case linkedT, ptrT: 2418 return isBin(t.val) 2419 default: 2420 return false 2421 } 2422 } 2423 2424 func isStruct(t *itype) bool { 2425 // Test first for a struct category, because a recursive interpreter struct may be 2426 // represented by an interface{} at reflect level. 2427 switch t.cat { 2428 case structT: 2429 return true 2430 case linkedT, ptrT: 2431 return isStruct(t.val) 2432 case valueT: 2433 k := t.rtype.Kind() 2434 return k == reflect.Struct || (k == reflect.Ptr && t.rtype.Elem().Kind() == reflect.Struct) 2435 default: 2436 return false 2437 } 2438 } 2439 2440 func isConstType(t *itype) bool { 2441 rt := t.TypeOf() 2442 return isBoolean(rt) || isString(rt) || isNumber(rt) 2443 } 2444 2445 func isInt(t reflect.Type) bool { 2446 if t == nil { 2447 return false 2448 } 2449 switch t.Kind() { 2450 case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64, reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Uintptr: 2451 return true 2452 } 2453 return false 2454 } 2455 2456 func isUint(t reflect.Type) bool { 2457 if t == nil { 2458 return false 2459 } 2460 switch t.Kind() { 2461 case reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Uintptr: 2462 return true 2463 } 2464 return false 2465 } 2466 2467 func isComplex(t reflect.Type) bool { 2468 if t == nil { 2469 return false 2470 } 2471 switch t.Kind() { 2472 case reflect.Complex64, reflect.Complex128: 2473 return true 2474 } 2475 return false 2476 } 2477 2478 func isFloat(t reflect.Type) bool { 2479 if t == nil { 2480 return false 2481 } 2482 switch t.Kind() { 2483 case reflect.Float32, reflect.Float64: 2484 return true 2485 } 2486 return false 2487 } 2488 2489 func isByteArray(t reflect.Type) bool { 2490 if t == nil { 2491 return false 2492 } 2493 k := t.Kind() 2494 return (k == reflect.Array || k == reflect.Slice) && t.Elem().Kind() == reflect.Uint8 2495 } 2496 2497 func isFloat32(t reflect.Type) bool { return t != nil && t.Kind() == reflect.Float32 } 2498 func isFloat64(t reflect.Type) bool { return t != nil && t.Kind() == reflect.Float64 } 2499 func isNumber(t reflect.Type) bool { 2500 return isInt(t) || isFloat(t) || isComplex(t) || isConstantValue(t) 2501 } 2502 func isBoolean(t reflect.Type) bool { return t != nil && t.Kind() == reflect.Bool } 2503 func isString(t reflect.Type) bool { return t != nil && t.Kind() == reflect.String } 2504 func isConstantValue(t reflect.Type) bool { return t != nil && t.Implements(constVal) }