diff options
| author | David Chase <drchase@google.com> | 2024-11-15 17:08:34 -0500 |
|---|---|---|
| committer | David Chase <drchase@google.com> | 2024-11-19 00:04:51 +0000 |
| commit | 170436c045f1303543e6d0bf8b36fccac57da2cd (patch) | |
| tree | 2c383dfdddacab1d55823ebcecc0282cf5ec2870 /src | |
| parent | b8fe88393b122a06e00163dc464bf8cd14187f4b (diff) | |
| download | go-170436c045f1303543e6d0bf8b36fccac57da2cd.tar.xz | |
cmd/compile: strongly favor closure inlining
This tweaks the inlining cost knob for closures
specifically, they receive a doubled budget. The
rationale for this is that closures have a lot of
"crud" in their IR that will disappear after inlining,
so the standard budget penalizes them unnecessarily.
This is also the cause of these bugs -- looking at the
code involved, these closures "should" be inlineable,
therefore tweak the parameters until behavior matches
expectations. It's not costly in binary size, because
the only-called-from-one-site case is common (especially
for rangefunc iterators).
I can imagine better fixes and I am going to try to
get that done, but this one is small and makes things
better.
Fixes #69411, #69539.
Change-Id: I8a892c40323173a723799e0ddad69dcc2724a8f9
Reviewed-on: https://go-review.googlesource.com/c/go/+/629195
Reviewed-by: Keith Randall <khr@google.com>
Reviewed-by: Keith Randall <khr@golang.org>
Reviewed-by: Robert Griesemer <gri@google.com>
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Diffstat (limited to 'src')
| -rw-r--r-- | src/cmd/cgo/internal/test/callback_windows.go | 5 | ||||
| -rw-r--r-- | src/cmd/compile/internal/inline/inl.go | 7 |
2 files changed, 10 insertions, 2 deletions
diff --git a/src/cmd/cgo/internal/test/callback_windows.go b/src/cmd/cgo/internal/test/callback_windows.go index 77bdfa4dd3..0e2b543a38 100644 --- a/src/cmd/cgo/internal/test/callback_windows.go +++ b/src/cmd/cgo/internal/test/callback_windows.go @@ -69,11 +69,11 @@ func testCallbackCallersSEH(t *testing.T) { want := []string{ "test._Cfunc_backtrace", "test.testCallbackCallersSEH.func1.1", - "test.testCallbackCallersSEH.func1", + // "test.testCallbackCallersSEH.func1", // hidden by inlining "test.goCallback", "test._Cfunc_callback", "test.nestedCall.func1", - "test.nestedCall", + // "test.nestedCall", // hidden by inlining "test.testCallbackCallersSEH", "test.TestCallbackCallersSEH", } @@ -84,6 +84,7 @@ func testCallbackCallersSEH(t *testing.T) { }) got := make([]string, 0, n) for i := 0; i < n; i++ { + // This test is brittle in the face of inliner changes f := runtime.FuncForPC(pc[i] - 1) if f == nil { continue diff --git a/src/cmd/compile/internal/inline/inl.go b/src/cmd/compile/internal/inline/inl.go index 6c0521d1f5..6835b919b6 100644 --- a/src/cmd/compile/internal/inline/inl.go +++ b/src/cmd/compile/internal/inline/inl.go @@ -206,6 +206,9 @@ func inlineBudget(fn *ir.Func, profile *pgoir.Profile, relaxed bool, verbose boo if relaxed { budget += inlheur.BudgetExpansion(inlineMaxBudget) } + if fn.ClosureParent != nil { + budget *= 2 + } return budget } @@ -861,6 +864,10 @@ var InlineCall = func(callerfn *ir.Func, call *ir.CallExpr, fn *ir.Func, inlInde // - whether the inlined function is "hot" according to PGO. func inlineCostOK(n *ir.CallExpr, caller, callee *ir.Func, bigCaller bool) (bool, int32, int32, bool) { maxCost := int32(inlineMaxBudget) + if callee.ClosureParent != nil { + maxCost *= 2 // favor inlining closures + } + if bigCaller { // We use this to restrict inlining into very big functions. // See issue 26546 and 17566. |
