about summary refs log tree commit diff
diff options
context:
space:
mode:
authorSNCPlay42 <SNCPlay42@gmail.com>2020-07-21 19:56:21 +0100
committerSNCPlay42 <SNCPlay42@gmail.com>2020-10-05 14:01:42 +0100
commit34ff35298938f0d0ae477618b17a41d5afc00a7a (patch)
tree85e85c741a158efd482d794d4c62c7d24c253221
parent62bfcfd8a3b1603e2b5f5e2c011aa0f35f117af1 (diff)
downloadrust-34ff35298938f0d0ae477618b17a41d5afc00a7a.tar.gz
rust-34ff35298938f0d0ae477618b17a41d5afc00a7a.zip
don't refer to async as 'generators'
and give return of async fn a better span
-rw-r--r--compiler/rustc_mir/src/borrow_check/diagnostics/region_name.rs30
-rw-r--r--src/test/ui/async-await/issue-74072-lifetime-name-annotations.rs29
-rw-r--r--src/test/ui/async-await/issue-74072-lifetime-name-annotations.stderr39
3 files changed, 92 insertions, 6 deletions
diff --git a/compiler/rustc_mir/src/borrow_check/diagnostics/region_name.rs b/compiler/rustc_mir/src/borrow_check/diagnostics/region_name.rs
index 2e5a231fef0..bf512451568 100644
--- a/compiler/rustc_mir/src/borrow_check/diagnostics/region_name.rs
+++ b/compiler/rustc_mir/src/borrow_check/diagnostics/region_name.rs
@@ -657,15 +657,33 @@ impl<'tcx> MirBorrowckCtxt<'_, 'tcx> {
 
         let (return_span, mir_description) = match tcx.hir().get(self.mir_hir_id()) {
             hir::Node::Expr(hir::Expr {
-                kind: hir::ExprKind::Closure(_, return_ty, _, span, gen_move),
+                kind: hir::ExprKind::Closure(_, return_ty, body_id, span, _),
                 ..
-            }) => (
-                match return_ty.output {
+            }) => {
+                let mut span = match return_ty.output {
                     hir::FnRetTy::DefaultReturn(_) => tcx.sess.source_map().end_point(*span),
                     hir::FnRetTy::Return(_) => return_ty.output.span(),
-                },
-                if gen_move.is_some() { " of generator" } else { " of closure" },
-            ),
+                };
+                let mir_description = match tcx.hir().body(*body_id).generator_kind {
+                    Some(hir::GeneratorKind::Async(gen)) => match gen {
+                        hir::AsyncGeneratorKind::Block => " of async block",
+                        hir::AsyncGeneratorKind::Closure => " of async closure",
+                        hir::AsyncGeneratorKind::Fn => {
+                            span = tcx
+                                .hir()
+                                .get(tcx.hir().get_parent_item(mir_hir_id))
+                                .fn_decl()
+                                .expect("generator lowered from async fn should be in fn")
+                                .output
+                                .span();
+                            " of async function"
+                        }
+                    },
+                    Some(hir::GeneratorKind::Gen) => " of generator",
+                    None => " of closure",
+                };
+                (span, mir_description)
+            }
             hir::Node::ImplItem(hir::ImplItem {
                 kind: hir::ImplItemKind::Fn(method_sig, _),
                 ..
diff --git a/src/test/ui/async-await/issue-74072-lifetime-name-annotations.rs b/src/test/ui/async-await/issue-74072-lifetime-name-annotations.rs
new file mode 100644
index 00000000000..f8e11633359
--- /dev/null
+++ b/src/test/ui/async-await/issue-74072-lifetime-name-annotations.rs
@@ -0,0 +1,29 @@
+// edition:2018
+#![feature(async_closure)]
+use std::future::Future;
+
+// test the quality of annotations giving lifetimes names (`'1`) when async constructs are involved
+
+pub async fn async_fn(x: &mut i32) -> &i32 {
+    let y = &*x;
+    *x += 1; //~ ERROR cannot assign to `*x` because it is borrowed
+    y
+}
+
+pub fn async_closure(x: &mut i32) -> impl Future<Output=&i32> {
+    (async move || {
+        let y = &*x;
+        *x += 1; //~ ERROR cannot assign to `*x` because it is borrowed
+        y
+    })()
+}
+
+pub fn async_block(x: &mut i32) -> impl Future<Output=&i32> {
+    async move {
+        let y = &*x;
+        *x += 1; //~ ERROR cannot assign to `*x` because it is borrowed
+        y
+    }
+}
+
+fn main() {}
diff --git a/src/test/ui/async-await/issue-74072-lifetime-name-annotations.stderr b/src/test/ui/async-await/issue-74072-lifetime-name-annotations.stderr
new file mode 100644
index 00000000000..997e36fe22c
--- /dev/null
+++ b/src/test/ui/async-await/issue-74072-lifetime-name-annotations.stderr
@@ -0,0 +1,39 @@
+error[E0506]: cannot assign to `*x` because it is borrowed
+  --> $DIR/issue-74072-lifetime-name-annotations.rs:9:5
+   |
+LL | pub async fn async_fn(x: &mut i32) -> &i32 {
+   |                                       ---- return type of async function is &'1 i32
+LL |     let y = &*x;
+   |             --- borrow of `*x` occurs here
+LL |     *x += 1;
+   |     ^^^^^^^ assignment to borrowed `*x` occurs here
+LL |     y
+   |     - returning this value requires that `*x` is borrowed for `'1`
+
+error[E0506]: cannot assign to `*x` because it is borrowed
+  --> $DIR/issue-74072-lifetime-name-annotations.rs:16:9
+   |
+LL |         let y = &*x;
+   |                 --- borrow of `*x` occurs here
+LL |         *x += 1;
+   |         ^^^^^^^ assignment to borrowed `*x` occurs here
+LL |         y
+   |         - returning this value requires that `*x` is borrowed for `'1`
+LL |     })()
+   |     - return type of async closure is &'1 i32
+
+error[E0506]: cannot assign to `*x` because it is borrowed
+  --> $DIR/issue-74072-lifetime-name-annotations.rs:24:9
+   |
+LL |         let y = &*x;
+   |                 --- borrow of `*x` occurs here
+LL |         *x += 1;
+   |         ^^^^^^^ assignment to borrowed `*x` occurs here
+LL |         y
+   |         - returning this value requires that `*x` is borrowed for `'1`
+LL |     }
+   |     - return type of async block is &'1 i32
+
+error: aborting due to 3 previous errors
+
+For more information about this error, try `rustc --explain E0506`.