From 7b67b68a0da091be2d7dc3e69c4df9a1a080d0de Mon Sep 17 00:00:00 2001 From: Jorropo Date: Thu, 4 Dec 2025 04:17:58 +0100 Subject: [PATCH] cmd/compile: use isUnsignedPowerOfTwo rather than isPowerOfTwo for unsigneds Fixes #76688 Change-Id: Icb8dab54a5ce7d83b656d50d5ea605d2a62b96f8 Reviewed-on: https://go-review.googlesource.com/c/go/+/726680 Auto-Submit: Jorropo LUCI-TryBot-Result: Go LUCI Reviewed-by: Cuong Manh Le Reviewed-by: Keith Randall Reviewed-by: Keith Randall Reviewed-by: Dmitri Shuralyov --- src/cmd/compile/internal/ssa/prove.go | 4 ++-- test/prove.go | 8 ++++++++ 2 files changed, 10 insertions(+), 2 deletions(-) diff --git a/src/cmd/compile/internal/ssa/prove.go b/src/cmd/compile/internal/ssa/prove.go index 1aab7e3eb77..39080a015e9 100644 --- a/src/cmd/compile/internal/ssa/prove.go +++ b/src/cmd/compile/internal/ssa/prove.go @@ -2885,9 +2885,9 @@ func simplifyBlock(sdom SparseTree, ft *factsTable, b *Block) { xl := ft.limits[x.ID] y := v.Args[1] yl := ft.limits[y.ID] - if xl.umin == xl.umax && isPowerOfTwo(int64(xl.umin)) || + if xl.umin == xl.umax && isUnsignedPowerOfTwo(xl.umin) || xl.min == xl.max && isPowerOfTwo(xl.min) || - yl.umin == yl.umax && isPowerOfTwo(int64(yl.umin)) || + yl.umin == yl.umax && isUnsignedPowerOfTwo(yl.umin) || yl.min == yl.max && isPowerOfTwo(yl.min) { // 0,1 * a power of two is better done as a shift break diff --git a/test/prove.go b/test/prove.go index 1b50317fe3e..e04b510e170 100644 --- a/test/prove.go +++ b/test/prove.go @@ -2718,6 +2718,14 @@ func detectStringLenRelation(s string) bool { return false } +func issue76688(x, y uint64) uint64 { + if x > 1 || y != 1<<63 { + return 42 + } + // We do not want to rewrite the multiply to a condselect here since opt can do a better job with a left shift. + return x * y +} + //go:noinline func prove(x int) { }