diff --git a/change_notes/2026-05-21-fix-fp-rule-5-13-4.md b/change_notes/2026-05-21-fix-fp-rule-5-13-4.md new file mode 100644 index 0000000000..3322c7db03 --- /dev/null +++ b/change_notes/2026-05-21-fix-fp-rule-5-13-4.md @@ -0,0 +1,5 @@ +- `RULE-5-13-4`, `M2-13-3` - `UnsignedIntegerLiteralsNotAppropriatelySuffixed.ql`, `MissingUSuffix.ql`: + - Remove FPs in user-defined literals and template instantiations. +- `M2-13-3` - `cpp/autosar/missing-u-suffix`: + - Remove FPs in user-defined literals and template instantiations. + \ No newline at end of file diff --git a/cpp/common/src/codingstandards/cpp/Cpp14Literal.qll b/cpp/common/src/codingstandards/cpp/Cpp14Literal.qll index 8e0c089f4d..3cce767770 100644 --- a/cpp/common/src/codingstandards/cpp/Cpp14Literal.qll +++ b/cpp/common/src/codingstandards/cpp/Cpp14Literal.qll @@ -5,9 +5,20 @@ */ module Cpp14Literal { private import cpp as StandardLibrary - - /** An numeric literal. */ - abstract class NumericLiteral extends StandardLibrary::Literal { } + private import codingstandards.cpp.UserDefinedLiteral + + /** A numeric literal. */ + abstract class NumericLiteral extends StandardLibrary::Literal { + NumericLiteral() { + // exclude user-defined literals as they define custom suffixes + not exists(StandardLibrary::FunctionCall fc | + this = fc.getArgument(0) and + fc.getTarget() instanceof UserDefinedLiteral + ) and + // exclude literals derived from template instantiations + not this.isFromTemplateInstantiation(_) + } + } /** Convenience for implementing class `UnrecognizedNumericLiteral` */ abstract private class RecognizedNumericLiteral extends StandardLibrary::Literal { } diff --git a/cpp/common/test/rules/unsignedintegerliteralsnotappropriatelysuffixed/UnsignedIntegerLiteralsNotAppropriatelySuffixed.expected b/cpp/common/test/rules/unsignedintegerliteralsnotappropriatelysuffixed/UnsignedIntegerLiteralsNotAppropriatelySuffixed.expected index 3326ede548..643c4672a6 100644 --- a/cpp/common/test/rules/unsignedintegerliteralsnotappropriatelysuffixed/UnsignedIntegerLiteralsNotAppropriatelySuffixed.expected +++ b/cpp/common/test/rules/unsignedintegerliteralsnotappropriatelysuffixed/UnsignedIntegerLiteralsNotAppropriatelySuffixed.expected @@ -1,18 +1,18 @@ -| test.cpp:111:3:111:12 | 2147483648 | Hex literal is an unsigned integer but does not include a 'U' suffix. | -| test.cpp:116:3:116:20 | 9223372036854775808 | Hex literal is an unsigned integer but does not include a 'U' suffix. | -| test.cpp:139:3:139:21 | 9223372036854775808 | Hex literal is an unsigned integer but does not include a 'U' suffix. | -| test.cpp:162:3:162:21 | 9223372036854775808 | Hex literal is an unsigned integer but does not include a 'U' suffix. | -| test.cpp:185:3:185:22 | 9223372036854775808 | Hex literal is an unsigned integer but does not include a 'U' suffix. | -| test.cpp:208:3:208:22 | 9223372036854775808 | Hex literal is an unsigned integer but does not include a 'U' suffix. | -| test.cpp:227:3:227:14 | 2147483648 | Octal literal is an unsigned integer but does not include a 'U' suffix. | -| test.cpp:232:3:232:25 | 9223372036854775808 | Octal literal is an unsigned integer but does not include a 'U' suffix. | -| test.cpp:249:3:249:26 | 9223372036854775808 | Octal literal is an unsigned integer but does not include a 'U' suffix. | -| test.cpp:266:3:266:26 | 9223372036854775808 | Octal literal is an unsigned integer but does not include a 'U' suffix. | -| test.cpp:283:3:283:27 | 9223372036854775808 | Octal literal is an unsigned integer but does not include a 'U' suffix. | -| test.cpp:300:3:300:27 | 9223372036854775808 | Octal literal is an unsigned integer but does not include a 'U' suffix. | -| test.cpp:315:3:315:36 | 2147483648 | Binary literal is an unsigned integer but does not include a 'U' suffix. | -| test.cpp:322:3:322:68 | 9223372036854775808 | Binary literal is an unsigned integer but does not include a 'U' suffix. | -| test.cpp:365:3:365:69 | 9223372036854775808 | Binary literal is an unsigned integer but does not include a 'U' suffix. | -| test.cpp:412:3:412:69 | 9223372036854775808 | Binary literal is an unsigned integer but does not include a 'U' suffix. | -| test.cpp:457:3:457:70 | 9223372036854775808 | Binary literal is an unsigned integer but does not include a 'U' suffix. | -| test.cpp:502:3:502:70 | 9223372036854775808 | Binary literal is an unsigned integer but does not include a 'U' suffix. | +| test.cpp:126:3:126:12 | 2147483648 | Hex literal is an unsigned integer but does not include a 'U' suffix. | +| test.cpp:131:3:131:20 | 9223372036854775808 | Hex literal is an unsigned integer but does not include a 'U' suffix. | +| test.cpp:154:3:154:21 | 9223372036854775808 | Hex literal is an unsigned integer but does not include a 'U' suffix. | +| test.cpp:177:3:177:21 | 9223372036854775808 | Hex literal is an unsigned integer but does not include a 'U' suffix. | +| test.cpp:200:3:200:22 | 9223372036854775808 | Hex literal is an unsigned integer but does not include a 'U' suffix. | +| test.cpp:223:3:223:22 | 9223372036854775808 | Hex literal is an unsigned integer but does not include a 'U' suffix. | +| test.cpp:242:3:242:14 | 2147483648 | Octal literal is an unsigned integer but does not include a 'U' suffix. | +| test.cpp:247:3:247:25 | 9223372036854775808 | Octal literal is an unsigned integer but does not include a 'U' suffix. | +| test.cpp:264:3:264:26 | 9223372036854775808 | Octal literal is an unsigned integer but does not include a 'U' suffix. | +| test.cpp:281:3:281:26 | 9223372036854775808 | Octal literal is an unsigned integer but does not include a 'U' suffix. | +| test.cpp:298:3:298:27 | 9223372036854775808 | Octal literal is an unsigned integer but does not include a 'U' suffix. | +| test.cpp:315:3:315:27 | 9223372036854775808 | Octal literal is an unsigned integer but does not include a 'U' suffix. | +| test.cpp:330:3:330:36 | 2147483648 | Binary literal is an unsigned integer but does not include a 'U' suffix. | +| test.cpp:337:3:337:68 | 9223372036854775808 | Binary literal is an unsigned integer but does not include a 'U' suffix. | +| test.cpp:380:3:380:69 | 9223372036854775808 | Binary literal is an unsigned integer but does not include a 'U' suffix. | +| test.cpp:427:3:427:69 | 9223372036854775808 | Binary literal is an unsigned integer but does not include a 'U' suffix. | +| test.cpp:472:3:472:70 | 9223372036854775808 | Binary literal is an unsigned integer but does not include a 'U' suffix. | +| test.cpp:517:3:517:70 | 9223372036854775808 | Binary literal is an unsigned integer but does not include a 'U' suffix. | diff --git a/cpp/common/test/rules/unsignedintegerliteralsnotappropriatelysuffixed/test.cpp b/cpp/common/test/rules/unsignedintegerliteralsnotappropriatelysuffixed/test.cpp index fcbd51b3de..1a32ab9d1e 100644 --- a/cpp/common/test/rules/unsignedintegerliteralsnotappropriatelysuffixed/test.cpp +++ b/cpp/common/test/rules/unsignedintegerliteralsnotappropriatelysuffixed/test.cpp @@ -105,6 +105,21 @@ void test_decimal_constants() { // than max long long int } +constexpr unsigned long long operator""_km(unsigned long long value) { + return value; +} + +void test_user_defined_literal_exclusion() { + 0x80000000_km; // COMPLIANT - user-defined literal argument should be excluded +} + +template +unsigned long long instantiated_literal_exclusion() { + return 0x80000000; // COMPLIANT - template instantiation should be excluded +} + +void test_instantiated_literal_exclusion() { instantiated_literal_exclusion(); } + void test_hexadecimal_constants() { 0x0; // COMPLIANT - uses signed int 0x7FFFFFFF; // COMPLIANT - max value held by signed int