5458: Use expect in some ra_hir_ty tests r=flodiebold a=lnicola



Co-authored-by: Laurențiu Nicola <lnicola@dend.ro>
This commit is contained in:
bors[bot] 2020-07-21 07:11:55 +00:00 committed by GitHub
commit 57664369af
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
3 changed files with 882 additions and 835 deletions

View file

@ -10,6 +10,7 @@ mod display_source_code;
use std::sync::Arc;
use expect::Expect;
use hir_def::{
body::{BodySourceMap, SyntheticSyntax},
child_by_source::ChildBySource,
@ -344,3 +345,15 @@ fn typing_whitespace_inside_a_function_should_not_invalidate_types() {
assert!(!format!("{:?}", events).contains("infer"), "{:#?}", events)
}
}
fn check_infer(ra_fixture: &str, expect: Expect) {
let mut actual = infer(ra_fixture);
actual.push('\n');
expect.assert_eq(&actual);
}
fn check_infer_with_mismatches(ra_fixture: &str, expect: Expect) {
let mut actual = infer_with_mismatches(ra_fixture, true);
actual.push('\n');
expect.assert_eq(&actual);
}

View file

@ -1,46 +1,29 @@
use insta::assert_snapshot;
use expect::expect;
use test_utils::mark;
use super::infer_with_mismatches;
// Infer with some common definitions and impls.
fn infer(source: &str) -> String {
let defs = r#"
#[lang = "sized"]
pub trait Sized {}
#[lang = "unsize"]
pub trait Unsize<T: ?Sized> {}
#[lang = "coerce_unsized"]
pub trait CoerceUnsized<T> {}
impl<'a, 'b: 'a, T: ?Sized + Unsize<U>, U: ?Sized> CoerceUnsized<&'a U> for &'b T {}
impl<T: ?Sized + Unsize<U>, U: ?Sized> CoerceUnsized<*mut U> for *mut T {}
"#;
// Append to the end to keep positions unchanged.
super::infer(&format!("{}{}", source, defs))
}
use super::{check_infer, check_infer_with_mismatches};
#[test]
fn infer_block_expr_type_mismatch() {
assert_snapshot!(
infer(r#"
check_infer(
r"
fn test() {
let a: i32 = { 1i64 };
}
"#),
@r###"
",
expect![[r"
10..40 '{ ...4 }; }': ()
20..21 'a': i32
29..37 '{ 1i64 }': i64
31..35 '1i64': i64
"###);
"]],
);
}
#[test]
fn coerce_places() {
assert_snapshot!(
infer(r#"
check_infer(
r#"
struct S<T> { a: T }
fn f<T>(_: &[T]) -> T { loop {} }
@ -62,8 +45,18 @@ fn test2() {
let f: [&[_]; 2] = [arr; 2];
let g: (&[_], &[_]) = (arr, arr);
}
"#),
@r###"
#[lang = "sized"]
pub trait Sized {}
#[lang = "unsize"]
pub trait Unsize<T: ?Sized> {}
#[lang = "coerce_unsized"]
pub trait CoerceUnsized<T> {}
impl<'a, 'b: 'a, T: ?Sized + Unsize<U>, U: ?Sized> CoerceUnsized<&'a U> for &'b T {}
impl<T: ?Sized + Unsize<U>, U: ?Sized> CoerceUnsized<*mut U> for *mut T {}
"#,
expect![[r"
30..31 '_': &[T]
44..55 '{ loop {} }': T
46..53 'loop {}': !
@ -108,20 +101,20 @@ fn test2() {
406..416 '(arr, arr)': (&[u8], &[u8])
407..410 'arr': &[u8; _]
412..415 'arr': &[u8; _]
"###
"]],
);
}
#[test]
fn infer_let_stmt_coerce() {
assert_snapshot!(
infer(r#"
check_infer(
r"
fn test() {
let x: &[isize] = &[1];
let x: *const [isize] = &[1];
}
"#),
@r###"
",
expect![[r"
10..75 '{ ...[1]; }': ()
20..21 'x': &[isize]
34..38 '&[1]': &[isize; _]
@ -131,13 +124,14 @@ fn test() {
68..72 '&[1]': &[isize; _]
69..72 '[1]': [isize; _]
70..71 '1': isize
"###);
"]],
);
}
#[test]
fn infer_custom_coerce_unsized() {
assert_snapshot!(
infer(r#"
check_infer(
r#"
struct A<T: ?Sized>(*const T);
struct B<T: ?Sized>(*const T);
struct C<T: ?Sized> { inner: *const T }
@ -154,8 +148,19 @@ fn test(a: A<[u8; 2]>, b: B<[u8; 2]>, c: C<[u8; 2]>) {
let e = foo2(b);
let f = foo3(c);
}
"#),
@r###"
#[lang = "sized"]
pub trait Sized {}
#[lang = "unsize"]
pub trait Unsize<T: ?Sized> {}
#[lang = "coerce_unsized"]
pub trait CoerceUnsized<T> {}
impl<'a, 'b: 'a, T: ?Sized + Unsize<U>, U: ?Sized> CoerceUnsized<&'a U> for &'b T {}
impl<T: ?Sized + Unsize<U>, U: ?Sized> CoerceUnsized<*mut U> for *mut T {}
"#,
expect![[r"
257..258 'x': A<[T]>
278..283 '{ x }': A<[T]>
280..281 'x': A<[T]>
@ -181,14 +186,14 @@ fn test(a: A<[u8; 2]>, b: B<[u8; 2]>, c: C<[u8; 2]>) {
470..474 'foo3': fn foo3<u8>(C<[u8]>) -> C<[u8]>
470..477 'foo3(c)': C<[u8]>
475..476 'c': C<[u8; _]>
"###
"]],
);
}
#[test]
fn infer_if_coerce() {
assert_snapshot!(
infer(r#"
check_infer(
r#"
fn foo<T>(x: &[T]) -> &[T] { loop {} }
fn test() {
let x = if true {
@ -197,8 +202,14 @@ fn test() {
&[1]
};
}
"#),
@r###"
#[lang = "sized"]
pub trait Sized {}
#[lang = "unsize"]
pub trait Unsize<T: ?Sized> {}
"#,
expect![[r"
10..11 'x': &[T]
27..38 '{ loop {} }': &[T]
29..36 'loop {}': !
@ -217,14 +228,14 @@ fn test() {
112..116 '&[1]': &[i32; _]
113..116 '[1]': [i32; _]
114..115 '1': i32
"###
"]],
);
}
#[test]
fn infer_if_else_coerce() {
assert_snapshot!(
infer(r#"
check_infer(
r#"
fn foo<T>(x: &[T]) -> &[T] { loop {} }
fn test() {
let x = if true {
@ -233,8 +244,18 @@ fn test() {
foo(&[1])
};
}
"#),
@r###"
#[lang = "sized"]
pub trait Sized {}
#[lang = "unsize"]
pub trait Unsize<T: ?Sized> {}
#[lang = "coerce_unsized"]
pub trait CoerceUnsized<T> {}
impl<'a, 'b: 'a, T: ?Sized + Unsize<U>, U: ?Sized> CoerceUnsized<&'a U> for &'b T {}
impl<T: ?Sized + Unsize<U>, U: ?Sized> CoerceUnsized<*mut U> for *mut T {}
"#,
expect![[r"
10..11 'x': &[T]
27..38 '{ loop {} }': &[T]
29..36 'loop {}': !
@ -253,14 +274,14 @@ fn test() {
111..115 '&[1]': &[i32; _]
112..115 '[1]': [i32; _]
113..114 '1': i32
"###
);
"]],
)
}
#[test]
fn infer_match_first_coerce() {
assert_snapshot!(
infer(r#"
check_infer(
r#"
fn foo<T>(x: &[T]) -> &[T] { loop {} }
fn test(i: i32) {
let x = match i {
@ -269,8 +290,13 @@ fn test(i: i32) {
_ => &[3],
};
}
"#),
@r###"
#[lang = "sized"]
pub trait Sized {}
#[lang = "unsize"]
pub trait Unsize<T: ?Sized> {}
"#,
expect![[r"
10..11 'x': &[T]
27..38 '{ loop {} }': &[T]
29..36 'loop {}': !
@ -296,14 +322,14 @@ fn test(i: i32) {
135..139 '&[3]': &[i32; _]
136..139 '[3]': [i32; _]
137..138 '3': i32
"###
"]],
);
}
#[test]
fn infer_match_second_coerce() {
assert_snapshot!(
infer(r#"
check_infer(
r#"
fn foo<T>(x: &[T]) -> &[T] { loop {} }
fn test(i: i32) {
let x = match i {
@ -312,8 +338,18 @@ fn test(i: i32) {
_ => &[3],
};
}
"#),
@r###"
#[lang = "sized"]
pub trait Sized {}
#[lang = "unsize"]
pub trait Unsize<T: ?Sized> {}
#[lang = "coerce_unsized"]
pub trait CoerceUnsized<T> {}
impl<'a, 'b: 'a, T: ?Sized + Unsize<U>, U: ?Sized> CoerceUnsized<&'a U> for &'b T {}
impl<T: ?Sized + Unsize<U>, U: ?Sized> CoerceUnsized<*mut U> for *mut T {}
"#,
expect![[r"
10..11 'x': &[T]
27..38 '{ loop {} }': &[T]
29..36 'loop {}': !
@ -339,7 +375,7 @@ fn test(i: i32) {
135..139 '&[3]': &[i32; _]
136..139 '[3]': [i32; _]
137..138 '3': i32
"###
"]],
);
}
@ -347,8 +383,8 @@ fn test(i: i32) {
fn coerce_merge_one_by_one1() {
mark::check!(coerce_merge_fail_fallback);
assert_snapshot!(
infer(r#"
check_infer(
r"
fn test() {
let t = &mut 1;
let x = match 1 {
@ -357,8 +393,8 @@ fn test() {
_ => t as *const i32,
};
}
"#),
@r###"
",
expect![[r"
10..144 '{ ... }; }': ()
20..21 't': &mut i32
24..30 '&mut 1': &mut i32
@ -377,30 +413,30 @@ fn test() {
114..115 '_': i32
119..120 't': &mut i32
119..134 't as *const i32': *const i32
"###
"]],
);
}
#[test]
fn return_coerce_unknown() {
assert_snapshot!(
infer_with_mismatches(r#"
check_infer_with_mismatches(
r"
fn foo() -> u32 {
return unknown;
}
"#, true),
@r###"
",
expect![[r"
16..39 '{ ...own; }': u32
22..36 'return unknown': !
29..36 'unknown': u32
"###
"]],
);
}
#[test]
fn coerce_autoderef() {
assert_snapshot!(
infer_with_mismatches(r#"
check_infer_with_mismatches(
r"
struct Foo;
fn takes_ref_foo(x: &Foo) {}
fn test() {
@ -408,8 +444,8 @@ fn test() {
takes_ref_foo(&&Foo);
takes_ref_foo(&&&Foo);
}
"#, true),
@r###"
",
expect![[r"
29..30 'x': &Foo
38..40 '{}': ()
51..132 '{ ...oo); }': ()
@ -428,14 +464,14 @@ fn test() {
123..128 '&&Foo': &&Foo
124..128 '&Foo': &Foo
125..128 'Foo': Foo
"###
"]],
);
}
#[test]
fn coerce_autoderef_generic() {
assert_snapshot!(
infer_with_mismatches(r#"
check_infer_with_mismatches(
r"
struct Foo;
fn takes_ref<T>(x: &T) -> T { *x }
fn test() {
@ -443,8 +479,8 @@ fn test() {
takes_ref(&&Foo);
takes_ref(&&&Foo);
}
"#, true),
@r###"
",
expect![[r"
28..29 'x': &T
40..46 '{ *x }': T
42..44 '*x': T
@ -465,14 +501,14 @@ fn test() {
117..122 '&&Foo': &&Foo
118..122 '&Foo': &Foo
119..122 'Foo': Foo
"###
"]],
);
}
#[test]
fn coerce_autoderef_block() {
assert_snapshot!(
infer_with_mismatches(r#"
check_infer_with_mismatches(
r#"
struct String {}
#[lang = "deref"]
trait Deref { type Target; }
@ -482,8 +518,8 @@ fn returns_string() -> String { loop {} }
fn test() {
takes_ref_str(&{ returns_string() });
}
"#, true),
@r###"
"#,
expect![[r"
126..127 'x': &str
135..137 '{}': ()
168..179 '{ loop {} }': String
@ -496,14 +532,14 @@ fn test() {
211..231 '{ retu...ng() }': String
213..227 'returns_string': fn returns_string() -> String
213..229 'return...ring()': String
"###
"]],
);
}
#[test]
fn closure_return_coerce() {
assert_snapshot!(
infer_with_mismatches(r#"
check_infer_with_mismatches(
r"
fn foo() {
let x = || {
if true {
@ -512,8 +548,8 @@ fn foo() {
&&1u32
};
}
"#, true),
@r###"
",
expect![[r"
9..105 '{ ... }; }': ()
19..20 'x': || -> &u32
23..102 '|| { ... }': || -> &u32
@ -527,35 +563,36 @@ fn foo() {
90..96 '&&1u32': &&u32
91..96 '&1u32': &u32
92..96 '1u32': u32
"###
"]],
);
}
#[test]
fn coerce_fn_item_to_fn_ptr() {
assert_snapshot!(
infer_with_mismatches(r#"
check_infer_with_mismatches(
r"
fn foo(x: u32) -> isize { 1 }
fn test() {
let f: fn(u32) -> isize = foo;
}
"#, true),
@r###"
",
expect![[r"
7..8 'x': u32
24..29 '{ 1 }': isize
26..27 '1': isize
40..78 '{ ...foo; }': ()
50..51 'f': fn(u32) -> isize
72..75 'foo': fn foo(u32) -> isize
"###
"]],
);
}
#[test]
fn coerce_fn_items_in_match_arms() {
mark::check!(coerce_fn_reification);
assert_snapshot!(
infer_with_mismatches(r#"
check_infer_with_mismatches(
r"
fn foo1(x: u32) -> isize { 1 }
fn foo2(x: u32) -> isize { 2 }
fn foo3(x: u32) -> isize { 3 }
@ -566,8 +603,8 @@ fn test() {
_ => foo3,
};
}
"#, true),
@r###"
",
expect![[r"
8..9 'x': u32
25..30 '{ 1 }': isize
27..28 '1': isize
@ -589,55 +626,55 @@ fn test() {
159..163 'foo2': fn foo2(u32) -> isize
173..174 '_': i32
178..182 'foo3': fn foo3(u32) -> isize
"###
"]],
);
}
#[test]
fn coerce_closure_to_fn_ptr() {
assert_snapshot!(
infer_with_mismatches(r#"
check_infer_with_mismatches(
r"
fn test() {
let f: fn(u32) -> isize = |x| { 1 };
}
"#, true),
@r###"
",
expect![[r"
10..54 '{ ...1 }; }': ()
20..21 'f': fn(u32) -> isize
42..51 '|x| { 1 }': |u32| -> isize
43..44 'x': u32
46..51 '{ 1 }': isize
48..49 '1': isize
"###
"]],
);
}
#[test]
fn coerce_placeholder_ref() {
// placeholders should unify, even behind references
assert_snapshot!(
infer_with_mismatches(r#"
check_infer_with_mismatches(
r"
struct S<T> { t: T }
impl<TT> S<TT> {
fn get(&self) -> &TT {
&self.t
}
}
"#, true),
@r###"
",
expect![[r"
50..54 'self': &S<TT>
63..86 '{ ... }': &TT
73..80 '&self.t': &TT
74..78 'self': &S<TT>
74..80 'self.t': TT
"###
"]],
);
}
#[test]
fn coerce_unsize_array() {
assert_snapshot!(
infer_with_mismatches(r#"
check_infer_with_mismatches(
r#"
#[lang = "unsize"]
pub trait Unsize<T> {}
#[lang = "coerce_unsized"]
@ -648,8 +685,8 @@ impl<T: Unsize<U>, U> CoerceUnsized<&U> for &T {}
fn test() {
let f: &[usize] = &[1, 2, 3];
}
"#, true),
@r###"
"#,
expect![[r"
161..198 '{ ... 3]; }': ()
171..172 'f': &[usize]
185..195 '&[1, 2, 3]': &[usize; _]
@ -657,14 +694,14 @@ fn test() {
187..188 '1': usize
190..191 '2': usize
193..194 '3': usize
"###
"]],
);
}
#[test]
fn coerce_unsize_trait_object_simple() {
assert_snapshot!(
infer_with_mismatches(r#"
check_infer_with_mismatches(
r#"
#[lang = "sized"]
pub trait Sized {}
#[lang = "unsize"]
@ -688,8 +725,8 @@ fn test() {
let obj: &dyn Bar<_, i8, i16> = &S;
let obj: &dyn Foo<i8, _> = &S;
}
"#, true),
@r###"
"#,
expect![[r"
424..539 '{ ... &S; }': ()
434..437 'obj': &dyn Baz<i8, i16>
459..461 '&S': &S<i8, i16>
@ -700,7 +737,7 @@ fn test() {
511..514 'obj': &dyn Foo<i8, usize>
534..536 '&S': &S<i8, {unknown}>
535..536 'S': S<i8, {unknown}>
"###
"]],
);
}
@ -709,8 +746,8 @@ fn test() {
// it. We used to support it, but Chalk doesn't.
#[ignore]
fn coerce_unsize_trait_object_to_trait_object() {
assert_snapshot!(
infer_with_mismatches(r#"
check_infer_with_mismatches(
r#"
#[lang = "sized"]
pub trait Sized {}
#[lang = "unsize"]
@ -736,8 +773,8 @@ fn test() {
let obj2: &dyn Baz<i8, i16> = &S;
let _: &dyn Foo<_, _> = obj2;
}
"#, true),
@r###"
"#,
expect![[r"
424..609 '{ ...bj2; }': ()
434..437 'obj': &dyn Baz<i8, i16>
459..461 '&S': &S<i8, i16>
@ -751,14 +788,14 @@ fn test() {
571..572 'S': S<i8, i16>
582..583 '_': &dyn Foo<i8, usize>
602..606 'obj2': &dyn Baz<i8, i16>
"###
"]],
);
}
#[test]
fn coerce_unsize_super_trait_cycle() {
assert_snapshot!(
infer_with_mismatches(r#"
check_infer_with_mismatches(
r#"
#[lang = "sized"]
pub trait Sized {}
#[lang = "unsize"]
@ -783,8 +820,8 @@ fn test() {
let obj: &dyn D = &S;
let obj: &dyn A = &S;
}
"#, true),
@r###"
"#,
expect![[r"
328..383 '{ ... &S; }': ()
338..341 'obj': &dyn D
352..354 '&S': &S
@ -792,7 +829,7 @@ fn test() {
364..367 'obj': &dyn A
378..380 '&S': &S
379..380 'S': S
"###
"]],
);
}
@ -801,8 +838,8 @@ fn test() {
fn coerce_unsize_generic() {
// FIXME: Implement this
// https://doc.rust-lang.org/reference/type-coercions.html#unsized-coercions
assert_snapshot!(
infer_with_mismatches(r#"
check_infer_with_mismatches(
r#"
#[lang = "unsize"]
pub trait Unsize<T> {}
#[lang = "coerce_unsized"]
@ -817,8 +854,8 @@ fn test() {
let _: &Foo<[usize]> = &Foo { t: [1, 2, 3] };
let _: &Bar<[usize]> = &Bar(Foo { t: [1, 2, 3] });
}
"#, true),
@r###"
"###
"#,
expect![[r"
"]],
);
}

View file

@ -1,6 +1,6 @@
use insta::assert_snapshot;
use expect::expect;
use super::{check_types, infer_with_mismatches};
use super::{check_infer_with_mismatches, check_types};
#[test]
fn infer_never1() {
@ -240,8 +240,8 @@ fn test(a: i32) {
#[test]
fn diverging_expression_1() {
let t = infer_with_mismatches(
r#"
check_infer_with_mismatches(
r"
//- /main.rs
fn test1() {
let x: u32 = return;
@ -261,10 +261,8 @@ fn test5() {
fn test6() {
let x: u32 = { let y: u32 = { loop {}; }; };
}
"#,
true,
);
assert_snapshot!(t, @r###"
",
expect![[r"
11..39 '{ ...urn; }': ()
21..22 'x': u32
30..36 'return': !
@ -299,12 +297,13 @@ fn test6() {
292..304 '{ loop {}; }': u32
294..301 'loop {}': !
299..301 '{}': ()
"###);
"]],
);
}
#[test]
fn diverging_expression_2() {
let t = infer_with_mismatches(
check_infer_with_mismatches(
r#"
//- /main.rs
fn test1() {
@ -312,9 +311,7 @@ fn test1() {
let x: u32 = { loop {}; "foo" };
}
"#,
true,
);
assert_snapshot!(t, @r###"
expect![[r#"
11..84 '{ ..." }; }': ()
54..55 'x': u32
63..81 '{ loop...foo" }': &str
@ -323,13 +320,14 @@ fn test1() {
74..79 '"foo"': &str
63..81: expected u32, got &str
74..79: expected u32, got &str
"###);
"#]],
);
}
#[test]
fn diverging_expression_3_break() {
let t = infer_with_mismatches(
r#"
check_infer_with_mismatches(
r"
//- /main.rs
fn test1() {
// should give type mismatch
@ -351,10 +349,8 @@ fn test3() {
// should give type mismatch as well
let x: u32 = { while true { return; }; };
}
"#,
true,
);
assert_snapshot!(t, @r###"
",
expect![[r"
11..85 '{ ...} }; }': ()
54..55 'x': u32
63..82 '{ loop...k; } }': ()
@ -408,5 +404,6 @@ fn test3() {
407..433: expected u32, got ()
546..564: expected u32, got ()
624..651: expected u32, got ()
"###);
"]],
);
}