cmd/compile/internal/amd64: simplify code generation for signed division

The same switch statement handles code generation for signed division of
words, double words and quad words. Rather than using multiple switch
statements to select the appropriate instructions, determine all of the
correctly sized operands up front, then use them as needed.

Updates #59089

Change-Id: I2b7567c8e0ecb9904c37607332538c95b0521dca
Reviewed-on: https://go-review.googlesource.com/c/go/+/482657
Run-TryBot: Joel Sing <joel@sing.id.au>
Reviewed-by: Keith Randall <khr@google.com>
Reviewed-by: Michael Knyszek <mknyszek@google.com>
Reviewed-by: Keith Randall <khr@golang.org>
TryBot-Result: Gopher Robot <gobot@golang.org>
This commit is contained in:
Joel Sing 2023-04-06 06:11:10 +10:00
parent 231f290e51
commit 2a41dbf13c

View file

@ -338,18 +338,20 @@ func ssaGenValue(s *ssagen.State, v *ssa.Value) {
r := v.Args[1].Reg() r := v.Args[1].Reg()
var j1 *obj.Prog var j1 *obj.Prog
var opCMP, opNEG, opSXD obj.As
switch v.Op {
case ssa.OpAMD64DIVQ:
opCMP, opNEG, opSXD = x86.ACMPQ, x86.ANEGQ, x86.ACQO
case ssa.OpAMD64DIVL:
opCMP, opNEG, opSXD = x86.ACMPL, x86.ANEGL, x86.ACDQ
case ssa.OpAMD64DIVW:
opCMP, opNEG, opSXD = x86.ACMPW, x86.ANEGW, x86.ACWD
}
// CPU faults upon signed overflow, which occurs when the most // CPU faults upon signed overflow, which occurs when the most
// negative int is divided by -1. Handle divide by -1 as a special case. // negative int is divided by -1. Handle divide by -1 as a special case.
if ssa.DivisionNeedsFixUp(v) { if ssa.DivisionNeedsFixUp(v) {
var c *obj.Prog c := s.Prog(opCMP)
switch v.Op {
case ssa.OpAMD64DIVQ:
c = s.Prog(x86.ACMPQ)
case ssa.OpAMD64DIVL:
c = s.Prog(x86.ACMPL)
case ssa.OpAMD64DIVW:
c = s.Prog(x86.ACMPW)
}
c.From.Type = obj.TYPE_REG c.From.Type = obj.TYPE_REG
c.From.Reg = r c.From.Reg = r
c.To.Type = obj.TYPE_CONST c.To.Type = obj.TYPE_CONST
@ -358,17 +360,8 @@ func ssaGenValue(s *ssagen.State, v *ssa.Value) {
j1.To.Type = obj.TYPE_BRANCH j1.To.Type = obj.TYPE_BRANCH
} }
// Sign extend dividend. // Sign extend dividend and perform division.
switch v.Op { s.Prog(opSXD)
case ssa.OpAMD64DIVQ:
s.Prog(x86.ACQO)
case ssa.OpAMD64DIVL:
s.Prog(x86.ACDQ)
case ssa.OpAMD64DIVW:
s.Prog(x86.ACWD)
}
// Issue divide.
p := s.Prog(v.Op.Asm()) p := s.Prog(v.Op.Asm())
p.From.Type = obj.TYPE_REG p.From.Type = obj.TYPE_REG
p.From.Reg = r p.From.Reg = r
@ -380,15 +373,7 @@ func ssaGenValue(s *ssagen.State, v *ssa.Value) {
// Issue -1 fixup code. // Issue -1 fixup code.
// n / -1 = -n // n / -1 = -n
var n1 *obj.Prog n1 := s.Prog(opNEG)
switch v.Op {
case ssa.OpAMD64DIVQ:
n1 = s.Prog(x86.ANEGQ)
case ssa.OpAMD64DIVL:
n1 = s.Prog(x86.ANEGL)
case ssa.OpAMD64DIVW:
n1 = s.Prog(x86.ANEGW)
}
n1.To.Type = obj.TYPE_REG n1.To.Type = obj.TYPE_REG
n1.To.Reg = x86.REG_AX n1.To.Reg = x86.REG_AX