From 3449b4970cdd780b10aef0e6b6cffe81ff962423 Mon Sep 17 00:00:00 2001 From: David Chase Date: Thu, 6 Apr 2023 14:42:53 -0400 Subject: [PATCH] [release-branch.go1.20] cmd/compile: remove broken LEA "optimization" CL 440035 added rewrite rules to simplify "costly" LEA instructions, but the types in the rewrites were wrong and the code would go bad if the wrong-typed register was spilled. CL 482536 attempted to fix this by correcting the type in the rewrite, but that "fix" broke something on windows-amd64-race. Instead / for-now, remove the offending rewrite rules. Updates #21735. Updates #59432. Fixes #59468. Change-Id: I0497c42db414f2055e1378e0a53e2bceee9cd5d9 Reviewed-on: https://go-review.googlesource.com/c/go/+/482820 Run-TryBot: David Chase Reviewed-by: Cherry Mui TryBot-Result: Gopher Robot (cherry picked from commit 6a97a60b4b80dfa9db91200c054d734e18dda115) Reviewed-on: https://go-review.googlesource.com/c/go/+/482164 Auto-Submit: Dmitri Shuralyov Reviewed-by: Keith Randall Reviewed-by: Keith Randall --- .../internal/ssa/_gen/AMD64latelower.rules | 8 - .../internal/ssa/rewriteAMD64latelower.go | 393 ------------------ 2 files changed, 401 deletions(-) diff --git a/src/cmd/compile/internal/ssa/_gen/AMD64latelower.rules b/src/cmd/compile/internal/ssa/_gen/AMD64latelower.rules index bcf453128aadf5..a1e63d6249ac8a 100644 --- a/src/cmd/compile/internal/ssa/_gen/AMD64latelower.rules +++ b/src/cmd/compile/internal/ssa/_gen/AMD64latelower.rules @@ -2,14 +2,6 @@ // Use of this source code is governed by a BSD-style // license that can be found in the LICENSE file. -// split 3 operand LEA. -// Note: Don't split pointer computations in order to avoid invalid pointers. -(LEA(Q|L|W)1 [c] {s} x y) && isPtr(x.Type) && c != 0 && s == nil => (ADD(Q|L|L) x (ADD(Q|L|L)const [c] y)) -(LEA(Q|L|W)1 [c] {s} x y) && !isPtr(x.Type) && c != 0 && s == nil => (ADD(Q|L|L) y (ADD(Q|L|L)const [c] x)) -(LEA(Q|L|W)2 [c] {s} x y) && !isPtr(t) && c != 0 && s == nil => (ADD(Q|L|L)const [c] (LEA(Q|L|W)2 x y)) -(LEA(Q|L|W)4 [c] {s} x y) && !isPtr(t) && c != 0 && s == nil => (ADD(Q|L|L)const [c] (LEA(Q|L|W)4 x y)) -(LEA(Q|L|W)8 [c] {s} x y) && !isPtr(t) && c != 0 && s == nil => (ADD(Q|L|L)const [c] (LEA(Q|L|W)8 x y)) - // Prefer SARX/SHLX/SHRX instruction because it has less register restriction on the shift input. (SAR(Q|L) x y) && buildcfg.GOAMD64 >= 3 => (SARX(Q|L) x y) (SHL(Q|L) x y) && buildcfg.GOAMD64 >= 3 => (SHLX(Q|L) x y) diff --git a/src/cmd/compile/internal/ssa/rewriteAMD64latelower.go b/src/cmd/compile/internal/ssa/rewriteAMD64latelower.go index 792cddd09e355c..907225716834e6 100644 --- a/src/cmd/compile/internal/ssa/rewriteAMD64latelower.go +++ b/src/cmd/compile/internal/ssa/rewriteAMD64latelower.go @@ -7,30 +7,6 @@ import "internal/buildcfg" func rewriteValueAMD64latelower(v *Value) bool { switch v.Op { - case OpAMD64LEAL1: - return rewriteValueAMD64latelower_OpAMD64LEAL1(v) - case OpAMD64LEAL2: - return rewriteValueAMD64latelower_OpAMD64LEAL2(v) - case OpAMD64LEAL4: - return rewriteValueAMD64latelower_OpAMD64LEAL4(v) - case OpAMD64LEAL8: - return rewriteValueAMD64latelower_OpAMD64LEAL8(v) - case OpAMD64LEAQ1: - return rewriteValueAMD64latelower_OpAMD64LEAQ1(v) - case OpAMD64LEAQ2: - return rewriteValueAMD64latelower_OpAMD64LEAQ2(v) - case OpAMD64LEAQ4: - return rewriteValueAMD64latelower_OpAMD64LEAQ4(v) - case OpAMD64LEAQ8: - return rewriteValueAMD64latelower_OpAMD64LEAQ8(v) - case OpAMD64LEAW1: - return rewriteValueAMD64latelower_OpAMD64LEAW1(v) - case OpAMD64LEAW2: - return rewriteValueAMD64latelower_OpAMD64LEAW2(v) - case OpAMD64LEAW4: - return rewriteValueAMD64latelower_OpAMD64LEAW4(v) - case OpAMD64LEAW8: - return rewriteValueAMD64latelower_OpAMD64LEAW8(v) case OpAMD64SARL: return rewriteValueAMD64latelower_OpAMD64SARL(v) case OpAMD64SARQ: @@ -46,375 +22,6 @@ func rewriteValueAMD64latelower(v *Value) bool { } return false } -func rewriteValueAMD64latelower_OpAMD64LEAL1(v *Value) bool { - v_1 := v.Args[1] - v_0 := v.Args[0] - b := v.Block - // match: (LEAL1 [c] {s} x y) - // cond: isPtr(x.Type) && c != 0 && s == nil - // result: (ADDL x (ADDLconst [c] y)) - for { - c := auxIntToInt32(v.AuxInt) - s := auxToSym(v.Aux) - for _i0 := 0; _i0 <= 1; _i0, v_0, v_1 = _i0+1, v_1, v_0 { - x := v_0 - y := v_1 - if !(isPtr(x.Type) && c != 0 && s == nil) { - continue - } - v.reset(OpAMD64ADDL) - v0 := b.NewValue0(v.Pos, OpAMD64ADDLconst, y.Type) - v0.AuxInt = int32ToAuxInt(c) - v0.AddArg(y) - v.AddArg2(x, v0) - return true - } - break - } - // match: (LEAL1 [c] {s} x y) - // cond: !isPtr(x.Type) && c != 0 && s == nil - // result: (ADDL y (ADDLconst [c] x)) - for { - c := auxIntToInt32(v.AuxInt) - s := auxToSym(v.Aux) - for _i0 := 0; _i0 <= 1; _i0, v_0, v_1 = _i0+1, v_1, v_0 { - x := v_0 - y := v_1 - if !(!isPtr(x.Type) && c != 0 && s == nil) { - continue - } - v.reset(OpAMD64ADDL) - v0 := b.NewValue0(v.Pos, OpAMD64ADDLconst, x.Type) - v0.AuxInt = int32ToAuxInt(c) - v0.AddArg(x) - v.AddArg2(y, v0) - return true - } - break - } - return false -} -func rewriteValueAMD64latelower_OpAMD64LEAL2(v *Value) bool { - v_1 := v.Args[1] - v_0 := v.Args[0] - b := v.Block - // match: (LEAL2 [c] {s} x y) - // cond: !isPtr(t) && c != 0 && s == nil - // result: (ADDLconst [c] (LEAL2 x y)) - for { - t := v.Type - c := auxIntToInt32(v.AuxInt) - s := auxToSym(v.Aux) - x := v_0 - y := v_1 - if !(!isPtr(t) && c != 0 && s == nil) { - break - } - v.reset(OpAMD64ADDLconst) - v.AuxInt = int32ToAuxInt(c) - v0 := b.NewValue0(v.Pos, OpAMD64LEAL2, x.Type) - v0.AddArg2(x, y) - v.AddArg(v0) - return true - } - return false -} -func rewriteValueAMD64latelower_OpAMD64LEAL4(v *Value) bool { - v_1 := v.Args[1] - v_0 := v.Args[0] - b := v.Block - // match: (LEAL4 [c] {s} x y) - // cond: !isPtr(t) && c != 0 && s == nil - // result: (ADDLconst [c] (LEAL4 x y)) - for { - t := v.Type - c := auxIntToInt32(v.AuxInt) - s := auxToSym(v.Aux) - x := v_0 - y := v_1 - if !(!isPtr(t) && c != 0 && s == nil) { - break - } - v.reset(OpAMD64ADDLconst) - v.AuxInt = int32ToAuxInt(c) - v0 := b.NewValue0(v.Pos, OpAMD64LEAL4, x.Type) - v0.AddArg2(x, y) - v.AddArg(v0) - return true - } - return false -} -func rewriteValueAMD64latelower_OpAMD64LEAL8(v *Value) bool { - v_1 := v.Args[1] - v_0 := v.Args[0] - b := v.Block - // match: (LEAL8 [c] {s} x y) - // cond: !isPtr(t) && c != 0 && s == nil - // result: (ADDLconst [c] (LEAL8 x y)) - for { - t := v.Type - c := auxIntToInt32(v.AuxInt) - s := auxToSym(v.Aux) - x := v_0 - y := v_1 - if !(!isPtr(t) && c != 0 && s == nil) { - break - } - v.reset(OpAMD64ADDLconst) - v.AuxInt = int32ToAuxInt(c) - v0 := b.NewValue0(v.Pos, OpAMD64LEAL8, x.Type) - v0.AddArg2(x, y) - v.AddArg(v0) - return true - } - return false -} -func rewriteValueAMD64latelower_OpAMD64LEAQ1(v *Value) bool { - v_1 := v.Args[1] - v_0 := v.Args[0] - b := v.Block - // match: (LEAQ1 [c] {s} x y) - // cond: isPtr(x.Type) && c != 0 && s == nil - // result: (ADDQ x (ADDQconst [c] y)) - for { - c := auxIntToInt32(v.AuxInt) - s := auxToSym(v.Aux) - for _i0 := 0; _i0 <= 1; _i0, v_0, v_1 = _i0+1, v_1, v_0 { - x := v_0 - y := v_1 - if !(isPtr(x.Type) && c != 0 && s == nil) { - continue - } - v.reset(OpAMD64ADDQ) - v0 := b.NewValue0(v.Pos, OpAMD64ADDQconst, y.Type) - v0.AuxInt = int32ToAuxInt(c) - v0.AddArg(y) - v.AddArg2(x, v0) - return true - } - break - } - // match: (LEAQ1 [c] {s} x y) - // cond: !isPtr(x.Type) && c != 0 && s == nil - // result: (ADDQ y (ADDQconst [c] x)) - for { - c := auxIntToInt32(v.AuxInt) - s := auxToSym(v.Aux) - for _i0 := 0; _i0 <= 1; _i0, v_0, v_1 = _i0+1, v_1, v_0 { - x := v_0 - y := v_1 - if !(!isPtr(x.Type) && c != 0 && s == nil) { - continue - } - v.reset(OpAMD64ADDQ) - v0 := b.NewValue0(v.Pos, OpAMD64ADDQconst, x.Type) - v0.AuxInt = int32ToAuxInt(c) - v0.AddArg(x) - v.AddArg2(y, v0) - return true - } - break - } - return false -} -func rewriteValueAMD64latelower_OpAMD64LEAQ2(v *Value) bool { - v_1 := v.Args[1] - v_0 := v.Args[0] - b := v.Block - // match: (LEAQ2 [c] {s} x y) - // cond: !isPtr(t) && c != 0 && s == nil - // result: (ADDQconst [c] (LEAQ2 x y)) - for { - t := v.Type - c := auxIntToInt32(v.AuxInt) - s := auxToSym(v.Aux) - x := v_0 - y := v_1 - if !(!isPtr(t) && c != 0 && s == nil) { - break - } - v.reset(OpAMD64ADDQconst) - v.AuxInt = int32ToAuxInt(c) - v0 := b.NewValue0(v.Pos, OpAMD64LEAQ2, x.Type) - v0.AddArg2(x, y) - v.AddArg(v0) - return true - } - return false -} -func rewriteValueAMD64latelower_OpAMD64LEAQ4(v *Value) bool { - v_1 := v.Args[1] - v_0 := v.Args[0] - b := v.Block - // match: (LEAQ4 [c] {s} x y) - // cond: !isPtr(t) && c != 0 && s == nil - // result: (ADDQconst [c] (LEAQ4 x y)) - for { - t := v.Type - c := auxIntToInt32(v.AuxInt) - s := auxToSym(v.Aux) - x := v_0 - y := v_1 - if !(!isPtr(t) && c != 0 && s == nil) { - break - } - v.reset(OpAMD64ADDQconst) - v.AuxInt = int32ToAuxInt(c) - v0 := b.NewValue0(v.Pos, OpAMD64LEAQ4, x.Type) - v0.AddArg2(x, y) - v.AddArg(v0) - return true - } - return false -} -func rewriteValueAMD64latelower_OpAMD64LEAQ8(v *Value) bool { - v_1 := v.Args[1] - v_0 := v.Args[0] - b := v.Block - // match: (LEAQ8 [c] {s} x y) - // cond: !isPtr(t) && c != 0 && s == nil - // result: (ADDQconst [c] (LEAQ8 x y)) - for { - t := v.Type - c := auxIntToInt32(v.AuxInt) - s := auxToSym(v.Aux) - x := v_0 - y := v_1 - if !(!isPtr(t) && c != 0 && s == nil) { - break - } - v.reset(OpAMD64ADDQconst) - v.AuxInt = int32ToAuxInt(c) - v0 := b.NewValue0(v.Pos, OpAMD64LEAQ8, x.Type) - v0.AddArg2(x, y) - v.AddArg(v0) - return true - } - return false -} -func rewriteValueAMD64latelower_OpAMD64LEAW1(v *Value) bool { - v_1 := v.Args[1] - v_0 := v.Args[0] - b := v.Block - // match: (LEAW1 [c] {s} x y) - // cond: isPtr(x.Type) && c != 0 && s == nil - // result: (ADDL x (ADDLconst [c] y)) - for { - c := auxIntToInt32(v.AuxInt) - s := auxToSym(v.Aux) - for _i0 := 0; _i0 <= 1; _i0, v_0, v_1 = _i0+1, v_1, v_0 { - x := v_0 - y := v_1 - if !(isPtr(x.Type) && c != 0 && s == nil) { - continue - } - v.reset(OpAMD64ADDL) - v0 := b.NewValue0(v.Pos, OpAMD64ADDLconst, y.Type) - v0.AuxInt = int32ToAuxInt(c) - v0.AddArg(y) - v.AddArg2(x, v0) - return true - } - break - } - // match: (LEAW1 [c] {s} x y) - // cond: !isPtr(x.Type) && c != 0 && s == nil - // result: (ADDL y (ADDLconst [c] x)) - for { - c := auxIntToInt32(v.AuxInt) - s := auxToSym(v.Aux) - for _i0 := 0; _i0 <= 1; _i0, v_0, v_1 = _i0+1, v_1, v_0 { - x := v_0 - y := v_1 - if !(!isPtr(x.Type) && c != 0 && s == nil) { - continue - } - v.reset(OpAMD64ADDL) - v0 := b.NewValue0(v.Pos, OpAMD64ADDLconst, x.Type) - v0.AuxInt = int32ToAuxInt(c) - v0.AddArg(x) - v.AddArg2(y, v0) - return true - } - break - } - return false -} -func rewriteValueAMD64latelower_OpAMD64LEAW2(v *Value) bool { - v_1 := v.Args[1] - v_0 := v.Args[0] - b := v.Block - // match: (LEAW2 [c] {s} x y) - // cond: !isPtr(t) && c != 0 && s == nil - // result: (ADDLconst [c] (LEAW2 x y)) - for { - t := v.Type - c := auxIntToInt32(v.AuxInt) - s := auxToSym(v.Aux) - x := v_0 - y := v_1 - if !(!isPtr(t) && c != 0 && s == nil) { - break - } - v.reset(OpAMD64ADDLconst) - v.AuxInt = int32ToAuxInt(c) - v0 := b.NewValue0(v.Pos, OpAMD64LEAW2, x.Type) - v0.AddArg2(x, y) - v.AddArg(v0) - return true - } - return false -} -func rewriteValueAMD64latelower_OpAMD64LEAW4(v *Value) bool { - v_1 := v.Args[1] - v_0 := v.Args[0] - b := v.Block - // match: (LEAW4 [c] {s} x y) - // cond: !isPtr(t) && c != 0 && s == nil - // result: (ADDLconst [c] (LEAW4 x y)) - for { - t := v.Type - c := auxIntToInt32(v.AuxInt) - s := auxToSym(v.Aux) - x := v_0 - y := v_1 - if !(!isPtr(t) && c != 0 && s == nil) { - break - } - v.reset(OpAMD64ADDLconst) - v.AuxInt = int32ToAuxInt(c) - v0 := b.NewValue0(v.Pos, OpAMD64LEAW4, x.Type) - v0.AddArg2(x, y) - v.AddArg(v0) - return true - } - return false -} -func rewriteValueAMD64latelower_OpAMD64LEAW8(v *Value) bool { - v_1 := v.Args[1] - v_0 := v.Args[0] - b := v.Block - // match: (LEAW8 [c] {s} x y) - // cond: !isPtr(t) && c != 0 && s == nil - // result: (ADDLconst [c] (LEAW8 x y)) - for { - t := v.Type - c := auxIntToInt32(v.AuxInt) - s := auxToSym(v.Aux) - x := v_0 - y := v_1 - if !(!isPtr(t) && c != 0 && s == nil) { - break - } - v.reset(OpAMD64ADDLconst) - v.AuxInt = int32ToAuxInt(c) - v0 := b.NewValue0(v.Pos, OpAMD64LEAW8, x.Type) - v0.AddArg2(x, y) - v.AddArg(v0) - return true - } - return false -} func rewriteValueAMD64latelower_OpAMD64SARL(v *Value) bool { v_1 := v.Args[1] v_0 := v.Args[0]