mirror of https://github.com/golang/go.git
cmd/compile: remove x86 arch-specific rules for +2ⁿ multiplication
amd64 and 386 have rules to reduce multiplication by a positive power of two, but a more general reduction (both for positive and negative powers of two) is already performed by generic rules that were added in CL 36323 to replace walkmul (see lines 166:173 in generic.rules). The x86 and amd64 rules are never triggered during all.bash and can be removed, reducing rules duplication. The change also adds a few code generation tests for amd64 and 386. Change-Id: I566d48186643bd722a4c0137fe94e513b8b20e36 Reviewed-on: https://go-review.googlesource.com/68450 Run-TryBot: Alberto Donizetti <alb.donizetti@gmail.com> TryBot-Result: Gobot Gobot <gobot@golang.org> Reviewed-by: Keith Randall <khr@golang.org>
This commit is contained in:
parent
07e36af7d6
commit
03614562ca
|
|
@ -276,17 +276,29 @@ var allAsmTests = []*asmTests{
|
|||
}
|
||||
|
||||
var linuxAMD64Tests = []*asmTest{
|
||||
// multiplication by powers of two
|
||||
{
|
||||
fn: `
|
||||
func f0(x int) int {
|
||||
return x * 64
|
||||
func $(n int) int {
|
||||
return n * 64
|
||||
}
|
||||
`,
|
||||
pos: []string{"\tSHLQ\t\\$6,"},
|
||||
neg: []string{"IMULQ"},
|
||||
},
|
||||
{
|
||||
fn: `
|
||||
func f1(x int) int {
|
||||
func $(n int) int {
|
||||
return -128*n
|
||||
}
|
||||
`,
|
||||
pos: []string{"SHLQ"},
|
||||
neg: []string{"IMULQ"},
|
||||
},
|
||||
|
||||
{
|
||||
fn: `
|
||||
func $(x int) int {
|
||||
return x * 96
|
||||
}
|
||||
`,
|
||||
|
|
@ -1148,6 +1160,26 @@ var linux386Tests = []*asmTest{
|
|||
pos: []string{"\tMOVL\t\\(.*\\)\\(.*\\*1\\),"},
|
||||
},
|
||||
|
||||
// multiplication by powers of two
|
||||
{
|
||||
fn: `
|
||||
func $(n int) int {
|
||||
return 32*n
|
||||
}
|
||||
`,
|
||||
pos: []string{"SHLL"},
|
||||
neg: []string{"IMULL"},
|
||||
},
|
||||
{
|
||||
fn: `
|
||||
func $(n int) int {
|
||||
return -64*n
|
||||
}
|
||||
`,
|
||||
pos: []string{"SHLL"},
|
||||
neg: []string{"IMULL"},
|
||||
},
|
||||
|
||||
// multiplication merging tests
|
||||
{
|
||||
fn: `
|
||||
|
|
|
|||
|
|
@ -539,7 +539,6 @@
|
|||
(MULLconst [41] x) -> (LEAL8 x (LEAL4 <v.Type> x x))
|
||||
(MULLconst [73] x) -> (LEAL8 x (LEAL8 <v.Type> x x))
|
||||
|
||||
(MULLconst [c] x) && isPowerOfTwo(c) -> (SHLLconst [log2(c)] x)
|
||||
(MULLconst [c] x) && isPowerOfTwo(c+1) && c >= 15 -> (SUBL (SHLLconst <v.Type> [log2(c+1)] x) x)
|
||||
(MULLconst [c] x) && isPowerOfTwo(c-1) && c >= 17 -> (LEAL1 (SHLLconst <v.Type> [log2(c-1)] x) x)
|
||||
(MULLconst [c] x) && isPowerOfTwo(c-2) && c >= 34 -> (LEAL2 (SHLLconst <v.Type> [log2(c-2)] x) x)
|
||||
|
|
|
|||
|
|
@ -931,7 +931,6 @@
|
|||
(MULQconst [41] x) -> (LEAQ8 x (LEAQ4 <v.Type> x x))
|
||||
(MULQconst [73] x) -> (LEAQ8 x (LEAQ8 <v.Type> x x))
|
||||
|
||||
(MULQconst [c] x) && isPowerOfTwo(c) -> (SHLQconst [log2(c)] x)
|
||||
(MULQconst [c] x) && isPowerOfTwo(c+1) && c >= 15 -> (SUBQ (SHLQconst <v.Type> [log2(c+1)] x) x)
|
||||
(MULQconst [c] x) && isPowerOfTwo(c-1) && c >= 17 -> (LEAQ1 (SHLQconst <v.Type> [log2(c-1)] x) x)
|
||||
(MULQconst [c] x) && isPowerOfTwo(c-2) && c >= 34 -> (LEAQ2 (SHLQconst <v.Type> [log2(c-2)] x) x)
|
||||
|
|
|
|||
|
|
@ -8543,20 +8543,6 @@ func rewriteValue386_Op386MULLconst_10(v *Value) bool {
|
|||
return true
|
||||
}
|
||||
// match: (MULLconst [c] x)
|
||||
// cond: isPowerOfTwo(c)
|
||||
// result: (SHLLconst [log2(c)] x)
|
||||
for {
|
||||
c := v.AuxInt
|
||||
x := v.Args[0]
|
||||
if !(isPowerOfTwo(c)) {
|
||||
break
|
||||
}
|
||||
v.reset(Op386SHLLconst)
|
||||
v.AuxInt = log2(c)
|
||||
v.AddArg(x)
|
||||
return true
|
||||
}
|
||||
// match: (MULLconst [c] x)
|
||||
// cond: isPowerOfTwo(c+1) && c >= 15
|
||||
// result: (SUBL (SHLLconst <v.Type> [log2(c+1)] x) x)
|
||||
for {
|
||||
|
|
@ -8624,11 +8610,6 @@ func rewriteValue386_Op386MULLconst_10(v *Value) bool {
|
|||
v.AddArg(x)
|
||||
return true
|
||||
}
|
||||
return false
|
||||
}
|
||||
func rewriteValue386_Op386MULLconst_20(v *Value) bool {
|
||||
b := v.Block
|
||||
_ = b
|
||||
// match: (MULLconst [c] x)
|
||||
// cond: isPowerOfTwo(c-8) && c >= 136
|
||||
// result: (LEAL8 (SHLLconst <v.Type> [log2(c-8)] x) x)
|
||||
|
|
@ -8646,6 +8627,11 @@ func rewriteValue386_Op386MULLconst_20(v *Value) bool {
|
|||
v.AddArg(x)
|
||||
return true
|
||||
}
|
||||
return false
|
||||
}
|
||||
func rewriteValue386_Op386MULLconst_20(v *Value) bool {
|
||||
b := v.Block
|
||||
_ = b
|
||||
// match: (MULLconst [c] x)
|
||||
// cond: c%3 == 0 && isPowerOfTwo(c/3)
|
||||
// result: (SHLLconst [log2(c/3)] (LEAL2 <v.Type> x x))
|
||||
|
|
|
|||
|
|
@ -14516,20 +14516,6 @@ func rewriteValueAMD64_OpAMD64MULQconst_10(v *Value) bool {
|
|||
return true
|
||||
}
|
||||
// match: (MULQconst [c] x)
|
||||
// cond: isPowerOfTwo(c)
|
||||
// result: (SHLQconst [log2(c)] x)
|
||||
for {
|
||||
c := v.AuxInt
|
||||
x := v.Args[0]
|
||||
if !(isPowerOfTwo(c)) {
|
||||
break
|
||||
}
|
||||
v.reset(OpAMD64SHLQconst)
|
||||
v.AuxInt = log2(c)
|
||||
v.AddArg(x)
|
||||
return true
|
||||
}
|
||||
// match: (MULQconst [c] x)
|
||||
// cond: isPowerOfTwo(c+1) && c >= 15
|
||||
// result: (SUBQ (SHLQconst <v.Type> [log2(c+1)] x) x)
|
||||
for {
|
||||
|
|
@ -14597,11 +14583,6 @@ func rewriteValueAMD64_OpAMD64MULQconst_10(v *Value) bool {
|
|||
v.AddArg(x)
|
||||
return true
|
||||
}
|
||||
return false
|
||||
}
|
||||
func rewriteValueAMD64_OpAMD64MULQconst_20(v *Value) bool {
|
||||
b := v.Block
|
||||
_ = b
|
||||
// match: (MULQconst [c] x)
|
||||
// cond: isPowerOfTwo(c-8) && c >= 136
|
||||
// result: (LEAQ8 (SHLQconst <v.Type> [log2(c-8)] x) x)
|
||||
|
|
@ -14619,6 +14600,11 @@ func rewriteValueAMD64_OpAMD64MULQconst_20(v *Value) bool {
|
|||
v.AddArg(x)
|
||||
return true
|
||||
}
|
||||
return false
|
||||
}
|
||||
func rewriteValueAMD64_OpAMD64MULQconst_20(v *Value) bool {
|
||||
b := v.Block
|
||||
_ = b
|
||||
// match: (MULQconst [c] x)
|
||||
// cond: c%3 == 0 && isPowerOfTwo(c/3)
|
||||
// result: (SHLQconst [log2(c/3)] (LEAQ2 <v.Type> x x))
|
||||
|
|
|
|||
Loading…
Reference in New Issue