func formatMember(obj types.Object, maxname int) string { var buf bytes.Buffer fmt.Fprintf(&buf, "%-5s %-*s", tokenOf(obj), maxname, obj.Name()) switch obj := obj.(type) { case *types.Const: fmt.Fprintf(&buf, " %s = %s", types.TypeString(obj.Pkg(), obj.Type()), obj.Val().String()) case *types.Func: fmt.Fprintf(&buf, " %s", types.TypeString(obj.Pkg(), obj.Type())) case *types.TypeName: // Abbreviate long aggregate type names. var abbrev string switch t := obj.Type().Underlying().(type) { case *types.Interface: if t.NumMethods() > 1 { abbrev = "interface{...}" } case *types.Struct: if t.NumFields() > 1 { abbrev = "struct{...}" } } if abbrev == "" { fmt.Fprintf(&buf, " %s", types.TypeString(obj.Pkg(), obj.Type().Underlying())) } else { fmt.Fprintf(&buf, " %s", abbrev) } case *types.Var: fmt.Fprintf(&buf, " %s", types.TypeString(obj.Pkg(), obj.Type())) } return buf.String() }
func (p *exporter) obj(obj types.Object) { if trace { p.tracef("object %s {\n", obj.Name()) defer p.tracef("}\n") } switch obj := obj.(type) { case *types.Const: p.int(constTag) p.string(obj.Name()) p.typ(obj.Type()) p.value(obj.Val()) case *types.TypeName: p.int(typeTag) // name is written by corresponding named type p.typ(obj.Type().(*types.Named)) case *types.Var: p.int(varTag) p.string(obj.Name()) p.typ(obj.Type()) case *types.Func: p.int(funcTag) p.string(obj.Name()) p.typ(obj.Type()) default: panic(fmt.Sprintf("unexpected object type %T", obj)) } }
// memberFromObject populates package pkg with a member for the // typechecker object obj. // // For objects from Go source code, syntax is the associated syntax // tree (for funcs and vars only); it will be used during the build // phase. // func memberFromObject(pkg *Package, obj types.Object, syntax ast.Node) { name := obj.Name() switch obj := obj.(type) { case *types.TypeName: pkg.Members[name] = &Type{ object: obj, pkg: pkg, } case *types.Const: c := &NamedConst{ object: obj, Value: NewConst(obj.Val(), obj.Type()), pkg: pkg, } pkg.values[obj] = c.Value pkg.Members[name] = c case *types.Var: g := &Global{ Pkg: pkg, name: name, object: obj, typ: types.NewPointer(obj.Type()), // address pos: obj.Pos(), } pkg.values[obj] = g pkg.Members[name] = g case *types.Func: sig := obj.Type().(*types.Signature) if sig.Recv() == nil && name == "init" { pkg.ninit++ name = fmt.Sprintf("init#%d", pkg.ninit) } fn := &Function{ name: name, object: obj, Signature: sig, syntax: syntax, pos: obj.Pos(), Pkg: pkg, Prog: pkg.Prog, } if syntax == nil { fn.Synthetic = "loaded from gc object file" } pkg.values[obj] = fn if sig.Recv() == nil { pkg.Members[name] = fn // package-level function } default: // (incl. *types.Package) panic("unexpected Object type: " + obj.String()) } }
func (p *printer) printObj(obj types.Object) { p.print(obj.Name()) typ, basic := obj.Type().Underlying().(*types.Basic) if basic && typ.Info()&types.IsUntyped != 0 { // don't write untyped types } else { p.print(" ") p.writeType(p.pkg, obj.Type()) } if obj, ok := obj.(*types.Const); ok { floatFmt := basic && typ.Info()&(types.IsFloat|types.IsComplex) != 0 p.print(" = ") p.print(valString(obj.Val(), floatFmt)) } }
func (g *Grapher) makeDefInfo(obj types.Object) (*DefKey, *defInfo, error) { switch obj := obj.(type) { case *types.Builtin: return &DefKey{"builtin", []string{obj.Name()}}, &defInfo{pkgscope: false, exported: true}, nil case *types.Nil: return &DefKey{"builtin", []string{"nil"}}, &defInfo{pkgscope: false, exported: true}, nil case *types.TypeName: if basic, ok := obj.Type().(*types.Basic); ok { return &DefKey{"builtin", []string{basic.Name()}}, &defInfo{pkgscope: false, exported: true}, nil } if obj.Name() == "error" { return &DefKey{"builtin", []string{obj.Name()}}, &defInfo{pkgscope: false, exported: true}, nil } case *types.PkgName: return &DefKey{obj.Imported().Path(), []string{}}, &defInfo{pkgscope: false, exported: true}, nil case *types.Const: var pkg string if obj.Pkg() == nil { pkg = "builtin" } else { pkg = obj.Pkg().Path() } if obj.Val().Kind() == exact.Bool && pkg == "builtin" { return &DefKey{pkg, []string{obj.Name()}}, &defInfo{pkgscope: false, exported: true}, nil } } if obj.Pkg() == nil { // builtin return &DefKey{"builtin", []string{obj.Name()}}, &defInfo{pkgscope: false, exported: true}, nil } path := g.path(obj) // Handle the case where a dir has 2 main packages that are not // intended to be compiled together and have overlapping def // paths. Prefix the def path with the filename. if obj.Pkg().Name() == "main" { p := g.program.Fset.Position(obj.Pos()) path = append([]string{filepath.Base(p.Filename)}, path...) } return &DefKey{obj.Pkg().Path(), path}, &defInfo{pkgscope: g.pkgscope[obj], exported: g.exported[obj]}, nil }