Skip to content

Commit d3c69a4

Browse files
committed
Warn write-only fields
1 parent 0e19020 commit d3c69a4

File tree

4 files changed

+66
-0
lines changed

4 files changed

+66
-0
lines changed

compiler/rustc_passes/src/dead.rs

+19
Original file line numberDiff line numberDiff line change
@@ -37,6 +37,19 @@ fn should_explore(tcx: TyCtxt<'_>, hir_id: hir::HirId) -> bool {
3737
)
3838
}
3939

40+
fn base_expr<'a>(expr: &'a hir::Expr<'a>) -> &'a hir::Expr<'a> {
41+
let mut current = expr;
42+
loop {
43+
match current.kind {
44+
hir::ExprKind::Field(base, ..) => {
45+
current = base;
46+
}
47+
_ => break,
48+
}
49+
}
50+
current
51+
}
52+
4053
struct MarkSymbolVisitor<'tcx> {
4154
worklist: Vec<hir::HirId>,
4255
tcx: TyCtxt<'tcx>,
@@ -263,6 +276,12 @@ impl<'tcx> Visitor<'tcx> for MarkSymbolVisitor<'tcx> {
263276
hir::ExprKind::MethodCall(..) => {
264277
self.lookup_and_handle_method(expr.hir_id);
265278
}
279+
hir::ExprKind::Assign(ref left, ref right, ..) => {
280+
// Ignore write to field
281+
self.visit_expr(base_expr(left));
282+
self.visit_expr(right);
283+
return;
284+
}
266285
hir::ExprKind::Field(ref lhs, ..) => {
267286
self.handle_field_access(&lhs, expr.hir_id);
268287
}

src/test/ui/borrowck/borrowck-assign-to-subfield.rs

+1
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
// run-pass
22
// pretty-expanded FIXME #23616
3+
#![allow(dead_code)]
34

45
pub fn main() {
56
struct A {
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
#![deny(dead_code)]
2+
3+
struct S {
4+
f: i32, //~ ERROR: field is never read
5+
sub: Sub, //~ ERROR: field is never read
6+
}
7+
8+
struct Sub {
9+
f: i32, //~ ERROR: field is never read
10+
}
11+
12+
fn field_write(s: &mut S) {
13+
s.f = 1;
14+
s.sub.f = 2;
15+
}
16+
17+
fn main() {
18+
let mut s = S { f: 0, sub: Sub { f: 0 } };
19+
field_write(&mut s);
20+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,26 @@
1+
error: field is never read: `f`
2+
--> $DIR/write-only-field.rs:4:5
3+
|
4+
LL | f: i32,
5+
| ^^^^^^
6+
|
7+
note: the lint level is defined here
8+
--> $DIR/write-only-field.rs:1:9
9+
|
10+
LL | #![deny(dead_code)]
11+
| ^^^^^^^^^
12+
13+
error: field is never read: `sub`
14+
--> $DIR/write-only-field.rs:5:5
15+
|
16+
LL | sub: Sub,
17+
| ^^^^^^^^
18+
19+
error: field is never read: `f`
20+
--> $DIR/write-only-field.rs:9:5
21+
|
22+
LL | f: i32,
23+
| ^^^^^^
24+
25+
error: aborting due to 3 previous errors
26+

0 commit comments

Comments
 (0)