1 // Copyright 2021 The Go Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style
3 // license that can be found in the LICENSE file.
10 "cmd/compile/internal/base"
11 "cmd/compile/internal/dwarfgen"
12 "cmd/compile/internal/ir"
13 "cmd/compile/internal/syntax"
14 "cmd/compile/internal/typecheck"
15 "cmd/compile/internal/types"
16 "cmd/compile/internal/types2"
20 // checkFiles configures and runs the types2 checker on the given
21 // parsed source files and then returns the result.
22 func checkFiles(noders []*noder) (posMap, *types2.Package, *types2.Info) {
23 if base.SyntaxErrors() != 0 {
27 // setup and syntax error reporting
29 files := make([]*syntax.File, len(noders))
30 for i, p := range noders {
36 ctxt := types2.NewContext()
37 importer := gcimports{
39 packages: make(map[string]*types2.Package),
41 conf := types2.Config{
43 GoVersion: base.Flag.Lang,
44 IgnoreBranchErrors: true, // parser already checked via syntax.CheckBranches mode
45 CompilerErrorMessages: true, // use error strings matching existing compiler errors
46 Error: func(err error) {
47 terr := err.(types2.Error)
48 base.ErrorfAt(m.makeXPos(terr.Pos), "%s", terr.Msg)
54 Types: make(map[syntax.Expr]types2.TypeAndValue),
55 Defs: make(map[*syntax.Name]types2.Object),
56 Uses: make(map[*syntax.Name]types2.Object),
57 Selections: make(map[*syntax.SelectorExpr]*types2.Selection),
58 Implicits: make(map[syntax.Node]types2.Object),
59 Scopes: make(map[syntax.Node]*types2.Scope),
60 Instances: make(map[*syntax.Name]types2.Instance),
64 pkg, err := conf.Check(base.Ctxt.Pkgpath, files, info)
68 base.FatalfAt(src.NoXPos, "conf.Check error: %v", err)
74 // check2 type checks a Go package using types2, and then generates IR
76 func check2(noders []*noder) {
77 m, pkg, info := checkFiles(noders)
80 target: typecheck.Target,
84 objs: make(map[types2.Object]*ir.Name),
85 typs: make(map[types2.Type]*types.Type),
90 // Information about sub-dictionary entries in a dictionary
91 type subDictInfo struct {
92 // Call or XDOT node that requires a dictionary.
94 // Saved CallExpr.X node (*ir.SelectorExpr or *InstExpr node) for a generic
95 // method or function call, since this node will get dropped when the generic
96 // method/function call is transformed to a call on the instantiated shape
97 // function. Nil for other kinds of calls or XDOTs.
101 // dictInfo is the dictionary format for an instantiation of a generic function with
102 // particular shapes. shapeParams, derivedTypes, subDictCalls, itabConvs, and methodExprClosures
103 // describe the actual dictionary entries in order, and the remaining fields are other info
104 // needed in doing dictionary processing during compilation.
105 type dictInfo struct {
106 // Types substituted for the type parameters, which are shape types.
107 shapeParams []*types.Type
108 // All types derived from those typeparams used in the instantiation.
109 derivedTypes []*types.Type
110 // Nodes in the instantiation that requires a subdictionary. Includes
111 // method and function calls (OCALL), function values (OFUNCINST), method
112 // values/expressions (OXDOT).
113 subDictCalls []subDictInfo
114 // Nodes in the instantiation that are a conversion from a typeparam/derived
115 // type to a specific interface.
117 // Method expression closures. For a generic type T with method M(arg1, arg2) res,
118 // these closures are func(rcvr T, arg1, arg2) res.
119 // These closures capture no variables, they are just the generic version of ·f symbols
120 // that live in the dictionary instead of in the readonly globals section.
121 methodExprClosures []methodExprClosure
123 // Mapping from each shape type that substitutes a type param, to its
124 // type bound (which is also substituted with shapes if it is parameterized)
125 shapeToBound map[*types.Type]*types.Type
127 // For type switches on nonempty interfaces, a map from OTYPE entries of
128 // HasShape type, to the interface type we're switching from.
129 type2switchType map[ir.Node]*types.Type
131 startSubDict int // Start of dict entries for subdictionaries
132 startItabConv int // Start of dict entries for itab conversions
133 startMethodExprClosures int // Start of dict entries for closures for method expressions
134 dictLen int // Total number of entries in dictionary
137 type methodExprClosure struct {
138 idx int // index in list of shape parameters
139 name string // method name
142 // instInfo is information gathered on an shape instantiation of a function.
143 type instInfo struct {
144 fun *ir.Func // The instantiated function (with body)
145 dictParam *ir.Name // The node inside fun that refers to the dictionary param
156 objs map[types2.Object]*ir.Name
157 typs map[types2.Type]*types.Type
158 marker dwarfgen.ScopeMarker
160 // laterFuncs records tasks that need to run after all declarations
163 // haveEmbed indicates whether the current node belongs to file that
164 // imports "embed" package.
167 // exprStmtOK indicates whether it's safe to generate expressions or
171 // types which we need to finish, by doing g.fillinMethods.
172 typesToFinalize []*typeDelayInfo
174 // True when we are compiling a top-level generic function or method. Use to
175 // avoid adding closures of generic functions/methods to the target.Decls
177 topFuncIsGeneric bool
179 // The context during type/function/method declarations that is used to
180 // uniquely name type parameters. We need unique names for type params so we
181 // can be sure they match up correctly between types2-to-types1 translation
182 // and types1 importing.
186 // genInst has the information for creating needed instantiations and modifying
187 // functions to use instantiations.
188 type genInst struct {
189 dnum int // for generating unique dictionary variables
191 // Map from the names of all instantiations to information about the
193 instInfoMap map[*types.Sym]*instInfo
195 // Dictionary syms which we need to finish, by writing out any itabconv
196 // or method expression closure entries.
197 dictSymsToFinalize []*delayInfo
199 // New instantiations created during this round of buildInstantiations().
203 func (g *irgen) later(fn func()) {
204 g.laterFuncs = append(g.laterFuncs, fn)
207 type delayInfo struct {
215 type typeDelayInfo struct {
220 func (g *irgen) generate(noders []*noder) {
221 types.LocalPkg.Name = g.self.Name()
222 typecheck.TypecheckAllowed = true
224 // Prevent size calculations until we set the underlying type
225 // for all package-block defined types.
226 types.DeferCheckSize()
228 // At this point, types2 has already handled name resolution and
229 // type checking. We just need to map from its object and type
230 // representations to those currently used by the rest of the
231 // compiler. This happens in a few passes.
233 // 1. Process all import declarations. We use the compiler's own
234 // importer for this, rather than types2's gcimporter-derived one,
235 // to handle extensions and inline function bodies correctly.
237 // Also, we need to do this in a separate pass, because mappings are
238 // instantiated on demand. If we interleaved processing import
239 // declarations with other declarations, it's likely we'd end up
240 // wanting to map an object/type from another source file, but not
241 // yet have the import data it relies on.
242 declLists := make([][]syntax.Decl, len(noders))
244 for i, p := range noders {
245 g.pragmaFlags(p.file.Pragma, ir.GoBuildPragma)
246 for j, decl := range p.file.DeclList {
247 switch decl := decl.(type) {
248 case *syntax.ImportDecl:
249 g.importDecl(p, decl)
251 declLists[i] = p.file.DeclList[j:]
252 continue Outer // no more ImportDecls
257 // 2. Process all package-block type declarations. As with imports,
258 // we need to make sure all types are properly instantiated before
259 // trying to map any expressions that utilize them. In particular,
260 // we need to make sure type pragmas are already known (see comment
261 // in irgen.typeDecl).
263 // We could perhaps instead defer processing of package-block
264 // variable initializers and function bodies, like noder does, but
265 // special-casing just package-block type declarations minimizes the
266 // differences between processing package-block and function-scoped
268 for _, declList := range declLists {
269 for _, decl := range declList {
270 switch decl := decl.(type) {
271 case *syntax.TypeDecl:
272 g.typeDecl((*ir.Nodes)(&g.target.Decls), decl)
276 types.ResumeCheckSize()
278 // 3. Process all remaining declarations.
279 for i, declList := range declLists {
281 g.haveEmbed = noders[i].importedEmbed
282 g.decls((*ir.Nodes)(&g.target.Decls), declList)
287 // 4. Run any "later" tasks. Avoid using 'range' so that tasks can
288 // recursively queue further tasks. (Not currently utilized though.)
289 for len(g.laterFuncs) > 0 {
290 fn := g.laterFuncs[0]
291 g.laterFuncs = g.laterFuncs[1:]
296 for _, n := range g.target.Decls {
297 s := fmt.Sprintf("\nafter noder2 %v", n)
302 for _, p := range noders {
303 // Process linkname and cgo pragmas.
306 // Double check for any type-checking inconsistencies. This can be
307 // removed once we're confident in IR generation results.
308 syntax.Crawl(p.file, func(n syntax.Node) bool {
314 if base.Flag.Complete {
315 for _, n := range g.target.Decls {
316 if fn, ok := n.(*ir.Func); ok {
317 if fn.Body == nil && fn.Nname.Sym().Linkname == "" {
318 base.ErrorfAt(fn.Pos(), "missing function body")
324 // Check for unusual case where noder2 encounters a type error that types2
325 // doesn't check for (e.g. notinheap incompatibility).
328 typecheck.DeclareUniverse()
330 // Create any needed instantiations of generic functions and transform
331 // existing and new functions to use those instantiations.
332 BuildInstantiations()
334 // Remove all generic functions from g.target.Decl, since they have been
335 // used for stenciling, but don't compile. Generic functions will already
336 // have been marked for export as appropriate.
338 for i, decl := range g.target.Decls {
339 if decl.Op() != ir.ODCLFUNC || !decl.Type().HasTParam() {
340 g.target.Decls[j] = g.target.Decls[i]
344 g.target.Decls = g.target.Decls[:j]
346 base.Assertf(len(g.laterFuncs) == 0, "still have %d later funcs", len(g.laterFuncs))
349 func (g *irgen) unhandled(what string, p poser) {
350 base.FatalfAt(g.pos(p), "unhandled %s: %T", what, p)
354 // delayTransform returns true if we should delay all transforms, because we are
355 // creating the nodes for a generic function/method.
356 func (g *irgen) delayTransform() bool {
357 return g.topFuncIsGeneric