(BitLen8 x) && buildcfg.GOAMD64 < 3 => (BSRL (LEAL1 <typ.UInt32> [1] (MOVBQZX <typ.UInt32> x) (MOVBQZX <typ.UInt32> x)))
(BitLen64 <t> x) && buildcfg.GOAMD64 >= 3 => (NEGQ (ADDQconst <t> [-64] (LZCNTQ x)))
// Use 64-bit version to allow const-fold remove unnecessary arithmetic.
-(BitLen(32|16|8) <t> x) && buildcfg.GOAMD64 >= 3 => (NEGQ (ADDQconst <t> [-32] (LZCNTL x)))
+(BitLen32 <t> x) && buildcfg.GOAMD64 >= 3 => (NEGQ (ADDQconst <t> [-32] (LZCNTL x)))
+(BitLen16 <t> x) && buildcfg.GOAMD64 >= 3 => (NEGQ (ADDQconst <t> [-32] (LZCNTL (MOVWQZX <x.Type> x))))
+(BitLen8 <t> x) && buildcfg.GOAMD64 >= 3 => (NEGQ (ADDQconst <t> [-32] (LZCNTL (MOVBQZX <x.Type> x))))
(Bswap(64|32) ...) => (BSWAP(Q|L) ...)
}
// match: (BitLen16 <t> x)
// cond: buildcfg.GOAMD64 >= 3
- // result: (NEGQ (ADDQconst <t> [-32] (LZCNTL x)))
+ // result: (NEGQ (ADDQconst <t> [-32] (LZCNTL (MOVWQZX <x.Type> x))))
for {
t := v.Type
x := v_0
v0 := b.NewValue0(v.Pos, OpAMD64ADDQconst, t)
v0.AuxInt = int32ToAuxInt(-32)
v1 := b.NewValue0(v.Pos, OpAMD64LZCNTL, typ.UInt32)
- v1.AddArg(x)
+ v2 := b.NewValue0(v.Pos, OpAMD64MOVWQZX, x.Type)
+ v2.AddArg(x)
+ v1.AddArg(v2)
v0.AddArg(v1)
v.AddArg(v0)
return true
}
// match: (BitLen8 <t> x)
// cond: buildcfg.GOAMD64 >= 3
- // result: (NEGQ (ADDQconst <t> [-32] (LZCNTL x)))
+ // result: (NEGQ (ADDQconst <t> [-32] (LZCNTL (MOVBQZX <x.Type> x))))
for {
t := v.Type
x := v_0
v0 := b.NewValue0(v.Pos, OpAMD64ADDQconst, t)
v0.AuxInt = int32ToAuxInt(-32)
v1 := b.NewValue0(v.Pos, OpAMD64LZCNTL, typ.UInt32)
- v1.AddArg(x)
+ v2 := b.NewValue0(v.Pos, OpAMD64MOVBQZX, x.Type)
+ v2.AddArg(x)
+ v1.AddArg(v2)
v0.AddArg(v1)
v.AddArg(v0)
return true
--- /dev/null
+// Copyright 2022 The Go Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style
+// license that can be found in the LICENSE file.
+
+package test
+
+import (
+ "math/bits"
+ "testing"
+)
+
+func TestBitLen64(t *testing.T) {
+ for i := 0; i <= 64; i++ {
+ got := bits.Len64(1 << i)
+ want := i + 1
+ if want == 65 {
+ want = 0
+ }
+ if got != want {
+ t.Errorf("Len64(1<<%d) = %d, want %d", i, got, want)
+ }
+ }
+}
+
+func TestBitLen32(t *testing.T) {
+ for i := 0; i <= 32; i++ {
+ got := bits.Len32(1 << i)
+ want := i + 1
+ if want == 33 {
+ want = 0
+ }
+ if got != want {
+ t.Errorf("Len32(1<<%d) = %d, want %d", i, got, want)
+ }
+ }
+}
+
+func TestBitLen16(t *testing.T) {
+ for i := 0; i <= 16; i++ {
+ got := bits.Len16(1 << i)
+ want := i + 1
+ if want == 17 {
+ want = 0
+ }
+ if got != want {
+ t.Errorf("Len16(1<<%d) = %d, want %d", i, got, want)
+ }
+ }
+}
+
+func TestBitLen8(t *testing.T) {
+ for i := 0; i <= 8; i++ {
+ got := bits.Len8(1 << i)
+ want := i + 1
+ if want == 9 {
+ want = 0
+ }
+ if got != want {
+ t.Errorf("Len8(1<<%d) = %d, want %d", i, got, want)
+ }
+ }
+}