Пример #1
0
func unknown(obj types.Object) bool {
	switch obj := obj.(type) {
	case field:
		fm, _, _ := types.LookupFieldOrMethod(obj.recv, obj.Pkg, obj.Name)
		_, ok := fm.(*types.Var)
		return !ok
	case *types.Func:
		if sig, ok := obj.Type.(*types.Signature); ok && sig.Recv != nil {
			fm, _, _ := types.LookupFieldOrMethod(sig.Recv.Type, obj.Pkg, obj.Name)
			_, ok := fm.(*types.Func)
			return !ok
		}
	}
	pkg := obj.GetPkg()
	return pkg != nil && pkg.Scope().Lookup(obj.GetName()) == nil
}
Пример #2
0
func (r *reader) obj(x ast.Expr) types.Object {
	switch x := x.(type) {
	case *ast.Ident:
		if obj := r.scope.LookupParent(x.Name); obj != nil {
			if v, ok := obj.(*types.Var); ok && v.Pkg == nil { // ignore local vars
				return nil
			}
			return obj
		}
		return unknownObject{pkg: r.pkg, name: x.Name}
	case *ast.SelectorExpr:
		// TODO: Type.Method and pkg.Type.Method
		n1 := name(x.X)
		n2 := x.Sel.Name
		switch obj := r.scope.LookupParent(n1).(type) {
		case *types.PkgName:
			if obj := obj.Pkg.Scope().Lookup(n2); obj != nil {
				return obj
			}
			return unknownObject{pkg: obj.Pkg, name: n2}
		case *types.Var:
			t := obj.Type
			fm, _, addr := types.LookupFieldOrMethod(t, r.pkg, n2)
			switch fm := fm.(type) {
			case *types.Func:
				sig := fm.Type.(*types.Signature)
				return types.NewFunc(0, r.pkg, n2, types.NewSignature(nil, newVar("", t), sig.Params, sig.Results, sig.IsVariadic))
			case *types.Var:
				return field{fm, t, addr}
			}
			return unknownObject{pkg: obj.Pkg, recv: t, name: n2}
		}
	}
	panic("unreachable")
}