Skip to content

Commit 24a264e

Browse files
authored
Merge pull request #690 from fjatWbyT/next
M0-1-9: Fix dead-code false positive when `constexpr` integer is used in array size
2 parents 8d5ce85 + 8564a44 commit 24a264e

File tree

6 files changed

+38
-14
lines changed

6 files changed

+38
-14
lines changed
Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,2 @@
1+
- `M0-1-9` - `DeadCode.qll`:
2+
- Fixes #678. Remove dead code false positive when integer constant expression is used to define the size of an array.

cpp/autosar/src/rules/M0-1-3/UnusedLocalVariable.ql

Lines changed: 1 addition & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -18,12 +18,6 @@ import cpp
1818
import codingstandards.cpp.autosar
1919
import codingstandards.cpp.deadcode.UnusedVariables
2020

21-
/** Gets the constant value of a constexpr/const variable. */
22-
private string getConstExprValue(Variable v) {
23-
result = v.getInitializer().getExpr().getValue() and
24-
(v.isConst() or v.isConstexpr())
25-
}
26-
2721
// This predicate is similar to getUseCount for M0-1-4 except that it also
2822
// considers static_asserts. This was created to cater for M0-1-3 specifically
2923
// and hence, doesn't attempt to reuse the M0-1-4 specific predicate
@@ -44,11 +38,7 @@ int getUseCountConservatively(Variable v) {
4438
count(StaticAssert s | s.getCondition().getAChild*().getValue() = getConstExprValue(v)) +
4539
// In case an array type uses a constant in the same scope as the constexpr variable,
4640
// consider it as used.
47-
count(ArrayType at, LocalVariable arrayVariable |
48-
arrayVariable.getType().resolveTypedefs() = at and
49-
v.(PotentiallyUnusedLocalVariable).getFunction() = arrayVariable.getFunction() and
50-
at.getArraySize().toString() = getConstExprValue(v)
51-
)
41+
countUsesInLocalArraySize(v)
5242
}
5343

5444
from PotentiallyUnusedLocalVariable v

cpp/common/src/codingstandards/cpp/deadcode/UnusedVariables.qll

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -150,3 +150,21 @@ predicate maybeACompileTimeTemplateArgument(Variable v) {
150150
)
151151
)
152152
}
153+
154+
/** Gets the constant value of a constexpr/const variable. */
155+
string getConstExprValue(Variable v) {
156+
result = v.getInitializer().getExpr().getValue() and
157+
(v.isConst() or v.isConstexpr())
158+
}
159+
160+
/**
161+
* Counts uses of `Variable` v in a local array of size `n`
162+
*/
163+
int countUsesInLocalArraySize(Variable v) {
164+
result =
165+
count(ArrayType at, LocalVariable arrayVariable |
166+
arrayVariable.getType().resolveTypedefs() = at and
167+
v.(PotentiallyUnusedLocalVariable).getFunction() = arrayVariable.getFunction() and
168+
at.getArraySize().toString() = getConstExprValue(v)
169+
)
170+
}

cpp/common/src/codingstandards/cpp/rules/deadcode/DeadCode.qll

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,7 @@ import codingstandards.cpp.Customizations
1616
import codingstandards.cpp.Exclusions
1717
import codingstandards.cpp.deadcode.UselessAssignments
1818
import codingstandards.cpp.deadcode.UnreachableCode
19+
import codingstandards.cpp.deadcode.UnusedVariables
1920

2021
abstract class DeadCodeSharedQuery extends Query { }
2122

@@ -39,6 +40,7 @@ predicate isDeadStmt(Stmt s) {
3940
// - All the declarations are variable declarations
4041
// - None of those variables are ever accessed in non-dead code
4142
// - The initializers for each of the variables are pure
43+
// - It isn't constexpr and used to declare an array size
4244
exists(DeclStmt ds |
4345
ds = s and
4446
// Use forex so that we don't flag "fake" generated `DeclStmt`s (e.g. those generated by the
@@ -50,7 +52,8 @@ predicate isDeadStmt(Stmt s) {
5052
not exists(VariableAccess va |
5153
va.getTarget() = v and
5254
not isDeadOrUnreachableStmt(va.getEnclosingStmt())
53-
)
55+
) and
56+
not countUsesInLocalArraySize(v) > 0
5457
)
5558
)
5659
)

cpp/common/test/rules/deadcode/DeadCode.expected

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -12,3 +12,6 @@
1212
| test.cpp:72:3:73:3 | try { ... } | This statement is dead code. |
1313
| test.cpp:73:17:74:3 | { ... } | This statement is dead code. |
1414
| test.cpp:79:17:80:3 | { ... } | This statement is dead code. |
15+
| test.cpp:85:3:85:43 | declaration | This statement is dead code. |
16+
| test.cpp:87:3:87:30 | declaration | This statement is dead code. |
17+
| test.cpp:90:3:90:50 | declaration | This statement is dead code. |

cpp/common/test/rules/deadcode/test.cpp

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -81,5 +81,13 @@ int test_dead_code(int x) {
8181

8282
static_assert(1); // COMPLIANT
8383

84-
return live5 + live6; // COMPLIANT
85-
}
84+
constexpr int constexpr_array_size{6}; // COMPLIANT
85+
int unused_array[constexpr_array_size]{}; // NON_COMPLIANT
86+
87+
constexpr int unused_int{2}; // NON_COMPLIANT
88+
89+
constexpr int constexpr_used_array[]{3, 4, 5}; // COMPLIANT
90+
constexpr int constexpr_unused_array[]{0, 1, 2}; // NON_COMPLIANT
91+
92+
return live5 + live6 + constexpr_used_array[1]; // COMPLIANT
93+
}

0 commit comments

Comments
 (0)