aboutsummaryrefslogtreecommitdiff
path: root/src/cmd/compile/internal/ssa/gen/generic.rules
diff options
context:
space:
mode:
Diffstat (limited to 'src/cmd/compile/internal/ssa/gen/generic.rules')
-rw-r--r--src/cmd/compile/internal/ssa/gen/generic.rules16
1 files changed, 15 insertions, 1 deletions
diff --git a/src/cmd/compile/internal/ssa/gen/generic.rules b/src/cmd/compile/internal/ssa/gen/generic.rules
index 8ec22d86e7..c7f6a232c6 100644
--- a/src/cmd/compile/internal/ssa/gen/generic.rules
+++ b/src/cmd/compile/internal/ssa/gen/generic.rules
@@ -137,6 +137,16 @@
(Xor32 (Const32 [c]) (Const32 [d])) -> (Const32 [int64(int32(c^d))])
(Xor64 (Const64 [c]) (Const64 [d])) -> (Const64 [c^d])
+(Ctz64 (Const64 [c])) && config.PtrSize == 4 -> (Const32 [ntz(c)])
+(Ctz32 (Const32 [c])) && config.PtrSize == 4 -> (Const32 [ntz32(c)])
+(Ctz16 (Const16 [c])) && config.PtrSize == 4 -> (Const32 [ntz16(c)])
+(Ctz8 (Const8 [c])) && config.PtrSize == 4 -> (Const32 [ntz8(c)])
+
+(Ctz64 (Const64 [c])) && config.PtrSize == 8 -> (Const64 [ntz(c)])
+(Ctz32 (Const32 [c])) && config.PtrSize == 8 -> (Const64 [ntz32(c)])
+(Ctz16 (Const16 [c])) && config.PtrSize == 8 -> (Const64 [ntz16(c)])
+(Ctz8 (Const8 [c])) && config.PtrSize == 8 -> (Const64 [ntz8(c)])
+
(Div8 (Const8 [c]) (Const8 [d])) && d != 0 -> (Const8 [int64(int8(c)/int8(d))])
(Div16 (Const16 [c]) (Const16 [d])) && d != 0 -> (Const16 [int64(int16(c)/int16(d))])
(Div32 (Const32 [c]) (Const32 [d])) && d != 0 -> (Const32 [int64(int32(c)/int32(d))])
@@ -917,7 +927,7 @@
(If (ConstBool [c]) yes no) && c == 0 -> (First no yes)
// Get rid of Convert ops for pointer arithmetic on unsafe.Pointer.
-(Convert (Add(64|32) (Convert ptr mem) off) mem) -> (Add(64|32) ptr off)
+(Convert (Add(64|32) (Convert ptr mem) off) mem) -> (AddPtr ptr off)
(Convert (Convert ptr mem) mem) -> ptr
// strength reduction of divide by a constant.
@@ -1780,6 +1790,10 @@
// is constant, which pushes constants to the outside
// of the expression. At that point, any constant-folding
// opportunities should be obvious.
+// Note: don't include AddPtr here! In order to maintain the
+// invariant that pointers must stay within the pointed-to object,
+// we can't pull part of a pointer computation above the AddPtr.
+// See issue 37881.
// x + (C + z) -> C + (x + z)
(Add64 (Add64 i:(Const64 <t>) z) x) && (z.Op != OpConst64 && x.Op != OpConst64) -> (Add64 i (Add64 <t> z x))