Skip to content

Commit 3c6bed4

Browse files
committed
C++: FP fix for "operator= doesn't return *this"
1 parent 47a548f commit 3c6bed4

File tree

3 files changed

+6
-5
lines changed

3 files changed

+6
-5
lines changed

cpp/ql/src/jsf/4.10 Classes/AV Rule 82.ql

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -72,7 +72,10 @@ predicate assignOperatorWithWrongType(Operator op, string msg) {
7272
predicate assignOperatorWithWrongResult(Operator op, string msg) {
7373
op.hasName("operator=")
7474
and not returnsDereferenceThis(op)
75-
and exists(op.getBlock())
75+
// If a function does not have a reachable `ReturnStmt` then either its body
76+
// was not in the snapshot or it was established by the extractor or the CFG
77+
// pruning that the function never returns.
78+
and exists(ReturnStmt ret | ret.getEnclosingFunction() = op and reachable(ret))
7679
and not op.getType() instanceof VoidType
7780
and not assignOperatorWithWrongType(op, _)
7881
and msg = "Assignment operator in class " + op.getDeclaringType().getName() + " does not return a reference to *this."

cpp/ql/test/query-tests/jsf/4.10 Classes/AV Rule 82/AV Rule 82.cpp

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -118,13 +118,13 @@ struct Exception {
118118

119119
class AlwaysThrows {
120120
public:
121-
AlwaysThrows &operator=(int _val) { // GOOD [FALSE POSITIVE]
121+
AlwaysThrows &operator=(int _val) { // GOOD (always throws)
122122
throw Exception();
123123
// No `return` statement is generated by the C++ front end because it can
124124
// statically see that the end of the function is unreachable.
125125
}
126126

127-
AlwaysThrows &operator=(int *_val) { // GOOD [FALSE POSITIVE]
127+
AlwaysThrows &operator=(int *_val) { // GOOD (always throws)
128128
int one = 1;
129129
if (one)
130130
throw Exception();

cpp/ql/test/query-tests/jsf/4.10 Classes/AV Rule 82/AV Rule 82.expected

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2,5 +2,3 @@
22
| AV Rule 82.cpp:24:8:24:16 | operator= | Assignment operator in class Bad2 should have return type Bad2&. Otherwise a copy is created at each call. |
33
| AV Rule 82.cpp:63:29:63:37 | operator= | Assignment operator in class TemplateReturnAssignment<T> does not return a reference to *this. |
44
| AV Rule 82.cpp:63:29:63:37 | operator= | Assignment operator in class TemplateReturnAssignment<int> does not return a reference to *this. |
5-
| AV Rule 82.cpp:121:17:121:25 | operator= | Assignment operator in class AlwaysThrows does not return a reference to *this. |
6-
| AV Rule 82.cpp:127:17:127:25 | operator= | Assignment operator in class AlwaysThrows does not return a reference to *this. |

0 commit comments

Comments
 (0)