about summary refs log tree commit diff
path: root/src/test
diff options
context:
space:
mode:
authorFabian Wolff <fabian.wolff@alumni.ethz.ch>2021-07-10 16:38:55 +0200
committerFabian Wolff <fabian.wolff@alumni.ethz.ch>2021-07-31 19:10:58 +0200
commit470cbc0e2eb52c2b80ba6940b6446aecb20f9b04 (patch)
treea1323b17d7938540e6161109ae4b0af576e4d385 /src/test
parent7069a8c2b78c5d23205de1cabb4c2a65229dbd8f (diff)
downloadrust-470cbc0e2eb52c2b80ba6940b6446aecb20f9b04.tar.gz
rust-470cbc0e2eb52c2b80ba6940b6446aecb20f9b04.zip
Require parentheses to avoid confusions around labeled break and loop expressions
Diffstat (limited to 'src/test')
-rw-r--r--src/test/ui/parser/lifetime_starts_expressions.rs32
-rw-r--r--src/test/ui/parser/lifetime_starts_expressions.stderr50
2 files changed, 65 insertions, 17 deletions
diff --git a/src/test/ui/parser/lifetime_starts_expressions.rs b/src/test/ui/parser/lifetime_starts_expressions.rs
index e0098793e1f..903b4de6ef4 100644
--- a/src/test/ui/parser/lifetime_starts_expressions.rs
+++ b/src/test/ui/parser/lifetime_starts_expressions.rs
@@ -1,13 +1,39 @@
+#![allow(unused, dead_code)]
+
 fn foo() -> u32 {
     return 'label: loop { break 'label 42; };
 }
 
 fn bar() -> u32 {
     loop { break 'label: loop { break 'label 42; }; }
-    //~^ ERROR expected identifier, found keyword `loop`
-    //~| ERROR expected type, found keyword `loop`
+    //~^ ERROR: parentheses are required around this expression to avoid confusion
+    //~| HELP: wrap the expression in parentheses
+}
+
+fn baz() -> u32 {
+    'label: loop {
+        break 'label
+        //~^ WARNING: this labeled break expression is easy to confuse with an unlabeled break
+            loop { break 42; };
+            //~^ HELP: wrap this expression in parentheses
+    };
+
+    'label2: loop {
+        break 'label2 'inner: loop { break 42; };
+        // no warnings or errors here
+    }
 }
 
 pub fn main() {
-    foo();
+    // Regression test for issue #86948, as resolved in #87026:
+    let a = 'first_loop: loop {
+        break 'first_loop 1;
+    };
+    let b = loop {
+        break 'inner_loop: loop {
+        //~^ ERROR: parentheses are required around this expression to avoid confusion
+        //~| HELP: wrap the expression in parentheses
+            break 'inner_loop 1;
+        };
+    };
 }
diff --git a/src/test/ui/parser/lifetime_starts_expressions.stderr b/src/test/ui/parser/lifetime_starts_expressions.stderr
index 7275841ebb8..3af2c6b9e57 100644
--- a/src/test/ui/parser/lifetime_starts_expressions.stderr
+++ b/src/test/ui/parser/lifetime_starts_expressions.stderr
@@ -1,23 +1,45 @@
-error: expected identifier, found keyword `loop`
-  --> $DIR/lifetime_starts_expressions.rs:6:26
+error: parentheses are required around this expression to avoid confusion with a labeled break expression
+  --> $DIR/lifetime_starts_expressions.rs:8:18
    |
 LL |     loop { break 'label: loop { break 'label 42; }; }
-   |                          ^^^^ expected identifier, found keyword
+   |                  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
    |
-help: you can escape reserved keywords to use them as identifiers
+help: wrap the expression in parentheses
    |
-LL |     loop { break 'label: r#loop { break 'label 42; }; }
-   |                          ^^^^^^
+LL |     loop { break ('label: loop { break 'label 42; }); }
+   |                  ^                                 ^
 
-error: expected type, found keyword `loop`
-  --> $DIR/lifetime_starts_expressions.rs:6:26
+error: parentheses are required around this expression to avoid confusion with a labeled break expression
+  --> $DIR/lifetime_starts_expressions.rs:33:15
    |
-LL |     loop { break 'label: loop { break 'label 42; }; }
-   |                        - ^^^^ expected type
-   |                        |
-   |                        help: maybe write a path separator here: `::`
+LL |           break 'inner_loop: loop {
+   |  _______________^
+LL | |
+LL | |
+LL | |             break 'inner_loop 1;
+LL | |         };
+   | |_________^
+   |
+help: wrap the expression in parentheses
+   |
+LL |         break ('inner_loop: loop {
+LL |
+LL |
+LL |             break 'inner_loop 1;
+LL |         });
+   |
+
+warning: this labeled break expression is easy to confuse with an unlabeled break with a labeled value expression
+  --> $DIR/lifetime_starts_expressions.rs:15:9
+   |
+LL | /         break 'label
+LL | |
+LL | |             loop { break 42; };
+   | |_____________-----------------^
+   |               |
+   |               help: wrap this expression in parentheses: `(loop { break 42; })`
    |
-   = note: `#![feature(type_ascription)]` lets you annotate an expression with a type: `<expr>: <type>`
+   = note: `#[warn(break_with_label_and_loop)]` on by default
 
-error: aborting due to 2 previous errors
+error: aborting due to 2 previous errors; 1 warning emitted