Skip to content
This repository was archived by the owner on May 28, 2025. It is now read-only.

Commit 707ce2b

Browse files
committed
Account for labels when suggesting loop instead of while true
1 parent dc1eee2 commit 707ce2b

File tree

7 files changed

+116
-12
lines changed

7 files changed

+116
-12
lines changed

compiler/rustc_lint/src/builtin.rs

Lines changed: 9 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -96,18 +96,24 @@ fn pierce_parens(mut expr: &ast::Expr) -> &ast::Expr {
9696

9797
impl EarlyLintPass for WhileTrue {
9898
fn check_expr(&mut self, cx: &EarlyContext<'_>, e: &ast::Expr) {
99-
if let ast::ExprKind::While(cond, ..) = &e.kind {
99+
if let ast::ExprKind::While(cond, _, label) = &e.kind {
100100
if let ast::ExprKind::Lit(ref lit) = pierce_parens(cond).kind {
101101
if let ast::LitKind::Bool(true) = lit.kind {
102102
if !lit.span.from_expansion() {
103103
let msg = "denote infinite loops with `loop { ... }`";
104-
let condition_span = cx.sess.source_map().guess_head_span(e.span);
104+
let condition_span = e.span.with_hi(cond.span.hi());
105105
cx.struct_span_lint(WHILE_TRUE, condition_span, |lint| {
106106
lint.build(msg)
107107
.span_suggestion_short(
108108
condition_span,
109109
"use `loop`",
110-
"loop".to_owned(),
110+
format!(
111+
"{}loop",
112+
label.map_or_else(String::new, |label| format!(
113+
"{}: ",
114+
label.ident,
115+
))
116+
),
111117
Applicability::MachineApplicable,
112118
)
113119
.emit();

src/test/ui/issues/issue-1962.fixed

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3,8 +3,8 @@
33

44
fn main() {
55
let mut i = 0;
6-
loop { //~ ERROR denote infinite loops with `loop
6+
'a: loop { //~ ERROR denote infinite loops with `loop
77
i += 1;
8-
if i == 5 { break; }
8+
if i == 5 { break 'a; }
99
}
1010
}

src/test/ui/issues/issue-1962.rs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3,8 +3,8 @@
33

44
fn main() {
55
let mut i = 0;
6-
while true { //~ ERROR denote infinite loops with `loop
6+
'a: while true { //~ ERROR denote infinite loops with `loop
77
i += 1;
8-
if i == 5 { break; }
8+
if i == 5 { break 'a; }
99
}
1010
}

src/test/ui/issues/issue-1962.stderr

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,8 @@
11
error: denote infinite loops with `loop { ... }`
22
--> $DIR/issue-1962.rs:6:5
33
|
4-
LL | while true {
5-
| ^^^^^^^^^^ help: use `loop`
4+
LL | 'a: while true {
5+
| ^^^^^^^^^^^^^^ help: use `loop`
66
|
77
= note: requested on the command line with `-D while-true`
88

src/test/ui/issues/issue-27042.stderr

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@ warning: denote infinite loops with `loop { ... }`
44
LL | / 'b:
55
LL | |
66
LL | | while true { break }; // but here we cite the whole loop
7-
| |____________________________^ help: use `loop`
7+
| |__________________^ help: use `loop`
88
|
99
= note: `#[warn(while_true)]` on by default
1010

src/test/ui/label/label_misspelled.rs

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -16,3 +16,25 @@ fn main() {
1616
//~^ ERROR cannot find value `for_loop` in this scope
1717
};
1818
}
19+
20+
fn foo() {
21+
'LOOP: loop {
22+
break LOOP;
23+
//~^ ERROR cannot find value `LOOP` in this scope
24+
};
25+
'while_loop: while true { //~ WARN denote infinite loops with
26+
break while_loop;
27+
//~^ ERROR cannot find value `while_loop` in this scope
28+
//~| ERROR `break` with value from a `while` loop
29+
};
30+
'while_let: while let Some(_) = Some(()) {
31+
break while_let;
32+
//~^ ERROR cannot find value `while_let` in this scope
33+
//~| ERROR `break` with value from a `while` loop
34+
}
35+
'for_loop: for _ in 0..3 {
36+
break for_loop;
37+
//~^ ERROR cannot find value `for_loop` in this scope
38+
//~| ERROR `break` with value from a `for` loop
39+
};
40+
}

src/test/ui/label/label_misspelled.stderr

Lines changed: 78 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -34,6 +34,42 @@ LL | for_loop;
3434
| not found in this scope
3535
| help: a label with a similar name exists: `'for_loop`
3636

37+
error[E0425]: cannot find value `LOOP` in this scope
38+
--> $DIR/label_misspelled.rs:22:15
39+
|
40+
LL | break LOOP;
41+
| ^^^^
42+
| |
43+
| not found in this scope
44+
| help: a label with a similar name exists: `'LOOP`
45+
46+
error[E0425]: cannot find value `while_loop` in this scope
47+
--> $DIR/label_misspelled.rs:26:15
48+
|
49+
LL | break while_loop;
50+
| ^^^^^^^^^^
51+
| |
52+
| not found in this scope
53+
| help: a label with a similar name exists: `'while_loop`
54+
55+
error[E0425]: cannot find value `while_let` in this scope
56+
--> $DIR/label_misspelled.rs:31:15
57+
|
58+
LL | break while_let;
59+
| ^^^^^^^^^
60+
| |
61+
| not found in this scope
62+
| help: a label with a similar name exists: `'while_let`
63+
64+
error[E0425]: cannot find value `for_loop` in this scope
65+
--> $DIR/label_misspelled.rs:36:15
66+
|
67+
LL | break for_loop;
68+
| ^^^^^^^^
69+
| |
70+
| not found in this scope
71+
| help: a label with a similar name exists: `'for_loop`
72+
3773
warning: denote infinite loops with `loop { ... }`
3874
--> $DIR/label_misspelled.rs:6:5
3975
|
@@ -42,6 +78,46 @@ LL | 'while_loop: while true {
4278
|
4379
= note: `#[warn(while_true)]` on by default
4480

45-
error: aborting due to 4 previous errors; 1 warning emitted
81+
warning: denote infinite loops with `loop { ... }`
82+
--> $DIR/label_misspelled.rs:25:5
83+
|
84+
LL | 'while_loop: while true {
85+
| ^^^^^^^^^^^^^^^^^^^^^^^ help: use `loop`
86+
87+
error[E0571]: `break` with value from a `while` loop
88+
--> $DIR/label_misspelled.rs:26:9
89+
|
90+
LL | break while_loop;
91+
| ^^^^^^^^^^^^^^^^ can only break with a value inside `loop` or breakable block
92+
|
93+
help: instead, use `break` on its own without a value inside this `while` loop
94+
|
95+
LL | break;
96+
| ^^^^^
97+
98+
error[E0571]: `break` with value from a `while` loop
99+
--> $DIR/label_misspelled.rs:31:9
100+
|
101+
LL | break while_let;
102+
| ^^^^^^^^^^^^^^^ can only break with a value inside `loop` or breakable block
103+
|
104+
help: instead, use `break` on its own without a value inside this `while` loop
105+
|
106+
LL | break;
107+
| ^^^^^
108+
109+
error[E0571]: `break` with value from a `for` loop
110+
--> $DIR/label_misspelled.rs:36:9
111+
|
112+
LL | break for_loop;
113+
| ^^^^^^^^^^^^^^ can only break with a value inside `loop` or breakable block
114+
|
115+
help: instead, use `break` on its own without a value inside this `for` loop
116+
|
117+
LL | break;
118+
| ^^^^^
119+
120+
error: aborting due to 11 previous errors; 2 warnings emitted
46121

47-
For more information about this error, try `rustc --explain E0425`.
122+
Some errors have detailed explanations: E0425, E0571.
123+
For more information about an error, try `rustc --explain E0425`.

0 commit comments

Comments
 (0)