From: Xiaolin Zhao Date: Tue, 16 Sep 2025 07:27:42 +0000 (+0800) Subject: cmd/compile: fix the issue of shift amount exceeding the valid range X-Git-Tag: go1.26rc1~837 X-Git-Url: http://www.git.cypherpunks.su/?a=commitdiff_plain;h=78ef487a6f;p=gostls13.git cmd/compile: fix the issue of shift amount exceeding the valid range Fixes #75479 Change-Id: I362d3e49090e94f91a840dd5a475978b59222a00 Reviewed-on: https://go-review.googlesource.com/c/go/+/704135 Reviewed-by: Mark Freeman LUCI-TryBot-Result: Go LUCI Reviewed-by: Michael Knyszek Reviewed-by: Meidan Li Reviewed-by: abner chenc --- diff --git a/src/cmd/compile/internal/ssa/_gen/LOONG64.rules b/src/cmd/compile/internal/ssa/_gen/LOONG64.rules index d0a64364d6..0d2384143c 100644 --- a/src/cmd/compile/internal/ssa/_gen/LOONG64.rules +++ b/src/cmd/compile/internal/ssa/_gen/LOONG64.rules @@ -717,7 +717,8 @@ (SRLVconst [rc] (MOVBUreg x)) && rc >= 8 => (MOVVconst [0]) // (x + x) << c -> x << c+1 -((SLLV|SLL)const [c] (ADDV x x)) => ((SLLV|SLL)const [c+1] x) +((SLLV|SLL)const [c] (ADDV x x)) && c < t.Size() * 8 - 1 => ((SLLV|SLL)const [c+1] x) +((SLLV|SLL)const [c] (ADDV x x)) && c >= t.Size() * 8 - 1 => (MOVVconst [0]) // mul by constant (MULV _ (MOVVconst [0])) => (MOVVconst [0]) diff --git a/src/cmd/compile/internal/ssa/_gen/LOONG64Ops.go b/src/cmd/compile/internal/ssa/_gen/LOONG64Ops.go index 0d5e0eb76f..a3db4def56 100644 --- a/src/cmd/compile/internal/ssa/_gen/LOONG64Ops.go +++ b/src/cmd/compile/internal/ssa/_gen/LOONG64Ops.go @@ -247,7 +247,7 @@ func init() { {name: "SLL", argLength: 2, reg: gp21, asm: "SLL"}, // arg0 << arg1, shift amount is mod 32 {name: "SLLV", argLength: 2, reg: gp21, asm: "SLLV"}, // arg0 << arg1, shift amount is mod 64 {name: "SLLconst", argLength: 1, reg: gp11, asm: "SLL", aux: "Int64"}, // arg0 << auxInt, auxInt should be in the range 0 to 31. - {name: "SLLVconst", argLength: 1, reg: gp11, asm: "SLLV", aux: "Int64"}, // arg0 << auxInt + {name: "SLLVconst", argLength: 1, reg: gp11, asm: "SLLV", aux: "Int64"}, // arg0 << auxInt, auxInt should be in the range 0 to 63. {name: "SRL", argLength: 2, reg: gp21, asm: "SRL"}, // arg0 >> arg1, shift amount is mod 32 {name: "SRLV", argLength: 2, reg: gp21, asm: "SRLV"}, // arg0 >> arg1, unsigned, shift amount is mod 64 {name: "SRLconst", argLength: 1, reg: gp11, asm: "SRL", aux: "Int64"}, // arg0 >> auxInt, auxInt should be in the range 0 to 31. diff --git a/src/cmd/compile/internal/ssa/rewriteLOONG64.go b/src/cmd/compile/internal/ssa/rewriteLOONG64.go index 6a9b723c8c..3990b2833b 100644 --- a/src/cmd/compile/internal/ssa/rewriteLOONG64.go +++ b/src/cmd/compile/internal/ssa/rewriteLOONG64.go @@ -6561,15 +6561,17 @@ func rewriteValueLOONG64_OpLOONG64SLLV(v *Value) bool { } func rewriteValueLOONG64_OpLOONG64SLLVconst(v *Value) bool { v_0 := v.Args[0] - // match: (SLLVconst [c] (ADDV x x)) + // match: (SLLVconst [c] (ADDV x x)) + // cond: c < t.Size() * 8 - 1 // result: (SLLVconst [c+1] x) for { + t := v.Type c := auxIntToInt64(v.AuxInt) if v_0.Op != OpLOONG64ADDV { break } x := v_0.Args[1] - if x != v_0.Args[0] { + if x != v_0.Args[0] || !(c < t.Size()*8-1) { break } v.reset(OpLOONG64SLLVconst) @@ -6577,6 +6579,23 @@ func rewriteValueLOONG64_OpLOONG64SLLVconst(v *Value) bool { v.AddArg(x) return true } + // match: (SLLVconst [c] (ADDV x x)) + // cond: c >= t.Size() * 8 - 1 + // result: (MOVVconst [0]) + for { + t := v.Type + c := auxIntToInt64(v.AuxInt) + if v_0.Op != OpLOONG64ADDV { + break + } + x := v_0.Args[1] + if x != v_0.Args[0] || !(c >= t.Size()*8-1) { + break + } + v.reset(OpLOONG64MOVVconst) + v.AuxInt = int64ToAuxInt(0) + return true + } // match: (SLLVconst [c] (MOVVconst [d])) // result: (MOVVconst [d< [c] (ADDV x x)) + // cond: c < t.Size() * 8 - 1 // result: (SLLconst [c+1] x) for { + t := v.Type c := auxIntToInt64(v.AuxInt) if v_0.Op != OpLOONG64ADDV { break } x := v_0.Args[1] - if x != v_0.Args[0] { + if x != v_0.Args[0] || !(c < t.Size()*8-1) { break } v.reset(OpLOONG64SLLconst) @@ -6609,6 +6630,23 @@ func rewriteValueLOONG64_OpLOONG64SLLconst(v *Value) bool { v.AddArg(x) return true } + // match: (SLLconst [c] (ADDV x x)) + // cond: c >= t.Size() * 8 - 1 + // result: (MOVVconst [0]) + for { + t := v.Type + c := auxIntToInt64(v.AuxInt) + if v_0.Op != OpLOONG64ADDV { + break + } + x := v_0.Args[1] + if x != v_0.Args[0] || !(c >= t.Size()*8-1) { + break + } + v.reset(OpLOONG64MOVVconst) + v.AuxInt = int64ToAuxInt(0) + return true + } return false } func rewriteValueLOONG64_OpLOONG64SRA(v *Value) bool { diff --git a/test/codegen/shift.go b/test/codegen/shift.go index 7385058726..4b0885a4dd 100644 --- a/test/codegen/shift.go +++ b/test/codegen/shift.go @@ -148,11 +148,13 @@ func lshConst64x2Add(x int64) int64 { } func lshConst32x31Add(x int32) int32 { + // loong64:-"SLL\t","MOVV\tR0" // riscv64:-"SLLI","MOV\t[$]0" return (x + x) << 31 } func lshConst64x63Add(x int64) int64 { + // loong64:-"SLLV","MOVV\tR0" // riscv64:-"SLLI","MOV\t[$]0" return (x + x) << 63 }