Skip to content

Commit bacc37d

Browse files
committed
Rust: Add additional tests for intraprocedural data flow
1 parent b3668f8 commit bacc37d

File tree

4 files changed

+190
-53
lines changed

4 files changed

+190
-53
lines changed
Lines changed: 61 additions & 31 deletions
Original file line numberDiff line numberDiff line change
@@ -1,31 +1,61 @@
1-
| main.rs:2:9:2:9 | [SSA] s | main.rs:3:33:3:33 | s |
2-
| main.rs:2:13:2:19 | "Hello" | main.rs:2:9:2:9 | s |
3-
| main.rs:6:18:6:21 | [SSA] cond | main.rs:9:16:9:19 | cond |
4-
| main.rs:7:9:7:9 | [SSA] a | main.rs:10:9:10:9 | a |
5-
| main.rs:7:13:7:13 | 1 | main.rs:7:9:7:9 | a |
6-
| main.rs:8:9:8:9 | [SSA] b | main.rs:12:9:12:9 | b |
7-
| main.rs:8:13:8:13 | 2 | main.rs:8:9:8:9 | b |
8-
| main.rs:9:9:9:9 | [SSA] c | main.rs:14:5:14:5 | c |
9-
| main.rs:9:13:13:5 | IfExpr | main.rs:9:9:9:9 | c |
10-
| main.rs:9:21:11:5 | BlockExpr | main.rs:9:13:13:5 | IfExpr |
11-
| main.rs:10:9:10:9 | a | main.rs:9:21:11:5 | BlockExpr |
12-
| main.rs:11:12:13:5 | BlockExpr | main.rs:9:13:13:5 | IfExpr |
13-
| main.rs:12:9:12:9 | b | main.rs:11:12:13:5 | BlockExpr |
14-
| main.rs:14:5:14:5 | c | main.rs:6:37:15:1 | BlockExpr |
15-
| main.rs:18:9:18:9 | [SSA] a | main.rs:20:15:20:15 | a |
16-
| main.rs:18:13:18:13 | 1 | main.rs:18:9:18:9 | a |
17-
| main.rs:19:9:19:9 | [SSA] b | main.rs:22:5:22:5 | b |
18-
| main.rs:19:13:21:5 | LoopExpr | main.rs:19:9:19:9 | b |
19-
| main.rs:20:9:20:15 | BreakExpr | main.rs:19:13:21:5 | LoopExpr |
20-
| main.rs:20:15:20:15 | a | main.rs:20:9:20:15 | BreakExpr |
21-
| main.rs:22:5:22:5 | b | main.rs:17:29:23:1 | BlockExpr |
22-
| main.rs:26:17:26:17 | 1 | main.rs:26:9:26:13 | i |
23-
| main.rs:27:5:27:5 | [SSA] i | main.rs:28:5:28:5 | i |
24-
| main.rs:27:5:27:5 | i | main.rs:27:5:27:5 | [SSA] i |
25-
| main.rs:28:5:28:5 | i | main.rs:25:24:29:1 | BlockExpr |
26-
| main.rs:31:21:31:21 | [SSA] a | main.rs:33:20:33:20 | a |
27-
| main.rs:31:29:31:29 | [SSA] b | main.rs:34:17:34:17 | b |
28-
| main.rs:31:37:31:37 | [SSA] c | main.rs:32:11:32:11 | c |
29-
| main.rs:32:5:35:5 | MatchExpr | main.rs:31:60:36:1 | BlockExpr |
30-
| main.rs:33:20:33:20 | a | main.rs:32:5:35:5 | MatchExpr |
31-
| main.rs:34:17:34:17 | b | main.rs:32:5:35:5 | MatchExpr |
1+
| main.rs:3:11:3:11 | [SSA] i | main.rs:4:12:4:12 | i |
2+
| main.rs:4:5:4:12 | ... + ... | main.rs:3:26:5:1 | BlockExpr |
3+
| main.rs:7:9:7:9 | [SSA] s | main.rs:8:20:8:20 | s |
4+
| main.rs:19:9:19:9 | [SSA] s | main.rs:20:10:20:10 | s |
5+
| main.rs:19:13:19:21 | CallExpr | main.rs:19:9:19:9 | s |
6+
| main.rs:23:18:23:21 | [SSA] cond | main.rs:26:16:26:19 | cond |
7+
| main.rs:24:9:24:9 | [SSA] a | main.rs:26:23:26:23 | a |
8+
| main.rs:24:13:24:21 | CallExpr | main.rs:24:9:24:9 | a |
9+
| main.rs:25:9:25:9 | [SSA] b | main.rs:26:34:26:34 | b |
10+
| main.rs:25:13:25:13 | 2 | main.rs:25:9:25:9 | b |
11+
| main.rs:26:9:26:9 | [SSA] c | main.rs:27:10:27:10 | c |
12+
| main.rs:26:13:26:36 | IfExpr | main.rs:26:9:26:9 | c |
13+
| main.rs:26:21:26:25 | BlockExpr | main.rs:26:13:26:36 | IfExpr |
14+
| main.rs:26:23:26:23 | a | main.rs:26:21:26:25 | BlockExpr |
15+
| main.rs:26:32:26:36 | BlockExpr | main.rs:26:13:26:36 | IfExpr |
16+
| main.rs:26:34:26:34 | b | main.rs:26:32:26:36 | BlockExpr |
17+
| main.rs:30:21:30:21 | [SSA] m | main.rs:32:19:32:19 | m |
18+
| main.rs:31:9:31:9 | [SSA] a | main.rs:33:20:33:20 | a |
19+
| main.rs:31:13:31:21 | CallExpr | main.rs:31:9:31:9 | a |
20+
| main.rs:32:9:32:9 | [SSA] b | main.rs:36:10:36:10 | b |
21+
| main.rs:32:13:35:5 | MatchExpr | main.rs:32:9:32:9 | b |
22+
| main.rs:33:20:33:20 | a | main.rs:32:13:35:5 | MatchExpr |
23+
| main.rs:34:17:34:17 | 0 | main.rs:32:13:35:5 | MatchExpr |
24+
| main.rs:40:9:40:9 | [SSA] a | main.rs:43:10:43:10 | a |
25+
| main.rs:40:13:42:5 | LoopExpr | main.rs:40:9:40:9 | a |
26+
| main.rs:41:9:41:15 | BreakExpr | main.rs:40:13:42:5 | LoopExpr |
27+
| main.rs:41:15:41:15 | 1 | main.rs:41:9:41:15 | BreakExpr |
28+
| main.rs:44:9:44:9 | [SSA] b | main.rs:47:10:47:10 | b |
29+
| main.rs:44:13:46:5 | LoopExpr | main.rs:44:9:44:9 | b |
30+
| main.rs:45:9:45:23 | BreakExpr | main.rs:44:13:46:5 | LoopExpr |
31+
| main.rs:45:15:45:23 | CallExpr | main.rs:45:9:45:23 | BreakExpr |
32+
| main.rs:51:9:51:13 | [SSA] i | main.rs:52:10:52:10 | i |
33+
| main.rs:51:17:51:17 | 1 | main.rs:51:9:51:13 | i |
34+
| main.rs:53:5:53:5 | [SSA] i | main.rs:54:10:54:10 | i |
35+
| main.rs:53:5:53:5 | i | main.rs:53:5:53:5 | [SSA] i |
36+
| main.rs:61:9:61:9 | [SSA] i | main.rs:62:11:62:11 | i |
37+
| main.rs:61:13:61:31 | CallExpr | main.rs:61:9:61:9 | i |
38+
| main.rs:66:9:66:9 | [SSA] a | main.rs:67:10:67:10 | a |
39+
| main.rs:66:13:66:26 | TupleExpr | main.rs:66:9:66:9 | a |
40+
| main.rs:67:10:67:10 | a | main.rs:68:10:68:10 | a |
41+
| main.rs:78:9:78:9 | [SSA] p | main.rs:83:10:83:10 | p |
42+
| main.rs:78:13:82:5 | RecordExpr | main.rs:78:9:78:9 | p |
43+
| main.rs:83:10:83:10 | p | main.rs:84:10:84:10 | p |
44+
| main.rs:84:10:84:10 | p | main.rs:85:10:85:10 | p |
45+
| main.rs:92:9:92:9 | [SSA] p | main.rs:97:38:97:38 | p |
46+
| main.rs:92:13:96:5 | RecordExpr | main.rs:92:9:92:9 | p |
47+
| main.rs:97:20:97:20 | [SSA] a | main.rs:98:10:98:10 | a |
48+
| main.rs:97:26:97:26 | [SSA] b | main.rs:99:10:99:10 | b |
49+
| main.rs:97:32:97:32 | [SSA] c | main.rs:100:10:100:10 | c |
50+
| main.rs:97:38:97:38 | p | main.rs:97:9:97:34 | RecordPat |
51+
| main.rs:104:9:104:10 | [SSA] s1 | main.rs:106:11:106:12 | s1 |
52+
| main.rs:104:14:104:28 | CallExpr | main.rs:104:9:104:10 | s1 |
53+
| main.rs:105:9:105:10 | [SSA] s2 | main.rs:110:11:110:12 | s2 |
54+
| main.rs:105:14:105:20 | CallExpr | main.rs:105:9:105:10 | s2 |
55+
| main.rs:107:14:107:14 | [SSA] n | main.rs:107:25:107:25 | n |
56+
| main.rs:107:20:107:26 | CallExpr | main.rs:106:5:109:5 | MatchExpr |
57+
| main.rs:108:17:108:23 | CallExpr | main.rs:106:5:109:5 | MatchExpr |
58+
| main.rs:110:5:113:5 | MatchExpr | main.rs:103:27:114:1 | BlockExpr |
59+
| main.rs:111:14:111:14 | [SSA] n | main.rs:111:25:111:25 | n |
60+
| main.rs:111:20:111:26 | CallExpr | main.rs:110:5:113:5 | MatchExpr |
61+
| main.rs:112:17:112:23 | CallExpr | main.rs:110:5:113:5 | MatchExpr |
Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
models
2+
edges
3+
nodes
4+
| main.rs:15:10:15:18 | CallExpr | semmle.label | CallExpr |
5+
subpaths
6+
testFailures
7+
#select
8+
| main.rs:15:10:15:18 | CallExpr | main.rs:15:10:15:18 | CallExpr | main.rs:15:10:15:18 | CallExpr | $@ | main.rs:15:10:15:18 | CallExpr | CallExpr |
Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
/**
2+
* @kind path-problem
3+
*/
4+
5+
import rust
6+
import utils.InlineFlowTest
7+
import DefaultFlowTest
8+
import ValueFlow::PathGraph
9+
10+
from ValueFlow::PathNode source, ValueFlow::PathNode sink
11+
where ValueFlow::flowPath(source, sink)
12+
select sink, source, sink, "$@", source, source.toString()
Lines changed: 109 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -1,41 +1,128 @@
1-
fn variable() {
2-
let s = "Hello";
3-
println!("{:?} data flow!", s);
1+
// Tests for intraprocedural data flow.
2+
3+
fn source(i: i64) -> i64 {
4+
1000 + i
5+
}
6+
7+
fn sink(s: i64) {
8+
println!("{}", s);
9+
}
10+
11+
// -----------------------------------------------------------------------------
12+
// Simple data flow through expressions and assignments
13+
14+
fn direct() {
15+
sink(source(1)); // $ hasValueFlow=1
16+
}
17+
18+
fn variable_usage() {
19+
let s = source(1);
20+
sink(s); // $ MISSING: hasValueFlow=1
421
}
522

6-
fn if_expression(cond: bool) -> i64 {
7-
let a = 1;
23+
fn if_expression(cond: bool) {
24+
let a = source(1);
825
let b = 2;
9-
let c = if cond {
10-
a
11-
} else {
12-
b
26+
let c = if cond { a } else { b };
27+
sink(c); // $ MISSING: hasValueFlow=1
28+
}
29+
30+
fn match_expression(m: Option<i64>) {
31+
let a = source(1);
32+
let b = match m {
33+
Some(_) => a,
34+
None => 0,
1335
};
14-
c
36+
sink(b); // $ MISSING: hasValueFlow=1
1537
}
1638

17-
fn loop_expression() -> i64 {
18-
let a = 1;
39+
fn loop_with_break() {
40+
let a = loop {
41+
break 1;
42+
};
43+
sink(a);
1944
let b = loop {
20-
break a;
45+
break source(1);
2146
};
22-
b
47+
sink(b); // $ MISSING: hasValueFlow=1
2348
}
2449

25-
fn assignment() -> i64 {
50+
fn assignment() {
2651
let mut i = 1;
27-
i = 2;
28-
i
52+
sink(i);
53+
i = source(2);
54+
sink(i); // $ MISSING: hasValueFlow=2
2955
}
3056

31-
fn match_expression(a: i64, b: i64, c: Option<i64>) -> i64 {
32-
match c {
33-
Some(_) => a,
34-
None => b,
57+
// -----------------------------------------------------------------------------
58+
// Data flow through data structures by writing and reading
59+
60+
fn box_deref() {
61+
let i = Box::new(source(1));
62+
sink(*i); // $ MISSING: hasValueFlow=1
63+
}
64+
65+
fn tuple() {
66+
let a = (source(1), 2);
67+
sink(a.0); // $ MISSING: hasValueFlow=1
68+
sink(a.1);
69+
}
70+
71+
struct Point {
72+
x: i64,
73+
y: i64,
74+
z: i64,
75+
}
76+
77+
fn struct_field() {
78+
let p = Point {
79+
x: source(1),
80+
y: 2,
81+
z: source(3),
82+
};
83+
sink(p.x); // MISSING: hasValueFlow=1
84+
sink(p.y);
85+
sink(p.z); // MISSING: hasValueFlow=3
86+
}
87+
88+
// -----------------------------------------------------------------------------
89+
// Data flow through data structures by pattern matching
90+
91+
fn struct_pattern_match() {
92+
let p = Point {
93+
x: source(1),
94+
y: 2,
95+
z: source(3),
96+
};
97+
let Point { x: a, y: b, z: c } = p;
98+
sink(a); // MISSING: hasValueFlow=1
99+
sink(b);
100+
sink(c); // MISSING: hasValueFlow=3
101+
}
102+
103+
fn option_pattern_match() {
104+
let s1 = Some(source(1));
105+
let s2 = Some(2);
106+
match s1 {
107+
Some(n) => sink(n), // MISSING: hasValueFlow=3
108+
None => sink(0),
109+
}
110+
match s2 {
111+
Some(n) => sink(n),
112+
None => sink(0),
35113
}
36114
}
37115

38116
fn main() {
39-
variable();
117+
direct();
118+
variable_usage();
40119
if_expression(true);
120+
match_expression(Some(0));
121+
loop_with_break();
122+
assignment();
123+
box_deref();
124+
tuple();
125+
struct_field();
126+
struct_pattern_match();
127+
option_pattern_match();
41128
}

0 commit comments

Comments
 (0)