From 4fe96ddaf6140de99ad8a046de3989478c443d03 Mon Sep 17 00:00:00 2001 From: Lulu Cai Date: Wed, 2 Apr 2025 10:23:40 +0800 Subject: [PATCH] LoongArch: Warn about right shifts of negative numbers The GNU Assembler User Guide says that the right shift operator ">>" in an expression is the same as the C operator. On LoongArch the assembler directives and instructions do not treat negative numbers ">>" the same way. The directives treats negative numbers ">>" as logical right shifts while the instructions treats them as arithmetic right shifts. The right shift of negative numbers in the instructions may be changed from an arithmetic right shift to a logical right shift in the future, and a warning is issued for this. --- gas/config/loongarch-parse.y | 3 ++ gas/testsuite/gas/loongarch/loongarch.exp | 1 + .../gas/loongarch/negative_right_shift.d | 40 +++++++++++++++++++ .../gas/loongarch/negative_right_shift.l | 13 ++++++ .../gas/loongarch/negative_right_shift.s | 32 +++++++++++++++ 5 files changed, 89 insertions(+) create mode 100644 gas/testsuite/gas/loongarch/negative_right_shift.d create mode 100644 gas/testsuite/gas/loongarch/negative_right_shift.l create mode 100644 gas/testsuite/gas/loongarch/negative_right_shift.s diff --git a/gas/config/loongarch-parse.y b/gas/config/loongarch-parse.y index ac35deee1de..97055fe42c3 100644 --- a/gas/config/loongarch-parse.y +++ b/gas/config/loongarch-parse.y @@ -225,6 +225,9 @@ emit_bin (int op) opr1 = opr1 << opr2; break; case RIGHT_OP: + if (opr1 < 0) + as_warn(_("Right shift of negative numbers may be changed " + "from arithmetic right shift to logical right shift!")); /* Algorithm right shift. */ opr1 = (offsetT)opr1 >> (offsetT)opr2; break; diff --git a/gas/testsuite/gas/loongarch/loongarch.exp b/gas/testsuite/gas/loongarch/loongarch.exp index 87595b91cce..0e836f7f217 100644 --- a/gas/testsuite/gas/loongarch/loongarch.exp +++ b/gas/testsuite/gas/loongarch/loongarch.exp @@ -36,5 +36,6 @@ if [istarget loongarch*-*-*] { if [istarget loongarch64-*-*] { run_list_test "illegal-operand" run_list_test "pseudo_op_option_fail" + run_list_test "negative_right_shift" } } diff --git a/gas/testsuite/gas/loongarch/negative_right_shift.d b/gas/testsuite/gas/loongarch/negative_right_shift.d new file mode 100644 index 00000000000..4237710c2b3 --- /dev/null +++ b/gas/testsuite/gas/loongarch/negative_right_shift.d @@ -0,0 +1,40 @@ +#as: +#objdump: -d +#skip: loongarch32-*-* +#warning_output: negative_right_shift.l + +.*: file format .* + + +Disassembly of section \.text: + +0+ : + 0: 03400000 nop + 4: 00000001 \.word 0x00000001 + 8: 00000001 \.word 0x00000001 + +0+c : + c: 02bff9ac addi.w \$t0, \$t1, -2 + 10: 02fff9ac addi.d \$t0, \$t1, -2 + 14: 13fff9ac addu16i.d \$t0, \$t1, -2 + 18: 15ffffcc lu12i.w \$t0, -2 + 1c: 17ffffcc lu32i.d \$t0, -2 + 20: 033ff9ac lu52i.d \$t0, \$t1, -2 + 24: 023ff9ac slti \$t0, \$t1, -2 + 28: 027ff9ac sltui \$t0, \$t1, -2 + 2c: 19ffffcc pcaddi \$t0, -2 + 30: 1dffffcc pcaddu12i \$t0, -2 + 34: 1fffffcc pcaddu18i \$t0, -2 + 38: 1bffffcc pcalau12i \$t0, -2 + 3c: 02bffdac addi.w \$t0, \$t1, -1 + 40: 02fffdac addi.d \$t0, \$t1, -1 + 44: 13fffdac addu16i.d \$t0, \$t1, -1 + 48: 15ffffec lu12i.w \$t0, -1 + 4c: 17ffffec lu32i.d \$t0, -1 + 50: 033ffdac lu52i.d \$t0, \$t1, -1 + 54: 023ffdac slti \$t0, \$t1, -1 + 58: 027ffdac sltui \$t0, \$t1, -1 + 5c: 19ffffec pcaddi \$t0, -1 + 60: 1dffffec pcaddu12i \$t0, -1 + 64: 1fffffec pcaddu18i \$t0, -1 + 68: 1bffffec pcalau12i \$t0, -1 diff --git a/gas/testsuite/gas/loongarch/negative_right_shift.l b/gas/testsuite/gas/loongarch/negative_right_shift.l new file mode 100644 index 00000000000..6edb2a5ebf8 --- /dev/null +++ b/gas/testsuite/gas/loongarch/negative_right_shift.l @@ -0,0 +1,13 @@ +.*: Assembler messages: +.*: Warning: Right shift of negative numbers may be changed from arithmetic right shift to logical right shift! +.*: Warning: Right shift of negative numbers may be changed from arithmetic right shift to logical right shift! +.*: Warning: Right shift of negative numbers may be changed from arithmetic right shift to logical right shift! +.*: Warning: Right shift of negative numbers may be changed from arithmetic right shift to logical right shift! +.*: Warning: Right shift of negative numbers may be changed from arithmetic right shift to logical right shift! +.*: Warning: Right shift of negative numbers may be changed from arithmetic right shift to logical right shift! +.*: Warning: Right shift of negative numbers may be changed from arithmetic right shift to logical right shift! +.*: Warning: Right shift of negative numbers may be changed from arithmetic right shift to logical right shift! +.*: Warning: Right shift of negative numbers may be changed from arithmetic right shift to logical right shift! +.*: Warning: Right shift of negative numbers may be changed from arithmetic right shift to logical right shift! +.*: Warning: Right shift of negative numbers may be changed from arithmetic right shift to logical right shift! +.*: Warning: Right shift of negative numbers may be changed from arithmetic right shift to logical right shift! diff --git a/gas/testsuite/gas/loongarch/negative_right_shift.s b/gas/testsuite/gas/loongarch/negative_right_shift.s new file mode 100644 index 00000000000..c6a8a1e7c6e --- /dev/null +++ b/gas/testsuite/gas/loongarch/negative_right_shift.s @@ -0,0 +1,32 @@ +directives: +.align -1>>62 +.word -1>>63 +.4byte -1>>63 + +insns: +addi.w $t0, $t1, -1<<1 +addi.d $t0, $t1, -1<<1 +addu16i.d $t0, $t1, -1<<1 +lu12i.w $t0, -1<<1 +lu32i.d $t0, -1<<1 +lu52i.d $t0, $t1, -1<<1 +slti $t0, $t1, -1<<1 +sltui $t0, $t1, -1<<1 +pcaddi $t0, -1<<1 +pcaddu12i $t0, -1<<1 +pcaddu18i $t0, -1<<1 +pcalau12i $t0, -1<<1 + +# warn +addi.w $t0, $t1, -1>>63 +addi.d $t0, $t1, -1>>63 +addu16i.d $t0, $t1, -1>>63 +lu12i.w $t0, -1>>63 +lu32i.d $t0, -1>>63 +lu52i.d $t0, $t1, -1>>63 +slti $t0, $t1, -1>>63 +sltui $t0, $t1, -1>>63 +pcaddi $t0, -1>>63 +pcaddu12i $t0, -1>>63 +pcaddu18i $t0, -1>>63 +pcalau12i $t0, -1>>63 -- 2.39.5