Skip to content

Commit b09235f

Browse files
committed
Fix FP for issue 216
exclude file stream call args and heuristic wrappers
1 parent 3aaf853 commit b09235f

File tree

4 files changed

+50
-1
lines changed

4 files changed

+50
-1
lines changed

change_notes/2023-03-16-fp-a5-1-1.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
* `A5-1-1` - reduce false positives by omitting literals written into file streams and wrappers around log and stream calls

cpp/autosar/src/rules/A5-1-1/LiteralValueUsedOutsideTypeInit.ql

Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,25 @@ import cpp
1818
import codingstandards.cpp.autosar
1919
import codingstandards.cpp.LoggingOperation
2020
import codingstandards.cpp.Literals
21+
import codingstandards.cpp.standardlibrary.FileStreams
22+
23+
/**
24+
* In a wrapper `Function`, all accesses of all `Parameters`
25+
* are in located in logging or stream calls
26+
*/
27+
class LoggerOrStreamWrapperFunction extends Function {
28+
LoggerOrStreamWrapperFunction() {
29+
forall(Parameter p | p.getFunction() = this |
30+
forall(VariableAccess va | va = p.getAnAccess() |
31+
(
32+
any(FileStreamFunctionCall fc).getAnArgument().getAChild*() = va
33+
or
34+
any(LoggingOperation logOp).getALoggedExpr().getAChild*() = va
35+
)
36+
)
37+
)
38+
}
39+
}
2140

2241
from Literal l
2342
where
@@ -26,6 +45,11 @@ where
2645
not exists(ConstructorCall cc | cc.getAnArgument() = l) and
2746
not exists(ConstructorFieldInit cf | cf.getExpr() = l) and
2847
not l = any(LoggingOperation logOp).getALoggedExpr().getAChild*() and
48+
not l = any(FileStreamFunctionCall fsc).getAnArgument().getAChild*() and
49+
// Exclude arguments to wrapper functions
50+
not exists(FunctionCall fc, LoggerOrStreamWrapperFunction w |
51+
fc.getAnArgument() = l and w.getACallToThisFunction() = fc
52+
) and
2953
// Exclude literal 0
3054
not l.getValue() = "0" and
3155
// Exclude character literals
Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,5 @@
11
| test.cpp:5:9:5:25 | constant string | Literal value "constant string" used outside of type initialization StringLiteral |
22
| test.cpp:14:23:14:25 | 100 | Literal value 100 used outside of type initialization Literal |
33
| test.cpp:54:7:54:7 | 1 | Literal value 1 used outside of type initialization Literal |
4+
| test.cpp:75:23:75:28 | test | Literal value "test" used outside of type initialization StringLiteral |
5+
| test.cpp:75:31:75:40 | not okay | Literal value "not okay" used outside of type initialization StringLiteral |

cpp/autosar/test/rules/A5-1-1/test.cpp

Lines changed: 23 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -52,4 +52,26 @@ void test_class() {
5252
void test_assignment() {
5353
int x = 0; // COMPLIANT - used in type initialization
5454
x = 1; // NON_COMPLIANT - used in assignment
55-
}
55+
}
56+
57+
void test_stream(std::ostream &os, const char *str) noexcept {
58+
os << str << "logging string"; // COMPLIANT - literal used in stream write
59+
}
60+
61+
#define WRAPPER_MACRO(X, Y) test_stream(X, Y)
62+
63+
void test_wrapper_stream(std::ostream &os, const char *str) noexcept {
64+
test_stream(os, "test"); // COMPLIANT - wrapper for stream write
65+
WRAPPER_MACRO(os, "test"); // COMPLIANT - wrapper for stream write
66+
}
67+
68+
void test_stream_two(std::ostream &os, const char *str,
69+
const char *alt) noexcept {
70+
os << str << "logging string"; // COMPLIANT - literal used in stream write
71+
throw alt;
72+
}
73+
74+
void test_not_wrapper_stream(std::ostream &os, const char *str) noexcept {
75+
test_stream_two(os, "test", "not okay"); // NON_COMPLIANT - test_stream_two is
76+
// not actually exclusively a wrapper
77+
}

0 commit comments

Comments
 (0)