]> Cypherpunks repositories - gostls13.git/commitdiff
[dev.regabi] cmd/compile: use ClosureVars for method value wrappers
authorMatthew Dempsky <mdempsky@google.com>
Mon, 4 Jan 2021 10:24:48 +0000 (02:24 -0800)
committerMatthew Dempsky <mdempsky@google.com>
Sun, 10 Jan 2021 08:02:16 +0000 (08:02 +0000)
Similar to with regular closures, we can change method value wrappers
to use ClosureVars and allow SSA construction to take care of wiring
it up appropriately.

Change-Id: I05c0b1bcec4e24305324755df35b7bc5b8a6ce7a
Reviewed-on: https://go-review.googlesource.com/c/go/+/281353
Run-TryBot: Matthew Dempsky <mdempsky@google.com>
TryBot-Result: Go Bot <gobot@golang.org>
Trust: Matthew Dempsky <mdempsky@google.com>
Reviewed-by: Keith Randall <khr@golang.org>
src/cmd/compile/internal/escape/escape.go
src/cmd/compile/internal/ir/name.go
src/cmd/compile/internal/typecheck/func.go

index 5df82d8cdc5648bd6eb5ad743ab8b81724cd3d80..9b9b8f6a5870c0b4144c94a3bf753afdc65a55e3 100644 (file)
@@ -583,6 +583,9 @@ func (e *escape) exprSkipInit(k hole, n ir.Node) {
                if n.Class == ir.PFUNC || n.Class == ir.PEXTERN {
                        return
                }
+               if n.IsClosureVar() && n.Defn == nil {
+                       return // ".this" from method value wrapper
+               }
                e.flow(k, e.oldLoc(n))
 
        case ir.ONAMEOFFSET:
index a51cf79929e466a75975bc91f205bd11d15cac65..cfb481e31cd1f5dafab5a53e7f4a16c1cd963aba 100644 (file)
@@ -264,7 +264,7 @@ const (
        nameNeedzero              // if it contains pointers, needs to be zeroed on function entry
        nameAutoTemp              // is the variable a temporary (implies no dwarf info. reset if escapes to heap)
        nameUsed                  // for variable declared and not used error
-       nameIsClosureVar          // PAUTOHEAP closure pseudo-variable; original at n.Name.Defn
+       nameIsClosureVar          // PAUTOHEAP closure pseudo-variable; original (if any) at n.Defn
        nameIsOutputParamHeapAddr // pointer to a result parameter's heap copy
        nameAddrtaken             // address taken, even if not moved to heap
        nameInlFormal             // PAUTO created by inliner, derived from callee formal
@@ -332,7 +332,7 @@ func (n *Name) SetVal(v constant.Value) {
 // it appears in the function that immediately contains the
 // declaration. Otherwise, Canonical simply returns n itself.
 func (n *Name) Canonical() *Name {
-       if n.IsClosureVar() {
+       if n.IsClosureVar() && n.Defn != nil {
                n = n.Defn.(*Name)
        }
        return n
index 8789395ffbd981a03f90702f307cdcd533da1fc1..12762f7ee8f55b2224a15cf3505a58b39c640a71 100644 (file)
@@ -246,29 +246,26 @@ func MethodValueWrapper(dot *ir.SelectorExpr) *ir.Func {
        fn.SetWrapper(true)
 
        // Declare and initialize variable holding receiver.
-       cr := ir.NewClosureRead(rcvrtype, types.Rnd(int64(types.PtrSize), int64(rcvrtype.Align)))
-       var ptr *ir.Name
-       var body []ir.Node
-       if rcvrtype.IsPtr() || rcvrtype.IsInterface() {
-               ptr = Temp(rcvrtype)
-               body = append(body, ir.NewAssignStmt(base.Pos, ptr, cr))
-       } else {
-               ptr = Temp(types.NewPtr(rcvrtype))
-               body = append(body, ir.NewAssignStmt(base.Pos, ptr, NodAddr(cr)))
-       }
+       ptr := ir.NewNameAt(base.Pos, Lookup(".this"))
+       ptr.Class = ir.PAUTOHEAP
+       ptr.SetType(rcvrtype)
+       ptr.Curfn = fn
+       ptr.SetIsClosureVar(true)
+       ptr.SetByval(true)
+       fn.ClosureVars = append(fn.ClosureVars, ptr)
 
        call := ir.NewCallExpr(base.Pos, ir.OCALL, ir.NewSelectorExpr(base.Pos, ir.OXDOT, ptr, meth), nil)
        call.Args = ir.ParamNames(tfn.Type())
        call.IsDDD = tfn.Type().IsVariadic()
+
+       var body ir.Node = call
        if t0.NumResults() != 0 {
                ret := ir.NewReturnStmt(base.Pos, nil)
                ret.Results = []ir.Node{call}
-               body = append(body, ret)
-       } else {
-               body = append(body, call)
+               body = ret
        }
 
-       fn.Body = body
+       fn.Body = []ir.Node{body}
        FinishFuncBody()
 
        Func(fn)