Commit graph

154 commits

Author SHA1 Message Date
Matthew Dempsky
08bf6d1405 cmd/compile/internal/ir: drop Inl.Body
We don't actually depend on Inl.Body anywhere, except it implicitly
serves to indicate whether Inl.Dcl has been populated. So replace it
with a boolean so we don't need to keep a useless copy of every
inlinable function body in memory.

While here, also add some Fatalfs to make sure there are no unused
local variables. The unified frontend now omits unreachable code
during export data writing, so there shouldn't be unused local
variables.

Also, since unified IR uses the same code/data to construct the
original function as inlined and/or imported functions, the Dcl list
should always be the same, which addresses the real root issue (i.e.,
that export/import could skew the Dcl lists).

Change-Id: I6e3435f3a0352f6efbae787344006efac1891e84
Reviewed-on: https://go-review.googlesource.com/c/go/+/523315
Auto-Submit: Matthew Dempsky <mdempsky@google.com>
Reviewed-by: Cherry Mui <cherryyz@google.com>
Reviewed-by: Cuong Manh Le <cuong.manhle.vn@gmail.com>
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
2023-08-29 20:28:07 +00:00
Cuong Manh Le
079c0441d5 cmd/compile: un-hide closure func in init function
Same as CL 492135, but for init function.

Fixes #62277

Change-Id: If5ff9bc2ce2a73193b1f7ee5f7f14045d1354f56
Reviewed-on: https://go-review.googlesource.com/c/go/+/522956
Run-TryBot: Cuong Manh Le <cuong.manhle.vn@gmail.com>
Reviewed-by: Matthew Dempsky <mdempsky@google.com>
Reviewed-by: Bryan Mills <bcmills@google.com>
TryBot-Result: Gopher Robot <gobot@golang.org>
Auto-Submit: Cuong Manh Le <cuong.manhle.vn@gmail.com>
2023-08-26 01:54:41 +00:00
Matthew Dempsky
88cb17e106 cmd/compile: create "init" function during noding
This CL arranges for package-scope initialization statements to be
constructed directly into their eventual "init" function, so we can
eliminate the roundabout solution of using InitTodoFunc.

While here, somewhat simplify and generalize the logic for outlining
map initialization statements.

Change-Id: I8aff042e6b266f7024de436424ec6711b8b69129
Reviewed-on: https://go-review.googlesource.com/c/go/+/522318
Run-TryBot: Matthew Dempsky <mdempsky@google.com>
Reviewed-by: Than McIntosh <thanm@google.com>
Reviewed-by: Cuong Manh Le <cuong.manhle.vn@gmail.com>
Auto-Submit: Matthew Dempsky <mdempsky@google.com>
TryBot-Result: Gopher Robot <gobot@golang.org>
2023-08-24 23:19:42 +00:00
Matthew Dempsky
f92741b1d8 cmd/compile/internal/noder: elide statically known "if" statements
In go.dev/cl/517775, I moved the frontend's deadcode elimination pass
into unified IR. But I also made a small enhancement: a branch like
"if x || true" is now detected as always taken, so the else branch can
be eliminated.

However, the inliner also has an optimization for delaying the
introduction of the result temporary variables when there's a single
return statement (added in go.dev/cl/266199). Consequently, the
inliner turns "if x || true { return true }; return true" into:

	if x || true {
		~R0 := true
		goto .i0
	}
	.i0:
	// code that uses ~R0

In turn, this confuses phi insertion, because it doesn't recognize
that the "if" statement is always taken, and so ~R0 will always be
initialized.

With this CL, after inlining we instead produce:

	_ = x || true
	~R0 := true
	goto .i0
	.i0:

Fixes #62211.

Change-Id: Ic8a12c9eb85833ee4e5d114f60e6c47817fce538
Reviewed-on: https://go-review.googlesource.com/c/go/+/522096
Reviewed-by: Than McIntosh <thanm@google.com>
Run-TryBot: Matthew Dempsky <mdempsky@google.com>
TryBot-Result: Gopher Robot <gobot@golang.org>
Auto-Submit: Matthew Dempsky <mdempsky@google.com>
Reviewed-by: Cuong Manh Le <cuong.manhle.vn@gmail.com>
2023-08-23 18:01:55 +00:00
Matthew Dempsky
3d15bfaa3e cmd/compile/internal/types: simplify iterating all parameters
The types.RecvsParamsResults, etc. helpers existed to make it "easier"
to iterate over all parameters, or recvs+params, or params+results;
but they end up still being quite clumsy to use due to the design goal
of not allocating temporary slices.

Now that recvs+params+results are stored in a single consecutive slice
anyway, we can just return different subslices and simplify the loops.

Change-Id: I84791b80dc099dfbfbbe6eddbc006135528c23b4
Reviewed-on: https://go-review.googlesource.com/c/go/+/521375
Auto-Submit: Matthew Dempsky <mdempsky@google.com>
TryBot-Result: Gopher Robot <gobot@golang.org>
Reviewed-by: Cuong Manh Le <cuong.manhle.vn@gmail.com>
Run-TryBot: Matthew Dempsky <mdempsky@google.com>
Reviewed-by: Than McIntosh <thanm@google.com>
2023-08-22 20:57:01 +00:00
Matthew Dempsky
14f5eb7f31 cmd/compile/internal/types: overhaul and simplify API
This CL removes a lot of the redundant methods for accessing struct
fields and signature parameters. In particular, users never have to
write ".Slice()" or ".FieldSlice()" anymore; the exported APIs just do
what you want.

Further internal refactorings to follow.

Change-Id: I45212f6772fe16aad39d0e68b82d71b0796e5639
Reviewed-on: https://go-review.googlesource.com/c/go/+/521295
Run-TryBot: Matthew Dempsky <mdempsky@google.com>
Reviewed-by: Cuong Manh Le <cuong.manhle.vn@gmail.com>
TryBot-Result: Gopher Robot <gobot@golang.org>
Reviewed-by: Austin Clements <austin@google.com>
Auto-Submit: Matthew Dempsky <mdempsky@google.com>
2023-08-22 01:53:41 +00:00
Matthew Dempsky
9ac6b00e79 cmd/compile/internal/typecheck: add selector helpers
This CL refactors common patterns for constructing field and method
selector expressions. Notably, XDotField and XDotMethod are now the
only two functions where a SelecterExpr with OXDOT is constructed.

Change-Id: I4c087225d8b295c4a6a92281ffcbcabafe2dc94d
Reviewed-on: https://go-review.googlesource.com/c/go/+/520979
Auto-Submit: Matthew Dempsky <mdempsky@google.com>
Run-TryBot: Matthew Dempsky <mdempsky@google.com>
Reviewed-by: Cuong Manh Le <cuong.manhle.vn@gmail.com>
Reviewed-by: Dmitri Shuralyov <dmitshur@google.com>
TryBot-Result: Gopher Robot <gobot@golang.org>
2023-08-20 05:57:18 +00:00
Matthew Dempsky
a2ec545e0a cmd/compile/internal/typecheck: add NewMethodExpr helper
This CL refactors the common pattern for constructing OMETHEXPR nodes,
which is the most common use of ir.TypeNode currently.

Change-Id: I446a21af97ab5a4bc2f04bbd581c1ede8a5ede60
Reviewed-on: https://go-review.googlesource.com/c/go/+/520978
Run-TryBot: Matthew Dempsky <mdempsky@google.com>
Auto-Submit: Matthew Dempsky <mdempsky@google.com>
Reviewed-by: Dmitri Shuralyov <dmitshur@google.com>
TryBot-Result: Gopher Robot <gobot@golang.org>
Reviewed-by: Cuong Manh Le <cuong.manhle.vn@gmail.com>
2023-08-20 05:56:51 +00:00
Matthew Dempsky
09b03117b0 cmd/compile/internal/ir: remove Ntype
This type used to provide extra type safety around which syntactic
nodes could also represent types, but now the only remaining use is
ir.TypeNode, and it always ends up as an ir.Node anyway. So we might
as well use Node instead.

Change-Id: Ia0842864794365b0e155dc5af154c673ffa2967b
Reviewed-on: https://go-review.googlesource.com/c/go/+/520609
Run-TryBot: Matthew Dempsky <mdempsky@google.com>
TryBot-Result: Gopher Robot <gobot@golang.org>
Reviewed-by: Dmitri Shuralyov <dmitshur@google.com>
Reviewed-by: Cuong Manh Le <cuong.manhle.vn@gmail.com>
Auto-Submit: Matthew Dempsky <mdempsky@google.com>
2023-08-18 22:38:58 +00:00
Matthew Dempsky
89eb6b76ae cmd/compile: remove some uses of ir.CurFunc
This CL updates several frontend passes to stop relying on
ir.CurFunc (at least directly).

Change-Id: I3c3529e81e27fb05d54a828f081f7c7efc31af67
Reviewed-on: https://go-review.googlesource.com/c/go/+/520606
Run-TryBot: Matthew Dempsky <mdempsky@google.com>
Reviewed-by: Cuong Manh Le <cuong.manhle.vn@gmail.com>
TryBot-Result: Gopher Robot <gobot@golang.org>
Reviewed-by: Dmitri Shuralyov <dmitshur@google.com>
Auto-Submit: Matthew Dempsky <mdempsky@google.com>
2023-08-18 22:38:50 +00:00
Matthew Dempsky
7e2e648a2d cmd/compile/internal/typecheck: normalize go/defer statements earlier
Normalizing go/defer statements to always use functions with zero
parameters and zero results was added to escape analysis, because that
was the earliest point at which all three frontends converged. Now
that we only have the unified frontend, we can do it during typecheck,
which is where we perform all other desugaring and normalization
rewrites.

Change-Id: Iebf7679b117fd78b1dffee2974bbf85ebc923b23
Reviewed-on: https://go-review.googlesource.com/c/go/+/520260
Reviewed-by: Cuong Manh Le <cuong.manhle.vn@gmail.com>
Run-TryBot: Matthew Dempsky <mdempsky@google.com>
Auto-Submit: Matthew Dempsky <mdempsky@google.com>
Reviewed-by: Dmitri Shuralyov <dmitshur@google.com>
TryBot-Result: Gopher Robot <gobot@golang.org>
2023-08-17 19:36:58 +00:00
Matthew Dempsky
f4e6815652 cmd/compile/internal/noder: remove inlined closure naming hack
I previously used a clumsy hack to copy Closgen back and forth while
inlining, to handle when an inlined function contains closures, which
need to each be uniquely numbered.

The real solution was to name the closures using r.inlCaller, rather
than r.curfn. This CL adds a helper method to do exactly this.

Change-Id: I510553b5d7a8f6581ea1d21604e834fd6338cb06
Reviewed-on: https://go-review.googlesource.com/c/go/+/520339
Run-TryBot: Matthew Dempsky <mdempsky@google.com>
Auto-Submit: Matthew Dempsky <mdempsky@google.com>
TryBot-Result: Gopher Robot <gobot@golang.org>
Reviewed-by: Dmitri Shuralyov <dmitshur@google.com>
Reviewed-by: Cuong Manh Le <cuong.manhle.vn@gmail.com>
2023-08-17 19:36:29 +00:00
Matthew Dempsky
4e411e7bc4 cmd/compile: cleanup Func construction
This CL moves more common Func-setup logic into ir.NewFunc. In
particular, it now handles constructing the Name and wiring them
together, setting the Typecheck bit, and setting Sym.Func.

Relatedly, this CL also extends typecheck.DeclFunc to append the
function to typecheck.Target.Funcs, so that callers no longer need to
do this.

Change-Id: Ifa0aded8df0517188eb295d0dccc107af85f1e8a
Reviewed-on: https://go-review.googlesource.com/c/go/+/520338
TryBot-Result: Gopher Robot <gobot@golang.org>
Reviewed-by: Cuong Manh Le <cuong.manhle.vn@gmail.com>
Auto-Submit: Matthew Dempsky <mdempsky@google.com>
Reviewed-by: Dmitri Shuralyov <dmitshur@google.com>
Run-TryBot: Matthew Dempsky <mdempsky@google.com>
2023-08-17 19:36:28 +00:00
Matthew Dempsky
5c6fbd2c3e cmd/compile: always construct typechecked closures
This CL extends ir.NewClosureFunc to take the signature type argument,
and to handle naming the closure and adding it to typecheck.Target.

It also removes the code for typechecking OCLOSURE and ODCLFUNC nodes,
by having them always constructed as typechecked. ODCLFUNC node
construction will be further simplified in the followup CL.

Change-Id: Iabde4557d33051ee470a3bc4fd49599490024cba
Reviewed-on: https://go-review.googlesource.com/c/go/+/520337
Run-TryBot: Matthew Dempsky <mdempsky@google.com>
TryBot-Result: Gopher Robot <gobot@golang.org>
Auto-Submit: Matthew Dempsky <mdempsky@google.com>
Reviewed-by: Dmitri Shuralyov <dmitshur@google.com>
Reviewed-by: Cuong Manh Le <cuong.manhle.vn@gmail.com>
2023-08-17 19:36:26 +00:00
Matthew Dempsky
e453971005 cmd/compile/internal/ir: add typ parameter to NewNameAt
Start making progress towards constructing IR with proper types.

Change-Id: Iad32c1cf60f30ceb8e07c31c8871b115570ac3bd
Reviewed-on: https://go-review.googlesource.com/c/go/+/520263
Run-TryBot: Matthew Dempsky <mdempsky@google.com>
TryBot-Result: Gopher Robot <gobot@golang.org>
Auto-Submit: Matthew Dempsky <mdempsky@google.com>
Reviewed-by: Dmitri Shuralyov <dmitshur@google.com>
Reviewed-by: Cuong Manh Le <cuong.manhle.vn@gmail.com>
2023-08-17 19:36:24 +00:00
Matthew Dempsky
3be2176d92 cmd/compile: improve ir.StaticValue and extract ir.StaticCalleeName
This CL extends ir.StaticValue to also work on closure variables.

Also, it extracts the code from escape analysis that's responsible for
determining the static callee of a function. This will be useful when
go/defer statement normalization is moved to typecheck.

Change-Id: I69e1f7fb185658dc9fbfdc69d0f511c84df1d3ac
Reviewed-on: https://go-review.googlesource.com/c/go/+/518959
Reviewed-by: Than McIntosh <thanm@google.com>
Run-TryBot: Matthew Dempsky <mdempsky@google.com>
Auto-Submit: Matthew Dempsky <mdempsky@google.com>
TryBot-Result: Gopher Robot <gobot@golang.org>
2023-08-15 20:43:50 +00:00
Matthew Dempsky
f47cfd6cb5 cmd/compile: simplify asmhdr and plugin exports handling
This CL removes a bunch of obsolete code, which made the overall
possible data flow of the compiler much harder to understand. In
particular, it:

1. Removes typecheck.Declare by inlining its only two remaining uses,
and simplifying them down to just the couple of relevant assignments
for each remaining caller.

2. Renames ir.Package.{Asms,Exports} to {AsmHdrDecls,PluginExports},
respectively, to better describe what they're used for. In particular,
PluginExports now actually holds only the subset of Exports that used
to be confusingly called "ptabs" in package reflectdata.

3. Renames reflectdata.WriteTabs to reflectdata.WritePluginTable, to
make it clearer what it does.

4. Removes the consistency checks on len(Exports) and len(ptabs),
since now it's plainly obvious that only the unified importer ever
appends to PluginExports.

Change-Id: Iedc9d0a4e7648de4e734f7e3e7df302580fed542
Reviewed-on: https://go-review.googlesource.com/c/go/+/518757
Reviewed-by: Keith Randall <khr@google.com>
Auto-Submit: Matthew Dempsky <mdempsky@google.com>
TryBot-Result: Gopher Robot <gobot@golang.org>
Reviewed-by: Keith Randall <khr@golang.org>
Run-TryBot: Matthew Dempsky <mdempsky@google.com>
2023-08-11 20:54:14 +00:00
Matthew Dempsky
e7e5913161 cmd/compile: cleanup ir.Package
Decls used to contain initializer statement for package-level
variables, but now it only contains ir.Funcs. So we might as well
rename it to Funcs and tighten its type to []*ir.Func.

Similarly, Externs always contains *ir.Names, so its type can be
constrained too.

Change-Id: I85b833e2f83d9d3559ab0ef8ab5d8324f4bc37b6
Reviewed-on: https://go-review.googlesource.com/c/go/+/517855
Reviewed-by: Cuong Manh Le <cuong.manhle.vn@gmail.com>
Run-TryBot: Matthew Dempsky <mdempsky@google.com>
Reviewed-by: Keith Randall <khr@golang.org>
Reviewed-by: Keith Randall <khr@google.com>
Auto-Submit: Matthew Dempsky <mdempsky@google.com>
TryBot-Result: Gopher Robot <gobot@golang.org>
2023-08-11 18:12:07 +00:00
Matthew Dempsky
59037ac93a cmd/compile: move early deadcode into unified writer
This CL moves the early deadcode elimination pass into the unified
writer. This allows shrinking the export data, by simplifying
expressions and removing unreachable statements. It also means we
don't need to repeatedly apply deadcode elimination on inlined calls
or instantiated generics.

Change-Id: I19bdb04861e50815fccdab39790f4aaa076121fd
Reviewed-on: https://go-review.googlesource.com/c/go/+/517775
Reviewed-by: Michael Knyszek <mknyszek@google.com>
Reviewed-by: Cuong Manh Le <cuong.manhle.vn@gmail.com>
Auto-Submit: Matthew Dempsky <mdempsky@google.com>
Run-TryBot: Matthew Dempsky <mdempsky@google.com>
Reviewed-by: Than McIntosh <thanm@google.com>
TryBot-Result: Gopher Robot <gobot@golang.org>
2023-08-11 18:03:52 +00:00
Matthew Dempsky
832212df9a cmd/compile: make use of types2.InitOrder
types2 already computes the order that package-level variables need to
be initialized in. Start using it.

Change-Id: Idf2740f963b8146f7c927f57effdbf245f41d355
Reviewed-on: https://go-review.googlesource.com/c/go/+/517617
Reviewed-by: Cuong Manh Le <cuong.manhle.vn@gmail.com>
Run-TryBot: Matthew Dempsky <mdempsky@google.com>
TryBot-Result: Gopher Robot <gobot@golang.org>
Reviewed-by: Michael Knyszek <mknyszek@google.com>
2023-08-11 17:45:02 +00:00
David Chase
fe1daf2e43 cmd/compile: use new for loop semantics for Go 1.22+ compilations
This includes version-dependent support for GOEXPERIMENT and
-d=loopvar, -d=loopvarhash, to allow testing/porting of old code.

Includes tests of downgrade (1.22 -> 1.21) and upgrade (1.21 -> 1.22)
based on //go:build lines (while running a 1.22 build/compiler).

Change-Id: Idd3be61a2b46acec33c7e7edac0924158cc726b4
Reviewed-on: https://go-review.googlesource.com/c/go/+/508819
Run-TryBot: David Chase <drchase@google.com>
Reviewed-by: Russ Cox <rsc@golang.org>
TryBot-Result: Gopher Robot <gobot@golang.org>
2023-08-08 21:20:26 +00:00
Cuong Manh Le
6dce882b3a cmd/compile: scanning closures body when visiting wrapper function
CL 410344 fixed missing method value wrapper, by visiting body of
wrapper function after applying inlining pass.

CL 492017 allow more inlining of functions that construct closures,
which ends up making the wrapper function now inlineable, but can
contain closure nodes that couldn't be inlined. These closures body may
contain OMETHVALUE nodes that we never seen, thus we need to scan
closures body for finding them.

Fixes #60945

Change-Id: Ia1e31420bb172ff87d7321d2da2989ef23e6ebb6
Reviewed-on: https://go-review.googlesource.com/c/go/+/505255
TryBot-Result: Gopher Robot <gobot@golang.org>
Reviewed-by: Than McIntosh <thanm@google.com>
Reviewed-by: Matthew Dempsky <mdempsky@google.com>
Run-TryBot: Cuong Manh Le <cuong.manhle.vn@gmail.com>
Auto-Submit: Cuong Manh Le <cuong.manhle.vn@gmail.com>
2023-06-23 14:29:16 +00:00
Keith Randall
bd3f44e4ff cmd/compile: constant-fold loads from constant dictionaries and types
Retrying the original CL with a small modification. The original CL
did not handle the case of reading an itab out of a dictionary
correctly.  When we read an itab out of a dictionary, we must treat
the type inside that itab as maybe being put in an interface.

Original CL: 486895
Revert CL: 490156

Change-Id: Id2dc1699d184cd8c63dac83986a70b60b4e6cbd7
Reviewed-on: https://go-review.googlesource.com/c/go/+/491495
Reviewed-by: Matthew Dempsky <mdempsky@google.com>
Reviewed-by: Cuong Manh Le <cuong.manhle.vn@gmail.com>
Run-TryBot: Keith Randall <khr@golang.org>
Reviewed-by: Keith Randall <khr@google.com>
TryBot-Result: Gopher Robot <gobot@golang.org>
2023-05-19 18:10:11 +00:00
Matthew Dempsky
7240d7e9e4 cmd/compile/internal/noder: suppress unionType consistency check
In the types1 universe, we only need to represent value types. For
interfaces, this means we only need to worry about pure interfaces. A
pure interface can embed a union type, but the overall union must be
equivalent to "any".

In go.dev/cl/458619, we changed the types1 reader to return "any", but
to incorporate a consistency check to make sure this is valid.
Unfortunately, a pure interface can actually still reference impure
interfaces, and in general this is hard to check precisely without
reimplementing a lot of types2 data structures and logic into types1.

We haven't had any other reports of this check failing since 1.20, so
it seems simplest to just suppress for now.

Fixes #60117.

Change-Id: I5053faafe2d1068c6d438b2193347546bf5330cd
Reviewed-on: https://go-review.googlesource.com/c/go/+/495455
Run-TryBot: Matthew Dempsky <mdempsky@google.com>
Auto-Submit: Matthew Dempsky <mdempsky@google.com>
Reviewed-by: Cuong Manh Le <cuong.manhle.vn@gmail.com>
Reviewed-by: Keith Randall <khr@golang.org>
TryBot-Result: Gopher Robot <gobot@golang.org>
Reviewed-by: Keith Randall <khr@google.com>
2023-05-16 21:34:45 +00:00
Chressie Himpel
f046180890 Revert "cmd/compile: constant-fold loads from constant dictionaries and types"
This reverts CL 486895.

Reason for revert: This breaks internal tests at Google, see b/280035614.

Change-Id: I48772a44f5f6070a7f06b5704e9f9aa272b5f978
Reviewed-on: https://go-review.googlesource.com/c/go/+/490156
TryBot-Result: Gopher Robot <gobot@golang.org>
Reviewed-by: Michael Stapelberg <stapelberg@google.com>
Reviewed-by: Cuong Manh Le <cuong.manhle.vn@gmail.com>
Run-TryBot: Michael Stapelberg <stapelberg@google.com>
Reviewed-by: David Chase <drchase@google.com>
2023-04-28 11:15:01 +00:00
Keith Randall
635839a17a cmd/compile: constant-fold loads from constant dictionaries and types
Update #59591

Change-Id: Id250a7779c5b53776fff73f3e678fec54d92a8e3
Reviewed-on: https://go-review.googlesource.com/c/go/+/486895
Reviewed-by: Cuong Manh Le <cuong.manhle.vn@gmail.com>
Reviewed-by: Dmitri Shuralyov <dmitshur@google.com>
Run-TryBot: Keith Randall <khr@golang.org>
Reviewed-by: Matthew Dempsky <mdempsky@google.com>
Auto-Submit: Keith Randall <khr@golang.org>
TryBot-Result: Gopher Robot <gobot@golang.org>
2023-04-27 21:12:07 +00:00
David Chase
5a7793b7b8 cmd/compile: add flag to FOR/RANGE to preserve loop semantics across inlines
This modifies the loopvar change to be tied to the
package if it is specified that way, and preserves
the change across inlining.

Down the road, this will be triggered (and flow correctly)
if the changed semantics are tied to Go version specified
in go.mod (or rather, for the compiler, by the specified
version for compilation).

Includes tests.

Change-Id: If54e8b6dd23273b86be5ba47838c90d38af9bd1a
Reviewed-on: https://go-review.googlesource.com/c/go/+/463595
TryBot-Result: Gopher Robot <gobot@golang.org>
Run-TryBot: David Chase <drchase@google.com>
Reviewed-by: Matthew Dempsky <mdempsky@google.com>
2023-03-06 18:34:53 +00:00
David Chase
c20d959163 cmd/compile: experimental loop iterator capture semantics change
Adds:
GOEXPERIMENT=loopvar (expected way of invoking)
-d=loopvar={-1,0,1,2,11,12} (for per-package control and/or logging)
-d=loopvarhash=... (for hash debugging)

loopvar=11,12 are for testing, benchmarking, and debugging.

If enabled,for loops of the form `for x,y := range thing`, if x and/or
y are addressed or captured by a closure, are transformed by renaming
x/y to a temporary and prepending an assignment to the body of the
loop x := tmp_x.  This changes the loop semantics by making each
iteration's instance of x be distinct from the others (currently they
are all aliased, and when this matters, it is almost always a bug).

3-range with captured iteration variables are also transformed,
though it is a more complex transformation.

"Optimized" to do a simpler transformation for
3-clause for where the increment is empty.

(Prior optimization of address-taking under Return disabled, because
it was incorrect; returns can have loops for children.  Restored in
a later CL.)

Includes support for -d=loopvarhash=<binary string> intended for use
with hash search and GOCOMPILEDEBUG=loopvarhash=<binary string>
(use `gossahash -e loopvarhash command-that-fails`).

Minor feature upgrades to hash-triggered features; clients can specify
that file-position hashes use only the most-inline position, and/or that
they use only the basenames of source files (not the full directory path).
Most-inlined is the right choice for debugging loop-iteration change
once the semantics are linked to the package across inlining; basename-only
makes it tractable to write tests (which, otherwise, depend on the full
pathname of the source file and thus vary).

Updates #57969.

Change-Id: I180a51a3f8d4173f6210c861f10de23de8a1b1db
Reviewed-on: https://go-review.googlesource.com/c/go/+/411904
Reviewed-by: Matthew Dempsky <mdempsky@google.com>
Run-TryBot: David Chase <drchase@google.com>
TryBot-Result: Gopher Robot <gobot@golang.org>
2023-03-06 18:34:24 +00:00
Evan Phoenix
02411bcd7c all: implement wasmimport directive
Go programs can now use the //go:wasmimport module_name function_name
directive to import functions from the WebAssembly runtime.

For now, the directive is restricted to the runtime and syscall/js
packages.

* Derived from CL 350737
* Original work modified to work with changes to the IR conversion code.
* Modification of CL 350737 changes to fully exist in Unified IR path (emp)
* Original work modified to work with changes to the ABI configuration code.
* Fixes #38248

Co-authored-by: Vedant Roy <vroy101@gmail.com>
Co-authored-by: Richard Musiol <mail@richard-musiol.de>
Co-authored-by: Johan Brandhorst-Satzkorn <johan.brandhorst@gmail.com>
Change-Id: I740719735d91c306ac718a435a78e1ee9686bc16
Reviewed-on: https://go-review.googlesource.com/c/go/+/463018
TryBot-Result: Gopher Robot <gobot@golang.org>
Run-TryBot: Johan Brandhorst-Satzkorn <johan.brandhorst@gmail.com>
Reviewed-by: Matthew Dempsky <mdempsky@google.com>
Reviewed-by: Dmitri Shuralyov <dmitshur@google.com>
Auto-Submit: Johan Brandhorst-Satzkorn <johan.brandhorst@gmail.com>
Reviewed-by: Johan Brandhorst-Satzkorn <johan.brandhorst@gmail.com>
2023-03-02 05:28:55 +00:00
Matthew Dempsky
37a2004b43 cmd/compile: relax overly strict assertion
The assertion here was to make sure the newly constructed and
typechecked expression selected the same receiver-qualified method,
but in the case of anonymous receiver types we can actually end up
with separate types.Field instances corresponding to each types.Type
instance. In that case, the assertion spuriously failed.

The fix here is to relax and assertion and just compare the method's
name and type (including receiver type).

Fixes #58563.

Change-Id: I67d51ddb020e6ed52671473c93fc08f283a40886
Reviewed-on: https://go-review.googlesource.com/c/go/+/471676
Auto-Submit: Matthew Dempsky <mdempsky@google.com>
Run-TryBot: Matthew Dempsky <mdempsky@google.com>
Reviewed-by: Dmitri Shuralyov <dmitshur@google.com>
Reviewed-by: Cuong Manh Le <cuong.manhle.vn@gmail.com>
TryBot-Result: Gopher Robot <gobot@golang.org>
2023-03-01 20:26:10 +00:00
David Chase
6dd20f4f12 cmd/compile: preserve full inlined location for ir.Name locals
This was noticed while testing hash-search debugging
of the loopvar experiment.

The change is incomplete -- it only addresses local
variables, not parameters.  The code to log/search
changes in loop variable semantics depends on this,
so that will be the test.

Change-Id: I0f84ab7696c6cab43486242cacaba6a0bfc45475
Reviewed-on: https://go-review.googlesource.com/c/go/+/464315
Reviewed-by: Matthew Dempsky <mdempsky@google.com>
TryBot-Result: Gopher Robot <gobot@golang.org>
Run-TryBot: David Chase <drchase@google.com>
2023-02-28 19:08:09 +00:00
Matthew Dempsky
fa9efd9171 cmd/compile/internal/noder: correct positions for synthetic closures
When inlining functions that contain function literals, we need to be
careful about position information. The OCLOSURE node should use the
inline-adjusted position, but the ODCLFUNC and its body should use the
original positions.

However, the same problem can arise with certain generic constructs,
which require the compiler to synthesize function literals to insert
dictionary arguments.

go.dev/cl/425395 fixed the issue with user-written function literals
in a somewhat kludgy way; this CL extends the same solution to
synthetic function literals.

This is all quite subtle and the solutions aren't terribly robust, so
longer term it's probably desirable to revisit how we track inlining
context for positions. But for now, this seems to be the least bad
solution, esp. for backporting to 1.20.

Updates #54625.
Fixes #58513.

Change-Id: Icc43a70dbb11a0e665cbc9e6a64ef274ad8253d1
Reviewed-on: https://go-review.googlesource.com/c/go/+/468415
TryBot-Result: Gopher Robot <gobot@golang.org>
Reviewed-by: Cuong Manh Le <cuong.manhle.vn@gmail.com>
Reviewed-by: Than McIntosh <thanm@google.com>
Run-TryBot: Matthew Dempsky <mdempsky@google.com>
2023-02-27 23:07:49 +00:00
Matthew Dempsky
f0b1563535 cmd/compile/internal/types: remove unneeded functionality
This CL removes a handful of features that were only needed for the
pre-unified frontends.

In particular, Type.Pkg was a hack for iexport so that
go/types.Var.Pkg could be precisely populated for struct fields and
signature parameters by gcimporter, but it's no longer necessary with
the unified export data format because we now write export data
directly from types2-supplied type descriptors.

Several other features (e.g., OrigType, implicit interfaces, type
parameters on signatures) are no longer relevant to the unified
frontend, because it only uses types1 to represent instantiated
generic types.

Updates #57410.

Change-Id: I84fd1da5e0b65d2ab91d244a7bb593821ee916e7
Reviewed-on: https://go-review.googlesource.com/c/go/+/458622
Reviewed-by: Keith Randall <khr@google.com>
TryBot-Result: Gopher Robot <gobot@golang.org>
Run-TryBot: Matthew Dempsky <mdempsky@google.com>
Reviewed-by: Keith Randall <khr@golang.org>
2023-01-26 21:56:49 +00:00
Matthew Dempsky
a7de684e1b cmd/compile/internal/noder: stop creating TUNION types
In the types1 universe under the unified frontend, we never need to
worry about type parameter constraints, so we only see pure
interfaces. However, we might still see interfaces that contain union
types, because of interfaces like "interface{ any | int }" (equivalent
to just "any").

We can handle these without needing to actually represent type unions
within types1 by simply mapping any union to "any".

Updates #57410.

Change-Id: I5e4efcf0339edbb01f4035c54fb6fb1f9ddc0c65
Reviewed-on: https://go-review.googlesource.com/c/go/+/458619
Run-TryBot: Matthew Dempsky <mdempsky@google.com>
Reviewed-by: Keith Randall <khr@google.com>
TryBot-Result: Gopher Robot <gobot@golang.org>
Reviewed-by: Keith Randall <khr@golang.org>
2023-01-26 21:43:08 +00:00
Matthew Dempsky
4f467f1082 cmd: remove GOEXPERIMENT=nounified knob
This CL removes the GOEXPERIMENT=nounified knob, and any conditional
statements that depend on that knob. Further CLs to remove unreachable
code follow this one.

Updates #57410.

Change-Id: I39c147e1a83601c73f8316a001705778fee64a91
Reviewed-on: https://go-review.googlesource.com/c/go/+/458615
Run-TryBot: Matthew Dempsky <mdempsky@google.com>
TryBot-Result: Gopher Robot <gobot@golang.org>
Reviewed-by: Cherry Mui <cherryyz@google.com>
2023-01-25 21:16:32 +00:00
Russ Cox
8a27154bcd cmd/dist: make toolchain build reproducible
- Build cmd with CGO_ENABLED=0. Doing so removes the C compiler
  toolchain from the reproducibility perimeter and also results in
  cmd/go and cmd/pprof binaries that are statically linked,
  so that they will run on a wider variety of systems.
  In particular the Linux versions will run on Alpine and NixOS
  without needing a simulation of libc.so.6.

  The potential downside of disabling cgo is that cmd/go and cmd/pprof
  use the pure Go network resolver instead of the host resolver on
  Unix systems. This means they will not be able to use non-DNS
  resolver mechanisms that may be specified in /etc/resolv.conf,
  such as mDNS. Neither program seems likely to need non-DNS names
  like those, however.

  macOS and Windows systems still use the host resolver, which they
  access without cgo.

- Build cmd with -trimpath when building a release.
  Doing so removes $GOPATH from the file name prefixes stored in the
  binary, so that the build directory does not leak into the final artifacts.

- When CC and CXX are empty, do not pick values to hard-code into
  the source tree and binaries. Instead, emit code that makes the
  right decision at runtime. In addition to reproducibility, this
  makes cross-compiled toolchains work better. A macOS toolchain
  cross-compiled on Linux will now correctly look for clang,
  instead of looking for gcc because it was built on Linux.

- Convert \ to / in file names stored in .a files.
  These are converted to / in the final binaries, but the hashes of
  the .a files affect the final build ID of the binaries. Without this
  change, builds of a Windows toolchain on Windows and non-Windows
  machines produce identical binaries except for the input hash part
  of the build ID.

- Due to the conversion of \ to / in .a files, convert back when
  reading inline bodies on Windows to preserve output file names
  in error messages.

Combined, these four changes (along with Go 1.20's removal of
installed pkg/**.a files and conversion of macOS net away from cgo)
make the output of make.bash fully reproducible, even when
cross-compiling: a released macOS toolchain built on Linux or Windows
will contain exactly the same bits as a released macOS toolchain
built on macOS.

The word "released" in the previous sentence is important.
For the build IDs in the binaries to work out the same on
both systems, a VERSION file must exist to provide a consistent
compiler build ID (instead of using a content hash of the binary).

For #24904.
Fixes #57007.

Change-Id: I665e1ef4ff207d6ff469452347dca5bfc81050e6
Reviewed-on: https://go-review.googlesource.com/c/go/+/454836
Reviewed-by: Bryan Mills <bcmills@google.com>
Run-TryBot: Russ Cox <rsc@golang.org>
Auto-Submit: Russ Cox <rsc@golang.org>
TryBot-Result: Gopher Robot <gobot@golang.org>
2023-01-17 23:10:31 +00:00
Matthew Dempsky
9944ba757b cmd/compile: fix transitive inlining of generic functions
If an imported, non-generic function F transitively calls a generic
function G[T], we may need to call CanInline on G[T].

While here, we can also take advantage of the fact that we know G[T]
was already seen and compiled in an imported package, so we don't need
to call InlineCalls or add it to typecheck.Target.Decls. This saves us
from wasting compile time re-creating DUPOK symbols that we know
already exist in the imported package's link objects.

Fixes #56280.

Change-Id: I3336786bee01616ee9f2b18908738e4ca41c8102
Reviewed-on: https://go-review.googlesource.com/c/go/+/443535
Run-TryBot: Matthew Dempsky <mdempsky@google.com>
TryBot-Result: Gopher Robot <gobot@golang.org>
Reviewed-by: David Chase <drchase@google.com>
Auto-Submit: Matthew Dempsky <mdempsky@google.com>
2022-11-08 21:26:09 +00:00
Michael Pratt
204be97d24 cmd/compile/internal/pgo: remove most global state
Since pgo is a new package, it is reasonably straightforward to
encapsulate its state into a non-global object that we pass around,
which will help keep it isolated.

There are no functional changes in this CL, just packaging up the
globals into a new object.

There are two major pieces of cleanup remaining:

1. reflectdata and noder have separate InlineCalls calls for method
   wrappers. The Profile is not plumbed there yet, but this is not a
   regression as the globals were previously set only right around the
   main inlining pass in gc.Main.

2. pgo.ListOfHotCallSites is still global, as it will require more work
   to clean up. It is effectively a local variable in InlinePackage,
   except that it assumes that InlineCalls is immediately preceded by a
   CanInline call for the same function. This is not necessarily true
   due to the recursive nature of CanInline. This also means that some
   InlineCalls calls may be missing the list of hot callsites right now.

For #55022.

Change-Id: Ic1fe41f73df96861c65f8bfeecff89862b367290
Reviewed-on: https://go-review.googlesource.com/c/go/+/446303
Reviewed-by: Cherry Mui <cherryyz@google.com>
TryBot-Result: Gopher Robot <gobot@golang.org>
Run-TryBot: Michael Pratt <mpratt@google.com>
2022-10-31 21:18:33 +00:00
Matthew Dempsky
dfdf55158d cmd/compile/internal/noder: fix type switch case vars package
When naming case variables, the unified frontend was using
typecheck.Lookup, which uses the current package, rather than
localIdent, which uses the package the variable was originally
declared in. When inlining across package boundaries, this could cause
the case variables to be associated with the wrong package.

In practice, I don't believe this has any negative consequences, but
it's inconsistent and triggered an ICE in typecheck.ClosureType, which
expected all captured variables to be declared in the same package.

Easy fix is to ensure case variables are declared in the correct
package by using localIdent.

Fixes #54912.

Change-Id: I7a429c708ad95723f46a67872cb0cf0c53a6a0d6
Reviewed-on: https://go-review.googlesource.com/c/go/+/428918
Run-TryBot: Matthew Dempsky <mdempsky@google.com>
TryBot-Result: Gopher Robot <gobot@golang.org>
Reviewed-by: Cuong Manh Le <cuong.manhle.vn@gmail.com>
Reviewed-by: Benny Siegert <bsiegert@gmail.com>
2022-09-07 17:26:39 +00:00
Matthew Dempsky
9fc09d2ffb cmd/compile/internal/noder: optimize itabs section of runtime dicts
Currently, the itabs section for runtime dictionaries includes its own
redundant *runtime._type pointers for typ and iface, which were
sometimes necessary. This simplified the initial implementation, but
is a little wasteful of space when the same type or interface appeared
across multiple (typ, iface) pairs.

This CL instead reuses the pointers from the rtypes section.

Change-Id: I48448515c319c0403c1a8e7706794d443176f0a4
Reviewed-on: https://go-review.googlesource.com/c/go/+/427754
Reviewed-by: Cuong Manh Le <cuong.manhle.vn@gmail.com>
Run-TryBot: Matthew Dempsky <mdempsky@google.com>
Reviewed-by: Keith Randall <khr@google.com>
TryBot-Result: Gopher Robot <gobot@golang.org>
Reviewed-by: Keith Randall <khr@golang.org>
2022-09-03 06:26:16 +00:00
Matthew Dempsky
34f0029a85 cmd/compile/internal/noder: allow OCONVNOP for identical iface conversions
In go.dev/cl/421821, I included a hack to force OCONVNOP back to
OCONVIFACE for conversions involving shape types and non-empty
interfaces. The comment correctly noted that this was only needed for
conversions between non-identical types, but the code was conservative
and applied to even conversions between identical types.

This CL adds an extra bool to record whether the conversion is between
identical types, so we can keep OCONVNOP instead of forcing back to
OCONVIFACE. This has a small improvement to generated code, because we
no longer need a convI2I call (as demonstrated by codegen/ifaces.go).

But more usefully, this is relevant to pruning unnecessary itab slots
in runtime dictionaries (next CL).

Change-Id: I94f89e961cd26629b925037fea58d283140766ff
Reviewed-on: https://go-review.googlesource.com/c/go/+/427678
Reviewed-by: Keith Randall <khr@golang.org>
Run-TryBot: Matthew Dempsky <mdempsky@google.com>
Reviewed-by: Cuong Manh Le <cuong.manhle.vn@gmail.com>
Reviewed-by: Keith Randall <khr@google.com>
TryBot-Result: Gopher Robot <gobot@golang.org>
2022-09-02 18:26:02 +00:00
Cuong Manh Le
8bbb362f4c cmd/compile: remove go:notinheap pragma
Updates #46731

Change-Id: I247fa9c7ca97feb9053665da7ff56e7f5b571f74
Reviewed-on: https://go-review.googlesource.com/c/go/+/422815
Reviewed-by: Keith Randall <khr@golang.org>
Run-TryBot: Cuong Manh Le <cuong.manhle.vn@gmail.com>
Reviewed-by: David Chase <drchase@google.com>
TryBot-Result: Gopher Robot <gobot@golang.org>
Reviewed-by: Joedian Reid <joedian@golang.org>
2022-09-02 18:24:59 +00:00
Matthew Dempsky
e4b624eae5 cmd/compile: use HaveInlineBody for unified IR
In go.dev/cl/419674 I added a mechanism to the inliner to allow
inlining to fail gracefully when a function body is missing, but I
missed we already have a mechanism for that: typecheck.HaveInlineBody.

This CL makes it overridable so that unified IR can plug in its
appropriate logic, like it does with the logic for building the
ir.InlinedCallExpr node.

While here, rename inline.NewInline to inline.InlineCall, because the
name "NewInline" is now a misnomer since we initialize it to oldInline
(now named oldInlineCall).

Change-Id: I4e65618d3725919f69e6f43cf409699d20fb797c
Reviewed-on: https://go-review.googlesource.com/c/go/+/427234
TryBot-Result: Gopher Robot <gobot@golang.org>
Reviewed-by: David Chase <drchase@google.com>
Run-TryBot: Matthew Dempsky <mdempsky@google.com>
Auto-Submit: Matthew Dempsky <mdempsky@google.com>
2022-08-31 22:22:43 +00:00
Cuong Manh Le
ddc93a536f cmd/compile: fix unified IR shapifying recursive instantiated types
Shape-based stenciling in unified IR is done by converting type argument
to its underlying type. So it agressively check that type argument is
not a TFORW. However, for recursive instantiated type argument, it may
still be a TFORW when shapifying happens. Thus the assertion failed,
causing the compiler crashing.

To fix it, just allow fully instantiated type when shapifying.

Fixes #54512
Fixes #54722

Change-Id: I527e3fd696388c8a37454e738f0324f0c2ec16cb
Reviewed-on: https://go-review.googlesource.com/c/go/+/426335
TryBot-Result: Gopher Robot <gobot@golang.org>
Auto-Submit: Cuong Manh Le <cuong.manhle.vn@gmail.com>
Run-TryBot: Cuong Manh Le <cuong.manhle.vn@gmail.com>
Reviewed-by: Heschi Kreinick <heschi@google.com>
Reviewed-by: Matthew Dempsky <mdempsky@google.com>
2022-08-30 17:23:27 +00:00
Matthew Dempsky
6a801d3082 cmd/compile/internal/noder: fix inlined function literal positions
When inlining function calls, we rewrite the position information on
all of the nodes to keep track of the inlining context. This is
necessary so that at runtime, we can synthesize additional stack
frames so that the inlining is transparent to the user.

However, for function literals, we *don't* want to apply this
rewriting to the underlying function. Because within the function
literal (when it's not itself inlined), the inlining context (if any)
will have already be available at the caller PC instead.

Unified IR was already getting this right in the case of user-written
statements within the function literal, which is what the unit test
for #46234 tested. However, it was still using inline-adjusted
positions for the function declaration and its parameters, which
occasionally end up getting used for generated code (e.g., loading
captured values from the closure record).

I've manually verified that this fixes the hang in
https://go.dev/play/p/avQ0qgRzOgt, and spot-checked the
-d=pctab=pctoinline output for kube-apiserver and kubelet and they
seem better.

However, I'm still working on a more robust test for this (hence
"Updates" not "Fixes") and internal assertions to verify that we're
emitting correct inline trees. In particular, there are still other
cases (even in the non-unified frontend) where we're producing
corrupt (but at least acyclic) inline trees.

Updates #54625.

Change-Id: Iacfd2e1eb06ae8dc299c0679f377461d3d46c15a
Reviewed-on: https://go-review.googlesource.com/c/go/+/425395
Run-TryBot: Matthew Dempsky <mdempsky@google.com>
Auto-Submit: Matthew Dempsky <mdempsky@google.com>
Reviewed-by: Cuong Manh Le <cuong.manhle.vn@gmail.com>
TryBot-Result: Gopher Robot <gobot@golang.org>
Reviewed-by: David Chase <drchase@google.com>
2022-08-25 18:46:22 +00:00
Matthew Dempsky
6985ab27df cmd/compile: fix unified IR's pointer-shaping
In CL 424734, I implemented pointer shaping for unified IR. Evidently
though, we didn't have any test cases that check that uses of
pointer-shaped expressions were handled correctly.

In the reported test case, the struct field "children items[*node[T]]"
gets shaped to "children items[go.shape.*uint8]" (underlying type
"[]go.shape.*uint8"); and so the expression "n.children[i]" has type
"go.shape.*uint8" and the ".items" field selection expression fails.

The fix implemented in this CL is that any expression of derived type
now gets an explicit "reshape" operation applied to it, to ensure it
has the appropriate type for its context. E.g., the "n.children[i]"
OINDEX expression above gets "reshaped" from "go.shape.*uint8" to
"*node[go.shape.int]", allowing the field selection to succeed.

This CL also adds a "-d=reshape" compiler debugging flag, because I
anticipate debugging reshaping operations will be something to come up
again in the future.

Fixes #54535.

Change-Id: Id847bd8f51300d2491d679505ee4d2e974ca972a
Reviewed-on: https://go-review.googlesource.com/c/go/+/424936
Reviewed-by: David Chase <drchase@google.com>
Reviewed-by: hopehook <hopehook@qq.com>
Reviewed-by: Cuong Manh Le <cuong.manhle.vn@gmail.com>
Run-TryBot: Matthew Dempsky <mdempsky@google.com>
TryBot-Result: Gopher Robot <gobot@golang.org>
2022-08-23 18:14:10 +00:00
Matthew Dempsky
aa6a7fa775 cmd/compile: fix reflect naming of local generic types
To disambiguate local types, we append a "·N" suffix to their name and
then trim it off again when producing their runtime type descriptors.

However, if a local type is generic, then we were further appending
the type arguments after this suffix, and the code in types/fmt.go
responsible for trimming didn't know to handle this.

We could extend the types/fmt.go code to look for the "·N" suffix
elsewhere in the type name, but this is risky because it could
legitimately (albeit unlikely) appear in struct field tags.

Instead, the most robust solution is to just change the mangling logic
to keep the "·N" suffix at the end, where types/fmt.go can easily and
reliably trim it.

Note: the "·N" suffix is still visible within the type arguments
list (e.g., the "·3" suffixes in nested.out), because we currently use
the link strings in the type arguments list.

Fixes #54456.

Change-Id: Ie9beaf7e5330982f539bff57b8d48868a3674a37
Reviewed-on: https://go-review.googlesource.com/c/go/+/424901
TryBot-Result: Gopher Robot <gobot@golang.org>
Run-TryBot: Matthew Dempsky <mdempsky@google.com>
Reviewed-by: Cuong Manh Le <cuong.manhle.vn@gmail.com>
Reviewed-by: Than McIntosh <thanm@google.com>
2022-08-23 18:13:48 +00:00
Matthew Dempsky
07cf24bdfe cmd/compile/internal/noder: set ir.Name.DictIndex for unified IR
For local variables of derived type, Delve relies on ir.Name.DictIndex
being set to the type's rtype index within the function's dictionary.
This CL implements that functionality within unified IR.

Manually double checked that Delve behaves correctly, at least as far
as I can tell from casual use. Specifically, I confirmed that running
the test program from TestDictIndex, stepping into testfn, and then
running `print mapvar` prints `map[int]main.CustomInt []`, which
matches the behavior under GOEXPERIMENT=nounified. (Also compare that
when ir.Name.DictIndex is *not* set by unified IR, `print mapvar`
instead prints `map[int]go.shape.int []`.)

Fixes #54514.

Change-Id: I90d443945895abfba04dc018f15e00217930091c
Reviewed-on: https://go-review.googlesource.com/c/go/+/424735
Reviewed-by: Cuong Manh Le <cuong.manhle.vn@gmail.com>
Reviewed-by: Keith Randall <khr@golang.org>
Run-TryBot: Matthew Dempsky <mdempsky@google.com>
Reviewed-by: Keith Randall <khr@google.com>
TryBot-Result: Gopher Robot <gobot@golang.org>
2022-08-18 17:26:17 +00:00
Matthew Dempsky
b23d469e85 cmd/compile/internal/noder: pointer shaping for unified IR
This CL implements pointer shaping in unified IR, corresponding to the
existing pointer shaping implemented in the non-unified frontend.

For example, if `func F[T any]` is instantiated as both `F[*int]` and
`F[*string]`, we'll now generate a single `F[go.shape.*uint8]` shaped
function that can be used by both.

Fixes #54513.

Change-Id: I2cef5ae411919e6dc5bcb3cac912abecb4cd5218
Reviewed-on: https://go-review.googlesource.com/c/go/+/424734
Run-TryBot: Matthew Dempsky <mdempsky@google.com>
Reviewed-by: Keith Randall <khr@golang.org>
TryBot-Result: Gopher Robot <gobot@golang.org>
Reviewed-by: Keith Randall <khr@google.com>
Reviewed-by: Cuong Manh Le <cuong.manhle.vn@gmail.com>
2022-08-18 17:26:10 +00:00
Matthew Dempsky
38edd9bd8d cmd/compile/internal/noder: shape-based stenciling for unified IR
This CL switches unified IR to use shape-based stenciling with runtime
dictionaries, like the existing non-unified frontend. Specifically,
when instantiating generic functions and types `X[T]`, we now also
instantiated shaped variants `X[shapify(T)]` that can be shared by
`T`'s with common underlying types.

For example, for generic function `F`, `F[int](args...)` will be
rewritten to `F[go.shape.int](&.dict.F[int], args...)`.

For generic type `T` with method `M` and value `t` of type `T[int]`,
`t.M(args...)` will be rewritten to `T[go.shape.int].M(t,
&.dict.T[int], args...)`.

Two notable distinctions from the non-unified frontend:

1. For simplicity, currently shaping is limited to simply converting
type arguments to their underlying type. Subsequent CLs will implement
more aggressive shaping.

2. For generic types, a single dictionary is generated to be shared by
all methods, rather than separate dictionaries for each method. I
originally went with this design because I have an idea of changing
interface calls to pass the itab pointer via the closure
register (which should have zero overhead), and then the interface
wrappers for generic methods could use the *runtime.itab to find the
runtime dictionary that corresponds to the dynamic type. This would
allow emitting fewer method wrappers.

However, this choice does have the consequence that currently even if
a method is unused and its code is pruned by the linker, it may have
produced runtime dictionary entries that need to be kept alive anyway.

I'm open to changing this to generate per-method dictionaries, though
this would require changing the unified IR export data format; so it
would be best to make this decision before Go 1.20.

The other option is making the linker smarter about pruning unneeded
dictionary entries, like how it already prunes itab entries. For
example, the runtime dictionary for `T[int]` could have a `R_DICTTYPE`
meta-relocation against symbol `.dicttype.T[go.shape.int]` that
declares it's a dictionary associated with that type; and then each
method on `T[go.shape.T]` could have `R_DICTUSE` meta-relocations
against `.dicttype.T[go.shape.T]+offset` indicating which fields
within dictionaries of that type need to be preserved.

Change-Id: I369580b1d93d19640a4b5ecada4f6231adcce3fd
Reviewed-on: https://go-review.googlesource.com/c/go/+/421821
Reviewed-by: David Chase <drchase@google.com>
Reviewed-by: Keith Randall <khr@golang.org>
Run-TryBot: Matthew Dempsky <mdempsky@google.com>
Reviewed-by: Cuong Manh Le <cuong.manhle.vn@gmail.com>
TryBot-Result: Gopher Robot <gobot@golang.org>
2022-08-18 13:16:21 +00:00