about summary refs log tree commit diff
diff options
context:
space:
mode:
-rw-r--r--src/test/ui/associated-types/associated-types-eq-hr.base.stderr (renamed from src/test/ui/associated-types/associated-types-eq-hr.stderr)22
-rw-r--r--src/test/ui/associated-types/associated-types-eq-hr.nll.stderr12
-rw-r--r--src/test/ui/associated-types/associated-types-eq-hr.rs14
-rw-r--r--src/test/ui/associated-types/associated-types-project-from-hrtb-in-fn-body.base.stderr (renamed from src/test/ui/associated-types/associated-types-project-from-hrtb-in-fn-body.stderr)2
-rw-r--r--src/test/ui/associated-types/associated-types-project-from-hrtb-in-fn-body.nll.stderr4
-rw-r--r--src/test/ui/associated-types/associated-types-project-from-hrtb-in-fn-body.rs8
-rw-r--r--src/test/ui/associated-types/associated-types-subtyping-1.base.stderr (renamed from src/test/ui/associated-types/associated-types-subtyping-1.stderr)4
-rw-r--r--src/test/ui/associated-types/associated-types-subtyping-1.nll.stderr4
-rw-r--r--src/test/ui/associated-types/associated-types-subtyping-1.rs12
-rw-r--r--src/test/ui/associated-types/cache/project-fn-ret-contravariant-nll.krisskross.stderr25
-rw-r--r--src/test/ui/associated-types/cache/project-fn-ret-contravariant-nll.rs55
-rw-r--r--src/test/ui/associated-types/cache/project-fn-ret-contravariant-nll.transmute.stderr11
-rw-r--r--src/test/ui/associated-types/cache/project-fn-ret-contravariant.krisskross.nll.stderr30
-rw-r--r--src/test/ui/associated-types/cache/project-fn-ret-contravariant.krisskross.stderr4
-rw-r--r--src/test/ui/associated-types/cache/project-fn-ret-contravariant.ok.stderr8
-rw-r--r--src/test/ui/associated-types/cache/project-fn-ret-contravariant.oneuse.stderr8
-rw-r--r--src/test/ui/associated-types/cache/project-fn-ret-contravariant.rs12
-rw-r--r--src/test/ui/associated-types/cache/project-fn-ret-contravariant.transmute.nll.stderr10
-rw-r--r--src/test/ui/associated-types/cache/project-fn-ret-contravariant.transmute.stderr2
-rw-r--r--src/test/ui/associated-types/cache/project-fn-ret-invariant-nll.krisskross.stderr (renamed from src/test/ui/associated-types/cache/project-fn-ret-invariant.krisskross.nll.stderr)4
-rw-r--r--src/test/ui/associated-types/cache/project-fn-ret-invariant-nll.oneuse.stderr (renamed from src/test/ui/associated-types/cache/project-fn-ret-invariant.oneuse.nll.stderr)4
-rw-r--r--src/test/ui/associated-types/cache/project-fn-ret-invariant-nll.rs68
-rw-r--r--src/test/ui/associated-types/cache/project-fn-ret-invariant-nll.transmute.stderr (renamed from src/test/ui/associated-types/cache/project-fn-ret-invariant.transmute.nll.stderr)2
-rw-r--r--src/test/ui/associated-types/cache/project-fn-ret-invariant.krisskross.stderr4
-rw-r--r--src/test/ui/associated-types/cache/project-fn-ret-invariant.ok.stderr8
-rw-r--r--src/test/ui/associated-types/cache/project-fn-ret-invariant.oneuse.stderr2
-rw-r--r--src/test/ui/associated-types/cache/project-fn-ret-invariant.rs10
-rw-r--r--src/test/ui/associated-types/cache/project-fn-ret-invariant.transmute.stderr4
-rw-r--r--src/test/ui/associated-types/higher-ranked-projection.badbase.stderr17
-rw-r--r--src/test/ui/associated-types/higher-ranked-projection.badnll.stderr17
-rw-r--r--src/test/ui/associated-types/higher-ranked-projection.good.stderr8
-rw-r--r--src/test/ui/associated-types/higher-ranked-projection.rs15
32 files changed, 280 insertions, 130 deletions
diff --git a/src/test/ui/associated-types/associated-types-eq-hr.stderr b/src/test/ui/associated-types/associated-types-eq-hr.base.stderr
index 1329e1382fd..4313078064c 100644
--- a/src/test/ui/associated-types/associated-types-eq-hr.stderr
+++ b/src/test/ui/associated-types/associated-types-eq-hr.base.stderr
@@ -1,18 +1,18 @@
 error[E0271]: type mismatch resolving `for<'x> <UintStruct as TheTrait<&'x isize>>::A == &'x isize`
-  --> $DIR/associated-types-eq-hr.rs:87:5
+  --> $DIR/associated-types-eq-hr.rs:91:5
    |
 LL |     foo::<UintStruct>();
    |     ^^^^^^^^^^^^^^^^^ type mismatch resolving `for<'x> <UintStruct as TheTrait<&'x isize>>::A == &'x isize`
    |
 note: expected this to be `&isize`
-  --> $DIR/associated-types-eq-hr.rs:26:14
+  --> $DIR/associated-types-eq-hr.rs:30:14
    |
 LL |     type A = &'a usize;
    |              ^^^^^^^^^
    = note: expected reference `&isize`
               found reference `&usize`
 note: required by a bound in `foo`
-  --> $DIR/associated-types-eq-hr.rs:45:36
+  --> $DIR/associated-types-eq-hr.rs:49:36
    |
 LL | fn foo<T>()
    |    --- required by a bound in this
@@ -21,20 +21,20 @@ LL |     T: for<'x> TheTrait<&'x isize, A = &'x isize>,
    |                                    ^^^^^^^^^^^^^ required by this bound in `foo`
 
 error[E0271]: type mismatch resolving `for<'x> <IntStruct as TheTrait<&'x isize>>::A == &'x usize`
-  --> $DIR/associated-types-eq-hr.rs:91:5
+  --> $DIR/associated-types-eq-hr.rs:95:5
    |
 LL |     bar::<IntStruct>();
    |     ^^^^^^^^^^^^^^^^ type mismatch resolving `for<'x> <IntStruct as TheTrait<&'x isize>>::A == &'x usize`
    |
 note: expected this to be `&usize`
-  --> $DIR/associated-types-eq-hr.rs:14:14
+  --> $DIR/associated-types-eq-hr.rs:18:14
    |
 LL |     type A = &'a isize;
    |              ^^^^^^^^^
    = note: expected reference `&usize`
               found reference `&isize`
 note: required by a bound in `bar`
-  --> $DIR/associated-types-eq-hr.rs:52:36
+  --> $DIR/associated-types-eq-hr.rs:56:36
    |
 LL | fn bar<T>()
    |    --- required by a bound in this
@@ -43,7 +43,7 @@ LL |     T: for<'x> TheTrait<&'x isize, A = &'x usize>,
    |                                    ^^^^^^^^^^^^^ required by this bound in `bar`
 
 error: implementation of `TheTrait` is not general enough
-  --> $DIR/associated-types-eq-hr.rs:96:5
+  --> $DIR/associated-types-eq-hr.rs:100:5
    |
 LL |     tuple_one::<Tuple>();
    |     ^^^^^^^^^^^^^^^^^^ implementation of `TheTrait` is not general enough
@@ -52,7 +52,7 @@ LL |     tuple_one::<Tuple>();
    = note: ...but it actually implements `TheTrait<(&'2 isize, &'2 isize)>`, for some specific lifetime `'2`
 
 error: implementation of `TheTrait` is not general enough
-  --> $DIR/associated-types-eq-hr.rs:96:5
+  --> $DIR/associated-types-eq-hr.rs:100:5
    |
 LL |     tuple_one::<Tuple>();
    |     ^^^^^^^^^^^^^^^^^^ implementation of `TheTrait` is not general enough
@@ -61,7 +61,7 @@ LL |     tuple_one::<Tuple>();
    = note: ...but it actually implements `TheTrait<(&'2 isize, &'2 isize)>`, for some specific lifetime `'2`
 
 error: implementation of `TheTrait` is not general enough
-  --> $DIR/associated-types-eq-hr.rs:102:5
+  --> $DIR/associated-types-eq-hr.rs:106:5
    |
 LL |     tuple_two::<Tuple>();
    |     ^^^^^^^^^^^^^^^^^^ implementation of `TheTrait` is not general enough
@@ -70,7 +70,7 @@ LL |     tuple_two::<Tuple>();
    = note: ...but it actually implements `TheTrait<(&'2 isize, &'2 isize)>`, for some specific lifetime `'2`
 
 error: implementation of `TheTrait` is not general enough
-  --> $DIR/associated-types-eq-hr.rs:102:5
+  --> $DIR/associated-types-eq-hr.rs:106:5
    |
 LL |     tuple_two::<Tuple>();
    |     ^^^^^^^^^^^^^^^^^^ implementation of `TheTrait` is not general enough
@@ -79,7 +79,7 @@ LL |     tuple_two::<Tuple>();
    = note: ...but it actually implements `TheTrait<(&'2 isize, &'2 isize)>`, for some specific lifetime `'2`
 
 error: implementation of `TheTrait` is not general enough
-  --> $DIR/associated-types-eq-hr.rs:112:5
+  --> $DIR/associated-types-eq-hr.rs:116:5
    |
 LL |     tuple_four::<Tuple>();
    |     ^^^^^^^^^^^^^^^^^^^ implementation of `TheTrait` is not general enough
diff --git a/src/test/ui/associated-types/associated-types-eq-hr.nll.stderr b/src/test/ui/associated-types/associated-types-eq-hr.nll.stderr
index b306ae273e8..8d128821656 100644
--- a/src/test/ui/associated-types/associated-types-eq-hr.nll.stderr
+++ b/src/test/ui/associated-types/associated-types-eq-hr.nll.stderr
@@ -1,18 +1,18 @@
 error[E0271]: type mismatch resolving `for<'x> <UintStruct as TheTrait<&'x isize>>::A == &'x isize`
-  --> $DIR/associated-types-eq-hr.rs:87:5
+  --> $DIR/associated-types-eq-hr.rs:91:5
    |
 LL |     foo::<UintStruct>();
    |     ^^^^^^^^^^^^^^^^^ type mismatch resolving `for<'x> <UintStruct as TheTrait<&'x isize>>::A == &'x isize`
    |
 note: expected this to be `&isize`
-  --> $DIR/associated-types-eq-hr.rs:26:14
+  --> $DIR/associated-types-eq-hr.rs:30:14
    |
 LL |     type A = &'a usize;
    |              ^^^^^^^^^
    = note: expected reference `&isize`
               found reference `&usize`
 note: required by a bound in `foo`
-  --> $DIR/associated-types-eq-hr.rs:45:36
+  --> $DIR/associated-types-eq-hr.rs:49:36
    |
 LL | fn foo<T>()
    |    --- required by a bound in this
@@ -21,20 +21,20 @@ LL |     T: for<'x> TheTrait<&'x isize, A = &'x isize>,
    |                                    ^^^^^^^^^^^^^ required by this bound in `foo`
 
 error[E0271]: type mismatch resolving `for<'x> <IntStruct as TheTrait<&'x isize>>::A == &'x usize`
-  --> $DIR/associated-types-eq-hr.rs:91:5
+  --> $DIR/associated-types-eq-hr.rs:95:5
    |
 LL |     bar::<IntStruct>();
    |     ^^^^^^^^^^^^^^^^ type mismatch resolving `for<'x> <IntStruct as TheTrait<&'x isize>>::A == &'x usize`
    |
 note: expected this to be `&usize`
-  --> $DIR/associated-types-eq-hr.rs:14:14
+  --> $DIR/associated-types-eq-hr.rs:18:14
    |
 LL |     type A = &'a isize;
    |              ^^^^^^^^^
    = note: expected reference `&usize`
               found reference `&isize`
 note: required by a bound in `bar`
-  --> $DIR/associated-types-eq-hr.rs:52:36
+  --> $DIR/associated-types-eq-hr.rs:56:36
    |
 LL | fn bar<T>()
    |    --- required by a bound in this
diff --git a/src/test/ui/associated-types/associated-types-eq-hr.rs b/src/test/ui/associated-types/associated-types-eq-hr.rs
index fb391913c32..deb3fd059f8 100644
--- a/src/test/ui/associated-types/associated-types-eq-hr.rs
+++ b/src/test/ui/associated-types/associated-types-eq-hr.rs
@@ -1,3 +1,7 @@
+// revisions: base nll
+// ignore-compare-mode-nll
+//[nll] compile-flags: -Z borrowck=mir
+
 // Check testing of equality constraints in a higher-ranked context.
 
 pub trait TheTrait<T> {
@@ -94,14 +98,14 @@ pub fn call_bar() {
 
 pub fn call_tuple_one() {
     tuple_one::<Tuple>();
-    //~^ ERROR implementation of `TheTrait` is not general enough
-    //~| ERROR implementation of `TheTrait` is not general enough
+    //[base]~^ ERROR implementation of `TheTrait` is not general enough
+    //[base]~| ERROR implementation of `TheTrait` is not general enough
 }
 
 pub fn call_tuple_two() {
     tuple_two::<Tuple>();
-    //~^ ERROR implementation of `TheTrait` is not general enough
-    //~| ERROR implementation of `TheTrait` is not general enough
+    //[base]~^ ERROR implementation of `TheTrait` is not general enough
+    //[base]~| ERROR implementation of `TheTrait` is not general enough
 }
 
 pub fn call_tuple_three() {
@@ -110,7 +114,7 @@ pub fn call_tuple_three() {
 
 pub fn call_tuple_four() {
     tuple_four::<Tuple>();
-    //~^ ERROR implementation of `TheTrait` is not general enough
+    //[base]~^ ERROR implementation of `TheTrait` is not general enough
 }
 
 fn main() {}
diff --git a/src/test/ui/associated-types/associated-types-project-from-hrtb-in-fn-body.stderr b/src/test/ui/associated-types/associated-types-project-from-hrtb-in-fn-body.base.stderr
index d5310c47fcf..fe238344263 100644
--- a/src/test/ui/associated-types/associated-types-project-from-hrtb-in-fn-body.stderr
+++ b/src/test/ui/associated-types/associated-types-project-from-hrtb-in-fn-body.base.stderr
@@ -1,5 +1,5 @@
 error[E0623]: lifetime mismatch
-  --> $DIR/associated-types-project-from-hrtb-in-fn-body.rs:22:40
+  --> $DIR/associated-types-project-from-hrtb-in-fn-body.rs:26:40
    |
 LL |     x: <I as Foo<&'a isize>>::A,
    |                  --------- these two types are declared with different lifetimes...
diff --git a/src/test/ui/associated-types/associated-types-project-from-hrtb-in-fn-body.nll.stderr b/src/test/ui/associated-types/associated-types-project-from-hrtb-in-fn-body.nll.stderr
index e12d42e5ed0..ae6ccb8af55 100644
--- a/src/test/ui/associated-types/associated-types-project-from-hrtb-in-fn-body.nll.stderr
+++ b/src/test/ui/associated-types/associated-types-project-from-hrtb-in-fn-body.nll.stderr
@@ -1,5 +1,5 @@
 error: lifetime may not live long enough
-  --> $DIR/associated-types-project-from-hrtb-in-fn-body.rs:22:29
+  --> $DIR/associated-types-project-from-hrtb-in-fn-body.rs:26:29
    |
 LL | fn bar<'a, 'b, I : for<'x> Foo<&'x isize>>(
    |        --  -- lifetime `'b` defined here
@@ -12,7 +12,7 @@ LL |     let z: I::A = if cond { x } else { y };
    = help: consider adding the following bound: `'a: 'b`
 
 error: lifetime may not live long enough
-  --> $DIR/associated-types-project-from-hrtb-in-fn-body.rs:22:40
+  --> $DIR/associated-types-project-from-hrtb-in-fn-body.rs:26:40
    |
 LL | fn bar<'a, 'b, I : for<'x> Foo<&'x isize>>(
    |        --  -- lifetime `'b` defined here
diff --git a/src/test/ui/associated-types/associated-types-project-from-hrtb-in-fn-body.rs b/src/test/ui/associated-types/associated-types-project-from-hrtb-in-fn-body.rs
index 9434a88e633..7ad12f2a1f3 100644
--- a/src/test/ui/associated-types/associated-types-project-from-hrtb-in-fn-body.rs
+++ b/src/test/ui/associated-types/associated-types-project-from-hrtb-in-fn-body.rs
@@ -1,3 +1,7 @@
+// ignore-compare-mode-nll
+// revisions: base nll
+// [nll]compile-flags: -Zborrowck=mir
+
 // Check projection of an associated type out of a higher-ranked
 // trait-bound in the context of a function body.
 
@@ -20,7 +24,9 @@ fn bar<'a, 'b, I : for<'x> Foo<&'x isize>>(
 {
     // x and y here have two distinct lifetimes:
     let z: I::A = if cond { x } else { y };
-    //~^ ERROR lifetime mismatch
+    //[base]~^ ERROR lifetime mismatch
+    //[nll]~^^ ERROR lifetime may not live long enough
+    //[nll]~| ERROR lifetime may not live long enough
 }
 
 pub fn main() {}
diff --git a/src/test/ui/associated-types/associated-types-subtyping-1.stderr b/src/test/ui/associated-types/associated-types-subtyping-1.base.stderr
index 58ceec9040b..35b3a83ee43 100644
--- a/src/test/ui/associated-types/associated-types-subtyping-1.stderr
+++ b/src/test/ui/associated-types/associated-types-subtyping-1.base.stderr
@@ -1,5 +1,5 @@
 error[E0623]: lifetime mismatch
-  --> $DIR/associated-types-subtyping-1.rs:26:38
+  --> $DIR/associated-types-subtyping-1.rs:31:38
    |
 LL | fn method2<'a,'b,T>(x: &'a T, y: &'b T)
    |                        -----     ----- these two types are declared with different lifetimes...
@@ -8,7 +8,7 @@ LL |     let _c: <T as Trait<'b>>::Type = a;
    |                                      ^ ...but data from `y` flows into `x` here
 
 error[E0623]: lifetime mismatch
-  --> $DIR/associated-types-subtyping-1.rs:35:38
+  --> $DIR/associated-types-subtyping-1.rs:41:38
    |
 LL | fn method3<'a,'b,T>(x: &'a T, y: &'b T)
    |                        -----     ----- these two types are declared with different lifetimes...
diff --git a/src/test/ui/associated-types/associated-types-subtyping-1.nll.stderr b/src/test/ui/associated-types/associated-types-subtyping-1.nll.stderr
index 11d3cfe5b46..44f918e12ba 100644
--- a/src/test/ui/associated-types/associated-types-subtyping-1.nll.stderr
+++ b/src/test/ui/associated-types/associated-types-subtyping-1.nll.stderr
@@ -1,5 +1,5 @@
 error: lifetime may not live long enough
-  --> $DIR/associated-types-subtyping-1.rs:24:12
+  --> $DIR/associated-types-subtyping-1.rs:28:12
    |
 LL | fn method2<'a,'b,T>(x: &'a T, y: &'b T)
    |            -- -- lifetime `'b` defined here
@@ -12,7 +12,7 @@ LL |     let a: <T as Trait<'a>>::Type = make_any();
    = help: consider adding the following bound: `'b: 'a`
 
 error: lifetime may not live long enough
-  --> $DIR/associated-types-subtyping-1.rs:35:13
+  --> $DIR/associated-types-subtyping-1.rs:41:13
    |
 LL | fn method3<'a,'b,T>(x: &'a T, y: &'b T)
    |            -- -- lifetime `'b` defined here
diff --git a/src/test/ui/associated-types/associated-types-subtyping-1.rs b/src/test/ui/associated-types/associated-types-subtyping-1.rs
index 012cffb7b97..5b75e023b85 100644
--- a/src/test/ui/associated-types/associated-types-subtyping-1.rs
+++ b/src/test/ui/associated-types/associated-types-subtyping-1.rs
@@ -1,3 +1,7 @@
+// ignore-compare-mode-nll
+// revisions: base nll
+// [nll]compile-flags: -Zborrowck=mir
+
 #![allow(unused_variables)]
 
 fn make_any<T>() -> T {  loop {} }
@@ -22,8 +26,10 @@ fn method2<'a,'b,T>(x: &'a T, y: &'b T)
 {
     // Note that &'static T <: &'a T.
     let a: <T as Trait<'a>>::Type = make_any();
+    //[nll]~^ ERROR lifetime may not live long enough
     let b: <T as Trait<'b>>::Type = make_any();
-    let _c: <T as Trait<'b>>::Type = a; //~ ERROR E0623
+    let _c: <T as Trait<'b>>::Type = a;
+    //[base]~^ ERROR E0623
 }
 
 fn method3<'a,'b,T>(x: &'a T, y: &'b T)
@@ -32,7 +38,9 @@ fn method3<'a,'b,T>(x: &'a T, y: &'b T)
     // Note that &'static T <: &'a T.
     let a: <T as Trait<'a>>::Type = make_any();
     let b: <T as Trait<'b>>::Type = make_any();
-    let _c: <T as Trait<'a>>::Type = b; //~ ERROR E0623
+    let _c: <T as Trait<'a>>::Type = b;
+    //[base]~^ ERROR E0623
+    //[nll]~^^ ERROR lifetime may not live long enough
 }
 
 fn method4<'a,'b,T>(x: &'a T, y: &'b T)
diff --git a/src/test/ui/associated-types/cache/project-fn-ret-contravariant-nll.krisskross.stderr b/src/test/ui/associated-types/cache/project-fn-ret-contravariant-nll.krisskross.stderr
new file mode 100644
index 00000000000..ed5518b628f
--- /dev/null
+++ b/src/test/ui/associated-types/cache/project-fn-ret-contravariant-nll.krisskross.stderr
@@ -0,0 +1,25 @@
+error[E0623]: lifetime mismatch
+  --> $DIR/project-fn-ret-contravariant-nll.rs:51:5
+   |
+LL | fn transmute<'a,'b>(x: &'a u32, y: &'b u32) -> (&'a u32, &'b u32) {
+   |                        -------                 ------------------
+   |                        |
+   |                        this parameter and the return type are declared with different lifetimes...
+...
+LL |    (a, b)
+   |     ^ ...but data from `y` is returned here
+
+error[E0623]: lifetime mismatch
+  --> $DIR/project-fn-ret-contravariant-nll.rs:51:8
+   |
+LL | fn transmute<'a,'b>(x: &'a u32, y: &'b u32) -> (&'a u32, &'b u32) {
+   |                                    -------     ------------------
+   |                                    |
+   |                                    this parameter and the return type are declared with different lifetimes...
+...
+LL |    (a, b)
+   |        ^ ...but data from `x` is returned here
+
+error: aborting due to 2 previous errors
+
+For more information about this error, try `rustc --explain E0623`.
diff --git a/src/test/ui/associated-types/cache/project-fn-ret-contravariant-nll.rs b/src/test/ui/associated-types/cache/project-fn-ret-contravariant-nll.rs
new file mode 100644
index 00000000000..c3ac9949c21
--- /dev/null
+++ b/src/test/ui/associated-types/cache/project-fn-ret-contravariant-nll.rs
@@ -0,0 +1,55 @@
+#![feature(unboxed_closures)]
+
+// Test for projection cache. We should be able to project distinct
+// lifetimes from `foo` as we reinstantiate it multiple times, but not
+// if we do it just once. In this variant, the region `'a` is used in
+// an contravariant position, which affects the results.
+
+// revisions: ok oneuse transmute krisskross
+//[ok] check-pass
+//[oneuse] check-pass
+
+// ignore-compare-mode-nll
+// FIXME(nll): When stabilizing, this test should replace `project-fn-ret-contravariant.rs`
+// The two would normally be just revisions, but this test uses revisions heavily, so splitting into
+// a separate test is just easier.
+
+#![allow(dead_code, unused_variables)]
+
+fn foo<'a>() -> &'a u32 { loop { } }
+
+fn bar<T>(t: T, x: T::Output) -> T::Output
+    where T: FnOnce<()>
+{
+    t()
+}
+
+#[cfg(ok)] // two instantiations: OK
+fn baz<'a,'b>(x: &'a u32, y: &'b u32) -> (&'a u32, &'b u32) {
+    let a = bar(foo, x);
+    let b = bar(foo, y);
+    (a, b)
+}
+
+#[cfg(oneuse)] // one instantiation: OK (surprisingly)
+fn baz<'a,'b>(x: &'a u32, y: &'b u32) -> (&'a u32, &'b u32) {
+    let f /* : fn() -> &'static u32 */ = foo; // <-- inferred type annotated
+    let a = bar(f, x); // this is considered ok because fn args are contravariant...
+    let b = bar(f, y); // ...and hence we infer T to distinct values in each call.
+    (a, b)
+}
+
+#[cfg(transmute)] // one instantiations: BAD
+fn baz<'a,'b>(x: &'a u32) -> &'static u32 {
+   bar(foo, x) //[transmute]~ ERROR E0759
+}
+
+#[cfg(krisskross)] // two instantiations, mixing and matching: BAD
+fn transmute<'a,'b>(x: &'a u32, y: &'b u32) -> (&'a u32, &'b u32) {
+   let a = bar(foo, y);
+   let b = bar(foo, x);
+   (a, b) //[krisskross]~ ERROR lifetime mismatch [E0623]
+   //[krisskross]~^ ERROR lifetime mismatch [E0623]
+}
+
+fn main() { }
diff --git a/src/test/ui/associated-types/cache/project-fn-ret-contravariant-nll.transmute.stderr b/src/test/ui/associated-types/cache/project-fn-ret-contravariant-nll.transmute.stderr
new file mode 100644
index 00000000000..ca57142ecee
--- /dev/null
+++ b/src/test/ui/associated-types/cache/project-fn-ret-contravariant-nll.transmute.stderr
@@ -0,0 +1,11 @@
+error[E0759]: `x` has lifetime `'a` but it needs to satisfy a `'static` lifetime requirement
+  --> $DIR/project-fn-ret-contravariant-nll.rs:44:8
+   |
+LL | fn baz<'a,'b>(x: &'a u32) -> &'static u32 {
+   |                  ------- this data with lifetime `'a`...
+LL |    bar(foo, x)
+   |        ^^^  - ...is used and required to live as long as `'static` here
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0759`.
diff --git a/src/test/ui/associated-types/cache/project-fn-ret-contravariant.krisskross.nll.stderr b/src/test/ui/associated-types/cache/project-fn-ret-contravariant.krisskross.nll.stderr
deleted file mode 100644
index a5b6d640391..00000000000
--- a/src/test/ui/associated-types/cache/project-fn-ret-contravariant.krisskross.nll.stderr
+++ /dev/null
@@ -1,30 +0,0 @@
-error: lifetime may not live long enough
-  --> $DIR/project-fn-ret-contravariant.rs:45:4
-   |
-LL | fn transmute<'a,'b>(x: &'a u32, y: &'b u32) -> (&'a u32, &'b u32) {
-   |              -- -- lifetime `'b` defined here
-   |              |
-   |              lifetime `'a` defined here
-...
-LL |    (a, b)
-   |    ^^^^^^ function was supposed to return data with lifetime `'b` but it is returning data with lifetime `'a`
-   |
-   = help: consider adding the following bound: `'a: 'b`
-
-error: lifetime may not live long enough
-  --> $DIR/project-fn-ret-contravariant.rs:45:4
-   |
-LL | fn transmute<'a,'b>(x: &'a u32, y: &'b u32) -> (&'a u32, &'b u32) {
-   |              -- -- lifetime `'b` defined here
-   |              |
-   |              lifetime `'a` defined here
-...
-LL |    (a, b)
-   |    ^^^^^^ function was supposed to return data with lifetime `'a` but it is returning data with lifetime `'b`
-   |
-   = help: consider adding the following bound: `'b: 'a`
-
-help: `'a` and `'b` must be the same: replace one with the other
-
-error: aborting due to 2 previous errors
-
diff --git a/src/test/ui/associated-types/cache/project-fn-ret-contravariant.krisskross.stderr b/src/test/ui/associated-types/cache/project-fn-ret-contravariant.krisskross.stderr
index fa4c6adb5ff..52824b3922e 100644
--- a/src/test/ui/associated-types/cache/project-fn-ret-contravariant.krisskross.stderr
+++ b/src/test/ui/associated-types/cache/project-fn-ret-contravariant.krisskross.stderr
@@ -1,5 +1,5 @@
 error[E0623]: lifetime mismatch
-  --> $DIR/project-fn-ret-contravariant.rs:45:5
+  --> $DIR/project-fn-ret-contravariant.rs:52:5
    |
 LL | fn transmute<'a,'b>(x: &'a u32, y: &'b u32) -> (&'a u32, &'b u32) {
    |                        -------                 ------------------
@@ -10,7 +10,7 @@ LL |    (a, b)
    |     ^ ...but data from `y` is returned here
 
 error[E0623]: lifetime mismatch
-  --> $DIR/project-fn-ret-contravariant.rs:45:8
+  --> $DIR/project-fn-ret-contravariant.rs:52:8
    |
 LL | fn transmute<'a,'b>(x: &'a u32, y: &'b u32) -> (&'a u32, &'b u32) {
    |                                    -------     ------------------
diff --git a/src/test/ui/associated-types/cache/project-fn-ret-contravariant.ok.stderr b/src/test/ui/associated-types/cache/project-fn-ret-contravariant.ok.stderr
deleted file mode 100644
index ed900079cfc..00000000000
--- a/src/test/ui/associated-types/cache/project-fn-ret-contravariant.ok.stderr
+++ /dev/null
@@ -1,8 +0,0 @@
-error: fatal error triggered by #[rustc_error]
-  --> $DIR/project-fn-ret-contravariant.rs:50:1
-   |
-LL | fn main() { }
-   | ^^^^^^^^^
-
-error: aborting due to previous error
-
diff --git a/src/test/ui/associated-types/cache/project-fn-ret-contravariant.oneuse.stderr b/src/test/ui/associated-types/cache/project-fn-ret-contravariant.oneuse.stderr
deleted file mode 100644
index ed900079cfc..00000000000
--- a/src/test/ui/associated-types/cache/project-fn-ret-contravariant.oneuse.stderr
+++ /dev/null
@@ -1,8 +0,0 @@
-error: fatal error triggered by #[rustc_error]
-  --> $DIR/project-fn-ret-contravariant.rs:50:1
-   |
-LL | fn main() { }
-   | ^^^^^^^^^
-
-error: aborting due to previous error
-
diff --git a/src/test/ui/associated-types/cache/project-fn-ret-contravariant.rs b/src/test/ui/associated-types/cache/project-fn-ret-contravariant.rs
index 1eeb01ccc84..7bd245d1c34 100644
--- a/src/test/ui/associated-types/cache/project-fn-ret-contravariant.rs
+++ b/src/test/ui/associated-types/cache/project-fn-ret-contravariant.rs
@@ -1,5 +1,4 @@
 #![feature(unboxed_closures)]
-#![feature(rustc_attrs)]
 
 // Test for projection cache. We should be able to project distinct
 // lifetimes from `foo` as we reinstantiate it multiple times, but not
@@ -7,6 +6,14 @@
 // an contravariant position, which affects the results.
 
 // revisions: ok oneuse transmute krisskross
+//[ok] check-pass
+//[oneuse] check-pass
+
+// ignore-compare-mode-nll
+// FIXME(nll): When stabilizing, this test should be replaced with
+// `project-fn-ret-contravariant-nll.rs` The two would normally be just
+// revisions, but this test uses revisions heavily, so splitting into
+// a separate test is just easier.
 
 #![allow(dead_code, unused_variables)]
 
@@ -46,5 +53,4 @@ fn transmute<'a,'b>(x: &'a u32, y: &'b u32) -> (&'a u32, &'b u32) {
    //[krisskross]~^ ERROR lifetime mismatch [E0623]
 }
 
-#[rustc_error]
-fn main() { } //[ok,oneuse]~ ERROR fatal error triggered by #[rustc_error]
+fn main() { }
diff --git a/src/test/ui/associated-types/cache/project-fn-ret-contravariant.transmute.nll.stderr b/src/test/ui/associated-types/cache/project-fn-ret-contravariant.transmute.nll.stderr
deleted file mode 100644
index f532c96ed2c..00000000000
--- a/src/test/ui/associated-types/cache/project-fn-ret-contravariant.transmute.nll.stderr
+++ /dev/null
@@ -1,10 +0,0 @@
-error: lifetime may not live long enough
-  --> $DIR/project-fn-ret-contravariant.rs:38:4
-   |
-LL | fn baz<'a,'b>(x: &'a u32) -> &'static u32 {
-   |        -- lifetime `'a` defined here
-LL |    bar(foo, x)
-   |    ^^^^^^^^^^^ returning this value requires that `'a` must outlive `'static`
-
-error: aborting due to previous error
-
diff --git a/src/test/ui/associated-types/cache/project-fn-ret-contravariant.transmute.stderr b/src/test/ui/associated-types/cache/project-fn-ret-contravariant.transmute.stderr
index 33f1e0f05b2..3d7f36ca32b 100644
--- a/src/test/ui/associated-types/cache/project-fn-ret-contravariant.transmute.stderr
+++ b/src/test/ui/associated-types/cache/project-fn-ret-contravariant.transmute.stderr
@@ -1,5 +1,5 @@
 error[E0759]: `x` has lifetime `'a` but it needs to satisfy a `'static` lifetime requirement
-  --> $DIR/project-fn-ret-contravariant.rs:38:8
+  --> $DIR/project-fn-ret-contravariant.rs:45:8
    |
 LL | fn baz<'a,'b>(x: &'a u32) -> &'static u32 {
    |                  ------- this data with lifetime `'a`...
diff --git a/src/test/ui/associated-types/cache/project-fn-ret-invariant.krisskross.nll.stderr b/src/test/ui/associated-types/cache/project-fn-ret-invariant-nll.krisskross.stderr
index 55532d6b9b3..231e98cf841 100644
--- a/src/test/ui/associated-types/cache/project-fn-ret-invariant.krisskross.nll.stderr
+++ b/src/test/ui/associated-types/cache/project-fn-ret-invariant-nll.krisskross.stderr
@@ -1,5 +1,5 @@
 error: lifetime may not live long enough
-  --> $DIR/project-fn-ret-invariant.rs:56:5
+  --> $DIR/project-fn-ret-invariant-nll.rs:63:5
    |
 LL | fn transmute<'a, 'b>(x: Type<'a>, y: Type<'b>) -> (Type<'a>, Type<'b>) {
    |              --  -- lifetime `'b` defined here
@@ -15,7 +15,7 @@ LL |     (a, b)
    = help: see <https://doc.rust-lang.org/nomicon/subtyping.html> for more information about variance
 
 error: lifetime may not live long enough
-  --> $DIR/project-fn-ret-invariant.rs:56:5
+  --> $DIR/project-fn-ret-invariant-nll.rs:63:5
    |
 LL | fn transmute<'a, 'b>(x: Type<'a>, y: Type<'b>) -> (Type<'a>, Type<'b>) {
    |              --  -- lifetime `'b` defined here
diff --git a/src/test/ui/associated-types/cache/project-fn-ret-invariant.oneuse.nll.stderr b/src/test/ui/associated-types/cache/project-fn-ret-invariant-nll.oneuse.stderr
index fd9eb05473a..1dbfff6a8cd 100644
--- a/src/test/ui/associated-types/cache/project-fn-ret-invariant.oneuse.nll.stderr
+++ b/src/test/ui/associated-types/cache/project-fn-ret-invariant-nll.oneuse.stderr
@@ -1,5 +1,5 @@
 error: lifetime may not live long enough
-  --> $DIR/project-fn-ret-invariant.rs:39:13
+  --> $DIR/project-fn-ret-invariant-nll.rs:46:13
    |
 LL | fn baz<'a, 'b>(x: Type<'a>, y: Type<'b>) -> (Type<'a>, Type<'b>) {
    |        --  -- lifetime `'b` defined here
@@ -15,7 +15,7 @@ LL |     let a = bar(f, x);
    = help: see <https://doc.rust-lang.org/nomicon/subtyping.html> for more information about variance
 
 error: lifetime may not live long enough
-  --> $DIR/project-fn-ret-invariant.rs:40:13
+  --> $DIR/project-fn-ret-invariant-nll.rs:47:13
    |
 LL | fn baz<'a, 'b>(x: Type<'a>, y: Type<'b>) -> (Type<'a>, Type<'b>) {
    |        --  -- lifetime `'b` defined here
diff --git a/src/test/ui/associated-types/cache/project-fn-ret-invariant-nll.rs b/src/test/ui/associated-types/cache/project-fn-ret-invariant-nll.rs
new file mode 100644
index 00000000000..6cd5c6417a9
--- /dev/null
+++ b/src/test/ui/associated-types/cache/project-fn-ret-invariant-nll.rs
@@ -0,0 +1,68 @@
+#![feature(unboxed_closures)]
+// Test for projection cache. We should be able to project distinct
+// lifetimes from `foo` as we reinstantiate it multiple times, but not
+// if we do it just once. In this variant, the region `'a` is used in
+// an invariant position, which affects the results.
+
+// revisions: ok oneuse transmute krisskross
+//[ok] check-pass
+
+// compile-flags: -Z borrowck=mir
+// ignore-compare-mode-nll
+// FIXME(nll): When stabilizing, this test should replace with `project-fn-ret-invariant.rs`
+// The two would normally be just revisions, but this test uses revisions heavily, so splitting into
+// a separate test is just easier.
+
+#![allow(dead_code, unused_variables)]
+
+use std::marker::PhantomData;
+
+struct Type<'a> {
+    // Invariant
+    data: PhantomData<fn(&'a u32) -> &'a u32>,
+}
+
+fn foo<'a>() -> Type<'a> {
+    loop {}
+}
+
+fn bar<T>(t: T, x: T::Output) -> T::Output
+where
+    T: FnOnce<()>,
+{
+    t()
+}
+
+#[cfg(ok)] // two instantiations: OK
+fn baz<'a, 'b>(x: Type<'a>, y: Type<'b>) -> (Type<'a>, Type<'b>) {
+    let a = bar(foo, x);
+    let b = bar(foo, y);
+    (a, b)
+}
+
+#[cfg(oneuse)] // one instantiation: BAD
+fn baz<'a, 'b>(x: Type<'a>, y: Type<'b>) -> (Type<'a>, Type<'b>) {
+    let f = foo; // <-- No consistent type can be inferred for `f` here.
+    let a = bar(f, x); //[oneuse]~ ERROR lifetime may not live long enough
+    let b = bar(f, y); //[oneuse]~ ERROR lifetime may not live long enough
+    (a, b)
+}
+
+#[cfg(transmute)] // one instantiations: BAD
+fn baz<'a, 'b>(x: Type<'a>) -> Type<'static> {
+    // Cannot instantiate `foo` with any lifetime other than `'a`,
+    // since it is provided as input.
+
+    bar(foo, x) //[transmute]~ ERROR lifetime may not live long enough
+}
+
+#[cfg(krisskross)] // two instantiations, mixing and matching: BAD
+fn transmute<'a, 'b>(x: Type<'a>, y: Type<'b>) -> (Type<'a>, Type<'b>) {
+    let a = bar(foo, y);
+    let b = bar(foo, x);
+    (a, b)
+    //[krisskross]~^ ERROR lifetime may not live long enough
+    //[krisskross]~| ERROR lifetime may not live long enough
+}
+
+fn main() {}
diff --git a/src/test/ui/associated-types/cache/project-fn-ret-invariant.transmute.nll.stderr b/src/test/ui/associated-types/cache/project-fn-ret-invariant-nll.transmute.stderr
index 5a7ead72949..352914f020c 100644
--- a/src/test/ui/associated-types/cache/project-fn-ret-invariant.transmute.nll.stderr
+++ b/src/test/ui/associated-types/cache/project-fn-ret-invariant-nll.transmute.stderr
@@ -1,5 +1,5 @@
 error: lifetime may not live long enough
-  --> $DIR/project-fn-ret-invariant.rs:49:5
+  --> $DIR/project-fn-ret-invariant-nll.rs:56:5
    |
 LL | fn baz<'a, 'b>(x: Type<'a>) -> Type<'static> {
    |        -- lifetime `'a` defined here
diff --git a/src/test/ui/associated-types/cache/project-fn-ret-invariant.krisskross.stderr b/src/test/ui/associated-types/cache/project-fn-ret-invariant.krisskross.stderr
index 9462121bdf2..fd1152dd80c 100644
--- a/src/test/ui/associated-types/cache/project-fn-ret-invariant.krisskross.stderr
+++ b/src/test/ui/associated-types/cache/project-fn-ret-invariant.krisskross.stderr
@@ -1,5 +1,5 @@
 error[E0623]: lifetime mismatch
-  --> $DIR/project-fn-ret-invariant.rs:54:22
+  --> $DIR/project-fn-ret-invariant.rs:60:22
    |
 LL | fn transmute<'a, 'b>(x: Type<'a>, y: Type<'b>) -> (Type<'a>, Type<'b>) {
    |                                      --------     --------------------
@@ -9,7 +9,7 @@ LL |     let a = bar(foo, y);
    |                      ^ ...but data from `x` is returned here
 
 error[E0623]: lifetime mismatch
-  --> $DIR/project-fn-ret-invariant.rs:56:9
+  --> $DIR/project-fn-ret-invariant.rs:62:9
    |
 LL | fn transmute<'a, 'b>(x: Type<'a>, y: Type<'b>) -> (Type<'a>, Type<'b>) {
    |                                      --------     --------------------
diff --git a/src/test/ui/associated-types/cache/project-fn-ret-invariant.ok.stderr b/src/test/ui/associated-types/cache/project-fn-ret-invariant.ok.stderr
deleted file mode 100644
index c3408500948..00000000000
--- a/src/test/ui/associated-types/cache/project-fn-ret-invariant.ok.stderr
+++ /dev/null
@@ -1,8 +0,0 @@
-error: fatal error triggered by #[rustc_error]
-  --> $DIR/project-fn-ret-invariant.rs:60:1
-   |
-LL | fn main() {}
-   | ^^^^^^^^^
-
-error: aborting due to previous error
-
diff --git a/src/test/ui/associated-types/cache/project-fn-ret-invariant.oneuse.stderr b/src/test/ui/associated-types/cache/project-fn-ret-invariant.oneuse.stderr
index 64b57223908..1b10c6b990a 100644
--- a/src/test/ui/associated-types/cache/project-fn-ret-invariant.oneuse.stderr
+++ b/src/test/ui/associated-types/cache/project-fn-ret-invariant.oneuse.stderr
@@ -1,5 +1,5 @@
 error[E0623]: lifetime mismatch
-  --> $DIR/project-fn-ret-invariant.rs:40:20
+  --> $DIR/project-fn-ret-invariant.rs:46:20
    |
 LL | fn baz<'a, 'b>(x: Type<'a>, y: Type<'b>) -> (Type<'a>, Type<'b>) {
    |                                --------     --------------------
diff --git a/src/test/ui/associated-types/cache/project-fn-ret-invariant.rs b/src/test/ui/associated-types/cache/project-fn-ret-invariant.rs
index 08d864f7836..d42d99d7783 100644
--- a/src/test/ui/associated-types/cache/project-fn-ret-invariant.rs
+++ b/src/test/ui/associated-types/cache/project-fn-ret-invariant.rs
@@ -1,11 +1,17 @@
 #![feature(unboxed_closures)]
-#![feature(rustc_attrs)]
 // Test for projection cache. We should be able to project distinct
 // lifetimes from `foo` as we reinstantiate it multiple times, but not
 // if we do it just once. In this variant, the region `'a` is used in
 // an invariant position, which affects the results.
 
 // revisions: ok oneuse transmute krisskross
+//[ok] check-pass
+
+// ignore-compare-mode-nll
+// FIXME(nll): When stabilizing, this test should be replaced with `project-fn-ret-invariant-nll.rs`
+// The two would normally be just revisions, but this test uses revisions heavily, so splitting into
+// a separate test is just easier.
+
 #![allow(dead_code, unused_variables)]
 
 use std::marker::PhantomData;
@@ -56,6 +62,4 @@ fn transmute<'a, 'b>(x: Type<'a>, y: Type<'b>) -> (Type<'a>, Type<'b>) {
     (a, b) //[krisskross]~ ERROR E0623
 }
 
-#[rustc_error]
 fn main() {}
-//[ok]~^ ERROR fatal error triggered by #[rustc_error]
diff --git a/src/test/ui/associated-types/cache/project-fn-ret-invariant.transmute.stderr b/src/test/ui/associated-types/cache/project-fn-ret-invariant.transmute.stderr
index 609627aaa9e..8c1d9d1e284 100644
--- a/src/test/ui/associated-types/cache/project-fn-ret-invariant.transmute.stderr
+++ b/src/test/ui/associated-types/cache/project-fn-ret-invariant.transmute.stderr
@@ -1,5 +1,5 @@
 error[E0759]: `x` has lifetime `'a` but it needs to satisfy a `'static` lifetime requirement
-  --> $DIR/project-fn-ret-invariant.rs:49:9
+  --> $DIR/project-fn-ret-invariant.rs:55:9
    |
 LL | fn baz<'a, 'b>(x: Type<'a>) -> Type<'static> {
    |                   -------- this data with lifetime `'a`...
@@ -8,7 +8,7 @@ LL |     bar(foo, x)
    |         ^^^  - ...is used and required to live as long as `'static` here
    |
 note: `'static` lifetime requirement introduced by the return type
-  --> $DIR/project-fn-ret-invariant.rs:45:37
+  --> $DIR/project-fn-ret-invariant.rs:51:37
    |
 LL | fn baz<'a, 'b>(x: Type<'a>) -> Type<'static> {
    |                                     ^^^^^^^ `'static` requirement introduced here
diff --git a/src/test/ui/associated-types/higher-ranked-projection.badbase.stderr b/src/test/ui/associated-types/higher-ranked-projection.badbase.stderr
new file mode 100644
index 00000000000..732f5d9584b
--- /dev/null
+++ b/src/test/ui/associated-types/higher-ranked-projection.badbase.stderr
@@ -0,0 +1,17 @@
+error[E0308]: mismatched types
+  --> $DIR/higher-ranked-projection.rs:25:5
+   |
+LL |     foo(());
+   |     ^^^ lifetime mismatch
+   |
+   = note: expected reference `&'a ()`
+              found reference `&()`
+note: the lifetime requirement is introduced here
+  --> $DIR/higher-ranked-projection.rs:16:33
+   |
+LL |     where for<'a> &'a T: Mirror<Image=U>
+   |                                 ^^^^^^^
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0308`.
diff --git a/src/test/ui/associated-types/higher-ranked-projection.badnll.stderr b/src/test/ui/associated-types/higher-ranked-projection.badnll.stderr
new file mode 100644
index 00000000000..8b2b87223a5
--- /dev/null
+++ b/src/test/ui/associated-types/higher-ranked-projection.badnll.stderr
@@ -0,0 +1,17 @@
+error[E0308]: mismatched types
+  --> $DIR/higher-ranked-projection.rs:25:5
+   |
+LL |     foo(());
+   |     ^^^^^^^ one type is more general than the other
+   |
+   = note: expected reference `&'a ()`
+              found reference `&()`
+note: the lifetime requirement is introduced here
+  --> $DIR/higher-ranked-projection.rs:16:33
+   |
+LL |     where for<'a> &'a T: Mirror<Image=U>
+   |                                 ^^^^^^^
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0308`.
diff --git a/src/test/ui/associated-types/higher-ranked-projection.good.stderr b/src/test/ui/associated-types/higher-ranked-projection.good.stderr
deleted file mode 100644
index 1dc41a2165f..00000000000
--- a/src/test/ui/associated-types/higher-ranked-projection.good.stderr
+++ /dev/null
@@ -1,8 +0,0 @@
-error: fatal error triggered by #[rustc_error]
-  --> $DIR/higher-ranked-projection.rs:24:1
-   |
-LL | fn main() {
-   | ^^^^^^^^^
-
-error: aborting due to previous error
-
diff --git a/src/test/ui/associated-types/higher-ranked-projection.rs b/src/test/ui/associated-types/higher-ranked-projection.rs
index 1b5476d4c36..8b1046b6bbc 100644
--- a/src/test/ui/associated-types/higher-ranked-projection.rs
+++ b/src/test/ui/associated-types/higher-ranked-projection.rs
@@ -1,6 +1,7 @@
-#![feature(rustc_attrs)]
-
-// revisions: good bad
+// ignore-compare-mode-nll
+// revisions: good badbase badnll
+//[good] check-pass
+// [badnll]compile-flags: -Zborrowck=mir
 
 trait Mirror {
     type Image;
@@ -10,7 +11,7 @@ impl<T> Mirror for T {
     type Image = T;
 }
 
-#[cfg(bad)]
+#[cfg(any(badbase, badnll))]
 fn foo<U, T>(_t: T)
     where for<'a> &'a T: Mirror<Image=U>
 {}
@@ -20,8 +21,8 @@ fn foo<U, T>(_t: T)
     where for<'a> &'a T: Mirror<Image=&'a U>
 {}
 
-#[rustc_error]
-fn main() { //[good]~ ERROR fatal error triggered by #[rustc_error]
+fn main() {
     foo(());
-    //[bad]~^ ERROR mismatched types
+    //[badbase]~^ ERROR mismatched types
+    //[badnll]~^^ ERROR mismatched types
 }