about summary refs log tree commit diff
diff options
context:
space:
mode:
authorEsteban Kuber <esteban@kuber.com.ar>2021-08-18 12:00:07 +0000
committerEsteban Kuber <esteban@kuber.com.ar>2021-08-18 14:05:15 +0000
commit9349046ed5b7db491830acc3ec63c29ef9d7f5e5 (patch)
treece311a48de67abd242c67666d833913901eb3df9
parent12a776b41d4ed9bd645cfd7bfb4eb3f95ffabd97 (diff)
downloadrust-9349046ed5b7db491830acc3ec63c29ef9d7f5e5.tar.gz
rust-9349046ed5b7db491830acc3ec63c29ef9d7f5e5.zip
review comment: use newtype to deduplicate logic
-rw-r--r--compiler/rustc_resolve/src/late/diagnostics.rs102
1 files changed, 70 insertions, 32 deletions
diff --git a/compiler/rustc_resolve/src/late/diagnostics.rs b/compiler/rustc_resolve/src/late/diagnostics.rs
index 10f74dc1a04..a602a58e517 100644
--- a/compiler/rustc_resolve/src/late/diagnostics.rs
+++ b/compiler/rustc_resolve/src/late/diagnostics.rs
@@ -2073,47 +2073,85 @@ impl<'tcx> LifetimeContext<'_, 'tcx> {
                         continue;
                     }
                 });
-                let span_unnamed_borrow = |span: Span| {
-                    let lo = span.lo() + BytePos(1);
-                    span.with_lo(lo).with_hi(lo)
-                };
-                let span_underscore_borrow = |span: Span| {
-                    let lo = span.lo() + BytePos(1);
-                    let hi = lo + BytePos(2);
-                    span.with_lo(lo).with_hi(hi)
-                };
-                let unnamed_borrow =
-                    |snippet: &str| snippet.starts_with('&') && !snippet.starts_with("&'");
+
+                struct Lifetime(Span, String);
+                impl Lifetime {
+                    fn is_unnamed(&self) -> bool {
+                        self.1.starts_with('&') && !self.1.starts_with("&'")
+                    }
+                    fn is_underscore(&self) -> bool {
+                        self.1.starts_with("&'_ ")
+                    }
+                    fn is_named(&self) -> bool {
+                        self.1.starts_with("&'")
+                    }
+                    fn suggestion(&self, sugg: String) -> Option<(Span, String)> {
+                        Some(
+                            match (
+                                self.is_unnamed(),
+                                self.is_underscore(),
+                                self.is_named(),
+                                sugg.starts_with("&"),
+                            ) {
+                                (true, _, _, false) => (self.span_unnamed_borrow(), sugg),
+                                (true, _, _, true) => {
+                                    (self.span_unnamed_borrow(), sugg[1..].to_string())
+                                }
+                                (_, true, _, false) => {
+                                    (self.span_underscore_borrow(), sugg.trim().to_string())
+                                }
+                                (_, true, _, true) => {
+                                    (self.span_underscore_borrow(), sugg[1..].trim().to_string())
+                                }
+                                (_, _, true, false) => {
+                                    (self.span_named_borrow(), sugg.trim().to_string())
+                                }
+                                (_, _, true, true) => {
+                                    (self.span_named_borrow(), sugg[1..].trim().to_string())
+                                }
+                                _ => return None,
+                            },
+                        )
+                    }
+                    fn span_unnamed_borrow(&self) -> Span {
+                        let lo = self.0.lo() + BytePos(1);
+                        self.0.with_lo(lo).with_hi(lo)
+                    }
+                    fn span_named_borrow(&self) -> Span {
+                        let lo = self.0.lo() + BytePos(1);
+                        self.0.with_lo(lo)
+                    }
+                    fn span_underscore_borrow(&self) -> Span {
+                        let lo = self.0.lo() + BytePos(1);
+                        let hi = lo + BytePos(2);
+                        self.0.with_lo(lo).with_hi(hi)
+                    }
+                }
+
                 for param in params {
                     if let Ok(snippet) = self.tcx.sess.source_map().span_to_snippet(param.span) {
-                        if unnamed_borrow(&snippet) {
-                            let span = span_unnamed_borrow(param.span);
-                            introduce_suggestion.push((span, "'a ".to_string()));
-                        } else if snippet.starts_with("&'_ ") {
-                            let span = span_underscore_borrow(param.span);
-                            introduce_suggestion.push((span, "'a".to_string()));
+                        if let Some((span, sugg)) =
+                            Lifetime(param.span, snippet).suggestion("'a ".to_string())
+                        {
+                            introduce_suggestion.push((span, sugg));
                         }
                     }
                 }
                 for (span, sugg) in spans_with_counts.iter().copied().zip(suggs.iter()).filter_map(
-                    |((span, _), sugg)| match sugg {
-                        Some(sugg) => Some((span, sugg)),
+                    |((span, _), sugg)| match &sugg {
+                        Some(sugg) => Some((span, sugg.to_string())),
                         _ => None,
                     },
                 ) {
-                    match self.tcx.sess.source_map().span_to_snippet(span) {
-                        Ok(snippet) if unnamed_borrow(&snippet) && sugg.starts_with("&") => {
-                            let span = span_unnamed_borrow(span);
-                            introduce_suggestion.push((span, sugg[1..].to_string()));
-                        }
-                        Ok(snippet) if snippet.starts_with("&'_ ") && sugg.starts_with("&") => {
-                            let span = span_underscore_borrow(span);
-                            introduce_suggestion.push((span, sugg[1..].to_string()));
-                        }
-                        _ => {
-                            introduce_suggestion.push((span, sugg.to_string()));
-                        }
-                    }
+                    let (span, sugg) = self
+                        .tcx
+                        .sess
+                        .source_map()
+                        .span_to_snippet(span)
+                        .ok()
+                        .and_then(|snippet| Lifetime(span, snippet).suggestion(sugg.clone()))
+                        .unwrap_or((span, sugg));
+                    introduce_suggestion.push((span, sugg.to_string()));
                 }
                 err.multipart_suggestion_with_style(
                     &msg,