]> git.lizzy.rs Git - rust.git/commitdiff
move some functions from parser.rs to diagostics.rs
authorAndrew Xu <andrewxuyuan@gmail.com>
Sun, 28 Apr 2019 05:28:07 +0000 (13:28 +0800)
committerAndrew Xu <andrewxuyuan@gmail.com>
Wed, 1 May 2019 11:54:48 +0000 (19:54 +0800)
parser.rs is too big. Some functions only for error reporting and error
recovery are being moved to diagostics.rs.

src/libsyntax/parse/diagnostics.rs [new file with mode: 0644]
src/libsyntax/parse/mod.rs
src/libsyntax/parse/parser.rs

diff --git a/src/libsyntax/parse/diagnostics.rs b/src/libsyntax/parse/diagnostics.rs
new file mode 100644 (file)
index 0000000..32e1ee9
--- /dev/null
@@ -0,0 +1,226 @@
+use crate::ast;
+use crate::ast::{Expr, ExprKind, Item, ItemKind, Pat, PatKind, QSelf, Ty, TyKind};
+use crate::parse::parser::PathStyle;
+use crate::parse::token;
+use crate::parse::PResult;
+use crate::parse::Parser;
+use crate::print::pprust;
+use crate::ptr::P;
+use crate::ThinVec;
+use errors::Applicability;
+use syntax_pos::Span;
+
+pub trait RecoverQPath: Sized + 'static {
+    const PATH_STYLE: PathStyle = PathStyle::Expr;
+    fn to_ty(&self) -> Option<P<Ty>>;
+    fn recovered(qself: Option<QSelf>, path: ast::Path) -> Self;
+}
+
+impl RecoverQPath for Ty {
+    const PATH_STYLE: PathStyle = PathStyle::Type;
+    fn to_ty(&self) -> Option<P<Ty>> {
+        Some(P(self.clone()))
+    }
+    fn recovered(qself: Option<QSelf>, path: ast::Path) -> Self {
+        Self {
+            span: path.span,
+            node: TyKind::Path(qself, path),
+            id: ast::DUMMY_NODE_ID,
+        }
+    }
+}
+
+impl RecoverQPath for Pat {
+    fn to_ty(&self) -> Option<P<Ty>> {
+        self.to_ty()
+    }
+    fn recovered(qself: Option<QSelf>, path: ast::Path) -> Self {
+        Self {
+            span: path.span,
+            node: PatKind::Path(qself, path),
+            id: ast::DUMMY_NODE_ID,
+        }
+    }
+}
+
+impl RecoverQPath for Expr {
+    fn to_ty(&self) -> Option<P<Ty>> {
+        self.to_ty()
+    }
+    fn recovered(qself: Option<QSelf>, path: ast::Path) -> Self {
+        Self {
+            span: path.span,
+            node: ExprKind::Path(qself, path),
+            attrs: ThinVec::new(),
+            id: ast::DUMMY_NODE_ID,
+        }
+    }
+}
+
+impl<'a> Parser<'a> {
+    crate fn maybe_report_ambiguous_plus(
+        &mut self,
+        allow_plus: bool,
+        impl_dyn_multi: bool,
+        ty: &Ty,
+    ) {
+        if !allow_plus && impl_dyn_multi {
+            let sum_with_parens = format!("({})", pprust::ty_to_string(&ty));
+            self.struct_span_err(ty.span, "ambiguous `+` in a type")
+                .span_suggestion(
+                    ty.span,
+                    "use parentheses to disambiguate",
+                    sum_with_parens,
+                    Applicability::MachineApplicable,
+                )
+                .emit();
+        }
+    }
+
+    crate fn maybe_recover_from_bad_type_plus(
+        &mut self,
+        allow_plus: bool,
+        ty: &Ty,
+    ) -> PResult<'a, ()> {
+        // Do not add `+` to expected tokens.
+        if !allow_plus || !self.token.is_like_plus() {
+            return Ok(());
+        }
+
+        self.bump(); // `+`
+        let bounds = self.parse_generic_bounds(None)?;
+        let sum_span = ty.span.to(self.prev_span);
+
+        let mut err = struct_span_err!(
+            self.sess.span_diagnostic,
+            sum_span,
+            E0178,
+            "expected a path on the left-hand side of `+`, not `{}`",
+            pprust::ty_to_string(ty)
+        );
+
+        match ty.node {
+            TyKind::Rptr(ref lifetime, ref mut_ty) => {
+                let sum_with_parens = pprust::to_string(|s| {
+                    use crate::print::pprust::PrintState;
+
+                    s.s.word("&")?;
+                    s.print_opt_lifetime(lifetime)?;
+                    s.print_mutability(mut_ty.mutbl)?;
+                    s.popen()?;
+                    s.print_type(&mut_ty.ty)?;
+                    s.print_type_bounds(" +", &bounds)?;
+                    s.pclose()
+                });
+                err.span_suggestion(
+                    sum_span,
+                    "try adding parentheses",
+                    sum_with_parens,
+                    Applicability::MachineApplicable,
+                );
+            }
+            TyKind::Ptr(..) | TyKind::BareFn(..) => {
+                err.span_label(sum_span, "perhaps you forgot parentheses?");
+            }
+            _ => {
+                err.span_label(sum_span, "expected a path");
+            }
+        }
+        err.emit();
+        Ok(())
+    }
+
+    /// Try to recover from associated item paths like `[T]::AssocItem`/`(T, U)::AssocItem`.
+    /// Attempt to convert the base expression/pattern/type into a type, parse the `::AssocItem`
+    /// tail, and combine them into a `<Ty>::AssocItem` expression/pattern/type.
+    crate fn maybe_recover_from_bad_qpath<T: RecoverQPath>(
+        &mut self,
+        base: P<T>,
+        allow_recovery: bool,
+    ) -> PResult<'a, P<T>> {
+        // Do not add `::` to expected tokens.
+        if allow_recovery && self.token == token::ModSep {
+            if let Some(ty) = base.to_ty() {
+                return self.maybe_recover_from_bad_qpath_stage_2(ty.span, ty);
+            }
+        }
+        Ok(base)
+    }
+
+    /// Given an already parsed `Ty` parse the `::AssocItem` tail and
+    /// combine them into a `<Ty>::AssocItem` expression/pattern/type.
+    crate fn maybe_recover_from_bad_qpath_stage_2<T: RecoverQPath>(
+        &mut self,
+        ty_span: Span,
+        ty: P<Ty>,
+    ) -> PResult<'a, P<T>> {
+        self.expect(&token::ModSep)?;
+
+        let mut path = ast::Path {
+            segments: Vec::new(),
+            span: syntax_pos::DUMMY_SP,
+        };
+        self.parse_path_segments(&mut path.segments, T::PATH_STYLE)?;
+        path.span = ty_span.to(self.prev_span);
+
+        let ty_str = self
+            .sess
+            .source_map()
+            .span_to_snippet(ty_span)
+            .unwrap_or_else(|_| pprust::ty_to_string(&ty));
+        self.diagnostic()
+            .struct_span_err(path.span, "missing angle brackets in associated item path")
+            .span_suggestion(
+                // this is a best-effort recovery
+                path.span,
+                "try",
+                format!("<{}>::{}", ty_str, path),
+                Applicability::MaybeIncorrect,
+            )
+            .emit();
+
+        let path_span = ty_span.shrink_to_hi(); // use an empty path since `position` == 0
+        Ok(P(T::recovered(
+            Some(QSelf {
+                ty,
+                path_span,
+                position: 0,
+            }),
+            path,
+        )))
+    }
+
+    crate fn maybe_consume_incorrect_semicolon(&mut self, items: &[P<Item>]) -> bool {
+        if self.eat(&token::Semi) {
+            let mut err = self.struct_span_err(self.prev_span, "expected item, found `;`");
+            err.span_suggestion_short(
+                self.prev_span,
+                "remove this semicolon",
+                String::new(),
+                Applicability::MachineApplicable,
+            );
+            if !items.is_empty() {
+                let previous_item = &items[items.len() - 1];
+                let previous_item_kind_name = match previous_item.node {
+                    // say "braced struct" because tuple-structs and
+                    // braceless-empty-struct declarations do take a semicolon
+                    ItemKind::Struct(..) => Some("braced struct"),
+                    ItemKind::Enum(..) => Some("enum"),
+                    ItemKind::Trait(..) => Some("trait"),
+                    ItemKind::Union(..) => Some("union"),
+                    _ => None,
+                };
+                if let Some(name) = previous_item_kind_name {
+                    err.help(&format!(
+                        "{} declarations are not followed by a semicolon",
+                        name
+                    ));
+                }
+            }
+            err.emit();
+            true
+        } else {
+            false
+        }
+    }
+}
index 371e8fe5cf66fd5c431fd6b95a55ad9f2dba98f5..608d00f5548f71a9a1f74c687106ccfe148a5a9f 100644 (file)
@@ -30,6 +30,7 @@
 pub mod lexer;
 pub mod token;
 pub mod attr;
+pub mod diagnostics;
 
 pub mod classify;
 
index 8efe84cdf016f087b3ef3f698702b734f3fc8994..6c64055ded1b1986ca82e9c1c31b27b2ee82358b 100644 (file)
@@ -189,41 +189,6 @@ enum PrevTokenKind {
     Other,
 }
 
-trait RecoverQPath: Sized + 'static {
-    const PATH_STYLE: PathStyle = PathStyle::Expr;
-    fn to_ty(&self) -> Option<P<Ty>>;
-    fn recovered(qself: Option<QSelf>, path: ast::Path) -> Self;
-}
-
-impl RecoverQPath for Ty {
-    const PATH_STYLE: PathStyle = PathStyle::Type;
-    fn to_ty(&self) -> Option<P<Ty>> {
-        Some(P(self.clone()))
-    }
-    fn recovered(qself: Option<QSelf>, path: ast::Path) -> Self {
-        Self { span: path.span, node: TyKind::Path(qself, path), id: ast::DUMMY_NODE_ID }
-    }
-}
-
-impl RecoverQPath for Pat {
-    fn to_ty(&self) -> Option<P<Ty>> {
-        self.to_ty()
-    }
-    fn recovered(qself: Option<QSelf>, path: ast::Path) -> Self {
-        Self { span: path.span, node: PatKind::Path(qself, path), id: ast::DUMMY_NODE_ID }
-    }
-}
-
-impl RecoverQPath for Expr {
-    fn to_ty(&self) -> Option<P<Ty>> {
-        self.to_ty()
-    }
-    fn recovered(qself: Option<QSelf>, path: ast::Path) -> Self {
-        Self { span: path.span, node: ExprKind::Path(qself, path),
-               attrs: ThinVec::new(), id: ast::DUMMY_NODE_ID }
-    }
-}
-
 /* ident is handled by common.rs */
 
 #[derive(Clone)]
@@ -1479,7 +1444,7 @@ fn bug(&self, m: &str) -> ! {
     fn span_err<S: Into<MultiSpan>>(&self, sp: S, m: &str) {
         self.sess.span_diagnostic.span_err(sp, m)
     }
-    fn struct_span_err<S: Into<MultiSpan>>(&self, sp: S, m: &str) -> DiagnosticBuilder<'a> {
+    crate fn struct_span_err<S: Into<MultiSpan>>(&self, sp: S, m: &str) -> DiagnosticBuilder<'a> {
         self.sess.span_diagnostic.struct_span_err(sp, m)
     }
     fn struct_span_warn<S: Into<MultiSpan>>(&self, sp: S, m: &str) -> DiagnosticBuilder<'a> {
@@ -1882,99 +1847,6 @@ fn parse_remaining_bounds(&mut self, generic_params: Vec<GenericParam>, path: as
         Ok(TyKind::TraitObject(bounds, TraitObjectSyntax::None))
     }
 
-    fn maybe_report_ambiguous_plus(&mut self, allow_plus: bool, impl_dyn_multi: bool, ty: &Ty) {
-        if !allow_plus && impl_dyn_multi {
-            let sum_with_parens = format!("({})", pprust::ty_to_string(&ty));
-            self.struct_span_err(ty.span, "ambiguous `+` in a type")
-                .span_suggestion(
-                    ty.span,
-                    "use parentheses to disambiguate",
-                    sum_with_parens,
-                    Applicability::MachineApplicable
-                ).emit();
-        }
-    }
-
-    fn maybe_recover_from_bad_type_plus(&mut self, allow_plus: bool, ty: &Ty) -> PResult<'a, ()> {
-        // Do not add `+` to expected tokens.
-        if !allow_plus || !self.token.is_like_plus() {
-            return Ok(())
-        }
-
-        self.bump(); // `+`
-        let bounds = self.parse_generic_bounds(None)?;
-        let sum_span = ty.span.to(self.prev_span);
-
-        let mut err = struct_span_err!(self.sess.span_diagnostic, sum_span, E0178,
-            "expected a path on the left-hand side of `+`, not `{}`", pprust::ty_to_string(ty));
-
-        match ty.node {
-            TyKind::Rptr(ref lifetime, ref mut_ty) => {
-                let sum_with_parens = pprust::to_string(|s| {
-                    use crate::print::pprust::PrintState;
-
-                    s.s.word("&")?;
-                    s.print_opt_lifetime(lifetime)?;
-                    s.print_mutability(mut_ty.mutbl)?;
-                    s.popen()?;
-                    s.print_type(&mut_ty.ty)?;
-                    s.print_type_bounds(" +", &bounds)?;
-                    s.pclose()
-                });
-                err.span_suggestion(
-                    sum_span,
-                    "try adding parentheses",
-                    sum_with_parens,
-                    Applicability::MachineApplicable
-                );
-            }
-            TyKind::Ptr(..) | TyKind::BareFn(..) => {
-                err.span_label(sum_span, "perhaps you forgot parentheses?");
-            }
-            _ => {
-                err.span_label(sum_span, "expected a path");
-            },
-        }
-        err.emit();
-        Ok(())
-    }
-
-    /// Try to recover from associated item paths like `[T]::AssocItem`/`(T, U)::AssocItem`.
-    /// Attempt to convert the base expression/pattern/type into a type, parse the `::AssocItem`
-    /// tail, and combine them into a `<Ty>::AssocItem` expression/pattern/type.
-    fn maybe_recover_from_bad_qpath<T: RecoverQPath>(&mut self, base: P<T>, allow_recovery: bool)
-                                                     -> PResult<'a, P<T>> {
-        // Do not add `::` to expected tokens.
-        if allow_recovery && self.token == token::ModSep {
-            if let Some(ty) = base.to_ty() {
-                return self.maybe_recover_from_bad_qpath_stage_2(ty.span, ty);
-            }
-        }
-        Ok(base)
-    }
-
-    /// Given an already parsed `Ty` parse the `::AssocItem` tail and
-    /// combine them into a `<Ty>::AssocItem` expression/pattern/type.
-    fn maybe_recover_from_bad_qpath_stage_2<T: RecoverQPath>(&mut self, ty_span: Span, ty: P<Ty>)
-                                                             -> PResult<'a, P<T>> {
-        self.expect(&token::ModSep)?;
-
-        let mut path = ast::Path { segments: Vec::new(), span: syntax_pos::DUMMY_SP };
-        self.parse_path_segments(&mut path.segments, T::PATH_STYLE)?;
-        path.span = ty_span.to(self.prev_span);
-
-        let ty_str = self.sess.source_map().span_to_snippet(ty_span)
-            .unwrap_or_else(|_| pprust::ty_to_string(&ty));
-        self.diagnostic()
-            .struct_span_err(path.span, "missing angle brackets in associated item path")
-            .span_suggestion( // this is a best-effort recovery
-                path.span, "try", format!("<{}>::{}", ty_str, path), Applicability::MaybeIncorrect
-            ).emit();
-
-        let path_span = ty_span.shrink_to_hi(); // use an empty path since `position` == 0
-        Ok(P(T::recovered(Some(QSelf { ty, path_span, position: 0 }), path)))
-    }
-
     fn parse_borrowed_pointee(&mut self) -> PResult<'a, TyKind> {
         let opt_lifetime = if self.check_lifetime() { Some(self.expect_lifetime()) } else { None };
         let mutbl = self.parse_mutability();
@@ -2410,7 +2282,7 @@ pub fn parse_path_allowing_meta(&mut self, style: PathStyle) -> PResult<'a, ast:
         self.parse_path(style)
     }
 
-    fn parse_path_segments(&mut self,
+    crate fn parse_path_segments(&mut self,
                            segments: &mut Vec<PathSegment>,
                            style: PathStyle)
                            -> PResult<'a, ()> {
@@ -5815,7 +5687,8 @@ fn parse_generic_bounds_common(&mut self,
         return Ok(bounds);
     }
 
-    fn parse_generic_bounds(&mut self, colon_span: Option<Span>) -> PResult<'a, GenericBounds> {
+    crate fn parse_generic_bounds(&mut self,
+                                  colon_span: Option<Span>) -> PResult<'a, GenericBounds> {
         self.parse_generic_bounds_common(true, colon_span)
     }
 
@@ -7352,37 +7225,6 @@ fn parse_defaultness(&mut self) -> Defaultness {
         }
     }
 
-    fn maybe_consume_incorrect_semicolon(&mut self, items: &[P<Item>]) -> bool {
-        if self.eat(&token::Semi) {
-            let mut err = self.struct_span_err(self.prev_span, "expected item, found `;`");
-            err.span_suggestion_short(
-                self.prev_span,
-                "remove this semicolon",
-                String::new(),
-                Applicability::MachineApplicable,
-            );
-            if !items.is_empty() {
-                let previous_item = &items[items.len()-1];
-                let previous_item_kind_name = match previous_item.node {
-                    // say "braced struct" because tuple-structs and
-                    // braceless-empty-struct declarations do take a semicolon
-                    ItemKind::Struct(..) => Some("braced struct"),
-                    ItemKind::Enum(..) => Some("enum"),
-                    ItemKind::Trait(..) => Some("trait"),
-                    ItemKind::Union(..) => Some("union"),
-                    _ => None,
-                };
-                if let Some(name) = previous_item_kind_name {
-                    err.help(&format!("{} declarations are not followed by a semicolon", name));
-                }
-            }
-            err.emit();
-            true
-        } else {
-            false
-        }
-    }
-
     /// Given a termination token, parses all of the items in a module.
     fn parse_mod_items(&mut self, term: &token::Token, inner_lo: Span) -> PResult<'a, Mod> {
         let mut items = vec![];