about summary refs log tree commit diff
diff options
context:
space:
mode:
authorMatthew Jasper <mjjasper1@gmail.com>2019-08-24 18:25:34 +0100
committerMatthew Jasper <mjjasper1@gmail.com>2019-08-24 18:25:34 +0100
commit365ff62fca0e1fb6511a47f5f50c4af4df250dfa (patch)
treefef7c6fd187e5fcf713a24bee0982aebb9a3a66e
parent478464570e60523adc6d303577d1782229ca1f93 (diff)
downloadrust-365ff62fca0e1fb6511a47f5f50c4af4df250dfa.tar.gz
rust-365ff62fca0e1fb6511a47f5f50c4af4df250dfa.zip
Don't unwrap the result of `span_to_snippet`
It can return `Err` due to macros being expanded across crates or
files.
-rw-r--r--src/librustc_mir/borrow_check/move_errors.rs84
-rw-r--r--src/librustc_mir/borrow_check/mutability_errors.rs4
-rw-r--r--src/test/ui/borrowck/move-error-snippets-ext.rs7
-rw-r--r--src/test/ui/borrowck/move-error-snippets.rs23
-rw-r--r--src/test/ui/borrowck/move-error-snippets.stderr15
5 files changed, 90 insertions, 43 deletions
diff --git a/src/librustc_mir/borrow_check/move_errors.rs b/src/librustc_mir/borrow_check/move_errors.rs
index 738a091b0dd..f10ff71b15e 100644
--- a/src/librustc_mir/borrow_check/move_errors.rs
+++ b/src/librustc_mir/borrow_check/move_errors.rs
@@ -415,20 +415,21 @@ impl<'a, 'tcx> MirBorrowckCtxt<'a, 'tcx> {
             "{:?}",
             move_place.ty(self.body, self.infcx.tcx).ty,
         );
-        let snippet = self.infcx.tcx.sess.source_map().span_to_snippet(span).unwrap();
-        let is_option = move_ty.starts_with("std::option::Option");
-        let is_result = move_ty.starts_with("std::result::Result");
-        if  is_option || is_result {
-            err.span_suggestion(
-                span,
-                &format!("consider borrowing the `{}`'s content", if is_option {
-                    "Option"
-                } else {
-                    "Result"
-                }),
-                format!("{}.as_ref()", snippet),
-                Applicability::MaybeIncorrect,
-            );
+        if let Ok(snippet) = self.infcx.tcx.sess.source_map().span_to_snippet(span) {
+            let is_option = move_ty.starts_with("std::option::Option");
+            let is_result = move_ty.starts_with("std::result::Result");
+            if is_option || is_result {
+                err.span_suggestion(
+                    span,
+                    &format!("consider borrowing the `{}`'s content", if is_option {
+                        "Option"
+                    } else {
+                        "Result"
+                    }),
+                    format!("{}.as_ref()", snippet),
+                    Applicability::MaybeIncorrect,
+                );
+            }
         }
         err
     }
@@ -439,19 +440,20 @@ impl<'a, 'tcx> MirBorrowckCtxt<'a, 'tcx> {
         err: &mut DiagnosticBuilder<'a>,
         span: Span,
     ) {
-        let snippet = self.infcx.tcx.sess.source_map().span_to_snippet(span).unwrap();
         match error {
             GroupedMoveError::MovesFromPlace {
                 mut binds_to,
                 move_from,
                 ..
             } => {
-                err.span_suggestion(
-                    span,
-                    "consider borrowing here",
-                    format!("&{}", snippet),
-                    Applicability::Unspecified,
-                );
+                if let Ok(snippet) = self.infcx.tcx.sess.source_map().span_to_snippet(span) {
+                    err.span_suggestion(
+                        span,
+                        "consider borrowing here",
+                        format!("&{}", snippet),
+                        Applicability::Unspecified,
+                    );
+                }
 
                 if binds_to.is_empty() {
                     let place_ty = move_from.ty(self.body, self.infcx.tcx).ty;
@@ -517,27 +519,27 @@ impl<'a, 'tcx> MirBorrowckCtxt<'a, 'tcx> {
                     ..
                 }))
             ) = bind_to.is_user_variable {
-                let pat_snippet = self.infcx.tcx.sess.source_map()
-                    .span_to_snippet(pat_span)
-                    .unwrap();
-                if pat_snippet.starts_with('&') {
-                    let pat_snippet = pat_snippet[1..].trim_start();
-                    let suggestion;
-                    let to_remove;
-                    if pat_snippet.starts_with("mut")
-                        && pat_snippet["mut".len()..].starts_with(Pattern_White_Space)
-                    {
-                        suggestion = pat_snippet["mut".len()..].trim_start();
-                        to_remove = "&mut";
-                    } else {
-                        suggestion = pat_snippet;
-                        to_remove = "&";
+                if let Ok(pat_snippet) = self.infcx.tcx.sess.source_map().span_to_snippet(pat_span)
+                {
+                    if pat_snippet.starts_with('&') {
+                        let pat_snippet = pat_snippet[1..].trim_start();
+                        let suggestion;
+                        let to_remove;
+                        if pat_snippet.starts_with("mut")
+                            && pat_snippet["mut".len()..].starts_with(Pattern_White_Space)
+                        {
+                            suggestion = pat_snippet["mut".len()..].trim_start();
+                            to_remove = "&mut";
+                        } else {
+                            suggestion = pat_snippet;
+                            to_remove = "&";
+                        }
+                        suggestions.push((
+                            pat_span,
+                            to_remove,
+                            suggestion.to_owned(),
+                        ));
                     }
-                    suggestions.push((
-                        pat_span,
-                        to_remove,
-                        suggestion.to_owned(),
-                    ));
                 }
             }
         }
diff --git a/src/librustc_mir/borrow_check/mutability_errors.rs b/src/librustc_mir/borrow_check/mutability_errors.rs
index 937c6383be3..e7f37431e50 100644
--- a/src/librustc_mir/borrow_check/mutability_errors.rs
+++ b/src/librustc_mir/borrow_check/mutability_errors.rs
@@ -711,8 +711,8 @@ fn annotate_struct_field(
 }
 
 /// If possible, suggest replacing `ref` with `ref mut`.
-fn suggest_ref_mut(tcx: TyCtxt<'_>, binding_span: Span) -> Option<(String)> {
-    let hi_src = tcx.sess.source_map().span_to_snippet(binding_span).unwrap();
+fn suggest_ref_mut(tcx: TyCtxt<'_>, binding_span: Span) -> Option<String> {
+    let hi_src = tcx.sess.source_map().span_to_snippet(binding_span).ok()?;
     if hi_src.starts_with("ref")
         && hi_src["ref".len()..].starts_with(Pattern_White_Space)
     {
diff --git a/src/test/ui/borrowck/move-error-snippets-ext.rs b/src/test/ui/borrowck/move-error-snippets-ext.rs
new file mode 100644
index 00000000000..c77f6c8276e
--- /dev/null
+++ b/src/test/ui/borrowck/move-error-snippets-ext.rs
@@ -0,0 +1,7 @@
+// ignore-test
+
+macro_rules! aaa {
+    ($c:ident) => {{
+        let a = $c;
+    }}
+}
diff --git a/src/test/ui/borrowck/move-error-snippets.rs b/src/test/ui/borrowck/move-error-snippets.rs
new file mode 100644
index 00000000000..64f95653828
--- /dev/null
+++ b/src/test/ui/borrowck/move-error-snippets.rs
@@ -0,0 +1,23 @@
+// Test that we don't ICE after trying to construct a cross-file snippet #63800.
+
+// compile-flags: --test
+
+#[macro_use]
+#[path = "move-error-snippets-ext.rs"]
+mod move_error_snippets_ext;
+
+struct A;
+
+macro_rules! sss {
+    () => {
+        #[test]
+        fn fff() {
+            static D: A = A;
+            aaa!(D);         //~ ERROR cannot move
+        }
+    };
+}
+
+sss!();
+
+fn main() {}
diff --git a/src/test/ui/borrowck/move-error-snippets.stderr b/src/test/ui/borrowck/move-error-snippets.stderr
new file mode 100644
index 00000000000..77463c48591
--- /dev/null
+++ b/src/test/ui/borrowck/move-error-snippets.stderr
@@ -0,0 +1,15 @@
+error[E0507]: cannot move out of static item `D`
+  --> $DIR/move-error-snippets.rs:16:18
+   |
+LL | | #[macro_use]
+   | |__________________^ move occurs because `D` has type `A`, which does not implement the `Copy` trait
+...
+LL |               aaa!(D);
+   |  __________________^
+...
+LL |   sss!();
+   |   ------- in this macro invocation
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0507`.