From 8fff3c76b9b1e7de4aa9b0cdb0989c72a88b15fc Mon Sep 17 00:00:00 2001 From: Tim Wojtulewicz Date: Thu, 21 Jul 2022 13:03:16 -0700 Subject: [PATCH] Handle error cases for bit-shift operators more cleanly --- src/Expr.cc | 40 +++++++++++++++++++++++-- testing/btest/Baseline/language.int/out | 1 + testing/btest/language/int.zeek | 4 +-- 3 files changed, 41 insertions(+), 4 deletions(-) diff --git a/src/Expr.cc b/src/Expr.cc index 7ba9559509..3882b9ca89 100644 --- a/src/Expr.cc +++ b/src/Expr.cc @@ -960,11 +960,47 @@ ValPtr BinaryExpr::Fold(Val* v1, Val* v2) const DO_UINT_FOLD(^); break; case EXPR_LSHIFT: - DO_INT_FOLD(<<); + { + if ( is_integral ) + { + if ( i2 < 0 ) + RuntimeError("left shift by negative value"); + else if ( i1 < 1 ) + RuntimeError("left shifting a negative number is undefined"); + + i3 = i1 << i2; + } + else if ( is_unsigned ) + { + if ( u2 < 0 ) + RuntimeError("left shift by negative value"); + + u3 = u1 << u2; + } + else + RuntimeErrorWithCallStack("bad type in BinaryExpr::Fold"); break; + } case EXPR_RSHIFT: - DO_INT_FOLD(>>); + { + if ( is_integral ) + { + if ( i2 < 0 ) + RuntimeError("right shift by negative value"); + + i3 = i1 >> i2; + } + else if ( is_unsigned ) + { + if ( u2 < 0 ) + RuntimeError("right shift by negative value"); + + u3 = u1 >> u2; + } + else + RuntimeErrorWithCallStack("bad type in BinaryExpr::Fold"); break; + } case EXPR_AND_AND: DO_INT_FOLD(&&); diff --git a/testing/btest/Baseline/language.int/out b/testing/btest/Baseline/language.int/out index b2f4f2c04a..f01f5a3de1 100644 --- a/testing/btest/Baseline/language.int/out +++ b/testing/btest/Baseline/language.int/out @@ -18,6 +18,7 @@ modulus operator (PASS) division operator (PASS) assignment operator (PASS) assignment operator (PASS) +bitwise lshift (PASS) bitwise rshift (PASS) max int value = 9223372036854775807 (PASS) min int value = -9223372036854775808 (PASS) diff --git a/testing/btest/language/int.zeek b/testing/btest/language/int.zeek index 1f010e8048..469cd56e07 100644 --- a/testing/btest/language/int.zeek +++ b/testing/btest/language/int.zeek @@ -54,7 +54,8 @@ event zeek_init() test_case( "assignment operator", i2 == 7 ); i2 -= 2; test_case( "assignment operator", i2 == 5 ); - test_case( "bitwise rshift", i10 >> 1 == -6 ); + test_case( "bitwise lshift", i6 << 1 == 24 ); + test_case( "bitwise rshift", i6 >> 1 == 6 ); # Max/min value tests @@ -68,4 +69,3 @@ event zeek_init() test_case( str4, str4 == "min int value = -9223372036854775808" ); } -