diff options
| author | Agniva De Sarker <agnivade@yahoo.co.in> | 2019-09-08 22:55:01 +0530 |
|---|---|---|
| committer | Agniva De Sarker <agniva.quicksilver@gmail.com> | 2019-09-10 09:12:32 +0000 |
| commit | b38be35e4c79fd3c5b9450e95cf092eaac094405 (patch) | |
| tree | 2f4de3c863fda4ed4d2bb24a27b2f85c5f7cea91 /src | |
| parent | b6ec56bc26a89e9733390dd41fade5baace5a641 (diff) | |
| download | go-b38be35e4c79fd3c5b9450e95cf092eaac094405.tar.xz | |
cmd/compile: optimize const rotates for wasm architecture
This removes the unnecessary code to check whether the shift
is within limits or not when the shift amount is a constant.
The rules hit 23034 times when building std cmd.
grep -E "Wasm.rules:(106|107|121|122|139|140)" rulelog | wc -l
23034
Reduces the size of pkg/js_wasm by 132 bytes.
Change-Id: I64a2b8faca08c3b5039d6a027d4676130d2db18d
Reviewed-on: https://go-review.googlesource.com/c/go/+/194239
Run-TryBot: Agniva De Sarker <agniva.quicksilver@gmail.com>
TryBot-Result: Gobot Gobot <gobot@golang.org>
Reviewed-by: Richard Musiol <neelance@gmail.com>
Diffstat (limited to 'src')
| -rw-r--r-- | src/cmd/compile/internal/ssa/gen/Wasm.rules | 6 | ||||
| -rw-r--r-- | src/cmd/compile/internal/ssa/rewriteWasm.go | 118 |
2 files changed, 124 insertions, 0 deletions
diff --git a/src/cmd/compile/internal/ssa/gen/Wasm.rules b/src/cmd/compile/internal/ssa/gen/Wasm.rules index 72080703f5..c9dd6e8084 100644 --- a/src/cmd/compile/internal/ssa/gen/Wasm.rules +++ b/src/cmd/compile/internal/ssa/gen/Wasm.rules @@ -103,6 +103,8 @@ // Unsigned shifts need to return 0 if shift amount is >= width of shifted value. (Lsh64x64 x y) && shiftIsBounded(v) -> (I64Shl x y) +(Lsh64x64 x (I64Const [c])) && uint64(c) < 64 -> (I64Shl x (I64Const [c])) +(Lsh64x64 x (I64Const [c])) && uint64(c) >= 64 -> (I64Const [0]) (Lsh64x64 x y) -> (Select (I64Shl x y) (I64Const [0]) (I64LtU y (I64Const [64]))) (Lsh64x(32|16|8) x y) -> (Lsh64x64 x (ZeroExt(32|16|8)to64 y)) @@ -116,6 +118,8 @@ (Lsh8x(32|16|8) x y) -> (Lsh64x64 x (ZeroExt(32|16|8)to64 y)) (Rsh64Ux64 x y) && shiftIsBounded(v) -> (I64ShrU x y) +(Rsh64Ux64 x (I64Const [c])) && uint64(c) < 64 -> (I64ShrU x (I64Const [c])) +(Rsh64Ux64 x (I64Const [c])) && uint64(c) >= 64 -> (I64Const [0]) (Rsh64Ux64 x y) -> (Select (I64ShrU x y) (I64Const [0]) (I64LtU y (I64Const [64]))) (Rsh64Ux(32|16|8) x y) -> (Rsh64Ux64 x (ZeroExt(32|16|8)to64 y)) @@ -132,6 +136,8 @@ // We implement this by setting the shift value to (width - 1) if the shift value is >= width. (Rsh64x64 x y) && shiftIsBounded(v) -> (I64ShrS x y) +(Rsh64x64 x (I64Const [c])) && uint64(c) < 64 -> (I64ShrS x (I64Const [c])) +(Rsh64x64 x (I64Const [c])) && uint64(c) >= 64 -> (I64ShrS x (I64Const [63])) (Rsh64x64 x y) -> (I64ShrS x (Select <typ.Int64> y (I64Const [63]) (I64LtU y (I64Const [64])))) (Rsh64x(32|16|8) x y) -> (Rsh64x64 x (ZeroExt(32|16|8)to64 y)) diff --git a/src/cmd/compile/internal/ssa/rewriteWasm.go b/src/cmd/compile/internal/ssa/rewriteWasm.go index 45b855027d..c9384af16a 100644 --- a/src/cmd/compile/internal/ssa/rewriteWasm.go +++ b/src/cmd/compile/internal/ssa/rewriteWasm.go @@ -2742,6 +2742,44 @@ func rewriteValueWasm_OpLsh64x64_0(v *Value) bool { v.AddArg(y) return true } + // match: (Lsh64x64 x (I64Const [c])) + // cond: uint64(c) < 64 + // result: (I64Shl x (I64Const [c])) + for { + _ = v.Args[1] + x := v.Args[0] + v_1 := v.Args[1] + if v_1.Op != OpWasmI64Const { + break + } + c := v_1.AuxInt + if !(uint64(c) < 64) { + break + } + v.reset(OpWasmI64Shl) + v.AddArg(x) + v0 := b.NewValue0(v.Pos, OpWasmI64Const, typ.Int64) + v0.AuxInt = c + v.AddArg(v0) + return true + } + // match: (Lsh64x64 x (I64Const [c])) + // cond: uint64(c) >= 64 + // result: (I64Const [0]) + for { + _ = v.Args[1] + v_1 := v.Args[1] + if v_1.Op != OpWasmI64Const { + break + } + c := v_1.AuxInt + if !(uint64(c) >= 64) { + break + } + v.reset(OpWasmI64Const) + v.AuxInt = 0 + return true + } // match: (Lsh64x64 x y) // cond: // result: (Select (I64Shl x y) (I64Const [0]) (I64LtU y (I64Const [64]))) @@ -4264,6 +4302,44 @@ func rewriteValueWasm_OpRsh64Ux64_0(v *Value) bool { v.AddArg(y) return true } + // match: (Rsh64Ux64 x (I64Const [c])) + // cond: uint64(c) < 64 + // result: (I64ShrU x (I64Const [c])) + for { + _ = v.Args[1] + x := v.Args[0] + v_1 := v.Args[1] + if v_1.Op != OpWasmI64Const { + break + } + c := v_1.AuxInt + if !(uint64(c) < 64) { + break + } + v.reset(OpWasmI64ShrU) + v.AddArg(x) + v0 := b.NewValue0(v.Pos, OpWasmI64Const, typ.Int64) + v0.AuxInt = c + v.AddArg(v0) + return true + } + // match: (Rsh64Ux64 x (I64Const [c])) + // cond: uint64(c) >= 64 + // result: (I64Const [0]) + for { + _ = v.Args[1] + v_1 := v.Args[1] + if v_1.Op != OpWasmI64Const { + break + } + c := v_1.AuxInt + if !(uint64(c) >= 64) { + break + } + v.reset(OpWasmI64Const) + v.AuxInt = 0 + return true + } // match: (Rsh64Ux64 x y) // cond: // result: (Select (I64ShrU x y) (I64Const [0]) (I64LtU y (I64Const [64]))) @@ -4355,6 +4431,48 @@ func rewriteValueWasm_OpRsh64x64_0(v *Value) bool { v.AddArg(y) return true } + // match: (Rsh64x64 x (I64Const [c])) + // cond: uint64(c) < 64 + // result: (I64ShrS x (I64Const [c])) + for { + _ = v.Args[1] + x := v.Args[0] + v_1 := v.Args[1] + if v_1.Op != OpWasmI64Const { + break + } + c := v_1.AuxInt + if !(uint64(c) < 64) { + break + } + v.reset(OpWasmI64ShrS) + v.AddArg(x) + v0 := b.NewValue0(v.Pos, OpWasmI64Const, typ.Int64) + v0.AuxInt = c + v.AddArg(v0) + return true + } + // match: (Rsh64x64 x (I64Const [c])) + // cond: uint64(c) >= 64 + // result: (I64ShrS x (I64Const [63])) + for { + _ = v.Args[1] + x := v.Args[0] + v_1 := v.Args[1] + if v_1.Op != OpWasmI64Const { + break + } + c := v_1.AuxInt + if !(uint64(c) >= 64) { + break + } + v.reset(OpWasmI64ShrS) + v.AddArg(x) + v0 := b.NewValue0(v.Pos, OpWasmI64Const, typ.Int64) + v0.AuxInt = 63 + v.AddArg(v0) + return true + } // match: (Rsh64x64 x y) // cond: // result: (I64ShrS x (Select <typ.Int64> y (I64Const [63]) (I64LtU y (I64Const [64])))) |
