Join GitHub today
GitHub is home to over 40 million developers working together to host and review code, manage projects, and build software together.Sign up
cmd/compile: js-wasm builder broke on "isfat" optimization #33916
https://go-review.googlesource.com/c/go/+/179578 changed plive.go's "isfat" function to treat single element arrays and single field structs as single-value objects rather than multi-value objects. The notable thing about this change is it means for things like:
The CL updated test expectations accordingly, but the js-wasm builder seemed to fail on these, as it still considered the struct live in some cases.
The CL has been reverted, but I think it would be good to understand why only js-wasm failed and land the change again.
I see. So in live2.go's bad40, immediately before SSA lowering, we have (v25 is the return value from makemap, and v23 is the mem object returned by it):
On most architectures (I tested amd64 and arm64, and I expect others are the same), this gets lowered to something like:
Critically, plive.go is able to recognize than this MOVQ clobbers
However, on wasm, this gets lowered to:
which I think is roughly comparable to something like:
That is, the address computation is split out separately, and plive.go can't figure out the store is clobbering anything.
I think wasm should switch to support SymOffset for its load and store operations like other GOARCHes.
It seems like the reason this isn't a bigger issue for wasm is that gc/ssa.go inserts OpVarDef instructions around assignments where possible. This issue came up because it introduced new cases where plive.go was able to detect a variable was dead where gc/ssa.go didn't notice.
So an alternative fix here would be to extend gc/ssa.go to incorporate the "isfat" logic for figuring out when it can insert
@mdempsky can you describe it more details?
Looking at SSA output, I see
gc/ssa.go emits OpVarDef when an assignments overwrites the entire variable. Currently it does this when an object is declared, and also immediately before assignments that overwrite the entire object (eg,
The alternative suggestion I was making was that gc/ssa.go should also recognize
I would expect it would just be a tweak to the existing OpVarDef logic in builder.assign.
Hmm, the same as I did, but still no luck, maybe I check the wrong place, let me re-check.
Assinging to 1-element array/1-field struct variable is considered clobbering the whole variable. By emitting OpVarDef in this case, liveness analysis can now know the variable is redefined. Also, the isfat is not necessary anymore, and will be removed in follow up CL. Fixes golang#33916 Change-Id: Iece0d90b05273f333d59d6ee5b12ee7dc71908c2 Reviewed-on: https://go-review.googlesource.com/c/go/+/192979 Run-TryBot: Cuong Manh Le <email@example.com> TryBot-Result: Gobot Gobot <firstname.lastname@example.org> Reviewed-by: Matthew Dempsky <email@example.com>