"cmd/compile/internal/base"
"cmd/compile/internal/ir"
"cmd/compile/internal/logopt"
+ "cmd/compile/internal/typecheck"
"cmd/compile/internal/types"
)
n.SetByval(!loc.addrtaken && !loc.reassigned && n.Type().Size() <= 128)
if !n.Byval() {
n.SetAddrtaken(true)
+ if n.Sym().Name == typecheck.LocalDictName {
+ base.FatalfAt(n.Pos(), "dictionary variable not captured by value")
+ }
}
if base.Flag.LowerM > 1 {
fn, formalParams, formalResults := startClosure(pos, outer, typ)
// This is the dictionary we want to use.
- // It may be a constant, or it may be a dictionary acquired from the outer function's dictionary.
+ // It may be a constant, it may be the outer functions's dictionary, or it may be
+ // a subdictionary acquired from the outer function's dictionary.
// For the latter, dictVar is a variable in the outer function's scope, set to the subdictionary
// read from the outer function's dictionary.
var dictVar *ir.Name
newfn.Dcl = append(newfn.Dcl, ldict)
as := ir.NewAssignStmt(x.Pos(), ldict, cdict)
as.SetTypecheck(1)
+ ldict.Defn = as
newfn.Body.Append(as)
// Create inst info for the instantiated closure. The dict
--- /dev/null
+// compile -G=3
+
+// Copyright 2022 The Go Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style
+// license that can be found in the LICENSE file.
+
+package main
+
+type Cache[E comparable] struct {
+ adder func(...E)
+}
+
+func New[E comparable]() *Cache[E] {
+ c := &Cache[E]{}
+
+ c.adder = func(elements ...E) {
+ for _, value := range elements {
+ value := value
+ go func() {
+ println(value)
+ }()
+ }
+ }
+
+ return c
+}
+
+func main() {
+ c := New[string]()
+ c.adder("test")
+}