Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Commit f417831

Browse files
committed
C++: Add two more tests to 'unsafe use of this'. First, test that post-dominance removes some results. Second, that a cast to the pure virtual function's defining class (skipping past a derived class that overrides the function) followed by a call to the function still results in an alert. This is also undefined behavior.
1 parent 896dee5 commit f417831

2 files changed

Lines changed: 43 additions & 25 deletions

File tree

Lines changed: 31 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -1,23 +1,26 @@
11
edges
22
| test.cpp:7:2:7:2 | InitializeParameter: B | test.cpp:8:10:8:13 | Load: this |
3-
| test.cpp:8:10:8:13 | Load: this | test.cpp:30:16:30:16 | InitializeParameter: x |
3+
| test.cpp:8:10:8:13 | Load: this | test.cpp:34:16:34:16 | InitializeParameter: x |
44
| test.cpp:11:10:11:10 | InitializeParameter: b | test.cpp:12:9:12:9 | Load: b |
55
| test.cpp:12:9:12:9 | CopyValue: (reference dereference) | test.cpp:12:9:12:9 | ConvertToNonVirtualBase: (A)... |
66
| test.cpp:12:9:12:9 | Load: b | test.cpp:12:9:12:9 | CopyValue: (reference dereference) |
77
| test.cpp:15:2:15:3 | InitializeParameter: ~B | test.cpp:16:3:16:3 | Load: this |
88
| test.cpp:16:3:16:3 | Load: this | file://:0:0:0:0 | ConvertToNonVirtualBase: (A *)... |
9-
| test.cpp:21:2:21:2 | InitializeParameter: C | test.cpp:21:6:21:6 | ConvertToNonVirtualBase: call to B |
9+
| test.cpp:21:2:21:2 | InitializeParameter: C | test.cpp:21:12:21:12 | ConvertToNonVirtualBase: call to B |
1010
| test.cpp:21:2:21:2 | InitializeParameter: C | test.cpp:22:10:22:13 | Load: this |
11-
| test.cpp:21:6:21:6 | ConvertToNonVirtualBase: call to B | test.cpp:7:2:7:2 | InitializeParameter: B |
12-
| test.cpp:22:10:22:13 | ConvertToNonVirtualBase: (B *)... | test.cpp:30:16:30:16 | InitializeParameter: x |
11+
| test.cpp:21:12:21:12 | ConvertToNonVirtualBase: call to B | test.cpp:7:2:7:2 | InitializeParameter: B |
12+
| test.cpp:22:10:22:13 | ConvertToNonVirtualBase: (B *)... | test.cpp:34:16:34:16 | InitializeParameter: x |
1313
| test.cpp:22:10:22:13 | Load: this | test.cpp:22:10:22:13 | ConvertToNonVirtualBase: (B *)... |
14-
| test.cpp:27:5:27:5 | InitializeParameter: D | test.cpp:27:14:27:17 | Load: this |
15-
| test.cpp:27:13:27:17 | ConvertToNonVirtualBase: (B)... | test.cpp:27:13:27:17 | CopyValue: (reference to) |
16-
| test.cpp:27:13:27:17 | CopyValue: (reference to) | test.cpp:11:10:11:10 | InitializeParameter: b |
17-
| test.cpp:27:13:27:17 | CopyValue: * ... | test.cpp:27:13:27:17 | ConvertToNonVirtualBase: (B)... |
18-
| test.cpp:27:14:27:17 | Load: this | test.cpp:27:13:27:17 | CopyValue: * ... |
19-
| test.cpp:30:16:30:16 | InitializeParameter: x | test.cpp:31:2:31:2 | Load: x |
20-
| test.cpp:31:2:31:2 | Load: x | test.cpp:31:2:31:2 | ConvertToNonVirtualBase: (A *)... |
14+
| test.cpp:31:5:31:5 | InitializeParameter: D | test.cpp:31:14:31:17 | Load: this |
15+
| test.cpp:31:13:31:17 | ConvertToNonVirtualBase: (B)... | test.cpp:31:13:31:17 | CopyValue: (reference to) |
16+
| test.cpp:31:13:31:17 | CopyValue: (reference to) | test.cpp:11:10:11:10 | InitializeParameter: b |
17+
| test.cpp:31:13:31:17 | CopyValue: * ... | test.cpp:31:13:31:17 | ConvertToNonVirtualBase: (B)... |
18+
| test.cpp:31:14:31:17 | Load: this | test.cpp:31:13:31:17 | CopyValue: * ... |
19+
| test.cpp:34:16:34:16 | InitializeParameter: x | test.cpp:35:2:35:2 | Load: x |
20+
| test.cpp:35:2:35:2 | Load: x | test.cpp:35:2:35:2 | ConvertToNonVirtualBase: (A *)... |
21+
| test.cpp:47:2:47:2 | InitializeParameter: F | test.cpp:48:8:48:11 | Load: this |
22+
| test.cpp:48:8:48:11 | ConvertToNonVirtualBase: (E *)... | test.cpp:48:4:48:11 | ConvertToNonVirtualBase: (A *)... |
23+
| test.cpp:48:8:48:11 | Load: this | test.cpp:48:8:48:11 | ConvertToNonVirtualBase: (E *)... |
2124
nodes
2225
| file://:0:0:0:0 | ConvertToNonVirtualBase: (A *)... | semmle.label | ConvertToNonVirtualBase: (A *)... |
2326
| test.cpp:7:2:7:2 | InitializeParameter: B | semmle.label | InitializeParameter: B |
@@ -29,19 +32,24 @@ nodes
2932
| test.cpp:15:2:15:3 | InitializeParameter: ~B | semmle.label | InitializeParameter: ~B |
3033
| test.cpp:16:3:16:3 | Load: this | semmle.label | Load: this |
3134
| test.cpp:21:2:21:2 | InitializeParameter: C | semmle.label | InitializeParameter: C |
32-
| test.cpp:21:6:21:6 | ConvertToNonVirtualBase: call to B | semmle.label | ConvertToNonVirtualBase: call to B |
35+
| test.cpp:21:12:21:12 | ConvertToNonVirtualBase: call to B | semmle.label | ConvertToNonVirtualBase: call to B |
3336
| test.cpp:22:10:22:13 | ConvertToNonVirtualBase: (B *)... | semmle.label | ConvertToNonVirtualBase: (B *)... |
3437
| test.cpp:22:10:22:13 | Load: this | semmle.label | Load: this |
35-
| test.cpp:27:5:27:5 | InitializeParameter: D | semmle.label | InitializeParameter: D |
36-
| test.cpp:27:13:27:17 | ConvertToNonVirtualBase: (B)... | semmle.label | ConvertToNonVirtualBase: (B)... |
37-
| test.cpp:27:13:27:17 | CopyValue: (reference to) | semmle.label | CopyValue: (reference to) |
38-
| test.cpp:27:13:27:17 | CopyValue: * ... | semmle.label | CopyValue: * ... |
39-
| test.cpp:27:14:27:17 | Load: this | semmle.label | Load: this |
40-
| test.cpp:30:16:30:16 | InitializeParameter: x | semmle.label | InitializeParameter: x |
41-
| test.cpp:31:2:31:2 | ConvertToNonVirtualBase: (A *)... | semmle.label | ConvertToNonVirtualBase: (A *)... |
42-
| test.cpp:31:2:31:2 | Load: x | semmle.label | Load: x |
38+
| test.cpp:31:5:31:5 | InitializeParameter: D | semmle.label | InitializeParameter: D |
39+
| test.cpp:31:13:31:17 | ConvertToNonVirtualBase: (B)... | semmle.label | ConvertToNonVirtualBase: (B)... |
40+
| test.cpp:31:13:31:17 | CopyValue: (reference to) | semmle.label | CopyValue: (reference to) |
41+
| test.cpp:31:13:31:17 | CopyValue: * ... | semmle.label | CopyValue: * ... |
42+
| test.cpp:31:14:31:17 | Load: this | semmle.label | Load: this |
43+
| test.cpp:34:16:34:16 | InitializeParameter: x | semmle.label | InitializeParameter: x |
44+
| test.cpp:35:2:35:2 | ConvertToNonVirtualBase: (A *)... | semmle.label | ConvertToNonVirtualBase: (A *)... |
45+
| test.cpp:35:2:35:2 | Load: x | semmle.label | Load: x |
46+
| test.cpp:47:2:47:2 | InitializeParameter: F | semmle.label | InitializeParameter: F |
47+
| test.cpp:48:4:48:11 | ConvertToNonVirtualBase: (A *)... | semmle.label | ConvertToNonVirtualBase: (A *)... |
48+
| test.cpp:48:8:48:11 | ConvertToNonVirtualBase: (E *)... | semmle.label | ConvertToNonVirtualBase: (E *)... |
49+
| test.cpp:48:8:48:11 | Load: this | semmle.label | Load: this |
4350
#select
44-
| test.cpp:12:11:12:11 | call to f | test.cpp:27:5:27:5 | InitializeParameter: D | test.cpp:12:9:12:9 | ConvertToNonVirtualBase: (A)... | Call to pure virtual function during construction |
51+
| test.cpp:12:11:12:11 | call to f | test.cpp:31:5:31:5 | InitializeParameter: D | test.cpp:12:9:12:9 | ConvertToNonVirtualBase: (A)... | Call to pure virtual function during construction |
4552
| test.cpp:16:3:16:3 | call to f | test.cpp:15:2:15:3 | InitializeParameter: ~B | file://:0:0:0:0 | ConvertToNonVirtualBase: (A *)... | Call to pure virtual function during destruction |
46-
| test.cpp:31:5:31:5 | call to f | test.cpp:7:2:7:2 | InitializeParameter: B | test.cpp:31:2:31:2 | ConvertToNonVirtualBase: (A *)... | Call to pure virtual function during construction |
47-
| test.cpp:31:5:31:5 | call to f | test.cpp:21:2:21:2 | InitializeParameter: C | test.cpp:31:2:31:2 | ConvertToNonVirtualBase: (A *)... | Call to pure virtual function during construction |
53+
| test.cpp:35:5:35:5 | call to f | test.cpp:7:2:7:2 | InitializeParameter: B | test.cpp:35:2:35:2 | ConvertToNonVirtualBase: (A *)... | Call to pure virtual function during construction |
54+
| test.cpp:35:5:35:5 | call to f | test.cpp:21:2:21:2 | InitializeParameter: C | test.cpp:35:2:35:2 | ConvertToNonVirtualBase: (A *)... | Call to pure virtual function during construction |
55+
| test.cpp:48:15:48:15 | call to f | test.cpp:47:2:47:2 | InitializeParameter: F | test.cpp:48:4:48:11 | ConvertToNonVirtualBase: (A *)... | Call to pure virtual function during construction |

cpp/ql/test/query-tests/Critical/UnsafeUseOfThis/test.cpp

Lines changed: 12 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -18,8 +18,12 @@ struct B : public A {
1818
};
1919

2020
struct C : public B {
21-
C() {
21+
C(bool b) {
2222
call_f(this);
23+
24+
if(b) {
25+
this->f(); // GOOD: Not a 'must' flow
26+
}
2327
}
2428
};
2529

@@ -37,4 +41,10 @@ struct E : public A {
3741
}
3842

3943
void f() override {}
40-
};
44+
};
45+
46+
struct F : public E {
47+
F() {
48+
((A*)this)->f(); // BAD: undefined behavior
49+
}
50+
};

0 commit comments

Comments
 (0)