diff --git a/src/cmd/compile/internal/gc/ssa.go b/src/cmd/compile/internal/gc/ssa.go index ecc449114d..d61f463ccf 100644 --- a/src/cmd/compile/internal/gc/ssa.go +++ b/src/cmd/compile/internal/gc/ssa.go @@ -3427,12 +3427,12 @@ func init() { func(s *state, n *Node, args []*ssa.Value) *ssa.Value { return s.newValue2(ssa.OpRotateLeft32, types.Types[TUINT32], args[0], args[1]) }, - sys.AMD64, sys.ARM64, sys.S390X) + sys.AMD64, sys.ARM64, sys.S390X, sys.PPC64) addF("math/bits", "RotateLeft64", func(s *state, n *Node, args []*ssa.Value) *ssa.Value { return s.newValue2(ssa.OpRotateLeft64, types.Types[TUINT64], args[0], args[1]) }, - sys.AMD64, sys.ARM64, sys.S390X) + sys.AMD64, sys.ARM64, sys.S390X, sys.PPC64) alias("math/bits", "RotateLeft", "math/bits", "RotateLeft64", p8...) makeOnesCountAMD64 := func(op64 ssa.Op, op32 ssa.Op) func(s *state, n *Node, args []*ssa.Value) *ssa.Value { diff --git a/src/cmd/compile/internal/ssa/gen/PPC64.rules b/src/cmd/compile/internal/ssa/gen/PPC64.rules index e5d5295908..8dee5a1cba 100644 --- a/src/cmd/compile/internal/ssa/gen/PPC64.rules +++ b/src/cmd/compile/internal/ssa/gen/PPC64.rules @@ -100,6 +100,14 @@ ( OR (SLW x (ANDconst [31] y)) (SRW x (SUB (MOVDconst [32]) (ANDconst [31] y)))) -> (ROTLW x y) (XOR (SLW x (ANDconst [31] y)) (SRW x (SUB (MOVDconst [32]) (ANDconst [31] y)))) -> (ROTLW x y) +// Lowering rotates +(RotateLeft32 x y) -> (ROTLW x y) +(RotateLeft64 x y) -> (ROTL x y) + +// Constant rotate generation +(ROTLW x (MOVDconst [c])) -> (ROTLWconst x [c&31]) +(ROTL x (MOVDconst [c])) -> (ROTLconst x [c&63]) + (Lsh64x64 x (Const64 [c])) && uint64(c) < 64 -> (SLDconst x [c]) (Rsh64x64 x (Const64 [c])) && uint64(c) < 64 -> (SRADconst x [c]) (Rsh64Ux64 x (Const64 [c])) && uint64(c) < 64 -> (SRDconst x [c]) diff --git a/src/cmd/compile/internal/ssa/rewritePPC64.go b/src/cmd/compile/internal/ssa/rewritePPC64.go index 302b785f61..9245f403b8 100644 --- a/src/cmd/compile/internal/ssa/rewritePPC64.go +++ b/src/cmd/compile/internal/ssa/rewritePPC64.go @@ -537,6 +537,10 @@ func rewriteValuePPC64(v *Value) bool { return rewriteValuePPC64_OpPPC64ORN_0(v) case OpPPC64ORconst: return rewriteValuePPC64_OpPPC64ORconst_0(v) + case OpPPC64ROTL: + return rewriteValuePPC64_OpPPC64ROTL_0(v) + case OpPPC64ROTLW: + return rewriteValuePPC64_OpPPC64ROTLW_0(v) case OpPPC64SUB: return rewriteValuePPC64_OpPPC64SUB_0(v) case OpPPC64XOR: @@ -551,6 +555,10 @@ func rewriteValuePPC64(v *Value) bool { return rewriteValuePPC64_OpPopCount64_0(v) case OpPopCount8: return rewriteValuePPC64_OpPopCount8_0(v) + case OpRotateLeft32: + return rewriteValuePPC64_OpRotateLeft32_0(v) + case OpRotateLeft64: + return rewriteValuePPC64_OpRotateLeft64_0(v) case OpRound: return rewriteValuePPC64_OpRound_0(v) case OpRound32F: @@ -25533,6 +25541,44 @@ func rewriteValuePPC64_OpPPC64ORconst_0(v *Value) bool { } return false } +func rewriteValuePPC64_OpPPC64ROTL_0(v *Value) bool { + // match: (ROTL x (MOVDconst [c])) + // cond: + // result: (ROTLconst x [c&63]) + for { + _ = v.Args[1] + x := v.Args[0] + v_1 := v.Args[1] + if v_1.Op != OpPPC64MOVDconst { + break + } + c := v_1.AuxInt + v.reset(OpPPC64ROTLconst) + v.AuxInt = c & 63 + v.AddArg(x) + return true + } + return false +} +func rewriteValuePPC64_OpPPC64ROTLW_0(v *Value) bool { + // match: (ROTLW x (MOVDconst [c])) + // cond: + // result: (ROTLWconst x [c&31]) + for { + _ = v.Args[1] + x := v.Args[0] + v_1 := v.Args[1] + if v_1.Op != OpPPC64MOVDconst { + break + } + c := v_1.AuxInt + v.reset(OpPPC64ROTLWconst) + v.AuxInt = c & 31 + v.AddArg(x) + return true + } + return false +} func rewriteValuePPC64_OpPPC64SUB_0(v *Value) bool { // match: (SUB x (MOVDconst [c])) // cond: is32Bit(-c) @@ -26086,6 +26132,34 @@ func rewriteValuePPC64_OpPopCount8_0(v *Value) bool { return true } } +func rewriteValuePPC64_OpRotateLeft32_0(v *Value) bool { + // match: (RotateLeft32 x y) + // cond: + // result: (ROTLW x y) + for { + _ = v.Args[1] + x := v.Args[0] + y := v.Args[1] + v.reset(OpPPC64ROTLW) + v.AddArg(x) + v.AddArg(y) + return true + } +} +func rewriteValuePPC64_OpRotateLeft64_0(v *Value) bool { + // match: (RotateLeft64 x y) + // cond: + // result: (ROTL x y) + for { + _ = v.Args[1] + x := v.Args[0] + y := v.Args[1] + v.reset(OpPPC64ROTL) + v.AddArg(x) + v.AddArg(y) + return true + } +} func rewriteValuePPC64_OpRound_0(v *Value) bool { // match: (Round x) // cond: