aboutsummaryrefslogtreecommitdiff
path: root/crates/hir_ty
diff options
context:
space:
mode:
authorcynecx <[email protected]>2021-02-28 20:15:26 +0000
committercynecx <[email protected]>2021-02-28 20:18:30 +0000
commit2cdd1ff1b50b7c71e9f8aaf03a58501a4af97dce (patch)
treeb581a78b79b40bffbe72c2fd7241ded8caea97b3 /crates/hir_ty
parent23d7dbfa5e7ba2cebf8c3f79b5d31285d79c1527 (diff)
hir_ty: use default type generic for box expressions
Diffstat (limited to 'crates/hir_ty')
-rw-r--r--crates/hir_ty/src/infer/expr.rs6
-rw-r--r--crates/hir_ty/src/tests/simple.rs55
2 files changed, 61 insertions, 0 deletions
diff --git a/crates/hir_ty/src/infer/expr.rs b/crates/hir_ty/src/infer/expr.rs
index 13240f790..98bc23173 100644
--- a/crates/hir_ty/src/infer/expr.rs
+++ b/crates/hir_ty/src/infer/expr.rs
@@ -488,6 +488,12 @@ impl<'a> InferenceContext<'a> {
488 if let Some(box_) = self.resolve_boxed_box() { 488 if let Some(box_) = self.resolve_boxed_box() {
489 let mut sb = Substs::builder(generics(self.db.upcast(), box_.into()).len()); 489 let mut sb = Substs::builder(generics(self.db.upcast(), box_.into()).len());
490 sb = sb.push(inner_ty); 490 sb = sb.push(inner_ty);
491 match self.db.generic_defaults(box_.into()).as_ref() {
492 [_, alloc_ty, ..] if !alloc_ty.value.is_unknown() => {
493 sb = sb.push(alloc_ty.value.clone());
494 }
495 _ => (),
496 }
491 sb = sb.fill(repeat_with(|| self.table.new_type_var())); 497 sb = sb.fill(repeat_with(|| self.table.new_type_var()));
492 Ty::Adt(box_, sb.build()) 498 Ty::Adt(box_, sb.build())
493 } else { 499 } else {
diff --git a/crates/hir_ty/src/tests/simple.rs b/crates/hir_ty/src/tests/simple.rs
index 12ec4657b..2947857a5 100644
--- a/crates/hir_ty/src/tests/simple.rs
+++ b/crates/hir_ty/src/tests/simple.rs
@@ -2491,3 +2491,58 @@ fn inner_use_enum_rename() {
2491 "#]], 2491 "#]],
2492 ) 2492 )
2493} 2493}
2494
2495#[test]
2496fn box_into_vec() {
2497 check_infer(
2498 r#"
2499#[lang = "sized"]
2500pub trait Sized {}
2501
2502#[lang = "unsize"]
2503pub trait Unsize<T: ?Sized> {}
2504
2505#[lang = "coerce_unsized"]
2506pub trait CoerceUnsized<T> {}
2507
2508pub unsafe trait Allocator {}
2509
2510pub struct Global;
2511unsafe impl Allocator for Global {}
2512
2513#[lang = "owned_box"]
2514#[fundamental]
2515pub struct Box<T: ?Sized, A: Allocator = Global>;
2516
2517impl<T: ?Sized + Unsize<U>, U: ?Sized, A: Allocator> CoerceUnsized<Box<U, A>> for Box<T, A> {}
2518
2519pub struct Vec<T, A: Allocator = Global> {}
2520
2521#[lang = "slice"]
2522impl<T> [T] {}
2523
2524#[lang = "slice_alloc"]
2525impl<T> [T] {
2526 pub fn into_vec<A: Allocator>(self: Box<Self, A>) -> Vec<T, A> {
2527 unimplemented!()
2528 }
2529}
2530
2531fn test() {
2532 let vec = <[_]>::into_vec(box [1i32]);
2533}
2534"#,
2535 expect![[r#"
2536 569..573 'self': Box<[T], A>
2537 602..634 '{ ... }': Vec<T, A>
2538 612..628 'unimpl...ted!()': Vec<T, A>
2539 648..694 '{ ...2]); }': ()
2540 658..661 'vec': Vec<i32, Global>
2541 664..679 '<[_]>::into_vec': fn into_vec<i32, Global>(Box<[i32], Global>) -> Vec<i32, Global>
2542 664..691 '<[_]>:...1i32])': Vec<i32, Global>
2543 680..690 'box [1i32]': Box<[i32; _], Global>
2544 684..690 '[1i32]': [i32; _]
2545 685..689 '1i32': i32
2546 "#]],
2547 )
2548}