1
0
mirror of https://github.com/golang/go synced 2024-11-26 04:47:57 -07:00

[dev.regabi] cmd/compile: remove Func.ClosureEnter

We can easily compute this on demand.

Passes toolstash -cmp.

Change-Id: I433d8adb2b1615ae05b2764e69904369a59542c5
Reviewed-on: https://go-review.googlesource.com/c/go/+/280994
Trust: Matthew Dempsky <mdempsky@google.com>
Run-TryBot: Matthew Dempsky <mdempsky@google.com>
Reviewed-by: Cuong Manh Le <cuong.manhle.vn@gmail.com>
TryBot-Result: Go Bot <gobot@golang.org>
This commit is contained in:
Matthew Dempsky 2021-01-01 02:14:45 -08:00
parent ece345aa69
commit 9ed1577779
5 changed files with 27 additions and 21 deletions

View File

@ -75,13 +75,6 @@ type Func struct {
// Byval set if they're captured by value. // Byval set if they're captured by value.
ClosureVars []*Name ClosureVars []*Name
// ClosureEnter holds the expressions that the enclosing function
// will use to initialize the closure's free variables. These
// correspond one-to-one with the variables in ClosureVars, and will
// be either an ONAME node (if the variable is captured by value) or
// an OADDR-of-ONAME node (if not).
ClosureEnter Nodes
// Parents records the parent scope of each scope within a // Parents records the parent scope of each scope within a
// function. The root scope (0) has no parent, so the i'th // function. The root scope (0) has no parent, so the i'th
// scope's parent is stored at Parents[i-1]. // scope's parent is stored at Parents[i-1].

View File

@ -20,7 +20,7 @@ func TestSizeof(t *testing.T) {
_32bit uintptr // size on 32bit platforms _32bit uintptr // size on 32bit platforms
_64bit uintptr // size on 64bit platforms _64bit uintptr // size on 64bit platforms
}{ }{
{Func{}, 196, 344}, {Func{}, 184, 320},
{Name{}, 124, 216}, {Name{}, 124, 216},
} }

View File

@ -122,20 +122,17 @@ func CaptureVars(fn *ir.Func) {
} }
out = append(out, v) out = append(out, v)
// type check the & of closed variables outside the closure, // type check closed variables outside the closure,
// so that the outer frame also grabs them and knows they escape. // so that the outer frame also grabs them and knows they escape.
types.CalcSize(v.Type()) Expr(v.Outer)
var outer ir.Node
outer = v.Outer
outermost := v.Defn.(*ir.Name) outermost := v.Defn.(*ir.Name)
// out parameters will be assigned to implicitly upon return. // out parameters will be assigned to implicitly upon return.
if outermost.Class_ != ir.PPARAMOUT && !outermost.Addrtaken() && !outermost.Assigned() && v.Type().Width <= 128 { if outermost.Class_ != ir.PPARAMOUT && !outermost.Addrtaken() && !outermost.Assigned() && v.Type().Size() <= 128 {
v.SetByval(true) v.SetByval(true)
} else { } else {
outermost.SetAddrtaken(true) outermost.SetAddrtaken(true)
outer = NodAddr(outer)
} }
if base.Flag.LowerM > 1 { if base.Flag.LowerM > 1 {
@ -147,11 +144,8 @@ func CaptureVars(fn *ir.Func) {
if v.Byval() { if v.Byval() {
how = "value" how = "value"
} }
base.WarnfAt(v.Pos(), "%v capturing by %s: %v (addr=%v assign=%v width=%d)", name, how, v.Sym(), outermost.Addrtaken(), outermost.Assigned(), int32(v.Type().Width)) base.WarnfAt(v.Pos(), "%v capturing by %s: %v (addr=%v assign=%v width=%d)", name, how, v.Sym(), outermost.Addrtaken(), outermost.Assigned(), v.Type().Size())
} }
outer = Expr(outer)
fn.ClosureEnter.Append(outer)
} }
fn.ClosureVars = out fn.ClosureVars = out

View File

@ -131,7 +131,7 @@ func walkClosure(clo *ir.ClosureExpr, init *ir.Nodes) ir.Node {
clos := ir.NewCompLitExpr(base.Pos, ir.OCOMPLIT, ir.TypeNode(typ).(ir.Ntype), nil) clos := ir.NewCompLitExpr(base.Pos, ir.OCOMPLIT, ir.TypeNode(typ).(ir.Ntype), nil)
clos.SetEsc(clo.Esc()) clos.SetEsc(clo.Esc())
clos.List.Set(append([]ir.Node{ir.NewUnaryExpr(base.Pos, ir.OCFUNC, fn.Nname)}, fn.ClosureEnter...)) clos.List.Set(append([]ir.Node{ir.NewUnaryExpr(base.Pos, ir.OCFUNC, fn.Nname)}, closureArgs(clo)...))
addr := typecheck.NodAddr(clos) addr := typecheck.NodAddr(clos)
addr.SetEsc(clo.Esc()) addr.SetEsc(clo.Esc())
@ -151,6 +151,26 @@ func walkClosure(clo *ir.ClosureExpr, init *ir.Nodes) ir.Node {
return walkExpr(cfn, init) return walkExpr(cfn, init)
} }
// closureArgs returns a slice of expressions that an be used to
// initialize the given closure's free variables. These correspond
// one-to-one with the variables in clo.Func.ClosureVars, and will be
// either an ONAME node (if the variable is captured by value) or an
// OADDR-of-ONAME node (if not).
func closureArgs(clo *ir.ClosureExpr) []ir.Node {
fn := clo.Func
args := make([]ir.Node, len(fn.ClosureVars))
for i, v := range fn.ClosureVars {
var outer ir.Node
outer = v.Outer
if !v.Byval() {
outer = typecheck.NodAddrAt(fn.Pos(), outer)
}
args[i] = typecheck.Expr(outer)
}
return args
}
func walkCallPart(n *ir.SelectorExpr, init *ir.Nodes) ir.Node { func walkCallPart(n *ir.SelectorExpr, init *ir.Nodes) ir.Node {
// Create closure in the form of a composite literal. // Create closure in the form of a composite literal.
// For x.M with receiver (x) type T, the generated code looks like: // For x.M with receiver (x) type T, the generated code looks like:

View File

@ -498,8 +498,7 @@ func walkCall(n *ir.CallExpr, init *ir.Nodes) ir.Node {
// Prepend captured variables to argument list. // Prepend captured variables to argument list.
clo := n.X.(*ir.ClosureExpr) clo := n.X.(*ir.ClosureExpr)
n.Args.Prepend(clo.Func.ClosureEnter...) n.Args.Prepend(closureArgs(clo)...)
clo.Func.ClosureEnter.Set(nil)
// Replace OCLOSURE with ONAME/PFUNC. // Replace OCLOSURE with ONAME/PFUNC.
n.X = clo.Func.Nname n.X = clo.Func.Nname