about summary refs log tree commit diff
diff options
context:
space:
mode:
authorbors <bors@rust-lang.org>2023-02-25 16:10:58 +0000
committerbors <bors@rust-lang.org>2023-02-25 16:10:58 +0000
commit289208bc9fb08704db37c6ce0fb700bbfb3b7099 (patch)
tree82cd1eeaa269a027b8193517948fa66e2685ee2c
parent9a4efb4cc3f6516d27c246bdb414e99bb916b554 (diff)
parent44e47fe4083adbd35889da7a6489ec3252a4f04b (diff)
downloadrust-289208bc9fb08704db37c6ce0fb700bbfb3b7099.tar.gz
rust-289208bc9fb08704db37c6ce0fb700bbfb3b7099.zip
Auto merge of #14203 - shilangyu:fix/angled-path-segments, r=lnicola
fix: Add check for extra path segments after a fully qualified one

`type A = <()>;` is parsed just fine by rust-analyzer, but then rejected by rustc:

```
error: expected `::`, found `;`
 --> x.rs:7:14
  |
7 | type A = <()>;
  |              ^ expected `::`

```

Fixed by adding a lookahead for the `::` token after fully-qualified path segments.
-rw-r--r--crates/hir-def/src/macro_expansion_tests/mbe/regression.rs1
-rw-r--r--crates/parser/src/grammar/paths.rs6
-rw-r--r--crates/parser/test_data/parser/inline/err/0016_angled_path_without_qual.rast49
-rw-r--r--crates/parser/test_data/parser/inline/err/0016_angled_path_without_qual.rs2
4 files changed, 58 insertions, 0 deletions
diff --git a/crates/hir-def/src/macro_expansion_tests/mbe/regression.rs b/crates/hir-def/src/macro_expansion_tests/mbe/regression.rs
index 8358a46f0a9..b663a291789 100644
--- a/crates/hir-def/src/macro_expansion_tests/mbe/regression.rs
+++ b/crates/hir-def/src/macro_expansion_tests/mbe/regression.rs
@@ -827,6 +827,7 @@ macro_rules! rgb_color {
 /* parse error: expected type */
 /* parse error: expected R_PAREN */
 /* parse error: expected R_ANGLE */
+/* parse error: expected `::` */
 /* parse error: expected COMMA */
 /* parse error: expected R_ANGLE */
 /* parse error: expected SEMICOLON */
diff --git a/crates/parser/src/grammar/paths.rs b/crates/parser/src/grammar/paths.rs
index 1064ae9970c..26490aa97e0 100644
--- a/crates/parser/src/grammar/paths.rs
+++ b/crates/parser/src/grammar/paths.rs
@@ -77,6 +77,9 @@ fn path_segment(p: &mut Parser<'_>, mode: Mode, first: bool) {
     // type X = <A as B>::Output;
     // fn foo() { <usize as Default>::default(); }
     if first && p.eat(T![<]) {
+        // test_err angled_path_without_qual
+        // type X = <()>;
+        // type Y = <A as B>;
         types::type_(p);
         if p.eat(T![as]) {
             if is_use_path_start(p) {
@@ -86,6 +89,9 @@ fn path_segment(p: &mut Parser<'_>, mode: Mode, first: bool) {
             }
         }
         p.expect(T![>]);
+        if !p.at(T![::]) {
+            p.error("expected `::`");
+        }
     } else {
         let empty = if first {
             p.eat(T![::]);
diff --git a/crates/parser/test_data/parser/inline/err/0016_angled_path_without_qual.rast b/crates/parser/test_data/parser/inline/err/0016_angled_path_without_qual.rast
new file mode 100644
index 00000000000..0529e9750e7
--- /dev/null
+++ b/crates/parser/test_data/parser/inline/err/0016_angled_path_without_qual.rast
@@ -0,0 +1,49 @@
+SOURCE_FILE
+  TYPE_ALIAS
+    TYPE_KW "type"
+    WHITESPACE " "
+    NAME
+      IDENT "X"
+    WHITESPACE " "
+    EQ "="
+    WHITESPACE " "
+    PATH_TYPE
+      PATH
+        PATH_SEGMENT
+          L_ANGLE "<"
+          TUPLE_TYPE
+            L_PAREN "("
+            R_PAREN ")"
+          R_ANGLE ">"
+    SEMICOLON ";"
+  WHITESPACE "\n"
+  TYPE_ALIAS
+    TYPE_KW "type"
+    WHITESPACE " "
+    NAME
+      IDENT "Y"
+    WHITESPACE " "
+    EQ "="
+    WHITESPACE " "
+    PATH_TYPE
+      PATH
+        PATH_SEGMENT
+          L_ANGLE "<"
+          PATH_TYPE
+            PATH
+              PATH_SEGMENT
+                NAME_REF
+                  IDENT "A"
+          WHITESPACE " "
+          AS_KW "as"
+          WHITESPACE " "
+          PATH_TYPE
+            PATH
+              PATH_SEGMENT
+                NAME_REF
+                  IDENT "B"
+          R_ANGLE ">"
+    SEMICOLON ";"
+  WHITESPACE "\n"
+error 13: expected `::`
+error 32: expected `::`
diff --git a/crates/parser/test_data/parser/inline/err/0016_angled_path_without_qual.rs b/crates/parser/test_data/parser/inline/err/0016_angled_path_without_qual.rs
new file mode 100644
index 00000000000..802d6cc14a4
--- /dev/null
+++ b/crates/parser/test_data/parser/inline/err/0016_angled_path_without_qual.rs
@@ -0,0 +1,2 @@
+type X = <()>;
+type Y = <A as B>;