From c557cc244b3f33f81fccc4b8bd91f0fc32893e7c Mon Sep 17 00:00:00 2001 From: Tony Zlatinski Date: Mon, 3 Mar 2025 12:11:12 -0600 Subject: [PATCH] Add warning on some cases of integer literal coercion Fix misisng warnings on: int x3 = 18446744073709551615; int x4 = 0xFFFFFFFFFFFFFFFF; Add test cases for the integer literal coercion --- source/slang/slang-parser.cpp | 7 ++++-- .../integer-literal-warnings.slang | 24 +++++++++++++++++++ .../atomic-int64-byte-address-buffer.slang | 2 +- 3 files changed, 30 insertions(+), 3 deletions(-) create mode 100644 tests/diagnostics/integer-literal-warnings.slang diff --git a/source/slang/slang-parser.cpp b/source/slang/slang-parser.cpp index aec3b4e908..ab1250c4b8 100644 --- a/source/slang/slang-parser.cpp +++ b/source/slang/slang-parser.cpp @@ -6897,7 +6897,7 @@ static IntegerLiteralValue _fixIntegerLiteral( // If the masked value is 0 or equal to the mask, we 'assume' no information is // lost // This allows for example -1u, to give 0xffffffff - // It also means 0xfffffffffffffffffu will give 0xffffffff, without a warning. + // It also means 0xffffffffffffffffu will give 0xffffffff, without a warning. if ((!(maskedValue == 0 || maskedValue == mask)) && sink && token) { // Output a warning that number has been altered @@ -6954,8 +6954,11 @@ static BaseType _determineNonSuffixedIntegerLiteralType( { baseType = BaseType::UInt64; - if (isDecimalBase) + // Emit warning if the value is too large for signed 64-bit, regardless of base + // This fixes the inconsistency between decimal and hex literals + if (sink && token) { + // There is an edge case here where 9223372036854775808 or INT64_MAX + 1 // brings us here, but the complete literal is -9223372036854775808 or INT64_MIN and is // valid. Unfortunately because the lexer handles the negative(-) part of the literal diff --git a/tests/diagnostics/integer-literal-warnings.slang b/tests/diagnostics/integer-literal-warnings.slang new file mode 100644 index 0000000000..53ee3d57a5 --- /dev/null +++ b/tests/diagnostics/integer-literal-warnings.slang @@ -0,0 +1,24 @@ +//TEST:SIMPLE(filecheck=CHECK): -target dxbc-assembly + +// Test that UINT64_MAX literals produce appropriate warnings +// This test verifies the fix from commit 0a3c1c8dbd6aa9501ea94a8de69d1a5967034b2c +// which ensures literals equivalent to UINT64_MAX produce appropriate warnings + +void main() +{ + // Decimal form of UINT64_MAX + // CHECK: warning 39999: integer literal is too large to be represented in a signed integer type, interpreting as unsigned + uint64_t a = 18446744073709551615; + + // Hex form of UINT64_MAX + // CHECK: warning 39999: integer literal is too large to be represented in a signed integer type, interpreting as unsigned + uint64_t b = 0xFFFFFFFFFFFFFFFF; + + // Assigning UINT64_MAX to int - should also warn about size + // CHECK: warning 39999: integer literal is too large to be represented in a signed integer type, interpreting as unsigned + int c = 18446744073709551615; + + // Also hex form to int + // CHECK: warning 39999: integer literal is too large to be represented in a signed integer type, interpreting as unsigned + int d = 0xFFFFFFFFFFFFFFFF; +} \ No newline at end of file diff --git a/tests/slang-extension/atomic-int64-byte-address-buffer.slang b/tests/slang-extension/atomic-int64-byte-address-buffer.slang index feb221f205..a51f4fbfa6 100644 --- a/tests/slang-extension/atomic-int64-byte-address-buffer.slang +++ b/tests/slang-extension/atomic-int64-byte-address-buffer.slang @@ -32,6 +32,6 @@ void computeMain(int3 dispatchThreadID : SV_DispatchThreadID) // Bit logical outputBuffer.InterlockedOrU64((idx << 3), (uint64_t(2) << 32) | (tid << 4)); outputBuffer.InterlockedXorU64((idx << 3), tid << 8); - outputBuffer.InterlockedAndU64((idx << 3), (uint64_t(tid | 2) << 32) | 0xffffffffffffffff); + outputBuffer.InterlockedAndU64((idx << 3), (uint64_t(tid | 2) << 32) | 0xffffffffffffffffULL); }