Clean up error messages regarding break/continue inside consts

This commit is contained in:
varkor 2018-07-01 18:31:07 +01:00
parent b00050f4cf
commit 30fde04780
3 changed files with 43 additions and 48 deletions

View File

@ -103,6 +103,7 @@ pub struct LoweringContext<'a> {
loop_scopes: Vec<NodeId>, loop_scopes: Vec<NodeId>,
is_in_loop_condition: bool, is_in_loop_condition: bool,
is_in_trait_impl: bool, is_in_trait_impl: bool,
is_in_anon_const: bool,
/// What to do when we encounter either an "anonymous lifetime /// What to do when we encounter either an "anonymous lifetime
/// reference". The term "anonymous" is meant to encompass both /// reference". The term "anonymous" is meant to encompass both
@ -230,6 +231,7 @@ pub fn lower_crate(
node_id_to_hir_id: IndexVec::new(), node_id_to_hir_id: IndexVec::new(),
is_generator: false, is_generator: false,
is_in_trait_impl: false, is_in_trait_impl: false,
is_in_anon_const: false,
lifetimes_to_define: Vec::new(), lifetimes_to_define: Vec::new(),
is_collecting_in_band_lifetimes: false, is_collecting_in_band_lifetimes: false,
in_scope_lifetimes: Vec::new(), in_scope_lifetimes: Vec::new(),
@ -968,33 +970,32 @@ impl<'a> LoweringContext<'a> {
} }
fn lower_loop_destination(&mut self, destination: Option<(NodeId, Label)>) -> hir::Destination { fn lower_loop_destination(&mut self, destination: Option<(NodeId, Label)>) -> hir::Destination {
let target_id = if self.is_in_anon_const {
Err(hir::LoopIdError::OutsideLoopScope)
} else {
match destination { match destination {
Some((id, label)) => { Some((id, _)) => {
let target_id = if let Def::Label(loop_id) = self.expect_full_def(id) { if let Def::Label(loop_id) = self.expect_full_def(id) {
Ok(self.lower_node_id(loop_id).node_id) Ok(self.lower_node_id(loop_id).node_id)
} else { } else {
Err(hir::LoopIdError::UnresolvedLabel) Err(hir::LoopIdError::UnresolvedLabel)
};
hir::Destination {
label: self.lower_label(Some(label)),
target_id,
} }
} }
None => { None => {
let target_id = self.loop_scopes self.loop_scopes
.last() .last()
.map(|innermost_loop_id| *innermost_loop_id) .map(|innermost_loop_id| *innermost_loop_id)
.map(|id| Ok(self.lower_node_id(id).node_id)) .map(|id| Ok(self.lower_node_id(id).node_id))
.unwrap_or(Err(hir::LoopIdError::OutsideLoopScope)) .unwrap_or(Err(hir::LoopIdError::OutsideLoopScope))
.into(); .into()
}
}
};
hir::Destination { hir::Destination {
label: None, label: self.lower_label(destination.map(|(_, label)| label)),
target_id, target_id,
} }
} }
}
}
fn lower_attrs(&mut self, attrs: &[Attribute]) -> hir::HirVec<Attribute> { fn lower_attrs(&mut self, attrs: &[Attribute]) -> hir::HirVec<Attribute> {
attrs attrs
@ -3440,13 +3441,22 @@ impl<'a> LoweringContext<'a> {
} }
fn lower_anon_const(&mut self, c: &AnonConst) -> hir::AnonConst { fn lower_anon_const(&mut self, c: &AnonConst) -> hir::AnonConst {
let LoweredNodeId { node_id, hir_id } = self.lower_node_id(c.id); let was_in_loop_condition = self.is_in_loop_condition;
self.is_in_loop_condition = false;
let was_in_anon_const = self.is_in_anon_const;
self.is_in_anon_const = true;
hir::AnonConst { let LoweredNodeId { node_id, hir_id } = self.lower_node_id(c.id);
let anon_const = hir::AnonConst {
id: node_id, id: node_id,
hir_id, hir_id,
body: self.lower_body(None, |this| this.lower_expr(&c.value)), body: self.lower_body(None, |this| this.lower_expr(&c.value)),
} };
self.is_in_anon_const = was_in_anon_const;
self.is_in_loop_condition = was_in_loop_condition;
anon_const
} }
fn lower_expr(&mut self, e: &Expr) -> hir::Expr { fn lower_expr(&mut self, e: &Expr) -> hir::Expr {

View File

@ -11,9 +11,7 @@
fn main() { fn main() {
|_: [_; continue]| {}; //~ ERROR: `continue` outside of loop |_: [_; continue]| {}; //~ ERROR: `continue` outside of loop
while |_: [_; continue]| {} {} //~ ERROR: `break` or `continue` with no label while |_: [_; continue]| {} {} //~ ERROR: `continue` outside of loop
//~^ ERROR: `continue` outside of loop
while |_: [_; break]| {} {} //~ ERROR: `break` or `continue` with no label while |_: [_; break]| {} {} //~ ERROR: `break` outside of loop
//~^ ERROR: `break` outside of loop
} }

View File

@ -4,31 +4,18 @@ error[E0268]: `continue` outside of loop
LL | |_: [_; continue]| {}; //~ ERROR: `continue` outside of loop LL | |_: [_; continue]| {}; //~ ERROR: `continue` outside of loop
| ^^^^^^^^ cannot break outside of a loop | ^^^^^^^^ cannot break outside of a loop
error[E0590]: `break` or `continue` with no label in the condition of a `while` loop
--> $DIR/closure-array-break-length.rs:14:19
|
LL | while |_: [_; continue]| {} {} //~ ERROR: `break` or `continue` with no label
| ^^^^^^^^ unlabeled `continue` in the condition of a `while` loop
error[E0268]: `continue` outside of loop error[E0268]: `continue` outside of loop
--> $DIR/closure-array-break-length.rs:14:19 --> $DIR/closure-array-break-length.rs:14:19
| |
LL | while |_: [_; continue]| {} {} //~ ERROR: `break` or `continue` with no label LL | while |_: [_; continue]| {} {} //~ ERROR: `continue` outside of loop
| ^^^^^^^^ cannot break outside of a loop | ^^^^^^^^ cannot break outside of a loop
error[E0590]: `break` or `continue` with no label in the condition of a `while` loop
--> $DIR/closure-array-break-length.rs:17:19
|
LL | while |_: [_; break]| {} {} //~ ERROR: `break` or `continue` with no label
| ^^^^^ unlabeled `break` in the condition of a `while` loop
error[E0268]: `break` outside of loop error[E0268]: `break` outside of loop
--> $DIR/closure-array-break-length.rs:17:19 --> $DIR/closure-array-break-length.rs:16:19
| |
LL | while |_: [_; break]| {} {} //~ ERROR: `break` or `continue` with no label LL | while |_: [_; break]| {} {} //~ ERROR: `break` outside of loop
| ^^^^^ cannot break outside of a loop | ^^^^^ cannot break outside of a loop
error: aborting due to 5 previous errors error: aborting due to 3 previous errors
Some errors occurred: E0268, E0590. For more information about this error, try `rustc --explain E0268`.
For more information about an error, try `rustc --explain E0268`.