Skip to content

Commit

Permalink
Recognise nested tuples/arrays/structs
Browse files Browse the repository at this point in the history
  • Loading branch information
varkor committed Dec 23, 2019
1 parent 5fa02ec commit 5ab4735
Show file tree
Hide file tree
Showing 3 changed files with 30 additions and 12 deletions.
25 changes: 14 additions & 11 deletions src/librustc_typeck/check/expr.rs
Expand Up @@ -723,6 +723,19 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
);
}

fn is_destructuring_place_expr(&self, expr: &'tcx hir::Expr) -> bool {
match &expr.kind {
ExprKind::Array(comps) | ExprKind::Tup(comps) => {
comps.iter().all(|e| self.is_destructuring_place_expr(e))
}
ExprKind::Struct(_path, fields, rest) => {
rest.as_ref().map(|e| self.is_destructuring_place_expr(e)).unwrap_or(true) &&
fields.iter().all(|f| self.is_destructuring_place_expr(&f.expr))
}
_ => expr.is_syntactic_place_expr(),
}
}

pub(crate) fn check_lhs_assignable(
&self,
lhs: &'tcx hir::Expr,
Expand All @@ -736,17 +749,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
DiagnosticId::Error(err_code.into()),
);
err.span_label(lhs.span, "cannot assign to this expression");
let destructuring_assignment = match &lhs.kind {
ExprKind::Array(comps) | ExprKind::Tup(comps) => {
comps.iter().all(|e| e.is_syntactic_place_expr())
}
ExprKind::Struct(_path, fields, rest) => {
rest.as_ref().map(|e| e.is_syntactic_place_expr()).unwrap_or(true) &&
fields.iter().all(|f| f.expr.is_syntactic_place_expr())
}
_ => false,
};
if destructuring_assignment {
if self.is_destructuring_place_expr(lhs) {
err.note("destructuring assignments are not yet supported");
err.note(
"for more information, see https://github.com/rust-lang/rfcs/issues/372",
Expand Down
4 changes: 4 additions & 0 deletions src/test/ui/bad/destructuring-assignment.rs
Expand Up @@ -18,4 +18,8 @@ fn main() {
//~^ ERROR binary assignment operation `+=` cannot be applied

S { x: a, ..s } = S { x: 3, y: 4 }; //~ ERROR invalid left-hand side of assignment

let c = 3;

((a, b), c) = ((3, 4), 5); //~ ERROR invalid left-hand side of assignment
}
13 changes: 12 additions & 1 deletion src/test/ui/bad/destructuring-assignment.stderr
Expand Up @@ -105,7 +105,18 @@ LL | S { x: a, ..s } = S { x: 3, y: 4 };
= note: destructuring assignments are not yet supported
= note: for more information, see https://github.com/rust-lang/rfcs/issues/372

error: aborting due to 10 previous errors
error[E0070]: invalid left-hand side of assignment
--> $DIR/destructuring-assignment.rs:24:5
|
LL | ((a, b), c) = ((3, 4), 5);
| -----------^^^^^^^^^^^^^^
| |
| cannot assign to this expression
|
= note: destructuring assignments are not yet supported
= note: for more information, see https://github.com/rust-lang/rfcs/issues/372

error: aborting due to 11 previous errors

Some errors have detailed explanations: E0067, E0070, E0368.
For more information about an error, try `rustc --explain E0067`.

0 comments on commit 5ab4735

Please sign in to comment.