about summary refs log tree commit diff
path: root/src
diff options
context:
space:
mode:
authorAndrei Homescu <ah@immunant.com>2019-07-12 15:32:46 -0700
committerAndrei Homescu <ah@immunant.com>2019-07-14 18:14:15 -0700
commit0c981e0a8a01426dbcac895d67dd33db7f5b6ff4 (patch)
tree54b0be1d57de26d32e273350f8f4c8710c13d864 /src
parent71f9384e3bec467158a628e2d11e77ffada16a90 (diff)
downloadrust-0c981e0a8a01426dbcac895d67dd33db7f5b6ff4.tar.gz
rust-0c981e0a8a01426dbcac895d67dd33db7f5b6ff4.zip
Make VaListImpl<'f> invariant over the 'f lifetime
Diffstat (limited to 'src')
-rw-r--r--src/libcore/ffi.rs13
-rw-r--r--src/test/ui/c-variadic/variadic-ffi-4.nll.stderr34
-rw-r--r--src/test/ui/c-variadic/variadic-ffi-4.rs4
-rw-r--r--src/test/ui/c-variadic/variadic-ffi-4.stderr122
4 files changed, 124 insertions, 49 deletions
diff --git a/src/libcore/ffi.rs b/src/libcore/ffi.rs
index 4f87cc506ef..eda0e7c518c 100644
--- a/src/libcore/ffi.rs
+++ b/src/libcore/ffi.rs
@@ -60,7 +60,10 @@ impl fmt::Debug for c_void {
 #[lang = "va_list"]
 pub struct VaListImpl<'f> {
     ptr: *mut c_void,
-    _marker: PhantomData<&'f c_void>,
+
+    // Invariant over `'f`, so each `VaListImpl<'f>` object is tied to
+    // the region of the function it's defined in
+    _marker: PhantomData<&'f mut &'f c_void>,
 }
 
 #[cfg(any(all(not(target_arch = "aarch64"), not(target_arch = "powerpc"),
@@ -96,7 +99,7 @@ pub struct VaListImpl<'f> {
     vr_top: *mut c_void,
     gr_offs: i32,
     vr_offs: i32,
-    _marker: PhantomData<&'f c_void>,
+    _marker: PhantomData<&'f mut &'f c_void>,
 }
 
 /// PowerPC ABI implementation of a `va_list`.
@@ -114,7 +117,7 @@ pub struct VaListImpl<'f> {
     reserved: u16,
     overflow_arg_area: *mut c_void,
     reg_save_area: *mut c_void,
-    _marker: PhantomData<&'f c_void>,
+    _marker: PhantomData<&'f mut &'f c_void>,
 }
 
 /// x86_64 ABI implementation of a `va_list`.
@@ -131,7 +134,7 @@ pub struct VaListImpl<'f> {
     fp_offset: i32,
     overflow_arg_area: *mut c_void,
     reg_save_area: *mut c_void,
-    _marker: PhantomData<&'f c_void>,
+    _marker: PhantomData<&'f mut &'f c_void>,
 }
 
 /// asm.js ABI implementation of a `va_list`.
@@ -148,7 +151,7 @@ pub struct VaListImpl<'f> {
 #[lang = "va_list"]
 pub struct VaListImpl<'f> {
     inner: [crate::mem::MaybeUninit<i32>; 4],
-    _marker: PhantomData<&'f c_void>,
+    _marker: PhantomData<&'f mut &'f c_void>,
 }
 
 #[cfg(all(target_arch = "asmjs", not(windows)))]
diff --git a/src/test/ui/c-variadic/variadic-ffi-4.nll.stderr b/src/test/ui/c-variadic/variadic-ffi-4.nll.stderr
index 3c5131835b5..4947d6e5291 100644
--- a/src/test/ui/c-variadic/variadic-ffi-4.nll.stderr
+++ b/src/test/ui/c-variadic/variadic-ffi-4.nll.stderr
@@ -27,6 +27,16 @@ error: lifetime may not live long enough
   --> $DIR/variadic-ffi-4.rs:20:5
    |
 LL | pub unsafe extern "C" fn no_escape3(_: usize, mut ap0: &mut VaListImpl, mut ap1: ...) {
+   |                                               -------                   ------- has type `core::ffi::VaListImpl<'2>`
+   |                                               |
+   |                                               has type `&mut core::ffi::VaListImpl<'1>`
+LL |     *ap0 = ap1;
+   |     ^^^^ assignment requires that `'1` must outlive `'2`
+
+error: lifetime may not live long enough
+  --> $DIR/variadic-ffi-4.rs:20:5
+   |
+LL | pub unsafe extern "C" fn no_escape3(_: usize, mut ap0: &mut VaListImpl, mut ap1: ...) {
    |                                               -------                   ------- has type `core::ffi::VaListImpl<'1>`
    |                                               |
    |                                               has type `&mut core::ffi::VaListImpl<'2>`
@@ -34,7 +44,7 @@ LL |     *ap0 = ap1;
    |     ^^^^ assignment requires that `'1` must outlive `'2`
 
 error: lifetime may not live long enough
-  --> $DIR/variadic-ffi-4.rs:24:5
+  --> $DIR/variadic-ffi-4.rs:25:5
    |
 LL | pub unsafe extern "C" fn no_escape4(_: usize, ap0: &mut VaListImpl, mut ap1: ...) {
    |                                               ---                   ------- has type `core::ffi::VaListImpl<'2>`
@@ -44,7 +54,7 @@ LL |     ap0 = &mut ap1;
    |     ^^^^^^^^^^^^^^ assignment requires that `'1` must outlive `'2`
 
 error: lifetime may not live long enough
-  --> $DIR/variadic-ffi-4.rs:24:5
+  --> $DIR/variadic-ffi-4.rs:25:5
    |
 LL | pub unsafe extern "C" fn no_escape4(_: usize, ap0: &mut VaListImpl, mut ap1: ...) {
    |                                               ---                   ------- has type `core::ffi::VaListImpl<'1>`
@@ -54,7 +64,7 @@ LL |     ap0 = &mut ap1;
    |     ^^^^^^^^^^^^^^ assignment requires that `'1` must outlive `'2`
 
 error[E0384]: cannot assign to immutable argument `ap0`
-  --> $DIR/variadic-ffi-4.rs:24:5
+  --> $DIR/variadic-ffi-4.rs:25:5
    |
 LL | pub unsafe extern "C" fn no_escape4(_: usize, ap0: &mut VaListImpl, mut ap1: ...) {
    |                                               --- help: make this binding mutable: `mut ap0`
@@ -62,7 +72,7 @@ LL |     ap0 = &mut ap1;
    |     ^^^^^^^^^^^^^^ cannot assign to immutable argument
 
 error[E0597]: `ap1` does not live long enough
-  --> $DIR/variadic-ffi-4.rs:24:11
+  --> $DIR/variadic-ffi-4.rs:25:11
    |
 LL | pub unsafe extern "C" fn no_escape4(_: usize, ap0: &mut VaListImpl, mut ap1: ...) {
    |                                                    - let's call the lifetime of this reference `'1`
@@ -76,16 +86,26 @@ LL | }
    | - `ap1` dropped here while still borrowed
 
 error: lifetime may not live long enough
-  --> $DIR/variadic-ffi-4.rs:32:5
+  --> $DIR/variadic-ffi-4.rs:33:12
+   |
+LL | pub unsafe extern "C" fn no_escape5(_: usize, mut ap0: &mut VaListImpl, mut ap1: ...) {
+   |                                               -------                   ------- has type `core::ffi::VaListImpl<'2>`
+   |                                               |
+   |                                               has type `&mut core::ffi::VaListImpl<'1>`
+LL |     *ap0 = ap1.clone();
+   |            ^^^^^^^^^^^ argument requires that `'1` must outlive `'2`
+
+error: lifetime may not live long enough
+  --> $DIR/variadic-ffi-4.rs:33:12
    |
 LL | pub unsafe extern "C" fn no_escape5(_: usize, mut ap0: &mut VaListImpl, mut ap1: ...) {
    |                                               -------                   ------- has type `core::ffi::VaListImpl<'1>`
    |                                               |
    |                                               has type `&mut core::ffi::VaListImpl<'2>`
 LL |     *ap0 = ap1.clone();
-   |     ^^^^ assignment requires that `'1` must outlive `'2`
+   |            ^^^^^^^^^^^ argument requires that `'1` must outlive `'2`
 
-error: aborting due to 9 previous errors
+error: aborting due to 11 previous errors
 
 Some errors have detailed explanations: E0384, E0597, E0621.
 For more information about an error, try `rustc --explain E0384`.
diff --git a/src/test/ui/c-variadic/variadic-ffi-4.rs b/src/test/ui/c-variadic/variadic-ffi-4.rs
index 07c32ecbfc2..4a50d352a5b 100644
--- a/src/test/ui/c-variadic/variadic-ffi-4.rs
+++ b/src/test/ui/c-variadic/variadic-ffi-4.rs
@@ -18,6 +18,7 @@ pub unsafe extern "C" fn no_escape2(_: usize, ap: ...) {
 
 pub unsafe extern "C" fn no_escape3(_: usize, mut ap0: &mut VaListImpl, mut ap1: ...) {
     *ap0 = ap1; //~ ERROR: mismatched types
+    //~^ ERROR: mismatched types
 }
 
 pub unsafe extern "C" fn no_escape4(_: usize, ap0: &mut VaListImpl, mut ap1: ...) {
@@ -29,5 +30,6 @@ pub unsafe extern "C" fn no_escape4(_: usize, ap0: &mut VaListImpl, mut ap1: ...
 }
 
 pub unsafe extern "C" fn no_escape5(_: usize, mut ap0: &mut VaListImpl, mut ap1: ...) {
-    *ap0 = ap1.clone(); //~ ERROR: cannot infer an appropriate lifetime
+    *ap0 = ap1.clone(); //~ ERROR: mismatched types
+    //~^ ERROR: mismatched types
 }
diff --git a/src/test/ui/c-variadic/variadic-ffi-4.stderr b/src/test/ui/c-variadic/variadic-ffi-4.stderr
index 72d4d8b6344..7aa510e6113 100644
--- a/src/test/ui/c-variadic/variadic-ffi-4.stderr
+++ b/src/test/ui/c-variadic/variadic-ffi-4.stderr
@@ -52,6 +52,7 @@ note: the anonymous lifetime #3 defined on the function body at 19:1...
    |
 LL | / pub unsafe extern "C" fn no_escape3(_: usize, mut ap0: &mut VaListImpl, mut ap1: ...) {
 LL | |     *ap0 = ap1;
+LL | |
 LL | | }
    | |_^
 note: ...does not necessarily outlive the anonymous lifetime #2 defined on the function body at 19:1
@@ -59,17 +60,43 @@ note: ...does not necessarily outlive the anonymous lifetime #2 defined on the f
    |
 LL | / pub unsafe extern "C" fn no_escape3(_: usize, mut ap0: &mut VaListImpl, mut ap1: ...) {
 LL | |     *ap0 = ap1;
+LL | |
+LL | | }
+   | |_^
+
+error[E0308]: mismatched types
+  --> $DIR/variadic-ffi-4.rs:20:12
+   |
+LL |     *ap0 = ap1;
+   |            ^^^ lifetime mismatch
+   |
+   = note: expected type `core::ffi::VaListImpl<'_>`
+              found type `core::ffi::VaListImpl<'_>`
+note: the anonymous lifetime #2 defined on the function body at 19:1...
+  --> $DIR/variadic-ffi-4.rs:19:1
+   |
+LL | / pub unsafe extern "C" fn no_escape3(_: usize, mut ap0: &mut VaListImpl, mut ap1: ...) {
+LL | |     *ap0 = ap1;
+LL | |
+LL | | }
+   | |_^
+note: ...does not necessarily outlive the anonymous lifetime #3 defined on the function body at 19:1
+  --> $DIR/variadic-ffi-4.rs:19:1
+   |
+LL | / pub unsafe extern "C" fn no_escape3(_: usize, mut ap0: &mut VaListImpl, mut ap1: ...) {
+LL | |     *ap0 = ap1;
+LL | |
 LL | | }
    | |_^
 
 error[E0490]: a value of type `core::ffi::VaListImpl<'_>` is borrowed for too long
-  --> $DIR/variadic-ffi-4.rs:24:11
+  --> $DIR/variadic-ffi-4.rs:25:11
    |
 LL |     ap0 = &mut ap1;
    |           ^^^^^^^^
    |
-note: the type is valid for the anonymous lifetime #1 defined on the function body at 23:1
-  --> $DIR/variadic-ffi-4.rs:23:1
+note: the type is valid for the anonymous lifetime #1 defined on the function body at 24:1
+  --> $DIR/variadic-ffi-4.rs:24:1
    |
 LL | / pub unsafe extern "C" fn no_escape4(_: usize, ap0: &mut VaListImpl, mut ap1: ...) {
 LL | |     ap0 = &mut ap1;
@@ -79,8 +106,8 @@ LL | |
 LL | |
 LL | | }
    | |_^
-note: but the borrow lasts for the anonymous lifetime #3 defined on the function body at 23:1
-  --> $DIR/variadic-ffi-4.rs:23:1
+note: but the borrow lasts for the anonymous lifetime #3 defined on the function body at 24:1
+  --> $DIR/variadic-ffi-4.rs:24:1
    |
 LL | / pub unsafe extern "C" fn no_escape4(_: usize, ap0: &mut VaListImpl, mut ap1: ...) {
 LL | |     ap0 = &mut ap1;
@@ -92,15 +119,15 @@ LL | | }
    | |_^
 
 error[E0308]: mismatched types
-  --> $DIR/variadic-ffi-4.rs:24:11
+  --> $DIR/variadic-ffi-4.rs:25:11
    |
 LL |     ap0 = &mut ap1;
    |           ^^^^^^^^ lifetime mismatch
    |
    = note: expected type `&mut core::ffi::VaListImpl<'_>`
               found type `&mut core::ffi::VaListImpl<'_>`
-note: the anonymous lifetime #3 defined on the function body at 23:1...
-  --> $DIR/variadic-ffi-4.rs:23:1
+note: the anonymous lifetime #3 defined on the function body at 24:1...
+  --> $DIR/variadic-ffi-4.rs:24:1
    |
 LL | / pub unsafe extern "C" fn no_escape4(_: usize, ap0: &mut VaListImpl, mut ap1: ...) {
 LL | |     ap0 = &mut ap1;
@@ -110,8 +137,8 @@ LL | |
 LL | |
 LL | | }
    | |_^
-note: ...does not necessarily outlive the anonymous lifetime #2 defined on the function body at 23:1
-  --> $DIR/variadic-ffi-4.rs:23:1
+note: ...does not necessarily outlive the anonymous lifetime #2 defined on the function body at 24:1
+  --> $DIR/variadic-ffi-4.rs:24:1
    |
 LL | / pub unsafe extern "C" fn no_escape4(_: usize, ap0: &mut VaListImpl, mut ap1: ...) {
 LL | |     ap0 = &mut ap1;
@@ -123,15 +150,15 @@ LL | | }
    | |_^
 
 error[E0308]: mismatched types
-  --> $DIR/variadic-ffi-4.rs:24:11
+  --> $DIR/variadic-ffi-4.rs:25:11
    |
 LL |     ap0 = &mut ap1;
    |           ^^^^^^^^ lifetime mismatch
    |
    = note: expected type `&mut core::ffi::VaListImpl<'_>`
               found type `&mut core::ffi::VaListImpl<'_>`
-note: the anonymous lifetime #2 defined on the function body at 23:1...
-  --> $DIR/variadic-ffi-4.rs:23:1
+note: the anonymous lifetime #2 defined on the function body at 24:1...
+  --> $DIR/variadic-ffi-4.rs:24:1
    |
 LL | / pub unsafe extern "C" fn no_escape4(_: usize, ap0: &mut VaListImpl, mut ap1: ...) {
 LL | |     ap0 = &mut ap1;
@@ -141,8 +168,8 @@ LL | |
 LL | |
 LL | | }
    | |_^
-note: ...does not necessarily outlive the anonymous lifetime #3 defined on the function body at 23:1
-  --> $DIR/variadic-ffi-4.rs:23:1
+note: ...does not necessarily outlive the anonymous lifetime #3 defined on the function body at 24:1
+  --> $DIR/variadic-ffi-4.rs:24:1
    |
 LL | / pub unsafe extern "C" fn no_escape4(_: usize, ap0: &mut VaListImpl, mut ap1: ...) {
 LL | |     ap0 = &mut ap1;
@@ -154,13 +181,13 @@ LL | | }
    | |_^
 
 error[E0495]: cannot infer an appropriate lifetime for borrow expression due to conflicting requirements
-  --> $DIR/variadic-ffi-4.rs:24:11
+  --> $DIR/variadic-ffi-4.rs:25:11
    |
 LL |     ap0 = &mut ap1;
    |           ^^^^^^^^
    |
-note: first, the lifetime cannot outlive the anonymous lifetime #3 defined on the function body at 23:1...
-  --> $DIR/variadic-ffi-4.rs:23:1
+note: first, the lifetime cannot outlive the anonymous lifetime #3 defined on the function body at 24:1...
+  --> $DIR/variadic-ffi-4.rs:24:1
    |
 LL | / pub unsafe extern "C" fn no_escape4(_: usize, ap0: &mut VaListImpl, mut ap1: ...) {
 LL | |     ap0 = &mut ap1;
@@ -171,12 +198,12 @@ LL | |
 LL | | }
    | |_^
 note: ...so that the type `core::ffi::VaListImpl<'_>` is not borrowed for too long
-  --> $DIR/variadic-ffi-4.rs:24:11
+  --> $DIR/variadic-ffi-4.rs:25:11
    |
 LL |     ap0 = &mut ap1;
    |           ^^^^^^^^
-note: but, the lifetime must be valid for the anonymous lifetime #1 defined on the function body at 23:1...
-  --> $DIR/variadic-ffi-4.rs:23:1
+note: but, the lifetime must be valid for the anonymous lifetime #1 defined on the function body at 24:1...
+  --> $DIR/variadic-ffi-4.rs:24:1
    |
 LL | / pub unsafe extern "C" fn no_escape4(_: usize, ap0: &mut VaListImpl, mut ap1: ...) {
 LL | |     ap0 = &mut ap1;
@@ -187,39 +214,62 @@ LL | |
 LL | | }
    | |_^
 note: ...so that reference does not outlive borrowed content
-  --> $DIR/variadic-ffi-4.rs:24:11
+  --> $DIR/variadic-ffi-4.rs:25:11
    |
 LL |     ap0 = &mut ap1;
    |           ^^^^^^^^
 
-error[E0495]: cannot infer an appropriate lifetime due to conflicting requirements
-  --> $DIR/variadic-ffi-4.rs:32:16
+error[E0308]: mismatched types
+  --> $DIR/variadic-ffi-4.rs:33:12
    |
 LL |     *ap0 = ap1.clone();
-   |                ^^^^^
+   |            ^^^^^^^^^^^ lifetime mismatch
    |
-note: first, the lifetime cannot outlive the anonymous lifetime #3 defined on the function body at 31:1...
-  --> $DIR/variadic-ffi-4.rs:31:1
+   = note: expected type `core::ffi::VaListImpl<'_>`
+              found type `core::ffi::VaListImpl<'_>`
+note: the anonymous lifetime #3 defined on the function body at 32:1...
+  --> $DIR/variadic-ffi-4.rs:32:1
    |
 LL | / pub unsafe extern "C" fn no_escape5(_: usize, mut ap0: &mut VaListImpl, mut ap1: ...) {
 LL | |     *ap0 = ap1.clone();
+LL | |
 LL | | }
    | |_^
-   = note: ...so that the types are compatible:
-           expected &core::ffi::VaListImpl<'_>
-              found &core::ffi::VaListImpl<'_>
-note: but, the lifetime must be valid for the anonymous lifetime #2 defined on the function body at 31:1...
-  --> $DIR/variadic-ffi-4.rs:31:1
+note: ...does not necessarily outlive the anonymous lifetime #2 defined on the function body at 32:1
+  --> $DIR/variadic-ffi-4.rs:32:1
    |
 LL | / pub unsafe extern "C" fn no_escape5(_: usize, mut ap0: &mut VaListImpl, mut ap1: ...) {
 LL | |     *ap0 = ap1.clone();
+LL | |
+LL | | }
+   | |_^
+
+error[E0308]: mismatched types
+  --> $DIR/variadic-ffi-4.rs:33:12
+   |
+LL |     *ap0 = ap1.clone();
+   |            ^^^^^^^^^^^ lifetime mismatch
+   |
+   = note: expected type `core::ffi::VaListImpl<'_>`
+              found type `core::ffi::VaListImpl<'_>`
+note: the anonymous lifetime #2 defined on the function body at 32:1...
+  --> $DIR/variadic-ffi-4.rs:32:1
+   |
+LL | / pub unsafe extern "C" fn no_escape5(_: usize, mut ap0: &mut VaListImpl, mut ap1: ...) {
+LL | |     *ap0 = ap1.clone();
+LL | |
+LL | | }
+   | |_^
+note: ...does not necessarily outlive the anonymous lifetime #3 defined on the function body at 32:1
+  --> $DIR/variadic-ffi-4.rs:32:1
+   |
+LL | / pub unsafe extern "C" fn no_escape5(_: usize, mut ap0: &mut VaListImpl, mut ap1: ...) {
+LL | |     *ap0 = ap1.clone();
+LL | |
 LL | | }
    | |_^
-   = note: ...so that the expression is assignable:
-           expected core::ffi::VaListImpl<'_>
-              found core::ffi::VaListImpl<'_>
 
-error: aborting due to 9 previous errors
+error: aborting due to 11 previous errors
 
 Some errors have detailed explanations: E0308, E0621.
 For more information about an error, try `rustc --explain E0308`.