]> Cypherpunks repositories - gostls13.git/commit
cmd/compile: compute faulting args before writing args to stack
authorKeith Randall <khr@golang.org>
Tue, 1 Nov 2016 22:28:10 +0000 (15:28 -0700)
committerKeith Randall <khr@golang.org>
Wed, 2 Nov 2016 21:34:12 +0000 (21:34 +0000)
commitcf28e5cc9d51928ae05df0b193edc7e39a28c413
tree747fac03ebcd09c92f04facab3173f101acebc6b
parent688995d1e91fcc36ac33bf34d6303e935d1b0a70
cmd/compile: compute faulting args before writing args to stack

when compiling f(a, b, c), we do something like:
  *(SP+0) = eval(a)
  *(SP+8) = eval(b)
  *(SP+16) = eval(c)
  call f

If one of those evaluations is later determined to unconditionally panic
(say eval(b) in this example), then the call is deadcode eliminated. But
any previous argument write (*(SP+0)=... here) is still around. Becuase
we only compute the size of the outarg area for calls which are still
around at the end of optimization, the space needed for *(SP+0)=v is not
accounted for and thus the outarg area may be too small.

The fix is to make sure that we evaluate any potentially panicing
operation before we write any of the args to the stack. It turns out
that fix is pretty easy, as we already have such a mechanism available
for function args. We just need to extend it to possibly panicing args
as well.

The resulting code (if b and c can panic, but a can't) is:
  tmpb = eval(b)
  *(SP+16) = eval(c)
  *(SP+0) = eval(a)
  *(SP+8) = tmpb
  call f

This change tickled a bug in how we find the arguments for intrinsic
calls, so that latent bug is fixed up as well.

Update #16760.

Change-Id: I0bf5edf370220f82bc036cf2085ecc24f356d166
Reviewed-on: https://go-review.googlesource.com/32551
Reviewed-by: Cherry Zhang <cherryyz@google.com>
src/cmd/compile/internal/gc/ssa.go
src/cmd/compile/internal/gc/subr.go
test/fixedbugs/issue16760.go [new file with mode: 0644]