// If typ represents a named type, Underlying returns
// the type that it was defined as. If all is true,
// it repeats this process until the type is not
// a named type.
425615
func (typ Type) Underlying(all bool) Type {
	for {
		id, _ := typ.Node.(*ast.Ident)
		if id == nil || id.Obj == nil {
			break
		}
		_, typNode := splitDecl(id.Obj, id)
		_, t := typ.ctxt.exprType(typNode, false, typ.Pkg)
		if t.Kind != ast.Typ {
			return badType
		}
		typ.Node = t.Node
		typ.Pkg = t.Pkg
		if !all {
			break
		}
	}
	return typ
}
173789
func (s *ValidateService) Type(typ ...string) *ValidateService {
	s.typ = append(s.typ, typ...)
	return s
}
563101
func (s *SnapshotCreateRepositoryService) Type(typ string) *SnapshotCreateRepositoryService {
	s.typ = typ
	return s
}
634404
func EvalType(expr Expr, sources Sources, typmap TypeMapper) DataType {
	if typmap == nil {
		typmap = nilTypeMapper{}
	}

	valuer := TypeValuerEval{
		TypeMapper: typmap,
		Sources:    sources,
	}
	typ, _ := valuer.EvalType(expr)
	return typ
}
293540
func (pkg *PackageInfo) TypeInfos() TypeInfos {
	var types TypeInfos
	for _, file := range pkg.Files {
		if file == nil {
			continue
		}
		ast.Inspect(file.AstFile(), func(node ast.Node) bool {
			decl, ok := node.(*ast.GenDecl)
			if !ok || decl.Tok != token.TYPE {
				return true
			}
			found := false
			for _, spec := range decl.Specs {
				ts, ok := spec.(*ast.TypeSpec)
				if !ok {
					continue
				}
				types = append(types, &TypeInfo{
					FileInfo: file,
					GenDecl:  decl,
					TypeSpec: ts,
				})
				found = true
			}
			return !found
		})
	}
	return types
}
710175
func (a *Assertions) IsType(expectedType interface{}, object interface{}, msgAndArgs ...interface{}) bool {
	if h, ok := a.t.(tHelper); ok {
		h.Helper()
	}
	return IsType(a.t, expectedType, object, msgAndArgs...)
}
1120425
func (u Universe) Type(n Name) *Type {
	return u.Package(n.Package).Type(n.Name)
}
1133097
func (m *Module) LookupType(name string) (TypeSpec, error) {
	if t, ok := m.Types[name]; ok {
		return t, nil
	}

	return nil, lookupError{Name: name}
}
541471
func (s *ExplainService) Type(typ string) *ExplainService {
	s.typ = typ
	return s
}
349674
func InsertType(t reflect.Type) {
	tname := nameof(t)
	if _, found := typemap[tname]; !found {
		typemap[tname] = t
	}
}
975016
func IsInputType(ttype Type) bool {
	switch GetNamed(ttype).(type) {
	case *Scalar, *Enum, *InputObject:
		return true
	default:
		return false
	}
}
1214672
func typeOf(i interface{}) string {
	if i == nil {
		return ""
	}
	return reflect.TypeOf(i).Elem().Name()
}
374121
func typDesc(typ reflect.Type) string {
	if typ.Kind() == reflect.Ptr {
		if msgT, err := GetMessageType(typ); err == nil {
			return fmt.Sprintf("a %s message", msgT.Name())
		}
	}
	return fmt.Sprintf("a value of kind %q", typ.Kind())
}
629408
func (p *Package) Type(typeName string) *Type {
	if t, ok := p.Types[typeName]; ok {
		return t
	}
	if p.Path == "" {
		// Import the standard builtin types!
		if t, ok := builtins.Types[typeName]; ok {
			p.Types[typeName] = t
			return t
		}
	}
	t := &Type{Name: Name{Package: p.Path, Name: typeName}}
	p.Types[typeName] = t
	return t
}
506253
func IsUnmarshalType(err error) bool {
	_, ok := Cause(err).(*UnmarshalTypeError)
	return ok
}
591277
func isCompat(t1, t2 *Type) bool {
	t1 = stripTypedef(t1)
	t2 = stripTypedef(t2)
	if t1 == nil || t2 == nil || t1.Kind != t2.Kind {
		return false
	}
	if t1 == t2 {
		return true
	}
	switch t1.Kind {
	default:
		// arithmetic
		return true
	case Ptr, Array:
		return isCompat(ptrBase(t1), ptrBase(t2))
	case Struct, Union, Enum:
		return t1.Tag != "" && t1.Tag == t2.Tag
	case Func:
		if len(t1.Decls) != len(t2.Decls) || !isCompat(t1.Base, t2.Base) {
			return false
		}
		for i, d1 := range t1.Decls {
			d2 := t2.Decls[i]
			if d1.Type == nil && d1.Name == "..." {
				if d2.Type == nil && d2.Name == "..." {
					continue
				}
				return false
			}
			if !isCompat(d1.Type, d2.Type) {
				return false
			}
		}
		return true
	}
}
76250
func namedOf(typ types.Type) *types.Named {
	if ptr, isPtr := typ.(*types.Pointer); isPtr {
		typ = ptr.Elem()
	}
	res, _ := typ.(*types.Named)
	return res
}