aboutsummaryrefslogtreecommitdiff
path: root/crates/hir_ty/src/tests/traits.rs
diff options
context:
space:
mode:
Diffstat (limited to 'crates/hir_ty/src/tests/traits.rs')
-rw-r--r--crates/hir_ty/src/tests/traits.rs3113
1 files changed, 3113 insertions, 0 deletions
diff --git a/crates/hir_ty/src/tests/traits.rs b/crates/hir_ty/src/tests/traits.rs
new file mode 100644
index 000000000..526e61caf
--- /dev/null
+++ b/crates/hir_ty/src/tests/traits.rs
@@ -0,0 +1,3113 @@
1use expect::expect;
2use test_utils::mark;
3
4use super::{check_infer, check_infer_with_mismatches, check_types};
5
6#[test]
7fn infer_await() {
8 check_types(
9 r#"
10//- /main.rs crate:main deps:core
11struct IntFuture;
12
13impl Future for IntFuture {
14 type Output = u64;
15}
16
17fn test() {
18 let r = IntFuture;
19 let v = r.await;
20 v;
21} //^ u64
22
23//- /core.rs crate:core
24#[prelude_import] use future::*;
25mod future {
26 #[lang = "future_trait"]
27 trait Future {
28 type Output;
29 }
30}
31"#,
32 );
33}
34
35#[test]
36fn infer_async() {
37 check_types(
38 r#"
39//- /main.rs crate:main deps:core
40async fn foo() -> u64 {
41 128
42}
43
44fn test() {
45 let r = foo();
46 let v = r.await;
47 v;
48} //^ u64
49
50//- /core.rs crate:core
51#[prelude_import] use future::*;
52mod future {
53 #[lang = "future_trait"]
54 trait Future {
55 type Output;
56 }
57}
58"#,
59 );
60}
61
62#[test]
63fn infer_desugar_async() {
64 check_types(
65 r#"
66//- /main.rs crate:main deps:core
67async fn foo() -> u64 {
68 128
69}
70
71fn test() {
72 let r = foo();
73 r;
74} //^ impl Future<Output = u64>
75
76//- /core.rs crate:core
77#[prelude_import] use future::*;
78mod future {
79 trait Future {
80 type Output;
81 }
82}
83
84"#,
85 );
86}
87
88#[test]
89fn infer_try() {
90 check_types(
91 r#"
92//- /main.rs crate:main deps:core
93fn test() {
94 let r: Result<i32, u64> = Result::Ok(1);
95 let v = r?;
96 v;
97} //^ i32
98
99//- /core.rs crate:core
100#[prelude_import] use ops::*;
101mod ops {
102 trait Try {
103 type Ok;
104 type Error;
105 }
106}
107
108#[prelude_import] use result::*;
109mod result {
110 enum Result<O, E> {
111 Ok(O),
112 Err(E)
113 }
114
115 impl<O, E> crate::ops::Try for Result<O, E> {
116 type Ok = O;
117 type Error = E;
118 }
119}
120"#,
121 );
122}
123
124#[test]
125fn infer_for_loop() {
126 check_types(
127 r#"
128//- /main.rs crate:main deps:core,alloc
129use alloc::collections::Vec;
130
131fn test() {
132 let v = Vec::new();
133 v.push("foo");
134 for x in v {
135 x;
136 } //^ &str
137}
138
139//- /core.rs crate:core
140#[prelude_import] use iter::*;
141mod iter {
142 trait IntoIterator {
143 type Item;
144 }
145}
146
147//- /alloc.rs crate:alloc deps:core
148mod collections {
149 struct Vec<T> {}
150 impl<T> Vec<T> {
151 fn new() -> Self { Vec {} }
152 fn push(&mut self, t: T) { }
153 }
154
155 impl<T> IntoIterator for Vec<T> {
156 type Item=T;
157 }
158}
159"#,
160 );
161}
162
163#[test]
164fn infer_ops_neg() {
165 check_types(
166 r#"
167//- /main.rs crate:main deps:std
168struct Bar;
169struct Foo;
170
171impl std::ops::Neg for Bar {
172 type Output = Foo;
173}
174
175fn test() {
176 let a = Bar;
177 let b = -a;
178 b;
179} //^ Foo
180
181//- /std.rs crate:std
182#[prelude_import] use ops::*;
183mod ops {
184 #[lang = "neg"]
185 pub trait Neg {
186 type Output;
187 }
188}
189"#,
190 );
191}
192
193#[test]
194fn infer_ops_not() {
195 check_types(
196 r#"
197//- /main.rs crate:main deps:std
198struct Bar;
199struct Foo;
200
201impl std::ops::Not for Bar {
202 type Output = Foo;
203}
204
205fn test() {
206 let a = Bar;
207 let b = !a;
208 b;
209} //^ Foo
210
211//- /std.rs crate:std
212#[prelude_import] use ops::*;
213mod ops {
214 #[lang = "not"]
215 pub trait Not {
216 type Output;
217 }
218}
219"#,
220 );
221}
222
223#[test]
224fn infer_from_bound_1() {
225 check_infer(
226 r#"
227 trait Trait<T> {}
228 struct S<T>(T);
229 impl<U> Trait<U> for S<U> {}
230 fn foo<T: Trait<u32>>(t: T) {}
231 fn test() {
232 let s = S(unknown);
233 foo(s);
234 }
235 "#,
236 expect![[r#"
237 85..86 't': T
238 91..93 '{}': ()
239 104..143 '{ ...(s); }': ()
240 114..115 's': S<u32>
241 118..119 'S': S<u32>(u32) -> S<u32>
242 118..128 'S(unknown)': S<u32>
243 120..127 'unknown': u32
244 134..137 'foo': fn foo<S<u32>>(S<u32>)
245 134..140 'foo(s)': ()
246 138..139 's': S<u32>
247 "#]],
248 );
249}
250
251#[test]
252fn infer_from_bound_2() {
253 check_infer(
254 r#"
255 trait Trait<T> {}
256 struct S<T>(T);
257 impl<U> Trait<U> for S<U> {}
258 fn foo<U, T: Trait<U>>(t: T) -> U {}
259 fn test() {
260 let s = S(unknown);
261 let x: u32 = foo(s);
262 }
263 "#,
264 expect![[r#"
265 86..87 't': T
266 97..99 '{}': ()
267 110..162 '{ ...(s); }': ()
268 120..121 's': S<u32>
269 124..125 'S': S<u32>(u32) -> S<u32>
270 124..134 'S(unknown)': S<u32>
271 126..133 'unknown': u32
272 144..145 'x': u32
273 153..156 'foo': fn foo<u32, S<u32>>(S<u32>) -> u32
274 153..159 'foo(s)': u32
275 157..158 's': S<u32>
276 "#]],
277 );
278}
279
280#[test]
281fn trait_default_method_self_bound_implements_trait() {
282 mark::check!(trait_self_implements_self);
283 check_infer(
284 r#"
285 trait Trait {
286 fn foo(&self) -> i64;
287 fn bar(&self) -> {
288 let x = self.foo();
289 }
290 }
291 "#,
292 expect![[r#"
293 26..30 'self': &Self
294 52..56 'self': &Self
295 61..96 '{ ... }': ()
296 75..76 'x': i64
297 79..83 'self': &Self
298 79..89 'self.foo()': i64
299 "#]],
300 );
301}
302
303#[test]
304fn trait_default_method_self_bound_implements_super_trait() {
305 check_infer(
306 r#"
307 trait SuperTrait {
308 fn foo(&self) -> i64;
309 }
310 trait Trait: SuperTrait {
311 fn bar(&self) -> {
312 let x = self.foo();
313 }
314 }
315 "#,
316 expect![[r#"
317 31..35 'self': &Self
318 85..89 'self': &Self
319 94..129 '{ ... }': ()
320 108..109 'x': i64
321 112..116 'self': &Self
322 112..122 'self.foo()': i64
323 "#]],
324 );
325}
326
327#[test]
328fn infer_project_associated_type() {
329 check_infer(
330 r#"
331 trait Iterable {
332 type Item;
333 }
334 struct S;
335 impl Iterable for S { type Item = u32; }
336 fn test<T: Iterable>() {
337 let x: <S as Iterable>::Item = 1;
338 let y: <T as Iterable>::Item = no_matter;
339 let z: T::Item = no_matter;
340 let a: <T>::Item = no_matter;
341 }
342 "#,
343 expect![[r#"
344 108..261 '{ ...ter; }': ()
345 118..119 'x': u32
346 145..146 '1': u32
347 156..157 'y': Iterable::Item<T>
348 183..192 'no_matter': Iterable::Item<T>
349 202..203 'z': Iterable::Item<T>
350 215..224 'no_matter': Iterable::Item<T>
351 234..235 'a': Iterable::Item<T>
352 249..258 'no_matter': Iterable::Item<T>
353 "#]],
354 );
355}
356
357#[test]
358fn infer_return_associated_type() {
359 check_infer(
360 r#"
361 trait Iterable {
362 type Item;
363 }
364 struct S;
365 impl Iterable for S { type Item = u32; }
366 fn foo1<T: Iterable>(t: T) -> T::Item {}
367 fn foo2<T: Iterable>(t: T) -> <T as Iterable>::Item {}
368 fn foo3<T: Iterable>(t: T) -> <T>::Item {}
369 fn test() {
370 let x = foo1(S);
371 let y = foo2(S);
372 let z = foo3(S);
373 }
374 "#,
375 expect![[r#"
376 106..107 't': T
377 123..125 '{}': ()
378 147..148 't': T
379 178..180 '{}': ()
380 202..203 't': T
381 221..223 '{}': ()
382 234..300 '{ ...(S); }': ()
383 244..245 'x': u32
384 248..252 'foo1': fn foo1<S>(S) -> <S as Iterable>::Item
385 248..255 'foo1(S)': u32
386 253..254 'S': S
387 265..266 'y': u32
388 269..273 'foo2': fn foo2<S>(S) -> <S as Iterable>::Item
389 269..276 'foo2(S)': u32
390 274..275 'S': S
391 286..287 'z': u32
392 290..294 'foo3': fn foo3<S>(S) -> <S as Iterable>::Item
393 290..297 'foo3(S)': u32
394 295..296 'S': S
395 "#]],
396 );
397}
398
399#[test]
400fn infer_associated_type_bound() {
401 check_infer(
402 r#"
403 trait Iterable {
404 type Item;
405 }
406 fn test<T: Iterable<Item=u32>>() {
407 let y: T::Item = unknown;
408 }
409 "#,
410 expect![[r#"
411 67..100 '{ ...own; }': ()
412 77..78 'y': u32
413 90..97 'unknown': u32
414 "#]],
415 );
416}
417
418#[test]
419fn infer_const_body() {
420 check_infer(
421 r#"
422 const A: u32 = 1 + 1;
423 static B: u64 = { let x = 1; x };
424 "#,
425 expect![[r#"
426 15..16 '1': u32
427 15..20 '1 + 1': u32
428 19..20 '1': u32
429 38..54 '{ let ...1; x }': u64
430 44..45 'x': u64
431 48..49 '1': u64
432 51..52 'x': u64
433 "#]],
434 );
435}
436
437#[test]
438fn tuple_struct_fields() {
439 check_infer(
440 r#"
441 struct S(i32, u64);
442 fn test() -> u64 {
443 let a = S(4, 6);
444 let b = a.0;
445 a.1
446 }
447 "#,
448 expect![[r#"
449 37..86 '{ ... a.1 }': u64
450 47..48 'a': S
451 51..52 'S': S(i32, u64) -> S
452 51..58 'S(4, 6)': S
453 53..54 '4': i32
454 56..57 '6': u64
455 68..69 'b': i32
456 72..73 'a': S
457 72..75 'a.0': i32
458 81..82 'a': S
459 81..84 'a.1': u64
460 "#]],
461 );
462}
463
464#[test]
465fn tuple_struct_with_fn() {
466 check_infer(
467 r#"
468 struct S(fn(u32) -> u64);
469 fn test() -> u64 {
470 let a = S(|i| 2*i);
471 let b = a.0(4);
472 a.0(2)
473 }
474 "#,
475 expect![[r#"
476 43..101 '{ ...0(2) }': u64
477 53..54 'a': S
478 57..58 'S': S(fn(u32) -> u64) -> S
479 57..67 'S(|i| 2*i)': S
480 59..66 '|i| 2*i': |u32| -> u64
481 60..61 'i': u32
482 63..64 '2': u32
483 63..66 '2*i': u32
484 65..66 'i': u32
485 77..78 'b': u64
486 81..82 'a': S
487 81..84 'a.0': fn(u32) -> u64
488 81..87 'a.0(4)': u64
489 85..86 '4': u32
490 93..94 'a': S
491 93..96 'a.0': fn(u32) -> u64
492 93..99 'a.0(2)': u64
493 97..98 '2': u32
494 "#]],
495 );
496}
497
498#[test]
499fn indexing_arrays() {
500 check_infer(
501 "fn main() { &mut [9][2]; }",
502 expect![[r#"
503 10..26 '{ &mut...[2]; }': ()
504 12..23 '&mut [9][2]': &mut {unknown}
505 17..20 '[9]': [i32; _]
506 17..23 '[9][2]': {unknown}
507 18..19 '9': i32
508 21..22 '2': i32
509 "#]],
510 )
511}
512
513#[test]
514fn infer_ops_index() {
515 check_types(
516 r#"
517//- /main.rs crate:main deps:std
518struct Bar;
519struct Foo;
520
521impl std::ops::Index<u32> for Bar {
522 type Output = Foo;
523}
524
525fn test() {
526 let a = Bar;
527 let b = a[1u32];
528 b;
529} //^ Foo
530
531//- /std.rs crate:std
532#[prelude_import] use ops::*;
533mod ops {
534 #[lang = "index"]
535 pub trait Index<Idx> {
536 type Output;
537 }
538}
539"#,
540 );
541}
542
543#[test]
544fn infer_ops_index_int() {
545 check_types(
546 r#"
547//- /main.rs crate:main deps:std
548struct Bar;
549struct Foo;
550
551impl std::ops::Index<u32> for Bar {
552 type Output = Foo;
553}
554
555struct Range;
556impl std::ops::Index<Range> for Bar {
557 type Output = Bar;
558}
559
560fn test() {
561 let a = Bar;
562 let b = a[1];
563 b;
564 //^ Foo
565}
566
567//- /std.rs crate:std
568#[prelude_import] use ops::*;
569mod ops {
570 #[lang = "index"]
571 pub trait Index<Idx> {
572 type Output;
573 }
574}
575"#,
576 );
577}
578
579#[test]
580fn infer_ops_index_autoderef() {
581 check_types(
582 r#"
583//- /main.rs crate:main deps:std
584fn test() {
585 let a = &[1u32, 2, 3];
586 let b = a[1u32];
587 b;
588} //^ u32
589
590//- /std.rs crate:std
591impl<T> ops::Index<u32> for [T] {
592 type Output = T;
593}
594
595#[prelude_import] use ops::*;
596mod ops {
597 #[lang = "index"]
598 pub trait Index<Idx> {
599 type Output;
600 }
601}
602"#,
603 );
604}
605
606#[test]
607fn deref_trait() {
608 check_types(
609 r#"
610#[lang = "deref"]
611trait Deref {
612 type Target;
613 fn deref(&self) -> &Self::Target;
614}
615
616struct Arc<T>;
617impl<T> Deref for Arc<T> {
618 type Target = T;
619}
620
621struct S;
622impl S {
623 fn foo(&self) -> u128 {}
624}
625
626fn test(s: Arc<S>) {
627 (*s, s.foo());
628} //^ (S, u128)
629"#,
630 );
631}
632
633#[test]
634fn deref_trait_with_inference_var() {
635 check_types(
636 r#"
637//- /main.rs
638#[lang = "deref"]
639trait Deref {
640 type Target;
641 fn deref(&self) -> &Self::Target;
642}
643
644struct Arc<T>;
645fn new_arc<T>() -> Arc<T> {}
646impl<T> Deref for Arc<T> {
647 type Target = T;
648}
649
650struct S;
651fn foo(a: Arc<S>) {}
652
653fn test() {
654 let a = new_arc();
655 let b = (*a);
656 //^ S
657 foo(a);
658}
659"#,
660 );
661}
662
663#[test]
664fn deref_trait_infinite_recursion() {
665 check_types(
666 r#"
667#[lang = "deref"]
668trait Deref {
669 type Target;
670 fn deref(&self) -> &Self::Target;
671}
672
673struct S;
674
675impl Deref for S {
676 type Target = S;
677}
678
679fn test(s: S) {
680 s.foo();
681} //^ {unknown}
682"#,
683 );
684}
685
686#[test]
687fn deref_trait_with_question_mark_size() {
688 check_types(
689 r#"
690#[lang = "deref"]
691trait Deref {
692 type Target;
693 fn deref(&self) -> &Self::Target;
694}
695
696struct Arc<T>;
697impl<T> Deref for Arc<T> {
698 type Target = T;
699}
700
701struct S;
702impl S {
703 fn foo(&self) -> u128 {}
704}
705
706fn test(s: Arc<S>) {
707 (*s, s.foo());
708} //^ (S, u128)
709"#,
710 );
711}
712
713#[test]
714fn obligation_from_function_clause() {
715 check_types(
716 r#"
717struct S;
718
719trait Trait<T> {}
720impl Trait<u32> for S {}
721
722fn foo<T: Trait<U>, U>(t: T) -> U {}
723
724fn test(s: S) {
725 (foo(s));
726} //^ u32
727"#,
728 );
729}
730
731#[test]
732fn obligation_from_method_clause() {
733 check_types(
734 r#"
735//- /main.rs
736struct S;
737
738trait Trait<T> {}
739impl Trait<isize> for S {}
740
741struct O;
742impl O {
743 fn foo<T: Trait<U>, U>(&self, t: T) -> U {}
744}
745
746fn test() {
747 O.foo(S);
748} //^ isize
749"#,
750 );
751}
752
753#[test]
754fn obligation_from_self_method_clause() {
755 check_types(
756 r#"
757struct S;
758
759trait Trait<T> {}
760impl Trait<i64> for S {}
761
762impl S {
763 fn foo<U>(&self) -> U where Self: Trait<U> {}
764}
765
766fn test() {
767 S.foo();
768} //^ i64
769"#,
770 );
771}
772
773#[test]
774fn obligation_from_impl_clause() {
775 check_types(
776 r#"
777struct S;
778
779trait Trait<T> {}
780impl Trait<&str> for S {}
781
782struct O<T>;
783impl<U, T: Trait<U>> O<T> {
784 fn foo(&self) -> U {}
785}
786
787fn test(o: O<S>) {
788 o.foo();
789} //^ &str
790"#,
791 );
792}
793
794#[test]
795fn generic_param_env_1() {
796 check_types(
797 r#"
798trait Clone {}
799trait Trait { fn foo(self) -> u128; }
800struct S;
801impl Clone for S {}
802impl<T> Trait for T where T: Clone {}
803fn test<T: Clone>(t: T) { t.foo(); }
804 //^ u128
805"#,
806 );
807}
808
809#[test]
810fn generic_param_env_1_not_met() {
811 check_types(
812 r#"
813//- /main.rs
814trait Clone {}
815trait Trait { fn foo(self) -> u128; }
816struct S;
817impl Clone for S {}
818impl<T> Trait for T where T: Clone {}
819fn test<T>(t: T) { t.foo(); }
820 //^ {unknown}
821"#,
822 );
823}
824
825#[test]
826fn generic_param_env_2() {
827 check_types(
828 r#"
829trait Trait { fn foo(self) -> u128; }
830struct S;
831impl Trait for S {}
832fn test<T: Trait>(t: T) { t.foo(); }
833 //^ u128
834"#,
835 );
836}
837
838#[test]
839fn generic_param_env_2_not_met() {
840 check_types(
841 r#"
842trait Trait { fn foo(self) -> u128; }
843struct S;
844impl Trait for S {}
845fn test<T>(t: T) { t.foo(); }
846 //^ {unknown}
847"#,
848 );
849}
850
851#[test]
852fn generic_param_env_deref() {
853 check_types(
854 r#"
855#[lang = "deref"]
856trait Deref {
857 type Target;
858}
859trait Trait {}
860impl<T> Deref for T where T: Trait {
861 type Target = i128;
862}
863fn test<T: Trait>(t: T) { (*t); }
864 //^ i128
865"#,
866 );
867}
868
869#[test]
870fn associated_type_placeholder() {
871 // inside the generic function, the associated type gets normalized to a placeholder `ApplL::Out<T>` [https://rust-lang.github.io/rustc-guide/traits/associated-types.html#placeholder-associated-types].
872 check_types(
873 r#"
874pub trait ApplyL {
875 type Out;
876}
877
878pub struct RefMutL<T>;
879
880impl<T> ApplyL for RefMutL<T> {
881 type Out = <T as ApplyL>::Out;
882}
883
884fn test<T: ApplyL>() {
885 let y: <RefMutL<T> as ApplyL>::Out = no_matter;
886 y;
887} //^ ApplyL::Out<T>
888"#,
889 );
890}
891
892#[test]
893fn associated_type_placeholder_2() {
894 check_types(
895 r#"
896pub trait ApplyL {
897 type Out;
898}
899fn foo<T: ApplyL>(t: T) -> <T as ApplyL>::Out;
900
901fn test<T: ApplyL>(t: T) {
902 let y = foo(t);
903 y;
904} //^ ApplyL::Out<T>
905"#,
906 );
907}
908
909#[test]
910fn argument_impl_trait() {
911 check_infer_with_mismatches(
912 r#"
913 trait Trait<T> {
914 fn foo(&self) -> T;
915 fn foo2(&self) -> i64;
916 }
917 fn bar(x: impl Trait<u16>) {}
918 struct S<T>(T);
919 impl<T> Trait<T> for S<T> {}
920
921 fn test(x: impl Trait<u64>, y: &impl Trait<u32>) {
922 x;
923 y;
924 let z = S(1);
925 bar(z);
926 x.foo();
927 y.foo();
928 z.foo();
929 x.foo2();
930 y.foo2();
931 z.foo2();
932 }
933 "#,
934 expect![[r#"
935 29..33 'self': &Self
936 54..58 'self': &Self
937 77..78 'x': impl Trait<u16>
938 97..99 '{}': ()
939 154..155 'x': impl Trait<u64>
940 174..175 'y': &impl Trait<u32>
941 195..323 '{ ...2(); }': ()
942 201..202 'x': impl Trait<u64>
943 208..209 'y': &impl Trait<u32>
944 219..220 'z': S<u16>
945 223..224 'S': S<u16>(u16) -> S<u16>
946 223..227 'S(1)': S<u16>
947 225..226 '1': u16
948 233..236 'bar': fn bar(S<u16>)
949 233..239 'bar(z)': ()
950 237..238 'z': S<u16>
951 245..246 'x': impl Trait<u64>
952 245..252 'x.foo()': u64
953 258..259 'y': &impl Trait<u32>
954 258..265 'y.foo()': u32
955 271..272 'z': S<u16>
956 271..278 'z.foo()': u16
957 284..285 'x': impl Trait<u64>
958 284..292 'x.foo2()': i64
959 298..299 'y': &impl Trait<u32>
960 298..306 'y.foo2()': i64
961 312..313 'z': S<u16>
962 312..320 'z.foo2()': i64
963 "#]],
964 );
965}
966
967#[test]
968fn argument_impl_trait_type_args_1() {
969 check_infer_with_mismatches(
970 r#"
971 trait Trait {}
972 trait Foo {
973 // this function has an implicit Self param, an explicit type param,
974 // and an implicit impl Trait param!
975 fn bar<T>(x: impl Trait) -> T { loop {} }
976 }
977 fn foo<T>(x: impl Trait) -> T { loop {} }
978 struct S;
979 impl Trait for S {}
980 struct F;
981 impl Foo for F {}
982
983 fn test() {
984 Foo::bar(S);
985 <F as Foo>::bar(S);
986 F::bar(S);
987 Foo::bar::<u32>(S);
988 <F as Foo>::bar::<u32>(S);
989
990 foo(S);
991 foo::<u32>(S);
992 foo::<u32, i32>(S); // we should ignore the extraneous i32
993 }
994 "#,
995 expect![[r#"
996 155..156 'x': impl Trait
997 175..186 '{ loop {} }': T
998 177..184 'loop {}': !
999 182..184 '{}': ()
1000 199..200 'x': impl Trait
1001 219..230 '{ loop {} }': T
1002 221..228 'loop {}': !
1003 226..228 '{}': ()
1004 300..509 '{ ... i32 }': ()
1005 306..314 'Foo::bar': fn bar<{unknown}, {unknown}>(S) -> {unknown}
1006 306..317 'Foo::bar(S)': {unknown}
1007 315..316 'S': S
1008 323..338 '<F as Foo>::bar': fn bar<F, {unknown}>(S) -> {unknown}
1009 323..341 '<F as ...bar(S)': {unknown}
1010 339..340 'S': S
1011 347..353 'F::bar': fn bar<F, {unknown}>(S) -> {unknown}
1012 347..356 'F::bar(S)': {unknown}
1013 354..355 'S': S
1014 362..377 'Foo::bar::<u32>': fn bar<{unknown}, u32>(S) -> u32
1015 362..380 'Foo::b...32>(S)': u32
1016 378..379 'S': S
1017 386..408 '<F as ...:<u32>': fn bar<F, u32>(S) -> u32
1018 386..411 '<F as ...32>(S)': u32
1019 409..410 'S': S
1020 418..421 'foo': fn foo<{unknown}>(S) -> {unknown}
1021 418..424 'foo(S)': {unknown}
1022 422..423 'S': S
1023 430..440 'foo::<u32>': fn foo<u32>(S) -> u32
1024 430..443 'foo::<u32>(S)': u32
1025 441..442 'S': S
1026 449..464 'foo::<u32, i32>': fn foo<u32>(S) -> u32
1027 449..467 'foo::<...32>(S)': u32
1028 465..466 'S': S
1029 "#]],
1030 );
1031}
1032
1033#[test]
1034fn argument_impl_trait_type_args_2() {
1035 check_infer_with_mismatches(
1036 r#"
1037 trait Trait {}
1038 struct S;
1039 impl Trait for S {}
1040 struct F<T>;
1041 impl<T> F<T> {
1042 fn foo<U>(self, x: impl Trait) -> (T, U) { loop {} }
1043 }
1044
1045 fn test() {
1046 F.foo(S);
1047 F::<u32>.foo(S);
1048 F::<u32>.foo::<i32>(S);
1049 F::<u32>.foo::<i32, u32>(S); // extraneous argument should be ignored
1050 }
1051 "#,
1052 expect![[r#"
1053 87..91 'self': F<T>
1054 93..94 'x': impl Trait
1055 118..129 '{ loop {} }': (T, U)
1056 120..127 'loop {}': !
1057 125..127 '{}': ()
1058 143..283 '{ ...ored }': ()
1059 149..150 'F': F<{unknown}>
1060 149..157 'F.foo(S)': ({unknown}, {unknown})
1061 155..156 'S': S
1062 163..171 'F::<u32>': F<u32>
1063 163..178 'F::<u32>.foo(S)': (u32, {unknown})
1064 176..177 'S': S
1065 184..192 'F::<u32>': F<u32>
1066 184..206 'F::<u3...32>(S)': (u32, i32)
1067 204..205 'S': S
1068 212..220 'F::<u32>': F<u32>
1069 212..239 'F::<u3...32>(S)': (u32, i32)
1070 237..238 'S': S
1071 "#]],
1072 );
1073}
1074
1075#[test]
1076fn argument_impl_trait_to_fn_pointer() {
1077 check_infer_with_mismatches(
1078 r#"
1079 trait Trait {}
1080 fn foo(x: impl Trait) { loop {} }
1081 struct S;
1082 impl Trait for S {}
1083
1084 fn test() {
1085 let f: fn(S) -> () = foo;
1086 }
1087 "#,
1088 expect![[r#"
1089 22..23 'x': impl Trait
1090 37..48 '{ loop {} }': ()
1091 39..46 'loop {}': !
1092 44..46 '{}': ()
1093 90..123 '{ ...foo; }': ()
1094 100..101 'f': fn(S)
1095 117..120 'foo': fn foo(S)
1096 "#]],
1097 );
1098}
1099
1100#[test]
1101fn impl_trait() {
1102 check_infer(
1103 r#"
1104 trait Trait<T> {
1105 fn foo(&self) -> T;
1106 fn foo2(&self) -> i64;
1107 }
1108 fn bar() -> impl Trait<u64> {}
1109
1110 fn test(x: impl Trait<u64>, y: &impl Trait<u64>) {
1111 x;
1112 y;
1113 let z = bar();
1114 x.foo();
1115 y.foo();
1116 z.foo();
1117 x.foo2();
1118 y.foo2();
1119 z.foo2();
1120 }
1121 "#,
1122 expect![[r#"
1123 29..33 'self': &Self
1124 54..58 'self': &Self
1125 98..100 '{}': ()
1126 110..111 'x': impl Trait<u64>
1127 130..131 'y': &impl Trait<u64>
1128 151..268 '{ ...2(); }': ()
1129 157..158 'x': impl Trait<u64>
1130 164..165 'y': &impl Trait<u64>
1131 175..176 'z': impl Trait<u64>
1132 179..182 'bar': fn bar() -> impl Trait<u64>
1133 179..184 'bar()': impl Trait<u64>
1134 190..191 'x': impl Trait<u64>
1135 190..197 'x.foo()': u64
1136 203..204 'y': &impl Trait<u64>
1137 203..210 'y.foo()': u64
1138 216..217 'z': impl Trait<u64>
1139 216..223 'z.foo()': u64
1140 229..230 'x': impl Trait<u64>
1141 229..237 'x.foo2()': i64
1142 243..244 'y': &impl Trait<u64>
1143 243..251 'y.foo2()': i64
1144 257..258 'z': impl Trait<u64>
1145 257..265 'z.foo2()': i64
1146 "#]],
1147 );
1148}
1149
1150#[test]
1151fn simple_return_pos_impl_trait() {
1152 mark::check!(lower_rpit);
1153 check_infer(
1154 r#"
1155 trait Trait<T> {
1156 fn foo(&self) -> T;
1157 }
1158 fn bar() -> impl Trait<u64> { loop {} }
1159
1160 fn test() {
1161 let a = bar();
1162 a.foo();
1163 }
1164 "#,
1165 expect![[r#"
1166 29..33 'self': &Self
1167 71..82 '{ loop {} }': !
1168 73..80 'loop {}': !
1169 78..80 '{}': ()
1170 94..129 '{ ...o(); }': ()
1171 104..105 'a': impl Trait<u64>
1172 108..111 'bar': fn bar() -> impl Trait<u64>
1173 108..113 'bar()': impl Trait<u64>
1174 119..120 'a': impl Trait<u64>
1175 119..126 'a.foo()': u64
1176 "#]],
1177 );
1178}
1179
1180#[test]
1181fn more_return_pos_impl_trait() {
1182 check_infer(
1183 r#"
1184 trait Iterator {
1185 type Item;
1186 fn next(&mut self) -> Self::Item;
1187 }
1188 trait Trait<T> {
1189 fn foo(&self) -> T;
1190 }
1191 fn bar() -> (impl Iterator<Item = impl Trait<u32>>, impl Trait<u64>) { loop {} }
1192 fn baz<T>(t: T) -> (impl Iterator<Item = impl Trait<T>>, impl Trait<T>) { loop {} }
1193
1194 fn test() {
1195 let (a, b) = bar();
1196 a.next().foo();
1197 b.foo();
1198 let (c, d) = baz(1u128);
1199 c.next().foo();
1200 d.foo();
1201 }
1202 "#,
1203 expect![[r#"
1204 49..53 'self': &mut Self
1205 101..105 'self': &Self
1206 184..195 '{ loop {} }': ({unknown}, {unknown})
1207 186..193 'loop {}': !
1208 191..193 '{}': ()
1209 206..207 't': T
1210 268..279 '{ loop {} }': ({unknown}, {unknown})
1211 270..277 'loop {}': !
1212 275..277 '{}': ()
1213 291..413 '{ ...o(); }': ()
1214 301..307 '(a, b)': (impl Iterator<Item = impl Trait<u32>>, impl Trait<u64>)
1215 302..303 'a': impl Iterator<Item = impl Trait<u32>>
1216 305..306 'b': impl Trait<u64>
1217 310..313 'bar': fn bar() -> (impl Iterator<Item = impl Trait<u32>>, impl Trait<u64>)
1218 310..315 'bar()': (impl Iterator<Item = impl Trait<u32>>, impl Trait<u64>)
1219 321..322 'a': impl Iterator<Item = impl Trait<u32>>
1220 321..329 'a.next()': impl Trait<u32>
1221 321..335 'a.next().foo()': u32
1222 341..342 'b': impl Trait<u64>
1223 341..348 'b.foo()': u64
1224 358..364 '(c, d)': (impl Iterator<Item = impl Trait<u128>>, impl Trait<u128>)
1225 359..360 'c': impl Iterator<Item = impl Trait<u128>>
1226 362..363 'd': impl Trait<u128>
1227 367..370 'baz': fn baz<u128>(u128) -> (impl Iterator<Item = impl Trait<u128>>, impl Trait<u128>)
1228 367..377 'baz(1u128)': (impl Iterator<Item = impl Trait<u128>>, impl Trait<u128>)
1229 371..376 '1u128': u128
1230 383..384 'c': impl Iterator<Item = impl Trait<u128>>
1231 383..391 'c.next()': impl Trait<u128>
1232 383..397 'c.next().foo()': u128
1233 403..404 'd': impl Trait<u128>
1234 403..410 'd.foo()': u128
1235 "#]],
1236 );
1237}
1238
1239#[test]
1240fn dyn_trait() {
1241 check_infer(
1242 r#"
1243 trait Trait<T> {
1244 fn foo(&self) -> T;
1245 fn foo2(&self) -> i64;
1246 }
1247 fn bar() -> dyn Trait<u64> {}
1248
1249 fn test(x: dyn Trait<u64>, y: &dyn Trait<u64>) {
1250 x;
1251 y;
1252 let z = bar();
1253 x.foo();
1254 y.foo();
1255 z.foo();
1256 x.foo2();
1257 y.foo2();
1258 z.foo2();
1259 }
1260 "#,
1261 expect![[r#"
1262 29..33 'self': &Self
1263 54..58 'self': &Self
1264 97..99 '{}': ()
1265 109..110 'x': dyn Trait<u64>
1266 128..129 'y': &dyn Trait<u64>
1267 148..265 '{ ...2(); }': ()
1268 154..155 'x': dyn Trait<u64>
1269 161..162 'y': &dyn Trait<u64>
1270 172..173 'z': dyn Trait<u64>
1271 176..179 'bar': fn bar() -> dyn Trait<u64>
1272 176..181 'bar()': dyn Trait<u64>
1273 187..188 'x': dyn Trait<u64>
1274 187..194 'x.foo()': u64
1275 200..201 'y': &dyn Trait<u64>
1276 200..207 'y.foo()': u64
1277 213..214 'z': dyn Trait<u64>
1278 213..220 'z.foo()': u64
1279 226..227 'x': dyn Trait<u64>
1280 226..234 'x.foo2()': i64
1281 240..241 'y': &dyn Trait<u64>
1282 240..248 'y.foo2()': i64
1283 254..255 'z': dyn Trait<u64>
1284 254..262 'z.foo2()': i64
1285 "#]],
1286 );
1287}
1288
1289#[test]
1290fn dyn_trait_in_impl() {
1291 check_infer(
1292 r#"
1293 trait Trait<T, U> {
1294 fn foo(&self) -> (T, U);
1295 }
1296 struct S<T, U> {}
1297 impl<T, U> S<T, U> {
1298 fn bar(&self) -> &dyn Trait<T, U> { loop {} }
1299 }
1300 trait Trait2<T, U> {
1301 fn baz(&self) -> (T, U);
1302 }
1303 impl<T, U> Trait2<T, U> for dyn Trait<T, U> { }
1304
1305 fn test(s: S<u32, i32>) {
1306 s.bar().baz();
1307 }
1308 "#,
1309 expect![[r#"
1310 32..36 'self': &Self
1311 102..106 'self': &S<T, U>
1312 128..139 '{ loop {} }': &dyn Trait<T, U>
1313 130..137 'loop {}': !
1314 135..137 '{}': ()
1315 175..179 'self': &Self
1316 251..252 's': S<u32, i32>
1317 267..289 '{ ...z(); }': ()
1318 273..274 's': S<u32, i32>
1319 273..280 's.bar()': &dyn Trait<u32, i32>
1320 273..286 's.bar().baz()': (u32, i32)
1321 "#]],
1322 );
1323}
1324
1325#[test]
1326fn dyn_trait_bare() {
1327 check_infer(
1328 r#"
1329 trait Trait {
1330 fn foo(&self) -> u64;
1331 }
1332 fn bar() -> Trait {}
1333
1334 fn test(x: Trait, y: &Trait) -> u64 {
1335 x;
1336 y;
1337 let z = bar();
1338 x.foo();
1339 y.foo();
1340 z.foo();
1341 }
1342 "#,
1343 expect![[r#"
1344 26..30 'self': &Self
1345 60..62 '{}': ()
1346 72..73 'x': dyn Trait
1347 82..83 'y': &dyn Trait
1348 100..175 '{ ...o(); }': ()
1349 106..107 'x': dyn Trait
1350 113..114 'y': &dyn Trait
1351 124..125 'z': dyn Trait
1352 128..131 'bar': fn bar() -> dyn Trait
1353 128..133 'bar()': dyn Trait
1354 139..140 'x': dyn Trait
1355 139..146 'x.foo()': u64
1356 152..153 'y': &dyn Trait
1357 152..159 'y.foo()': u64
1358 165..166 'z': dyn Trait
1359 165..172 'z.foo()': u64
1360 "#]],
1361 );
1362}
1363
1364#[test]
1365fn weird_bounds() {
1366 check_infer(
1367 r#"
1368 trait Trait {}
1369 fn test(a: impl Trait + 'lifetime, b: impl 'lifetime, c: impl (Trait), d: impl ('lifetime), e: impl ?Sized, f: impl Trait + ?Sized) {}
1370 "#,
1371 expect![[r#"
1372 23..24 'a': impl Trait + {error}
1373 50..51 'b': impl {error}
1374 69..70 'c': impl Trait
1375 86..87 'd': impl {error}
1376 107..108 'e': impl {error}
1377 123..124 'f': impl Trait + {error}
1378 147..149 '{}': ()
1379 "#]],
1380 );
1381}
1382
1383#[test]
1384#[ignore]
1385fn error_bound_chalk() {
1386 check_types(
1387 r#"
1388trait Trait {
1389 fn foo(&self) -> u32 {}
1390}
1391
1392fn test(x: (impl Trait + UnknownTrait)) {
1393 x.foo();
1394} //^ u32
1395"#,
1396 );
1397}
1398
1399#[test]
1400fn assoc_type_bindings() {
1401 check_infer(
1402 r#"
1403 trait Trait {
1404 type Type;
1405 }
1406
1407 fn get<T: Trait>(t: T) -> <T as Trait>::Type {}
1408 fn get2<U, T: Trait<Type = U>>(t: T) -> U {}
1409 fn set<T: Trait<Type = u64>>(t: T) -> T {t}
1410
1411 struct S<T>;
1412 impl<T> Trait for S<T> { type Type = T; }
1413
1414 fn test<T: Trait<Type = u32>>(x: T, y: impl Trait<Type = i64>) {
1415 get(x);
1416 get2(x);
1417 get(y);
1418 get2(y);
1419 get(set(S));
1420 get2(set(S));
1421 get2(S::<str>);
1422 }
1423 "#,
1424 expect![[r#"
1425 49..50 't': T
1426 77..79 '{}': ()
1427 111..112 't': T
1428 122..124 '{}': ()
1429 154..155 't': T
1430 165..168 '{t}': T
1431 166..167 't': T
1432 256..257 'x': T
1433 262..263 'y': impl Trait<Type = i64>
1434 289..397 '{ ...r>); }': ()
1435 295..298 'get': fn get<T>(T) -> <T as Trait>::Type
1436 295..301 'get(x)': u32
1437 299..300 'x': T
1438 307..311 'get2': fn get2<u32, T>(T) -> u32
1439 307..314 'get2(x)': u32
1440 312..313 'x': T
1441 320..323 'get': fn get<impl Trait<Type = i64>>(impl Trait<Type = i64>) -> <impl Trait<Type = i64> as Trait>::Type
1442 320..326 'get(y)': i64
1443 324..325 'y': impl Trait<Type = i64>
1444 332..336 'get2': fn get2<i64, impl Trait<Type = i64>>(impl Trait<Type = i64>) -> i64
1445 332..339 'get2(y)': i64
1446 337..338 'y': impl Trait<Type = i64>
1447 345..348 'get': fn get<S<u64>>(S<u64>) -> <S<u64> as Trait>::Type
1448 345..356 'get(set(S))': u64
1449 349..352 'set': fn set<S<u64>>(S<u64>) -> S<u64>
1450 349..355 'set(S)': S<u64>
1451 353..354 'S': S<u64>
1452 362..366 'get2': fn get2<u64, S<u64>>(S<u64>) -> u64
1453 362..374 'get2(set(S))': u64
1454 367..370 'set': fn set<S<u64>>(S<u64>) -> S<u64>
1455 367..373 'set(S)': S<u64>
1456 371..372 'S': S<u64>
1457 380..384 'get2': fn get2<str, S<str>>(S<str>) -> str
1458 380..394 'get2(S::<str>)': str
1459 385..393 'S::<str>': S<str>
1460 "#]],
1461 );
1462}
1463
1464#[test]
1465fn impl_trait_assoc_binding_projection_bug() {
1466 check_types(
1467 r#"
1468//- /main.rs crate:main deps:std
1469pub trait Language {
1470 type Kind;
1471}
1472pub enum RustLanguage {}
1473impl Language for RustLanguage {
1474 type Kind = SyntaxKind;
1475}
1476struct SyntaxNode<L> {}
1477fn foo() -> impl Iterator<Item = SyntaxNode<RustLanguage>> {}
1478
1479trait Clone {
1480 fn clone(&self) -> Self;
1481}
1482
1483fn api_walkthrough() {
1484 for node in foo() {
1485 node.clone();
1486 } //^ {unknown}
1487}
1488
1489//- /std.rs crate:std
1490#[prelude_import] use iter::*;
1491mod iter {
1492 trait IntoIterator {
1493 type Item;
1494 }
1495 trait Iterator {
1496 type Item;
1497 }
1498 impl<T: Iterator> IntoIterator for T {
1499 type Item = <T as Iterator>::Item;
1500 }
1501}
1502"#,
1503 );
1504}
1505
1506#[test]
1507fn projection_eq_within_chalk() {
1508 check_infer(
1509 r#"
1510 trait Trait1 {
1511 type Type;
1512 }
1513 trait Trait2<T> {
1514 fn foo(self) -> T;
1515 }
1516 impl<T, U> Trait2<T> for U where U: Trait1<Type = T> {}
1517
1518 fn test<T: Trait1<Type = u32>>(x: T) {
1519 x.foo();
1520 }
1521 "#,
1522 expect![[r#"
1523 61..65 'self': Self
1524 163..164 'x': T
1525 169..185 '{ ...o(); }': ()
1526 175..176 'x': T
1527 175..182 'x.foo()': u32
1528 "#]],
1529 );
1530}
1531
1532#[test]
1533fn where_clause_trait_in_scope_for_method_resolution() {
1534 check_types(
1535 r#"
1536mod foo {
1537 trait Trait {
1538 fn foo(&self) -> u32 {}
1539 }
1540}
1541
1542fn test<T: foo::Trait>(x: T) {
1543 x.foo();
1544} //^ u32
1545"#,
1546 );
1547}
1548
1549#[test]
1550fn super_trait_method_resolution() {
1551 check_infer(
1552 r#"
1553 mod foo {
1554 trait SuperTrait {
1555 fn foo(&self) -> u32 {}
1556 }
1557 }
1558 trait Trait1: foo::SuperTrait {}
1559 trait Trait2 where Self: foo::SuperTrait {}
1560
1561 fn test<T: Trait1, U: Trait2>(x: T, y: U) {
1562 x.foo();
1563 y.foo();
1564 }
1565 "#,
1566 expect![[r#"
1567 49..53 'self': &Self
1568 62..64 '{}': ()
1569 181..182 'x': T
1570 187..188 'y': U
1571 193..222 '{ ...o(); }': ()
1572 199..200 'x': T
1573 199..206 'x.foo()': u32
1574 212..213 'y': U
1575 212..219 'y.foo()': u32
1576 "#]],
1577 );
1578}
1579
1580#[test]
1581fn super_trait_impl_trait_method_resolution() {
1582 check_infer(
1583 r#"
1584 mod foo {
1585 trait SuperTrait {
1586 fn foo(&self) -> u32 {}
1587 }
1588 }
1589 trait Trait1: foo::SuperTrait {}
1590
1591 fn test(x: &impl Trait1) {
1592 x.foo();
1593 }
1594 "#,
1595 expect![[r#"
1596 49..53 'self': &Self
1597 62..64 '{}': ()
1598 115..116 'x': &impl Trait1
1599 132..148 '{ ...o(); }': ()
1600 138..139 'x': &impl Trait1
1601 138..145 'x.foo()': u32
1602 "#]],
1603 );
1604}
1605
1606#[test]
1607fn super_trait_cycle() {
1608 // This just needs to not crash
1609 check_infer(
1610 r#"
1611 trait A: B {}
1612 trait B: A {}
1613
1614 fn test<T: A>(x: T) {
1615 x.foo();
1616 }
1617 "#,
1618 expect![[r#"
1619 43..44 'x': T
1620 49..65 '{ ...o(); }': ()
1621 55..56 'x': T
1622 55..62 'x.foo()': {unknown}
1623 "#]],
1624 );
1625}
1626
1627#[test]
1628fn super_trait_assoc_type_bounds() {
1629 check_infer(
1630 r#"
1631 trait SuperTrait { type Type; }
1632 trait Trait where Self: SuperTrait {}
1633
1634 fn get2<U, T: Trait<Type = U>>(t: T) -> U {}
1635 fn set<T: Trait<Type = u64>>(t: T) -> T {t}
1636
1637 struct S<T>;
1638 impl<T> SuperTrait for S<T> { type Type = T; }
1639 impl<T> Trait for S<T> {}
1640
1641 fn test() {
1642 get2(set(S));
1643 }
1644 "#,
1645 expect![[r#"
1646 102..103 't': T
1647 113..115 '{}': ()
1648 145..146 't': T
1649 156..159 '{t}': T
1650 157..158 't': T
1651 258..279 '{ ...S)); }': ()
1652 264..268 'get2': fn get2<u64, S<u64>>(S<u64>) -> u64
1653 264..276 'get2(set(S))': u64
1654 269..272 'set': fn set<S<u64>>(S<u64>) -> S<u64>
1655 269..275 'set(S)': S<u64>
1656 273..274 'S': S<u64>
1657 "#]],
1658 );
1659}
1660
1661#[test]
1662fn fn_trait() {
1663 check_infer(
1664 r#"
1665 trait FnOnce<Args> {
1666 type Output;
1667
1668 fn call_once(self, args: Args) -> <Self as FnOnce<Args>>::Output;
1669 }
1670
1671 fn test<F: FnOnce(u32, u64) -> u128>(f: F) {
1672 f.call_once((1, 2));
1673 }
1674 "#,
1675 expect![[r#"
1676 56..60 'self': Self
1677 62..66 'args': Args
1678 149..150 'f': F
1679 155..183 '{ ...2)); }': ()
1680 161..162 'f': F
1681 161..180 'f.call...1, 2))': u128
1682 173..179 '(1, 2)': (u32, u64)
1683 174..175 '1': u32
1684 177..178 '2': u64
1685 "#]],
1686 );
1687}
1688
1689#[test]
1690fn fn_ptr_and_item() {
1691 check_infer(
1692 r#"
1693 #[lang="fn_once"]
1694 trait FnOnce<Args> {
1695 type Output;
1696
1697 fn call_once(self, args: Args) -> Self::Output;
1698 }
1699
1700 trait Foo<T> {
1701 fn foo(&self) -> T;
1702 }
1703
1704 struct Bar<T>(T);
1705
1706 impl<A1, R, F: FnOnce(A1) -> R> Foo<(A1, R)> for Bar<F> {
1707 fn foo(&self) -> (A1, R) {}
1708 }
1709
1710 enum Opt<T> { None, Some(T) }
1711 impl<T> Opt<T> {
1712 fn map<U, F: FnOnce(T) -> U>(self, f: F) -> Opt<U> {}
1713 }
1714
1715 fn test() {
1716 let bar: Bar<fn(u8) -> u32>;
1717 bar.foo();
1718
1719 let opt: Opt<u8>;
1720 let f: fn(u8) -> u32;
1721 opt.map(f);
1722 }
1723 "#,
1724 expect![[r#"
1725 74..78 'self': Self
1726 80..84 'args': Args
1727 139..143 'self': &Self
1728 243..247 'self': &Bar<F>
1729 260..262 '{}': ()
1730 346..350 'self': Opt<T>
1731 352..353 'f': F
1732 368..370 '{}': ()
1733 384..500 '{ ...(f); }': ()
1734 394..397 'bar': Bar<fn(u8) -> u32>
1735 423..426 'bar': Bar<fn(u8) -> u32>
1736 423..432 'bar.foo()': (u8, u32)
1737 443..446 'opt': Opt<u8>
1738 465..466 'f': fn(u8) -> u32
1739 487..490 'opt': Opt<u8>
1740 487..497 'opt.map(f)': Opt<u32>
1741 495..496 'f': fn(u8) -> u32
1742 "#]],
1743 );
1744}
1745
1746#[test]
1747fn fn_trait_deref_with_ty_default() {
1748 check_infer(
1749 r#"
1750 #[lang = "deref"]
1751 trait Deref {
1752 type Target;
1753
1754 fn deref(&self) -> &Self::Target;
1755 }
1756
1757 #[lang="fn_once"]
1758 trait FnOnce<Args> {
1759 type Output;
1760
1761 fn call_once(self, args: Args) -> Self::Output;
1762 }
1763
1764 struct Foo;
1765
1766 impl Foo {
1767 fn foo(&self) -> usize {}
1768 }
1769
1770 struct Lazy<T, F = fn() -> T>(F);
1771
1772 impl<T, F> Lazy<T, F> {
1773 pub fn new(f: F) -> Lazy<T, F> {}
1774 }
1775
1776 impl<T, F: FnOnce() -> T> Deref for Lazy<T, F> {
1777 type Target = T;
1778 }
1779
1780 fn test() {
1781 let lazy1: Lazy<Foo, _> = Lazy::new(|| Foo);
1782 let r1 = lazy1.foo();
1783
1784 fn make_foo_fn() -> Foo {}
1785 let make_foo_fn_ptr: fn() -> Foo = make_foo_fn;
1786 let lazy2: Lazy<Foo, _> = Lazy::new(make_foo_fn_ptr);
1787 let r2 = lazy2.foo();
1788 }
1789 "#,
1790 expect![[r#"
1791 64..68 'self': &Self
1792 165..169 'self': Self
1793 171..175 'args': Args
1794 239..243 'self': &Foo
1795 254..256 '{}': ()
1796 334..335 'f': F
1797 354..356 '{}': ()
1798 443..689 '{ ...o(); }': ()
1799 453..458 'lazy1': Lazy<Foo, || -> Foo>
1800 475..484 'Lazy::new': fn new<Foo, || -> Foo>(|| -> Foo) -> Lazy<Foo, || -> Foo>
1801 475..492 'Lazy::...| Foo)': Lazy<Foo, || -> Foo>
1802 485..491 '|| Foo': || -> Foo
1803 488..491 'Foo': Foo
1804 502..504 'r1': usize
1805 507..512 'lazy1': Lazy<Foo, || -> Foo>
1806 507..518 'lazy1.foo()': usize
1807 560..575 'make_foo_fn_ptr': fn() -> Foo
1808 591..602 'make_foo_fn': fn make_foo_fn() -> Foo
1809 612..617 'lazy2': Lazy<Foo, fn() -> Foo>
1810 634..643 'Lazy::new': fn new<Foo, fn() -> Foo>(fn() -> Foo) -> Lazy<Foo, fn() -> Foo>
1811 634..660 'Lazy::...n_ptr)': Lazy<Foo, fn() -> Foo>
1812 644..659 'make_foo_fn_ptr': fn() -> Foo
1813 670..672 'r2': usize
1814 675..680 'lazy2': Lazy<Foo, fn() -> Foo>
1815 675..686 'lazy2.foo()': usize
1816 549..551 '{}': ()
1817 "#]],
1818 );
1819}
1820
1821#[test]
1822fn closure_1() {
1823 check_infer(
1824 r#"
1825 #[lang = "fn_once"]
1826 trait FnOnce<Args> {
1827 type Output;
1828 }
1829
1830 enum Option<T> { Some(T), None }
1831 impl<T> Option<T> {
1832 fn map<U, F: FnOnce(T) -> U>(self, f: F) -> Option<U> {}
1833 }
1834
1835 fn test() {
1836 let x = Option::Some(1u32);
1837 x.map(|v| v + 1);
1838 x.map(|_v| 1u64);
1839 let y: Option<i64> = x.map(|_v| 1);
1840 }
1841 "#,
1842 expect![[r#"
1843 147..151 'self': Option<T>
1844 153..154 'f': F
1845 172..174 '{}': ()
1846 188..307 '{ ... 1); }': ()
1847 198..199 'x': Option<u32>
1848 202..214 'Option::Some': Some<u32>(u32) -> Option<u32>
1849 202..220 'Option...(1u32)': Option<u32>
1850 215..219 '1u32': u32
1851 226..227 'x': Option<u32>
1852 226..242 'x.map(...v + 1)': Option<u32>
1853 232..241 '|v| v + 1': |u32| -> u32
1854 233..234 'v': u32
1855 236..237 'v': u32
1856 236..241 'v + 1': u32
1857 240..241 '1': u32
1858 248..249 'x': Option<u32>
1859 248..264 'x.map(... 1u64)': Option<u64>
1860 254..263 '|_v| 1u64': |u32| -> u64
1861 255..257 '_v': u32
1862 259..263 '1u64': u64
1863 274..275 'y': Option<i64>
1864 291..292 'x': Option<u32>
1865 291..304 'x.map(|_v| 1)': Option<i64>
1866 297..303 '|_v| 1': |u32| -> i64
1867 298..300 '_v': u32
1868 302..303 '1': i64
1869 "#]],
1870 );
1871}
1872
1873#[test]
1874fn closure_2() {
1875 check_infer(
1876 r#"
1877 trait FnOnce<Args> {
1878 type Output;
1879 }
1880
1881 fn test<F: FnOnce(u32) -> u64>(f: F) {
1882 f(1);
1883 let g = |v| v + 1;
1884 g(1u64);
1885 let h = |v| 1u128 + v;
1886 }
1887 "#,
1888 expect![[r#"
1889 72..73 'f': F
1890 78..154 '{ ...+ v; }': ()
1891 84..85 'f': F
1892 84..88 'f(1)': {unknown}
1893 86..87 '1': i32
1894 98..99 'g': |u64| -> i32
1895 102..111 '|v| v + 1': |u64| -> i32
1896 103..104 'v': u64
1897 106..107 'v': u64
1898 106..111 'v + 1': i32
1899 110..111 '1': i32
1900 117..118 'g': |u64| -> i32
1901 117..124 'g(1u64)': i32
1902 119..123 '1u64': u64
1903 134..135 'h': |u128| -> u128
1904 138..151 '|v| 1u128 + v': |u128| -> u128
1905 139..140 'v': u128
1906 142..147 '1u128': u128
1907 142..151 '1u128 + v': u128
1908 150..151 'v': u128
1909 "#]],
1910 );
1911}
1912
1913#[test]
1914fn closure_as_argument_inference_order() {
1915 check_infer(
1916 r#"
1917 #[lang = "fn_once"]
1918 trait FnOnce<Args> {
1919 type Output;
1920 }
1921
1922 fn foo1<T, U, F: FnOnce(T) -> U>(x: T, f: F) -> U {}
1923 fn foo2<T, U, F: FnOnce(T) -> U>(f: F, x: T) -> U {}
1924
1925 struct S;
1926 impl S {
1927 fn method(self) -> u64;
1928
1929 fn foo1<T, U, F: FnOnce(T) -> U>(self, x: T, f: F) -> U {}
1930 fn foo2<T, U, F: FnOnce(T) -> U>(self, f: F, x: T) -> U {}
1931 }
1932
1933 fn test() {
1934 let x1 = foo1(S, |s| s.method());
1935 let x2 = foo2(|s| s.method(), S);
1936 let x3 = S.foo1(S, |s| s.method());
1937 let x4 = S.foo2(|s| s.method(), S);
1938 }
1939 "#,
1940 expect![[r#"
1941 94..95 'x': T
1942 100..101 'f': F
1943 111..113 '{}': ()
1944 147..148 'f': F
1945 153..154 'x': T
1946 164..166 '{}': ()
1947 201..205 'self': S
1948 253..257 'self': S
1949 259..260 'x': T
1950 265..266 'f': F
1951 276..278 '{}': ()
1952 316..320 'self': S
1953 322..323 'f': F
1954 328..329 'x': T
1955 339..341 '{}': ()
1956 355..514 '{ ... S); }': ()
1957 365..367 'x1': u64
1958 370..374 'foo1': fn foo1<S, u64, |S| -> u64>(S, |S| -> u64) -> u64
1959 370..393 'foo1(S...hod())': u64
1960 375..376 'S': S
1961 378..392 '|s| s.method()': |S| -> u64
1962 379..380 's': S
1963 382..383 's': S
1964 382..392 's.method()': u64
1965 403..405 'x2': u64
1966 408..412 'foo2': fn foo2<S, u64, |S| -> u64>(|S| -> u64, S) -> u64
1967 408..431 'foo2(|...(), S)': u64
1968 413..427 '|s| s.method()': |S| -> u64
1969 414..415 's': S
1970 417..418 's': S
1971 417..427 's.method()': u64
1972 429..430 'S': S
1973 441..443 'x3': u64
1974 446..447 'S': S
1975 446..471 'S.foo1...hod())': u64
1976 453..454 'S': S
1977 456..470 '|s| s.method()': |S| -> u64
1978 457..458 's': S
1979 460..461 's': S
1980 460..470 's.method()': u64
1981 481..483 'x4': u64
1982 486..487 'S': S
1983 486..511 'S.foo2...(), S)': u64
1984 493..507 '|s| s.method()': |S| -> u64
1985 494..495 's': S
1986 497..498 's': S
1987 497..507 's.method()': u64
1988 509..510 'S': S
1989 "#]],
1990 );
1991}
1992
1993#[test]
1994fn fn_item_fn_trait() {
1995 check_types(
1996 r#"
1997#[lang = "fn_once"]
1998trait FnOnce<Args> {
1999 type Output;
2000}
2001
2002struct S;
2003
2004fn foo() -> S {}
2005
2006fn takes_closure<U, F: FnOnce() -> U>(f: F) -> U { f() }
2007
2008fn test() {
2009 takes_closure(foo);
2010} //^^^^^^^^^^^^^^^^^^ S
2011"#,
2012 );
2013}
2014
2015#[test]
2016fn unselected_projection_in_trait_env_1() {
2017 check_types(
2018 r#"
2019//- /main.rs
2020trait Trait {
2021 type Item;
2022}
2023
2024trait Trait2 {
2025 fn foo(&self) -> u32;
2026}
2027
2028fn test<T: Trait>() where T::Item: Trait2 {
2029 let x: T::Item = no_matter;
2030 x.foo();
2031} //^ u32
2032"#,
2033 );
2034}
2035
2036#[test]
2037fn unselected_projection_in_trait_env_2() {
2038 check_types(
2039 r#"
2040trait Trait<T> {
2041 type Item;
2042}
2043
2044trait Trait2 {
2045 fn foo(&self) -> u32;
2046}
2047
2048fn test<T, U>() where T::Item: Trait2, T: Trait<U::Item>, U: Trait<()> {
2049 let x: T::Item = no_matter;
2050 x.foo();
2051} //^ u32
2052"#,
2053 );
2054}
2055
2056#[test]
2057fn unselected_projection_on_impl_self() {
2058 check_infer(
2059 r#"
2060 //- /main.rs
2061 trait Trait {
2062 type Item;
2063
2064 fn f(&self, x: Self::Item);
2065 }
2066
2067 struct S;
2068
2069 impl Trait for S {
2070 type Item = u32;
2071 fn f(&self, x: Self::Item) { let y = x; }
2072 }
2073
2074 struct S2;
2075
2076 impl Trait for S2 {
2077 type Item = i32;
2078 fn f(&self, x: <Self>::Item) { let y = x; }
2079 }
2080 "#,
2081 expect![[r#"
2082 40..44 'self': &Self
2083 46..47 'x': Trait::Item<Self>
2084 126..130 'self': &S
2085 132..133 'x': u32
2086 147..161 '{ let y = x; }': ()
2087 153..154 'y': u32
2088 157..158 'x': u32
2089 228..232 'self': &S2
2090 234..235 'x': i32
2091 251..265 '{ let y = x; }': ()
2092 257..258 'y': i32
2093 261..262 'x': i32
2094 "#]],
2095 );
2096}
2097
2098#[test]
2099fn unselected_projection_on_trait_self() {
2100 check_types(
2101 r#"
2102trait Trait {
2103 type Item;
2104
2105 fn f(&self) -> Self::Item { loop {} }
2106}
2107
2108struct S;
2109impl Trait for S {
2110 type Item = u32;
2111}
2112
2113fn test() {
2114 S.f();
2115} //^ u32
2116"#,
2117 );
2118}
2119
2120#[test]
2121fn unselected_projection_chalk_fold() {
2122 check_types(
2123 r#"
2124trait Interner {}
2125trait Fold<I: Interner, TI = I> {
2126 type Result;
2127}
2128
2129struct Ty<I: Interner> {}
2130impl<I: Interner, TI: Interner> Fold<I, TI> for Ty<I> {
2131 type Result = Ty<TI>;
2132}
2133
2134fn fold<I: Interner, T>(interner: &I, t: T) -> T::Result
2135where
2136 T: Fold<I, I>,
2137{
2138 loop {}
2139}
2140
2141fn foo<I: Interner>(interner: &I, t: Ty<I>) {
2142 fold(interner, t);
2143} //^ Ty<I>
2144"#,
2145 );
2146}
2147
2148#[test]
2149fn trait_impl_self_ty() {
2150 check_types(
2151 r#"
2152trait Trait<T> {
2153 fn foo(&self);
2154}
2155
2156struct S;
2157
2158impl Trait<Self> for S {}
2159
2160fn test() {
2161 S.foo();
2162} //^ ()
2163"#,
2164 );
2165}
2166
2167#[test]
2168fn trait_impl_self_ty_cycle() {
2169 check_types(
2170 r#"
2171trait Trait {
2172 fn foo(&self);
2173}
2174
2175struct S<T>;
2176
2177impl Trait for S<Self> {}
2178
2179fn test() {
2180 S.foo();
2181} //^ {unknown}
2182"#,
2183 );
2184}
2185
2186#[test]
2187fn unselected_projection_in_trait_env_cycle_1() {
2188 // this is a legitimate cycle
2189 check_types(
2190 r#"
2191trait Trait {
2192 type Item;
2193}
2194
2195trait Trait2<T> {}
2196
2197fn test<T: Trait>() where T: Trait2<T::Item> {
2198 let x: T::Item = no_matter;
2199} //^ {unknown}
2200"#,
2201 );
2202}
2203
2204#[test]
2205fn unselected_projection_in_trait_env_cycle_2() {
2206 // this is a legitimate cycle
2207 check_types(
2208 r#"
2209//- /main.rs
2210trait Trait<T> {
2211 type Item;
2212}
2213
2214fn test<T, U>() where T: Trait<U::Item>, U: Trait<T::Item> {
2215 let x: T::Item = no_matter;
2216} //^ {unknown}
2217"#,
2218 );
2219}
2220
2221#[test]
2222fn inline_assoc_type_bounds_1() {
2223 check_types(
2224 r#"
2225trait Iterator {
2226 type Item;
2227}
2228trait OtherTrait<T> {
2229 fn foo(&self) -> T;
2230}
2231
2232// workaround for Chalk assoc type normalization problems
2233pub struct S<T>;
2234impl<T: Iterator> Iterator for S<T> {
2235 type Item = <T as Iterator>::Item;
2236}
2237
2238fn test<I: Iterator<Item: OtherTrait<u32>>>() {
2239 let x: <S<I> as Iterator>::Item;
2240 x.foo();
2241} //^ u32
2242"#,
2243 );
2244}
2245
2246#[test]
2247fn inline_assoc_type_bounds_2() {
2248 check_types(
2249 r#"
2250trait Iterator {
2251 type Item;
2252}
2253
2254fn test<I: Iterator<Item: Iterator<Item = u32>>>() {
2255 let x: <<I as Iterator>::Item as Iterator>::Item;
2256 x;
2257} //^ u32
2258"#,
2259 );
2260}
2261
2262#[test]
2263fn proc_macro_server_types() {
2264 check_infer(
2265 r#"
2266 macro_rules! with_api {
2267 ($S:ident, $self:ident, $m:ident) => {
2268 $m! {
2269 TokenStream {
2270 fn new() -> $S::TokenStream;
2271 },
2272 Group {
2273 },
2274 }
2275 };
2276 }
2277 macro_rules! associated_item {
2278 (type TokenStream) =>
2279 (type TokenStream: 'static;);
2280 (type Group) =>
2281 (type Group: 'static;);
2282 ($($item:tt)*) => ($($item)*;)
2283 }
2284 macro_rules! declare_server_traits {
2285 ($($name:ident {
2286 $(fn $method:ident($($arg:ident: $arg_ty:ty),* $(,)?) $(-> $ret_ty:ty)?;)*
2287 }),* $(,)?) => {
2288 pub trait Types {
2289 $(associated_item!(type $name);)*
2290 }
2291
2292 $(pub trait $name: Types {
2293 $(associated_item!(fn $method($($arg: $arg_ty),*) $(-> $ret_ty)?);)*
2294 })*
2295
2296 pub trait Server: Types $(+ $name)* {}
2297 impl<S: Types $(+ $name)*> Server for S {}
2298 }
2299 }
2300
2301 with_api!(Self, self_, declare_server_traits);
2302 struct G {}
2303 struct T {}
2304 struct Rustc;
2305 impl Types for Rustc {
2306 type TokenStream = T;
2307 type Group = G;
2308 }
2309
2310 fn make<T>() -> T { loop {} }
2311 impl TokenStream for Rustc {
2312 fn new() -> Self::TokenStream {
2313 let group: Self::Group = make();
2314 make()
2315 }
2316 }
2317 "#,
2318 expect![[r#"
2319 1061..1072 '{ loop {} }': T
2320 1063..1070 'loop {}': !
2321 1068..1070 '{}': ()
2322 1136..1199 '{ ... }': T
2323 1150..1155 'group': G
2324 1171..1175 'make': fn make<G>() -> G
2325 1171..1177 'make()': G
2326 1187..1191 'make': fn make<T>() -> T
2327 1187..1193 'make()': T
2328 "#]],
2329 );
2330}
2331
2332#[test]
2333fn unify_impl_trait() {
2334 check_infer_with_mismatches(
2335 r#"
2336 trait Trait<T> {}
2337
2338 fn foo(x: impl Trait<u32>) { loop {} }
2339 fn bar<T>(x: impl Trait<T>) -> T { loop {} }
2340
2341 struct S<T>(T);
2342 impl<T> Trait<T> for S<T> {}
2343
2344 fn default<T>() -> T { loop {} }
2345
2346 fn test() -> impl Trait<i32> {
2347 let s1 = S(default());
2348 foo(s1);
2349 let x: i32 = bar(S(default()));
2350 S(default())
2351 }
2352 "#,
2353 expect![[r#"
2354 26..27 'x': impl Trait<u32>
2355 46..57 '{ loop {} }': ()
2356 48..55 'loop {}': !
2357 53..55 '{}': ()
2358 68..69 'x': impl Trait<T>
2359 91..102 '{ loop {} }': T
2360 93..100 'loop {}': !
2361 98..100 '{}': ()
2362 171..182 '{ loop {} }': T
2363 173..180 'loop {}': !
2364 178..180 '{}': ()
2365 213..309 '{ ...t()) }': S<{unknown}>
2366 223..225 's1': S<u32>
2367 228..229 'S': S<u32>(u32) -> S<u32>
2368 228..240 'S(default())': S<u32>
2369 230..237 'default': fn default<u32>() -> u32
2370 230..239 'default()': u32
2371 246..249 'foo': fn foo(S<u32>)
2372 246..253 'foo(s1)': ()
2373 250..252 's1': S<u32>
2374 263..264 'x': i32
2375 272..275 'bar': fn bar<i32>(S<i32>) -> i32
2376 272..289 'bar(S(...lt()))': i32
2377 276..277 'S': S<i32>(i32) -> S<i32>
2378 276..288 'S(default())': S<i32>
2379 278..285 'default': fn default<i32>() -> i32
2380 278..287 'default()': i32
2381 295..296 'S': S<{unknown}>({unknown}) -> S<{unknown}>
2382 295..307 'S(default())': S<{unknown}>
2383 297..304 'default': fn default<{unknown}>() -> {unknown}
2384 297..306 'default()': {unknown}
2385 "#]],
2386 );
2387}
2388
2389#[test]
2390fn assoc_types_from_bounds() {
2391 check_infer(
2392 r#"
2393 //- /main.rs
2394 #[lang = "fn_once"]
2395 trait FnOnce<Args> {
2396 type Output;
2397 }
2398
2399 trait T {
2400 type O;
2401 }
2402
2403 impl T for () {
2404 type O = ();
2405 }
2406
2407 fn f<X, F>(_v: F)
2408 where
2409 X: T,
2410 F: FnOnce(&X::O),
2411 { }
2412
2413 fn main() {
2414 f::<(), _>(|z| { z; });
2415 }
2416 "#,
2417 expect![[r#"
2418 133..135 '_v': F
2419 178..181 '{ }': ()
2420 193..224 '{ ... }); }': ()
2421 199..209 'f::<(), _>': fn f<(), |&()| -> ()>(|&()| -> ())
2422 199..221 'f::<()... z; })': ()
2423 210..220 '|z| { z; }': |&()| -> ()
2424 211..212 'z': &()
2425 214..220 '{ z; }': ()
2426 216..217 'z': &()
2427 "#]],
2428 );
2429}
2430
2431#[test]
2432fn associated_type_bound() {
2433 check_types(
2434 r#"
2435pub trait Trait {
2436 type Item: OtherTrait<u32>;
2437}
2438pub trait OtherTrait<T> {
2439 fn foo(&self) -> T;
2440}
2441
2442// this is just a workaround for chalk#234
2443pub struct S<T>;
2444impl<T: Trait> Trait for S<T> {
2445 type Item = <T as Trait>::Item;
2446}
2447
2448fn test<T: Trait>() {
2449 let y: <S<T> as Trait>::Item = no_matter;
2450 y.foo();
2451} //^ u32
2452"#,
2453 );
2454}
2455
2456#[test]
2457fn dyn_trait_through_chalk() {
2458 check_types(
2459 r#"
2460struct Box<T> {}
2461#[lang = "deref"]
2462trait Deref {
2463 type Target;
2464}
2465impl<T> Deref for Box<T> {
2466 type Target = T;
2467}
2468trait Trait {
2469 fn foo(&self);
2470}
2471
2472fn test(x: Box<dyn Trait>) {
2473 x.foo();
2474} //^ ()
2475"#,
2476 );
2477}
2478
2479#[test]
2480fn string_to_owned() {
2481 check_types(
2482 r#"
2483struct String {}
2484pub trait ToOwned {
2485 type Owned;
2486 fn to_owned(&self) -> Self::Owned;
2487}
2488impl ToOwned for str {
2489 type Owned = String;
2490}
2491fn test() {
2492 "foo".to_owned();
2493} //^ String
2494"#,
2495 );
2496}
2497
2498#[test]
2499fn iterator_chain() {
2500 check_infer(
2501 r#"
2502 //- /main.rs
2503 #[lang = "fn_once"]
2504 trait FnOnce<Args> {
2505 type Output;
2506 }
2507 #[lang = "fn_mut"]
2508 trait FnMut<Args>: FnOnce<Args> { }
2509
2510 enum Option<T> { Some(T), None }
2511 use Option::*;
2512
2513 pub trait Iterator {
2514 type Item;
2515
2516 fn filter_map<B, F>(self, f: F) -> FilterMap<Self, F>
2517 where
2518 F: FnMut(Self::Item) -> Option<B>,
2519 { loop {} }
2520
2521 fn for_each<F>(self, f: F)
2522 where
2523 F: FnMut(Self::Item),
2524 { loop {} }
2525 }
2526
2527 pub trait IntoIterator {
2528 type Item;
2529 type IntoIter: Iterator<Item = Self::Item>;
2530 fn into_iter(self) -> Self::IntoIter;
2531 }
2532
2533 pub struct FilterMap<I, F> { }
2534 impl<B, I: Iterator, F> Iterator for FilterMap<I, F>
2535 where
2536 F: FnMut(I::Item) -> Option<B>,
2537 {
2538 type Item = B;
2539 }
2540
2541 #[stable(feature = "rust1", since = "1.0.0")]
2542 impl<I: Iterator> IntoIterator for I {
2543 type Item = I::Item;
2544 type IntoIter = I;
2545
2546 fn into_iter(self) -> I {
2547 self
2548 }
2549 }
2550
2551 struct Vec<T> {}
2552 impl<T> Vec<T> {
2553 fn new() -> Self { loop {} }
2554 }
2555
2556 impl<T> IntoIterator for Vec<T> {
2557 type Item = T;
2558 type IntoIter = IntoIter<T>;
2559 }
2560
2561 pub struct IntoIter<T> { }
2562 impl<T> Iterator for IntoIter<T> {
2563 type Item = T;
2564 }
2565
2566 fn main() {
2567 Vec::<i32>::new().into_iter()
2568 .filter_map(|x| if x > 0 { Some(x as u32) } else { None })
2569 .for_each(|y| { y; });
2570 }
2571 "#,
2572 expect![[r#"
2573 226..230 'self': Self
2574 232..233 'f': F
2575 317..328 '{ loop {} }': FilterMap<Self, F>
2576 319..326 'loop {}': !
2577 324..326 '{}': ()
2578 349..353 'self': Self
2579 355..356 'f': F
2580 405..416 '{ loop {} }': ()
2581 407..414 'loop {}': !
2582 412..414 '{}': ()
2583 525..529 'self': Self
2584 854..858 'self': I
2585 865..885 '{ ... }': I
2586 875..879 'self': I
2587 944..955 '{ loop {} }': Vec<T>
2588 946..953 'loop {}': !
2589 951..953 '{}': ()
2590 1142..1269 '{ ... }); }': ()
2591 1148..1163 'Vec::<i32>::new': fn new<i32>() -> Vec<i32>
2592 1148..1165 'Vec::<...:new()': Vec<i32>
2593 1148..1177 'Vec::<...iter()': IntoIter<i32>
2594 1148..1240 'Vec::<...one })': FilterMap<IntoIter<i32>, |i32| -> Option<u32>>
2595 1148..1266 'Vec::<... y; })': ()
2596 1194..1239 '|x| if...None }': |i32| -> Option<u32>
2597 1195..1196 'x': i32
2598 1198..1239 'if x >...None }': Option<u32>
2599 1201..1202 'x': i32
2600 1201..1206 'x > 0': bool
2601 1205..1206 '0': i32
2602 1207..1225 '{ Some...u32) }': Option<u32>
2603 1209..1213 'Some': Some<u32>(u32) -> Option<u32>
2604 1209..1223 'Some(x as u32)': Option<u32>
2605 1214..1215 'x': i32
2606 1214..1222 'x as u32': u32
2607 1231..1239 '{ None }': Option<u32>
2608 1233..1237 'None': Option<u32>
2609 1255..1265 '|y| { y; }': |u32| -> ()
2610 1256..1257 'y': u32
2611 1259..1265 '{ y; }': ()
2612 1261..1262 'y': u32
2613 "#]],
2614 );
2615}
2616
2617#[test]
2618fn nested_assoc() {
2619 check_types(
2620 r#"
2621struct Bar;
2622struct Foo;
2623
2624trait A {
2625 type OutputA;
2626}
2627
2628impl A for Bar {
2629 type OutputA = Foo;
2630}
2631
2632trait B {
2633 type Output;
2634 fn foo() -> Self::Output;
2635}
2636
2637impl<T:A> B for T {
2638 type Output = T::OutputA;
2639 fn foo() -> Self::Output { loop {} }
2640}
2641
2642fn main() {
2643 Bar::foo();
2644} //^ Foo
2645"#,
2646 );
2647}
2648
2649#[test]
2650fn trait_object_no_coercion() {
2651 check_infer_with_mismatches(
2652 r#"
2653 trait Foo {}
2654
2655 fn foo(x: &dyn Foo) {}
2656
2657 fn test(x: &dyn Foo) {
2658 foo(x);
2659 }
2660 "#,
2661 expect![[r#"
2662 21..22 'x': &dyn Foo
2663 34..36 '{}': ()
2664 46..47 'x': &dyn Foo
2665 59..74 '{ foo(x); }': ()
2666 65..68 'foo': fn foo(&dyn Foo)
2667 65..71 'foo(x)': ()
2668 69..70 'x': &dyn Foo
2669 "#]],
2670 );
2671}
2672
2673#[test]
2674fn builtin_copy() {
2675 check_infer_with_mismatches(
2676 r#"
2677 #[lang = "copy"]
2678 trait Copy {}
2679
2680 struct IsCopy;
2681 impl Copy for IsCopy {}
2682 struct NotCopy;
2683
2684 trait Test { fn test(&self) -> bool; }
2685 impl<T: Copy> Test for T {}
2686
2687 fn test() {
2688 IsCopy.test();
2689 NotCopy.test();
2690 (IsCopy, IsCopy).test();
2691 (IsCopy, NotCopy).test();
2692 }
2693 "#,
2694 expect![[r#"
2695 110..114 'self': &Self
2696 166..267 '{ ...t(); }': ()
2697 172..178 'IsCopy': IsCopy
2698 172..185 'IsCopy.test()': bool
2699 191..198 'NotCopy': NotCopy
2700 191..205 'NotCopy.test()': {unknown}
2701 211..227 '(IsCop...sCopy)': (IsCopy, IsCopy)
2702 211..234 '(IsCop...test()': bool
2703 212..218 'IsCopy': IsCopy
2704 220..226 'IsCopy': IsCopy
2705 240..257 '(IsCop...tCopy)': (IsCopy, NotCopy)
2706 240..264 '(IsCop...test()': {unknown}
2707 241..247 'IsCopy': IsCopy
2708 249..256 'NotCopy': NotCopy
2709 "#]],
2710 );
2711}
2712
2713#[test]
2714fn builtin_fn_def_copy() {
2715 check_infer_with_mismatches(
2716 r#"
2717 #[lang = "copy"]
2718 trait Copy {}
2719
2720 fn foo() {}
2721 fn bar<T: Copy>(T) -> T {}
2722 struct Struct(usize);
2723 enum Enum { Variant(usize) }
2724
2725 trait Test { fn test(&self) -> bool; }
2726 impl<T: Copy> Test for T {}
2727
2728 fn test() {
2729 foo.test();
2730 bar.test();
2731 Struct.test();
2732 Enum::Variant.test();
2733 }
2734 "#,
2735 expect![[r#"
2736 41..43 '{}': ()
2737 60..61 'T': {unknown}
2738 68..70 '{}': ()
2739 68..70: expected T, got ()
2740 145..149 'self': &Self
2741 201..281 '{ ...t(); }': ()
2742 207..210 'foo': fn foo()
2743 207..217 'foo.test()': bool
2744 223..226 'bar': fn bar<{unknown}>({unknown}) -> {unknown}
2745 223..233 'bar.test()': bool
2746 239..245 'Struct': Struct(usize) -> Struct
2747 239..252 'Struct.test()': bool
2748 258..271 'Enum::Variant': Variant(usize) -> Enum
2749 258..278 'Enum::...test()': bool
2750 "#]],
2751 );
2752}
2753
2754#[test]
2755fn builtin_fn_ptr_copy() {
2756 check_infer_with_mismatches(
2757 r#"
2758 #[lang = "copy"]
2759 trait Copy {}
2760
2761 trait Test { fn test(&self) -> bool; }
2762 impl<T: Copy> Test for T {}
2763
2764 fn test(f1: fn(), f2: fn(usize) -> u8, f3: fn(u8, u8) -> &u8) {
2765 f1.test();
2766 f2.test();
2767 f3.test();
2768 }
2769 "#,
2770 expect![[r#"
2771 54..58 'self': &Self
2772 108..110 'f1': fn()
2773 118..120 'f2': fn(usize) -> u8
2774 139..141 'f3': fn(u8, u8) -> &u8
2775 162..210 '{ ...t(); }': ()
2776 168..170 'f1': fn()
2777 168..177 'f1.test()': bool
2778 183..185 'f2': fn(usize) -> u8
2779 183..192 'f2.test()': bool
2780 198..200 'f3': fn(u8, u8) -> &u8
2781 198..207 'f3.test()': bool
2782 "#]],
2783 );
2784}
2785
2786#[test]
2787fn builtin_sized() {
2788 check_infer_with_mismatches(
2789 r#"
2790 #[lang = "sized"]
2791 trait Sized {}
2792
2793 trait Test { fn test(&self) -> bool; }
2794 impl<T: Sized> Test for T {}
2795
2796 fn test() {
2797 1u8.test();
2798 (*"foo").test(); // not Sized
2799 (1u8, 1u8).test();
2800 (1u8, *"foo").test(); // not Sized
2801 }
2802 "#,
2803 expect![[r#"
2804 56..60 'self': &Self
2805 113..228 '{ ...ized }': ()
2806 119..122 '1u8': u8
2807 119..129 '1u8.test()': bool
2808 135..150 '(*"foo").test()': {unknown}
2809 136..142 '*"foo"': str
2810 137..142 '"foo"': &str
2811 169..179 '(1u8, 1u8)': (u8, u8)
2812 169..186 '(1u8, ...test()': bool
2813 170..173 '1u8': u8
2814 175..178 '1u8': u8
2815 192..205 '(1u8, *"foo")': (u8, str)
2816 192..212 '(1u8, ...test()': {unknown}
2817 193..196 '1u8': u8
2818 198..204 '*"foo"': str
2819 199..204 '"foo"': &str
2820 "#]],
2821 );
2822}
2823
2824#[test]
2825fn integer_range_iterate() {
2826 check_types(
2827 r#"
2828//- /main.rs crate:main deps:core
2829fn test() {
2830 for x in 0..100 { x; }
2831} //^ i32
2832
2833//- /core.rs crate:core
2834pub mod ops {
2835 pub struct Range<Idx> {
2836 pub start: Idx,
2837 pub end: Idx,
2838 }
2839}
2840
2841pub mod iter {
2842 pub trait Iterator {
2843 type Item;
2844 }
2845
2846 pub trait IntoIterator {
2847 type Item;
2848 type IntoIter: Iterator<Item = Self::Item>;
2849 }
2850
2851 impl<T> IntoIterator for T where T: Iterator {
2852 type Item = <T as Iterator>::Item;
2853 type IntoIter = Self;
2854 }
2855}
2856
2857trait Step {}
2858impl Step for i32 {}
2859impl Step for i64 {}
2860
2861impl<A: Step> iter::Iterator for ops::Range<A> {
2862 type Item = A;
2863}
2864"#,
2865 );
2866}
2867
2868#[test]
2869fn infer_closure_arg() {
2870 check_infer(
2871 r#"
2872 //- /lib.rs
2873
2874 enum Option<T> {
2875 None,
2876 Some(T)
2877 }
2878
2879 fn foo() {
2880 let s = Option::None;
2881 let f = |x: Option<i32>| {};
2882 (&f)(s)
2883 }
2884 "#,
2885 expect![[r#"
2886 52..126 '{ ...)(s) }': ()
2887 62..63 's': Option<i32>
2888 66..78 'Option::None': Option<i32>
2889 88..89 'f': |Option<i32>| -> ()
2890 92..111 '|x: Op...2>| {}': |Option<i32>| -> ()
2891 93..94 'x': Option<i32>
2892 109..111 '{}': ()
2893 117..124 '(&f)(s)': ()
2894 118..120 '&f': &|Option<i32>| -> ()
2895 119..120 'f': |Option<i32>| -> ()
2896 122..123 's': Option<i32>
2897 "#]],
2898 );
2899}
2900
2901#[test]
2902fn infer_fn_trait_arg() {
2903 check_infer(
2904 r#"
2905 //- /lib.rs deps:std
2906
2907 #[lang = "fn_once"]
2908 pub trait FnOnce<Args> {
2909 type Output;
2910
2911 extern "rust-call" fn call_once(&self, args: Args) -> Self::Output;
2912 }
2913
2914 #[lang = "fn"]
2915 pub trait Fn<Args>:FnOnce<Args> {
2916 extern "rust-call" fn call(&self, args: Args) -> Self::Output;
2917 }
2918
2919 enum Option<T> {
2920 None,
2921 Some(T)
2922 }
2923
2924 fn foo<F, T>(f: F) -> T
2925 where
2926 F: Fn(Option<i32>) -> T,
2927 {
2928 let s = None;
2929 f(s)
2930 }
2931 "#,
2932 expect![[r#"
2933 101..105 'self': &Self
2934 107..111 'args': Args
2935 220..224 'self': &Self
2936 226..230 'args': Args
2937 313..314 'f': F
2938 359..389 '{ ...f(s) }': T
2939 369..370 's': Option<i32>
2940 373..377 'None': Option<i32>
2941 383..384 'f': F
2942 383..387 'f(s)': T
2943 385..386 's': Option<i32>
2944 "#]],
2945 );
2946}
2947
2948#[test]
2949fn infer_box_fn_arg() {
2950 check_infer(
2951 r#"
2952 //- /lib.rs deps:std
2953
2954 #[lang = "fn_once"]
2955 pub trait FnOnce<Args> {
2956 type Output;
2957
2958 extern "rust-call" fn call_once(self, args: Args) -> Self::Output;
2959 }
2960
2961 #[lang = "deref"]
2962 pub trait Deref {
2963 type Target: ?Sized;
2964
2965 fn deref(&self) -> &Self::Target;
2966 }
2967
2968 #[lang = "owned_box"]
2969 pub struct Box<T: ?Sized> {
2970 inner: *mut T,
2971 }
2972
2973 impl<T: ?Sized> Deref for Box<T> {
2974 type Target = T;
2975
2976 fn deref(&self) -> &T {
2977 &self.inner
2978 }
2979 }
2980
2981 enum Option<T> {
2982 None,
2983 Some(T)
2984 }
2985
2986 fn foo() {
2987 let s = Option::None;
2988 let f: Box<dyn FnOnce(&Option<i32>)> = box (|ps| {});
2989 f(&s)
2990 }
2991 "#,
2992 expect![[r#"
2993 100..104 'self': Self
2994 106..110 'args': Args
2995 214..218 'self': &Self
2996 384..388 'self': &Box<T>
2997 396..423 '{ ... }': &T
2998 406..417 '&self.inner': &*mut T
2999 407..411 'self': &Box<T>
3000 407..417 'self.inner': *mut T
3001 478..575 '{ ...(&s) }': FnOnce::Output<dyn FnOnce<(&Option<i32>,)>, (&Option<i32>,)>
3002 488..489 's': Option<i32>
3003 492..504 'Option::None': Option<i32>
3004 514..515 'f': Box<dyn FnOnce<(&Option<i32>,)>>
3005 549..562 'box (|ps| {})': Box<|{unknown}| -> ()>
3006 554..561 '|ps| {}': |{unknown}| -> ()
3007 555..557 'ps': {unknown}
3008 559..561 '{}': ()
3009 568..569 'f': Box<dyn FnOnce<(&Option<i32>,)>>
3010 568..573 'f(&s)': FnOnce::Output<dyn FnOnce<(&Option<i32>,)>, (&Option<i32>,)>
3011 570..572 '&s': &Option<i32>
3012 571..572 's': Option<i32>
3013 "#]],
3014 );
3015}
3016
3017#[test]
3018fn infer_dyn_fn_output() {
3019 check_types(
3020 r#"
3021#[lang = "fn_once"]
3022pub trait FnOnce<Args> {
3023 type Output;
3024 extern "rust-call" fn call_once(self, args: Args) -> Self::Output;
3025}
3026
3027#[lang = "fn"]
3028pub trait Fn<Args>: FnOnce<Args> {
3029 extern "rust-call" fn call(&self, args: Args) -> Self::Output;
3030}
3031
3032fn foo() {
3033 let f: &dyn Fn() -> i32;
3034 f();
3035 //^^^ i32
3036}"#,
3037 );
3038}
3039
3040#[test]
3041fn infer_dyn_fn_once_output() {
3042 check_types(
3043 r#"
3044#[lang = "fn_once"]
3045pub trait FnOnce<Args> {
3046 type Output;
3047 extern "rust-call" fn call_once(self, args: Args) -> Self::Output;
3048}
3049
3050fn foo() {
3051 let f: dyn FnOnce() -> i32;
3052 f();
3053 //^^^ i32
3054}"#,
3055 );
3056}
3057
3058#[test]
3059fn variable_kinds_1() {
3060 check_types(
3061 r#"
3062trait Trait<T> { fn get(self, t: T) -> T; }
3063struct S;
3064impl Trait<u128> for S {}
3065impl Trait<f32> for S {}
3066fn test() {
3067 S.get(1);
3068 //^^^^^^^^ u128
3069 S.get(1.);
3070 //^^^^^^^^ f32
3071}
3072 "#,
3073 );
3074}
3075
3076#[test]
3077fn variable_kinds_2() {
3078 check_types(
3079 r#"
3080trait Trait { fn get(self) -> Self; }
3081impl Trait for u128 {}
3082impl Trait for f32 {}
3083fn test() {
3084 1.get();
3085 //^^^^^^^ u128
3086 (1.).get();
3087 //^^^^^^^^^^ f32
3088}
3089 "#,
3090 );
3091}
3092
3093#[test]
3094fn underscore_import() {
3095 check_types(
3096 r#"
3097mod tr {
3098 pub trait Tr {
3099 fn method(&self) -> u8 { 0 }
3100 }
3101}
3102
3103struct Tr;
3104impl crate::tr::Tr for Tr {}
3105
3106use crate::tr::Tr as _;
3107fn test() {
3108 Tr.method();
3109 //^^^^^^^^^^^ u8
3110}
3111 "#,
3112 );
3113}