Skip to content

Commit 0f992b9

Browse files
committed
cmd/compile: not use REGTMP in ZeroRange on ARM64
For async preemption, we will be using REGTMP as a temporary register in injected call on ARM64, which will clobber it. So any code that uses REGTMP is not safe for async preemption. For ZeroRange, which is inserted at the function entry where there is no register live, we could just use a different register and avoid REGTMP. Change-Id: I3db763828df6846908c9843a9912597efb9efcdf Reviewed-on: https://go-review.googlesource.com/c/go/+/203458 Run-TryBot: Cherry Zhang <[email protected]> TryBot-Result: Gobot Gobot <[email protected]> Reviewed-by: Austin Clements <[email protected]>
1 parent 2ff746d commit 0f992b9

File tree

2 files changed

+14
-6
lines changed

2 files changed

+14
-6
lines changed

src/cmd/compile/internal/arm64/ggen.go

Lines changed: 8 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -44,12 +44,16 @@ func zerorange(pp *gc.Progs, p *obj.Prog, off, cnt int64, _ *uint32) *obj.Prog {
4444
p.To.Sym = gc.Duffzero
4545
p.To.Offset = 4 * (64 - cnt/(2*int64(gc.Widthptr)))
4646
} else {
47-
p = pp.Appendpp(p, arm64.AMOVD, obj.TYPE_CONST, 0, 8+off-8, obj.TYPE_REG, arm64.REGTMP, 0)
47+
// Not using REGTMP, so this is async preemptible (async preemption clobbers REGTMP).
48+
// We are at the function entry, where no register is live, so it is okay to clobber
49+
// other registers
50+
const rtmp = arm64.REG_R20
51+
p = pp.Appendpp(p, arm64.AMOVD, obj.TYPE_CONST, 0, 8+off-8, obj.TYPE_REG, rtmp, 0)
4852
p = pp.Appendpp(p, arm64.AMOVD, obj.TYPE_REG, arm64.REGSP, 0, obj.TYPE_REG, arm64.REGRT1, 0)
49-
p = pp.Appendpp(p, arm64.AADD, obj.TYPE_REG, arm64.REGTMP, 0, obj.TYPE_REG, arm64.REGRT1, 0)
53+
p = pp.Appendpp(p, arm64.AADD, obj.TYPE_REG, rtmp, 0, obj.TYPE_REG, arm64.REGRT1, 0)
5054
p.Reg = arm64.REGRT1
51-
p = pp.Appendpp(p, arm64.AMOVD, obj.TYPE_CONST, 0, cnt, obj.TYPE_REG, arm64.REGTMP, 0)
52-
p = pp.Appendpp(p, arm64.AADD, obj.TYPE_REG, arm64.REGTMP, 0, obj.TYPE_REG, arm64.REGRT2, 0)
55+
p = pp.Appendpp(p, arm64.AMOVD, obj.TYPE_CONST, 0, cnt, obj.TYPE_REG, rtmp, 0)
56+
p = pp.Appendpp(p, arm64.AADD, obj.TYPE_REG, rtmp, 0, obj.TYPE_REG, arm64.REGRT2, 0)
5357
p.Reg = arm64.REGRT1
5458
p = pp.Appendpp(p, arm64.AMOVD, obj.TYPE_REG, arm64.REGZERO, 0, obj.TYPE_MEM, arm64.REGRT1, int64(gc.Widthptr))
5559
p.Scond = arm64.C_XPRE

src/cmd/compile/internal/gc/go.go

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -256,8 +256,12 @@ type Arch struct {
256256
Use387 bool // should 386 backend use 387 FP instructions instead of sse2.
257257
SoftFloat bool
258258

259-
PadFrame func(int64) int64
260-
ZeroRange func(*Progs, *obj.Prog, int64, int64, *uint32) *obj.Prog
259+
PadFrame func(int64) int64
260+
261+
// ZeroRange zeroes a range of memory on stack. It is only inserted
262+
// at function entry, and it is ok to clobber registers.
263+
ZeroRange func(*Progs, *obj.Prog, int64, int64, *uint32) *obj.Prog
264+
261265
Ginsnop func(*Progs) *obj.Prog
262266
Ginsnopdefer func(*Progs) *obj.Prog // special ginsnop for deferreturn
263267

0 commit comments

Comments
 (0)