Skip to content

Commit 22eba6a

Browse files
mdempskygopherbot
authored andcommitted
cmd/compile/internal/ir: remove old variable capture logic
This logic is no longer used, since the removal of the non-unified frontends. Change-Id: I7256d4eb06f0b4e5308bc7c7476e90af9e70b7d8 Reviewed-on: https://go-review.googlesource.com/c/go/+/524215 Reviewed-by: Keith Randall <[email protected]> LUCI-TryBot-Result: Go LUCI <[email protected]> Reviewed-by: Keith Randall <[email protected]> Auto-Submit: Matthew Dempsky <[email protected]>
1 parent fcb75c8 commit 22eba6a

File tree

2 files changed

+5
-147
lines changed

2 files changed

+5
-147
lines changed

src/cmd/compile/internal/ir/name.go

Lines changed: 4 additions & 146 deletions
Original file line numberDiff line numberDiff line change
@@ -47,7 +47,7 @@ type Name struct {
4747
Embed *[]Embed // list of embedded files, for ONAME var
4848

4949
// For a local variable (not param) or extern, the initializing assignment (OAS or OAS2).
50-
// For a closure var, the ONAME node of the outer captured variable.
50+
// For a closure var, the ONAME node of the original (outermost) captured variable.
5151
// For the case-local variables of a type switch, the type switch guard (OTYPESW).
5252
// For a range variable, the range statement (ORANGE)
5353
// For a recv variable in a case of a select statement, the receive assignment (OSELRECV2)
@@ -59,77 +59,9 @@ type Name struct {
5959

6060
Heapaddr *Name // temp holding heap address of param
6161

62-
// ONAME closure linkage
63-
// Consider:
64-
//
65-
// func f() {
66-
// x := 1 // x1
67-
// func() {
68-
// use(x) // x2
69-
// func() {
70-
// use(x) // x3
71-
// --- parser is here ---
72-
// }()
73-
// }()
74-
// }
75-
//
76-
// There is an original declaration of x and then a chain of mentions of x
77-
// leading into the current function. Each time x is mentioned in a new closure,
78-
// we create a variable representing x for use in that specific closure,
79-
// since the way you get to x is different in each closure.
80-
//
81-
// Let's number the specific variables as shown in the code:
82-
// x1 is the original x, x2 is when mentioned in the closure,
83-
// and x3 is when mentioned in the closure in the closure.
84-
//
85-
// We keep these linked (assume N > 1):
86-
//
87-
// - x1.Defn = original declaration statement for x (like most variables)
88-
// - x1.Innermost = current innermost closure x (in this case x3), or nil for none
89-
// - x1.IsClosureVar() = false
90-
//
91-
// - xN.Defn = x1, N > 1
92-
// - xN.IsClosureVar() = true, N > 1
93-
// - x2.Outer = nil
94-
// - xN.Outer = x(N-1), N > 2
95-
//
96-
//
97-
// When we look up x in the symbol table, we always get x1.
98-
// Then we can use x1.Innermost (if not nil) to get the x
99-
// for the innermost known closure function,
100-
// but the first reference in a closure will find either no x1.Innermost
101-
// or an x1.Innermost with .Funcdepth < Funcdepth.
102-
// In that case, a new xN must be created, linked in with:
103-
//
104-
// xN.Defn = x1
105-
// xN.Outer = x1.Innermost
106-
// x1.Innermost = xN
107-
//
108-
// When we finish the function, we'll process its closure variables
109-
// and find xN and pop it off the list using:
110-
//
111-
// x1 := xN.Defn
112-
// x1.Innermost = xN.Outer
113-
//
114-
// We leave x1.Innermost set so that we can still get to the original
115-
// variable quickly. Not shown here, but once we're
116-
// done parsing a function and no longer need xN.Outer for the
117-
// lexical x reference links as described above, funcLit
118-
// recomputes xN.Outer as the semantic x reference link tree,
119-
// even filling in x in intermediate closures that might not
120-
// have mentioned it along the way to inner closures that did.
121-
// See funcLit for details.
122-
//
123-
// During the eventual compilation, then, for closure variables we have:
124-
//
125-
// xN.Defn = original variable
126-
// xN.Outer = variable captured in next outward scope
127-
// to make closure where xN appears
128-
//
129-
// Because of the sharding of pieces of the node, x.Defn means x.Name.Defn
130-
// and x.Innermost/Outer means x.Name.Param.Innermost/Outer.
131-
Innermost *Name
132-
Outer *Name
62+
// Outer points to the immediately enclosing function's copy of this
63+
// closure variable. If not a closure variable, then Outer is nil.
64+
Outer *Name
13365
}
13466

13567
func (n *Name) isExpr() {}
@@ -406,80 +338,6 @@ func NewHiddenParam(pos src.XPos, fn *Func, sym *types.Sym, typ *types.Type) *Na
406338
return NewClosureVar(pos, fn, fake)
407339
}
408340

409-
// CaptureName returns a Name suitable for referring to n from within function
410-
// fn or from the package block if fn is nil. If n is a free variable declared
411-
// within a function that encloses fn, then CaptureName returns the closure
412-
// variable that refers to n within fn, creating it if necessary.
413-
// Otherwise, it simply returns n.
414-
func CaptureName(pos src.XPos, fn *Func, n *Name) *Name {
415-
if n.Op() != ONAME || n.Curfn == nil {
416-
return n // okay to use directly
417-
}
418-
if n.IsClosureVar() {
419-
base.FatalfAt(pos, "misuse of CaptureName on closure variable: %v", n)
420-
}
421-
422-
c := n.Innermost
423-
if c == nil {
424-
c = n
425-
}
426-
if c.Curfn == fn {
427-
return c
428-
}
429-
430-
if fn == nil {
431-
base.FatalfAt(pos, "package-block reference to %v, declared in %v", n, n.Curfn)
432-
}
433-
434-
// Do not have a closure var for the active closure yet; make one.
435-
c = NewClosureVar(pos, fn, c)
436-
437-
// Link into list of active closure variables.
438-
// Popped from list in FinishCaptureNames.
439-
n.Innermost = c
440-
441-
return c
442-
}
443-
444-
// FinishCaptureNames handles any work leftover from calling CaptureName
445-
// earlier. outerfn should be the function that immediately encloses fn.
446-
func FinishCaptureNames(pos src.XPos, outerfn, fn *Func) {
447-
// closure-specific variables are hanging off the
448-
// ordinary ones; see CaptureName above.
449-
// unhook them.
450-
// make the list of pointers for the closure call.
451-
for _, cv := range fn.ClosureVars {
452-
// Unlink from n; see comment above on type Name for these fields.
453-
n := cv.Defn.(*Name)
454-
n.Innermost = cv.Outer
455-
456-
// If the closure usage of n is not dense, we need to make it
457-
// dense by recapturing n within the enclosing function.
458-
//
459-
// That is, suppose we just finished parsing the innermost
460-
// closure f4 in this code:
461-
//
462-
// func f() {
463-
// n := 1
464-
// func() { // f2
465-
// use(n)
466-
// func() { // f3
467-
// func() { // f4
468-
// use(n)
469-
// }()
470-
// }()
471-
// }()
472-
// }
473-
//
474-
// At this point cv.Outer is f2's n; there is no n for f3. To
475-
// construct the closure f4 from within f3, we need to use f3's
476-
// n and in this case we need to create f3's n with CaptureName.
477-
//
478-
// We'll decide later in walk whether to use v directly or &v.
479-
cv.Outer = CaptureName(pos, outerfn, n)
480-
}
481-
}
482-
483341
// SameSource reports whether two nodes refer to the same source
484342
// element.
485343
//

src/cmd/compile/internal/ir/sizeof_test.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -21,7 +21,7 @@ func TestSizeof(t *testing.T) {
2121
_64bit uintptr // size on 64bit platforms
2222
}{
2323
{Func{}, 192, 336},
24-
{Name{}, 100, 176},
24+
{Name{}, 96, 168},
2525
}
2626

2727
for _, tt := range tests {

0 commit comments

Comments
 (0)