aboutsummaryrefslogtreecommitdiff
path: root/crates/ra_hir_ty/src/tests/coercion.rs
diff options
context:
space:
mode:
Diffstat (limited to 'crates/ra_hir_ty/src/tests/coercion.rs')
-rw-r--r--crates/ra_hir_ty/src/tests/coercion.rs138
1 files changed, 138 insertions, 0 deletions
diff --git a/crates/ra_hir_ty/src/tests/coercion.rs b/crates/ra_hir_ty/src/tests/coercion.rs
index 42330b269..60ad6e9be 100644
--- a/crates/ra_hir_ty/src/tests/coercion.rs
+++ b/crates/ra_hir_ty/src/tests/coercion.rs
@@ -548,3 +548,141 @@ impl<TT> S<TT> {
548 "### 548 "###
549 ); 549 );
550} 550}
551
552#[test]
553fn coerce_unsize_array() {
554 assert_snapshot!(
555 infer_with_mismatches(r#"
556#[lang = "unsize"]
557pub trait Unsize<T> {}
558#[lang = "coerce_unsized"]
559pub trait CoerceUnsized<T> {}
560
561impl<T: Unsize<U>, U> CoerceUnsized<&U> for &T {}
562
563fn test() {
564 let f: &[usize] = &[1, 2, 3];
565}
566"#, true),
567 @r###"
568 [162; 199) '{ ... 3]; }': ()
569 [172; 173) 'f': &[usize]
570 [186; 196) '&[1, 2, 3]': &[usize; _]
571 [187; 196) '[1, 2, 3]': [usize; _]
572 [188; 189) '1': usize
573 [191; 192) '2': usize
574 [194; 195) '3': usize
575 "###
576 );
577}
578
579#[test]
580fn coerce_unsize_trait_object() {
581 assert_snapshot!(
582 infer_with_mismatches(r#"
583#[lang = "unsize"]
584pub trait Unsize<T> {}
585#[lang = "coerce_unsized"]
586pub trait CoerceUnsized<T> {}
587
588impl<T: Unsize<U>, U> CoerceUnsized<&U> for &T {}
589
590trait Foo<T, U> {}
591trait Bar<U, T, X>: Foo<T, U> {}
592trait Baz<T, X>: Bar<usize, T, X> {}
593
594struct S<T, X>;
595impl<T, X> Foo<T, usize> for S<T, X> {}
596impl<T, X> Bar<usize, T, X> for S<T, X> {}
597impl<T, X> Baz<T, X> for S<T, X> {}
598
599fn test() {
600 let obj: &dyn Baz<i8, i16> = &S;
601 let obj: &dyn Bar<_, _, _> = obj;
602 let obj: &dyn Foo<_, _> = obj;
603 let obj2: &dyn Baz<i8, i16> = &S;
604 let _: &dyn Foo<_, _> = obj2;
605}
606"#, true),
607 @r###"
608 [388; 573) '{ ...bj2; }': ()
609 [398; 401) 'obj': &dyn Baz<i8, i16>
610 [423; 425) '&S': &S<i8, i16>
611 [424; 425) 'S': S<i8, i16>
612 [435; 438) 'obj': &dyn Bar<usize, i8, i16>
613 [460; 463) 'obj': &dyn Baz<i8, i16>
614 [473; 476) 'obj': &dyn Foo<i8, usize>
615 [495; 498) 'obj': &dyn Bar<usize, i8, i16>
616 [508; 512) 'obj2': &dyn Baz<i8, i16>
617 [534; 536) '&S': &S<i8, i16>
618 [535; 536) 'S': S<i8, i16>
619 [546; 547) '_': &dyn Foo<i8, usize>
620 [566; 570) 'obj2': &dyn Baz<i8, i16>
621 "###
622 );
623}
624
625#[test]
626fn coerce_unsize_super_trait_cycle() {
627 assert_snapshot!(
628 infer_with_mismatches(r#"
629#[lang = "unsize"]
630pub trait Unsize<T> {}
631#[lang = "coerce_unsized"]
632pub trait CoerceUnsized<T> {}
633
634impl<T: Unsize<U>, U> CoerceUnsized<&U> for &T {}
635
636trait A {}
637trait B: C + A {}
638trait C: B {}
639trait D: C
640
641struct S;
642impl A for S {}
643impl B for S {}
644impl C for S {}
645impl D for S {}
646
647fn test() {
648 let obj: &dyn D = &S;
649 let obj: &dyn A = obj;
650}
651"#, true),
652 @r###"
653 [292; 348) '{ ...obj; }': ()
654 [302; 305) 'obj': &dyn D
655 [316; 318) '&S': &S
656 [317; 318) 'S': S
657 [328; 331) 'obj': &dyn A
658 [342; 345) 'obj': &dyn D
659 "###
660 );
661}
662
663#[ignore]
664#[test]
665fn coerce_unsize_generic() {
666 // FIXME: Implement this
667 // https://doc.rust-lang.org/reference/type-coercions.html#unsized-coercions
668 assert_snapshot!(
669 infer_with_mismatches(r#"
670#[lang = "unsize"]
671pub trait Unsize<T> {}
672#[lang = "coerce_unsized"]
673pub trait CoerceUnsized<T> {}
674
675impl<T: Unsize<U>, U> CoerceUnsized<&U> for &T {}
676
677struct Foo<T> { t: T };
678struct Bar<T>(Foo<T>);
679
680fn test() {
681 let _: &Foo<[usize]> = &Foo { t: [1, 2, 3] };
682 let _: &Bar<[usize]> = &Bar(Foo { t: [1, 2, 3] });
683}
684"#, true),
685 @r###"
686 "###
687 );
688}