Skip to content

Commit f003e92

Browse files
Don't Suggest Labeling const and unsafe Blocks
1 parent 764675e commit f003e92

5 files changed

+75
-37
lines changed

compiler/rustc_passes/src/loops.rs

+26-14
Original file line numberDiff line numberDiff line change
@@ -19,17 +19,25 @@ use crate::errors::{
1919
OutsideLoopSuggestion, UnlabeledCfInWhileCondition, UnlabeledInLabeledBlock,
2020
};
2121

22+
/// The context in which a block is encountered.
2223
#[derive(Clone, Copy, Debug, PartialEq)]
2324
enum Context {
2425
Normal,
2526
Fn,
2627
Loop(hir::LoopSource),
2728
Closure(Span),
28-
Coroutine { coroutine_span: Span, kind: hir::CoroutineDesugaring, source: hir::CoroutineSource },
29+
Coroutine {
30+
coroutine_span: Span,
31+
kind: hir::CoroutineDesugaring,
32+
source: hir::CoroutineSource,
33+
},
2934
UnlabeledBlock(Span),
3035
UnlabeledIfBlock(Span),
3136
LabeledBlock,
32-
Constant,
37+
/// E.g. The labeled block inside `['_'; 'block: { break 'block 1 + 2; }]`.
38+
AnonConst,
39+
/// E.g. `const { ... }`.
40+
ConstBlock,
3341
}
3442

3543
#[derive(Clone)]
@@ -90,11 +98,11 @@ impl<'a, 'hir> Visitor<'hir> for CheckLoopVisitor<'a, 'hir> {
9098
}
9199

92100
fn visit_anon_const(&mut self, c: &'hir hir::AnonConst) {
93-
self.with_context(Constant, |v| intravisit::walk_anon_const(v, c));
101+
self.with_context(AnonConst, |v| intravisit::walk_anon_const(v, c));
94102
}
95103

96104
fn visit_inline_const(&mut self, c: &'hir hir::ConstBlock) {
97-
self.with_context(Constant, |v| intravisit::walk_inline_const(v, c));
105+
self.with_context(ConstBlock, |v| intravisit::walk_inline_const(v, c));
98106
}
99107

100108
fn visit_fn(
@@ -128,7 +136,7 @@ impl<'a, 'hir> Visitor<'hir> for CheckLoopVisitor<'a, 'hir> {
128136
&& matches!(
129137
ck_loop.cx_stack.last(),
130138
Some(&Normal)
131-
| Some(&Constant)
139+
| Some(&AnonConst)
132140
| Some(&UnlabeledBlock(_))
133141
| Some(&UnlabeledIfBlock(_))
134142
)
@@ -175,14 +183,18 @@ impl<'a, 'hir> Visitor<'hir> for CheckLoopVisitor<'a, 'hir> {
175183
hir::ExprKind::Block(ref b, Some(_label)) => {
176184
self.with_context(LabeledBlock, |v| v.visit_block(b));
177185
}
178-
hir::ExprKind::Block(ref b, None) if matches!(self.cx_stack.last(), Some(&Fn)) => {
186+
hir::ExprKind::Block(ref b, None)
187+
if matches!(self.cx_stack.last(), Some(&Fn) | Some(&ConstBlock)) =>
188+
{
179189
self.with_context(Normal, |v| v.visit_block(b));
180190
}
181-
hir::ExprKind::Block(ref b, None)
182-
if matches!(
183-
self.cx_stack.last(),
184-
Some(&Normal) | Some(&Constant) | Some(&UnlabeledBlock(_))
185-
) =>
191+
hir::ExprKind::Block(
192+
ref b @ hir::Block { rules: hir::BlockCheckMode::DefaultBlock, .. },
193+
None,
194+
) if matches!(
195+
self.cx_stack.last(),
196+
Some(&Normal) | Some(&AnonConst) | Some(&UnlabeledBlock(_))
197+
) =>
186198
{
187199
self.with_context(UnlabeledBlock(b.span.shrink_to_lo()), |v| v.visit_block(b));
188200
}
@@ -353,7 +365,7 @@ impl<'a, 'hir> CheckLoopVisitor<'a, 'hir> {
353365
UnlabeledIfBlock(_) if br_cx_kind == BreakContextKind::Break => {
354366
self.require_break_cx(br_cx_kind, span, break_span, cx_pos - 1);
355367
}
356-
Normal | Constant | Fn | UnlabeledBlock(_) | UnlabeledIfBlock(_) => {
368+
Normal | AnonConst | Fn | UnlabeledBlock(_) | UnlabeledIfBlock(_) | ConstBlock => {
357369
self.sess.dcx().emit_err(OutsideLoop {
358370
spans: vec![span],
359371
name: &br_cx_kind.to_string(),
@@ -365,7 +377,7 @@ impl<'a, 'hir> CheckLoopVisitor<'a, 'hir> {
365377
}
366378

367379
fn require_label_in_labeled_block(
368-
&mut self,
380+
&self,
369381
span: Span,
370382
label: &Destination,
371383
cf_type: &str,
@@ -380,7 +392,7 @@ impl<'a, 'hir> CheckLoopVisitor<'a, 'hir> {
380392
false
381393
}
382394

383-
fn report_outside_loop_error(&mut self) {
395+
fn report_outside_loop_error(&self) {
384396
for (s, block) in &self.block_breaks {
385397
self.sess.dcx().emit_err(OutsideLoop {
386398
spans: block.spans.clone(),

tests/ui/inline-const/break-inside-inline-const-issue-128604.rs

+7
Original file line numberDiff line numberDiff line change
@@ -15,4 +15,11 @@ fn main() {
1515
break;
1616
//~^ ERROR `break` outside of a loop or labeled block
1717
};
18+
19+
{
20+
const {
21+
break;
22+
//~^ ERROR `break` outside of a loop or labeled block
23+
}
24+
}
1825
}

tests/ui/inline-const/break-inside-inline-const-issue-128604.stderr

+13-13
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,15 @@
1+
error[E0268]: `break` outside of a loop or labeled block
2+
--> $DIR/break-inside-inline-const-issue-128604.rs:15:9
3+
|
4+
LL | break;
5+
| ^^^^^ cannot `break` outside of a loop or labeled block
6+
7+
error[E0268]: `break` outside of a loop or labeled block
8+
--> $DIR/break-inside-inline-const-issue-128604.rs:21:13
9+
|
10+
LL | break;
11+
| ^^^^^ cannot `break` outside of a loop or labeled block
12+
113
error[E0268]: `break` outside of a loop or labeled block
214
--> $DIR/break-inside-inline-const-issue-128604.rs:2:21
315
|
@@ -22,18 +34,6 @@ LL |
2234
LL ~ break 'block;
2335
|
2436

25-
error[E0268]: `break` outside of a loop or labeled block
26-
--> $DIR/break-inside-inline-const-issue-128604.rs:15:9
27-
|
28-
LL | break;
29-
| ^^^^^ cannot `break` outside of a loop or labeled block
30-
|
31-
help: consider labeling this block to be able to break within it
32-
|
33-
LL ~ const 'block: {
34-
LL ~ break 'block;
35-
|
36-
37-
error: aborting due to 3 previous errors
37+
error: aborting due to 4 previous errors
3838

3939
For more information about this error, try `rustc --explain E0268`.

tests/ui/unsafe/break-inside-unsafe-block-issue-128604.rs

+16
Original file line numberDiff line numberDiff line change
@@ -15,4 +15,20 @@ fn main() {
1515
//~^ ERROR `break` outside of a loop or labeled block
1616
}
1717

18+
{
19+
//~^ HELP consider labeling this block to be able to break within it
20+
unsafe {
21+
break;
22+
//~^ ERROR `break` outside of a loop or labeled block
23+
}
24+
}
25+
26+
while 2 > 1 {
27+
unsafe {
28+
if true || false {
29+
break;
30+
}
31+
}
32+
}
33+
1834
}

tests/ui/unsafe/break-inside-unsafe-block-issue-128604.stderr

+13-10
Original file line numberDiff line numberDiff line change
@@ -3,11 +3,12 @@ error[E0268]: `break` outside of a loop or labeled block
33
|
44
LL | let a = ["_"; unsafe { break; 1 + 2 }];
55
| ^^^^^ cannot `break` outside of a loop or labeled block
6+
7+
error[E0268]: `break` outside of a loop or labeled block
8+
--> $DIR/break-inside-unsafe-block-issue-128604.rs:14:9
69
|
7-
help: consider labeling this block to be able to break within it
8-
|
9-
LL | let a = ["_"; 'block: unsafe { break 'block; 1 + 2 }];
10-
| +++++++ ++++++
10+
LL | break;
11+
| ^^^^^ cannot `break` outside of a loop or labeled block
1112

1213
error[E0268]: `break` outside of a loop or labeled block
1314
--> $DIR/break-inside-unsafe-block-issue-128604.rs:8:13
@@ -23,17 +24,19 @@ LL ~ break 'block;
2324
|
2425

2526
error[E0268]: `break` outside of a loop or labeled block
26-
--> $DIR/break-inside-unsafe-block-issue-128604.rs:14:9
27+
--> $DIR/break-inside-unsafe-block-issue-128604.rs:21:13
2728
|
28-
LL | break;
29-
| ^^^^^ cannot `break` outside of a loop or labeled block
29+
LL | break;
30+
| ^^^^^ cannot `break` outside of a loop or labeled block
3031
|
3132
help: consider labeling this block to be able to break within it
3233
|
33-
LL ~ 'block: unsafe {
34-
LL ~ break 'block;
34+
LL ~ 'block: {
35+
LL |
36+
LL | unsafe {
37+
LL ~ break 'block;
3538
|
3639

37-
error: aborting due to 3 previous errors
40+
error: aborting due to 4 previous errors
3841

3942
For more information about this error, try `rustc --explain E0268`.

0 commit comments

Comments
 (0)