about summary refs log tree commit diff
path: root/tests/ui/impl-trait/precise-capturing
diff options
context:
space:
mode:
authorEric Huss <eric@huss.org>2024-11-15 09:53:38 -0800
committerEric Huss <eric@huss.org>2024-11-15 09:54:06 -0800
commitd163541022248c12f166a2606cb3295986540318 (patch)
tree99c9380946f2ba850fdad096e0fc31ac89241dfb /tests/ui/impl-trait/precise-capturing
parent76fd47124b8f8037b6187169b2cdf39139466952 (diff)
downloadrust-d163541022248c12f166a2606cb3295986540318.tar.gz
rust-d163541022248c12f166a2606cb3295986540318.zip
Add test for precise-capturing from an external macro
Diffstat (limited to 'tests/ui/impl-trait/precise-capturing')
-rw-r--r--tests/ui/impl-trait/precise-capturing/auxiliary/no-use-macro.rs20
-rw-r--r--tests/ui/impl-trait/precise-capturing/auxiliary/no-use-pm.rs29
-rw-r--r--tests/ui/impl-trait/precise-capturing/external-macro.rs29
-rw-r--r--tests/ui/impl-trait/precise-capturing/external-macro.stderr89
4 files changed, 167 insertions, 0 deletions
diff --git a/tests/ui/impl-trait/precise-capturing/auxiliary/no-use-macro.rs b/tests/ui/impl-trait/precise-capturing/auxiliary/no-use-macro.rs
new file mode 100644
index 00000000000..2efdc2342c1
--- /dev/null
+++ b/tests/ui/impl-trait/precise-capturing/auxiliary/no-use-macro.rs
@@ -0,0 +1,20 @@
+// A macro_rules macro in 2015 that has an RPIT without `use<>` that would
+// cause a problem with 2024 capturing rules.
+
+#[macro_export]
+macro_rules! macro_rpit {
+    () => {
+        fn test_mbe(x: &Vec<i32>) -> impl std::fmt::Display {
+            x[0]
+        }
+
+        pub fn from_mbe() {
+            let mut x = vec![];
+            x.push(1);
+
+            let element = test_mbe(&x);
+            x.push(2);
+            println!("{element}");
+        }
+    };
+}
diff --git a/tests/ui/impl-trait/precise-capturing/auxiliary/no-use-pm.rs b/tests/ui/impl-trait/precise-capturing/auxiliary/no-use-pm.rs
new file mode 100644
index 00000000000..e197dcfef80
--- /dev/null
+++ b/tests/ui/impl-trait/precise-capturing/auxiliary/no-use-pm.rs
@@ -0,0 +1,29 @@
+// A proc-macro in 2015 that has an RPIT without `use<>` that would cause a
+// problem with 2024 capturing rules.
+
+//@ force-host
+//@ no-prefer-dynamic
+
+#![crate_type = "proc-macro"]
+
+extern crate proc_macro;
+use proc_macro::TokenStream;
+
+#[proc_macro]
+pub fn pm_rpit(input: TokenStream) -> TokenStream {
+    "fn test_pm(x: &Vec<i32>) -> impl std::fmt::Display {
+    x[0]
+}
+
+pub fn from_pm() {
+    let mut x = vec![];
+    x.push(1);
+
+    let element = test_pm(&x);
+    x.push(2);
+    println!(\"{element}\");
+}
+"
+    .parse()
+    .unwrap()
+}
diff --git a/tests/ui/impl-trait/precise-capturing/external-macro.rs b/tests/ui/impl-trait/precise-capturing/external-macro.rs
new file mode 100644
index 00000000000..72f72bc7b05
--- /dev/null
+++ b/tests/ui/impl-trait/precise-capturing/external-macro.rs
@@ -0,0 +1,29 @@
+// Tests that code generated from an external macro (MBE and proc-macro) that
+// has an RPIT will not fail when the call-site is 2024.
+// https://github.com/rust-lang/rust/issues/132917
+
+//@ aux-crate: no_use_pm=no-use-pm.rs
+//@ aux-crate: no_use_macro=no-use-macro.rs
+//@ edition: 2024
+//@ compile-flags:-Z unstable-options
+
+no_use_pm::pm_rpit!{}
+//~^ ERROR: cannot borrow `x` as mutable
+
+no_use_macro::macro_rpit!{}
+//~^ ERROR: cannot borrow `x` as mutable
+
+fn main() {
+    let mut x = vec![];
+    x.push(1);
+
+    let element = test_pm(&x);
+    x.push(2);
+    //~^ ERROR: cannot borrow `x` as mutable
+    println!("{element}");
+
+    let element = test_mbe(&x);
+    x.push(2);
+    //~^ ERROR: cannot borrow `x` as mutable
+    println!("{element}");
+}
diff --git a/tests/ui/impl-trait/precise-capturing/external-macro.stderr b/tests/ui/impl-trait/precise-capturing/external-macro.stderr
new file mode 100644
index 00000000000..88a142088dd
--- /dev/null
+++ b/tests/ui/impl-trait/precise-capturing/external-macro.stderr
@@ -0,0 +1,89 @@
+error[E0502]: cannot borrow `x` as mutable because it is also borrowed as immutable
+  --> $DIR/external-macro.rs:10:1
+   |
+LL | no_use_pm::pm_rpit!{}
+   | ^^^^^^^^^^^^^^^^^^^^^
+   | |
+   | mutable borrow occurs here
+   | immutable borrow occurs here
+   | immutable borrow later used here
+   |
+note: this call may capture more lifetimes than intended, because Rust 2024 has adjusted the `impl Trait` lifetime capture rules
+  --> $DIR/external-macro.rs:10:1
+   |
+LL | no_use_pm::pm_rpit!{}
+   | ^^^^^^^^^^^^^^^^^^^^^
+   = note: this error originates in the macro `no_use_pm::pm_rpit` (in Nightly builds, run with -Z macro-backtrace for more info)
+help: use the precise capturing `use<...>` syntax to make the captures explicit
+   |
+LL | no_use_pm::pm_rpit!{} + use<>
+   |                       +++++++
+
+error[E0502]: cannot borrow `x` as mutable because it is also borrowed as immutable
+  --> $DIR/external-macro.rs:13:1
+   |
+LL | no_use_macro::macro_rpit!{}
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^
+   | |
+   | mutable borrow occurs here
+   | immutable borrow occurs here
+   | immutable borrow later used here
+   |
+note: this call may capture more lifetimes than intended, because Rust 2024 has adjusted the `impl Trait` lifetime capture rules
+  --> $DIR/external-macro.rs:13:1
+   |
+LL | no_use_macro::macro_rpit!{}
+   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^
+   = note: this error originates in the macro `no_use_macro::macro_rpit` (in Nightly builds, run with -Z macro-backtrace for more info)
+help: use the precise capturing `use<...>` syntax to make the captures explicit
+  --> $DIR/auxiliary/no-use-macro.rs:7:60
+   |
+LL |         fn test_mbe(x: &Vec<i32>) -> impl std::fmt::Display + use<> {
+   |                                                             +++++++
+
+error[E0502]: cannot borrow `x` as mutable because it is also borrowed as immutable
+  --> $DIR/external-macro.rs:21:5
+   |
+LL |     let element = test_pm(&x);
+   |                           -- immutable borrow occurs here
+LL |     x.push(2);
+   |     ^^^^^^^^^ mutable borrow occurs here
+LL |
+LL |     println!("{element}");
+   |               --------- immutable borrow later used here
+   |
+note: this call may capture more lifetimes than intended, because Rust 2024 has adjusted the `impl Trait` lifetime capture rules
+  --> $DIR/external-macro.rs:20:19
+   |
+LL |     let element = test_pm(&x);
+   |                   ^^^^^^^^^^^
+help: use the precise capturing `use<...>` syntax to make the captures explicit
+   |
+LL | no_use_pm::pm_rpit!{} + use<>
+   |                       +++++++
+
+error[E0502]: cannot borrow `x` as mutable because it is also borrowed as immutable
+  --> $DIR/external-macro.rs:26:5
+   |
+LL |     let element = test_pm(&x);
+   |                           -- immutable borrow occurs here
+...
+LL |     x.push(2);
+   |     ^^^^^^^^^ mutable borrow occurs here
+...
+LL | }
+   | - immutable borrow might be used here, when `element` is dropped and runs the destructor for type `impl std::fmt::Display`
+   |
+note: this call may capture more lifetimes than intended, because Rust 2024 has adjusted the `impl Trait` lifetime capture rules
+  --> $DIR/external-macro.rs:20:19
+   |
+LL |     let element = test_pm(&x);
+   |                   ^^^^^^^^^^^
+help: use the precise capturing `use<...>` syntax to make the captures explicit
+   |
+LL | no_use_pm::pm_rpit!{} + use<>
+   |                       +++++++
+
+error: aborting due to 4 previous errors
+
+For more information about this error, try `rustc --explain E0502`.