aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorHannes Domani <ssbssa@yahoo.de>2024-06-11 20:32:59 +0200
committerHannes Domani <ssbssa@yahoo.de>2024-06-11 20:36:34 +0200
commit50f4e9c3c3e5115b346f361de1374837c990f14b (patch)
tree002a6fabba8f02b8ea3c5ae11914e06d301d77cb
parentd17731525424349d7e63b517acf9f45114979fbb (diff)
downloadgdb-50f4e9c3c3e5115b346f361de1374837c990f14b.zip
gdb-50f4e9c3c3e5115b346f361de1374837c990f14b.tar.gz
gdb-50f4e9c3c3e5115b346f361de1374837c990f14b.tar.bz2
Fix too-large or negative right shift of negative numbers
As seen in these test failures: print -1 >> -1 warning: right shift count is negative $N = 0 (gdb) FAIL: gdb.base/bitshift.exp: lang=c: neg lhs/rhs: print -1 >> -1 print -4 >> -2 warning: right shift count is negative $N = 0 (gdb) FAIL: gdb.base/bitshift.exp: lang=c: neg lhs/rhs: print -4 >> -2 Fixed by restoring the logic from before the switch to gmp. Approved-By: Tom Tromey <tom@tromey.com>
-rw-r--r--gdb/testsuite/gdb.base/bitshift.exp1
-rw-r--r--gdb/valarith.c16
2 files changed, 16 insertions, 1 deletions
diff --git a/gdb/testsuite/gdb.base/bitshift.exp b/gdb/testsuite/gdb.base/bitshift.exp
index 17f6b78..d6e2521 100644
--- a/gdb/testsuite/gdb.base/bitshift.exp
+++ b/gdb/testsuite/gdb.base/bitshift.exp
@@ -348,6 +348,7 @@ proc test_shifts {} {
test_shift $lang "print -3 >> 1" " = -2"
test_shift $lang "print -8 >> 1" " = -4"
test_shift $lang "print [make_int64 $lang -8] >> 1" " = -4"
+ test_rshift_tl $lang "print -8 >> 100" " = -1"
}
# Make sure an unsigned 64-bit value with high bit set isn't
diff --git a/gdb/valarith.c b/gdb/valarith.c
index 7034fa6..6160b0e 100644
--- a/gdb/valarith.c
+++ b/gdb/valarith.c
@@ -1303,7 +1303,21 @@ scalar_binop (struct value *arg1, struct value *arg2, enum exp_opcode op)
{
unsigned long nbits;
if (!check_valid_shift_count (op, result_type, type2, v2, nbits))
- v = 0;
+ {
+ /* Pretend the too-large shift was decomposed in a
+ number of smaller shifts. An arithmetic signed
+ right shift of a negative number always yields -1
+ with such semantics. This is the right thing to
+ do for Go, and we might as well do it for
+ languages where it is undefined. Also, pretend a
+ shift by a negative number was a shift by the
+ negative number cast to unsigned, which is the
+ same as shifting by a too-large number. */
+ if (v1 < 0 && !result_type->is_unsigned ())
+ v = -1;
+ else
+ v = 0;
+ }
else
v = v1 >> nbits;
}