Commit a509cae9 authored by Matthew Dempsky's avatar Matthew Dempsky

cmd/compile: record InlCost in export data

Previously, we were treating cross-package function calls as free for
inlining budgeting.

In theory, we should be able to recompute InlCost from the
exported/reimported function bodies. However, that process mutates the
structure of the Node AST enough that it doesn't preserve InlCost. To
avoid unexpected issues, just record and restore InlCost in the export
data.

Fixes #19261.

Change-Id: Iac2bc0d32d4f948b64524aca657051f9fc96d92d
Reviewed-on: https://go-review.googlesource.com/70151
Run-TryBot: Matthew Dempsky <mdempsky@google.com>
Reviewed-by: 's avatarRobert Griesemer <gri@golang.org>
parent 1fbeccb1
...@@ -377,6 +377,7 @@ func export(out *bufio.Writer, trace bool) int { ...@@ -377,6 +377,7 @@ func export(out *bufio.Writer, trace bool) int {
p.tracef("\n----\nfunc { %#v }\n", f.Inl) p.tracef("\n----\nfunc { %#v }\n", f.Inl)
} }
p.int(i) p.int(i)
p.int(int(f.InlCost))
p.stmtList(f.Inl) p.stmtList(f.Inl)
if p.trace { if p.trace {
p.tracef("\n") p.tracef("\n")
......
...@@ -187,6 +187,7 @@ func Import(imp *types.Pkg, in *bufio.Reader) { ...@@ -187,6 +187,7 @@ func Import(imp *types.Pkg, in *bufio.Reader) {
// them only for functions with inlineable bodies. funchdr does // them only for functions with inlineable bodies. funchdr does
// parameter renaming which doesn't matter if we don't have a body. // parameter renaming which doesn't matter if we don't have a body.
inlCost := p.int()
if f := p.funcList[i]; f != nil { if f := p.funcList[i]; f != nil {
// function not yet imported - read body and set it // function not yet imported - read body and set it
funchdr(f) funchdr(f)
...@@ -200,6 +201,7 @@ func Import(imp *types.Pkg, in *bufio.Reader) { ...@@ -200,6 +201,7 @@ func Import(imp *types.Pkg, in *bufio.Reader) {
body = []*Node{nod(OEMPTY, nil, nil)} body = []*Node{nod(OEMPTY, nil, nil)}
} }
f.Func.Inl.Set(body) f.Func.Inl.Set(body)
f.Func.InlCost = int32(inlCost)
funcbody() funcbody()
} else { } else {
// function already imported - read body but discard declarations // function already imported - read body but discard declarations
......
// Copyright 2017 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 p
func F() { // ERROR "can inline F"
print(1, 2, 3, 4, 5, 6, 7, 8, 9, 10)
print(1, 2, 3, 4, 5, 6, 7, 8, 9, 10)
print(1, 2, 3, 4, 5, 6, 7, 8, 9, 10)
print(1, 2, 3, 4, 5, 6, 7, 8, 9, 10)
print(1, 2, 3, 4, 5, 6, 7, 8, 9, 10)
print(1, 2, 3, 4, 5, 6, 7, 8, 9, 10)
}
func G() {
F() // ERROR "inlining call to F"
print(1, 2, 3, 4, 5, 6, 7, 8, 9, 10)
print(1, 2, 3, 4, 5, 6, 7, 8, 9, 10)
print(1, 2, 3, 4, 5, 6, 7, 8, 9, 10)
print(1, 2, 3, 4, 5, 6, 7, 8, 9, 10)
print(1, 2, 3, 4, 5, 6, 7, 8, 9, 10)
print(1, 2, 3, 4, 5, 6, 7, 8, 9, 10)
}
// Copyright 2017 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 q
import "./p"
func H() {
p.F() // ERROR "inlining call to p.F"
print(1, 2, 3, 4, 5, 6, 7, 8, 9, 10)
print(1, 2, 3, 4, 5, 6, 7, 8, 9, 10)
print(1, 2, 3, 4, 5, 6, 7, 8, 9, 10)
print(1, 2, 3, 4, 5, 6, 7, 8, 9, 10)
print(1, 2, 3, 4, 5, 6, 7, 8, 9, 10)
print(1, 2, 3, 4, 5, 6, 7, 8, 9, 10)
}
// errorcheckdir -0 -m
// Copyright 2017 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 ignored
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment