diff options
Diffstat (limited to 'crates/hir_ty/src/lib.rs')
-rw-r--r-- | crates/hir_ty/src/lib.rs | 80 |
1 files changed, 48 insertions, 32 deletions
diff --git a/crates/hir_ty/src/lib.rs b/crates/hir_ty/src/lib.rs index 4c0ebcfe3..1abb0440f 100644 --- a/crates/hir_ty/src/lib.rs +++ b/crates/hir_ty/src/lib.rs | |||
@@ -99,6 +99,18 @@ impl TypeWalk for ProjectionTy { | |||
99 | } | 99 | } |
100 | } | 100 | } |
101 | 101 | ||
102 | #[derive(Clone, Copy, PartialEq, Eq, Debug, Hash)] | ||
103 | pub struct FnSig { | ||
104 | pub variadic: bool, | ||
105 | } | ||
106 | |||
107 | #[derive(Clone, PartialEq, Eq, Debug, Hash)] | ||
108 | pub struct FnPointer { | ||
109 | pub num_args: usize, | ||
110 | pub sig: FnSig, | ||
111 | pub substs: Substs, | ||
112 | } | ||
113 | |||
102 | /// A type. | 114 | /// A type. |
103 | /// | 115 | /// |
104 | /// See also the `TyKind` enum in rustc (librustc/ty/sty.rs), which represents | 116 | /// See also the `TyKind` enum in rustc (librustc/ty/sty.rs), which represents |
@@ -166,7 +178,7 @@ pub enum Ty { | |||
166 | /// | 178 | /// |
167 | /// The closure signature is stored in a `FnPtr` type in the first type | 179 | /// The closure signature is stored in a `FnPtr` type in the first type |
168 | /// parameter. | 180 | /// parameter. |
169 | Closure { def: DefWithBodyId, expr: ExprId, substs: Substs }, | 181 | Closure(DefWithBodyId, ExprId, Substs), |
170 | 182 | ||
171 | /// Represents a foreign type declared in external blocks. | 183 | /// Represents a foreign type declared in external blocks. |
172 | ForeignType(TypeAliasId), | 184 | ForeignType(TypeAliasId), |
@@ -179,8 +191,7 @@ pub enum Ty { | |||
179 | /// fn foo() -> i32 { 1 } | 191 | /// fn foo() -> i32 { 1 } |
180 | /// let bar: fn() -> i32 = foo; | 192 | /// let bar: fn() -> i32 = foo; |
181 | /// ``` | 193 | /// ``` |
182 | // FIXME make this a Ty variant like in Chalk | 194 | Function(FnPointer), |
183 | FnPtr { num_args: u16, is_varargs: bool, substs: Substs }, | ||
184 | 195 | ||
185 | /// A "projection" type corresponds to an (unnormalized) | 196 | /// A "projection" type corresponds to an (unnormalized) |
186 | /// projection like `<P0 as Trait<P1..Pn>>::Foo`. Note that the | 197 | /// projection like `<P0 as Trait<P1..Pn>>::Foo`. Note that the |
@@ -535,22 +546,29 @@ pub enum TyKind { | |||
535 | /// A function signature as seen by type inference: Several parameter types and | 546 | /// A function signature as seen by type inference: Several parameter types and |
536 | /// one return type. | 547 | /// one return type. |
537 | #[derive(Clone, PartialEq, Eq, Debug)] | 548 | #[derive(Clone, PartialEq, Eq, Debug)] |
538 | pub struct FnSig { | 549 | pub struct CallableSig { |
539 | params_and_return: Arc<[Ty]>, | 550 | params_and_return: Arc<[Ty]>, |
540 | is_varargs: bool, | 551 | is_varargs: bool, |
541 | } | 552 | } |
542 | 553 | ||
543 | /// A polymorphic function signature. | 554 | /// A polymorphic function signature. |
544 | pub type PolyFnSig = Binders<FnSig>; | 555 | pub type PolyFnSig = Binders<CallableSig>; |
545 | 556 | ||
546 | impl FnSig { | 557 | impl CallableSig { |
547 | pub fn from_params_and_return(mut params: Vec<Ty>, ret: Ty, is_varargs: bool) -> FnSig { | 558 | pub fn from_params_and_return(mut params: Vec<Ty>, ret: Ty, is_varargs: bool) -> CallableSig { |
548 | params.push(ret); | 559 | params.push(ret); |
549 | FnSig { params_and_return: params.into(), is_varargs } | 560 | CallableSig { params_and_return: params.into(), is_varargs } |
561 | } | ||
562 | |||
563 | pub fn from_fn_ptr(fn_ptr: &FnPointer) -> CallableSig { | ||
564 | CallableSig { | ||
565 | params_and_return: Arc::clone(&fn_ptr.substs.0), | ||
566 | is_varargs: fn_ptr.sig.variadic, | ||
567 | } | ||
550 | } | 568 | } |
551 | 569 | ||
552 | pub fn from_fn_ptr_substs(substs: &Substs, is_varargs: bool) -> FnSig { | 570 | pub fn from_substs(substs: &Substs) -> CallableSig { |
553 | FnSig { params_and_return: Arc::clone(&substs.0), is_varargs } | 571 | CallableSig { params_and_return: Arc::clone(&substs.0), is_varargs: false } |
554 | } | 572 | } |
555 | 573 | ||
556 | pub fn params(&self) -> &[Ty] { | 574 | pub fn params(&self) -> &[Ty] { |
@@ -562,7 +580,7 @@ impl FnSig { | |||
562 | } | 580 | } |
563 | } | 581 | } |
564 | 582 | ||
565 | impl TypeWalk for FnSig { | 583 | impl TypeWalk for CallableSig { |
566 | fn walk(&self, f: &mut impl FnMut(&Ty)) { | 584 | fn walk(&self, f: &mut impl FnMut(&Ty)) { |
567 | for t in self.params_and_return.iter() { | 585 | for t in self.params_and_return.iter() { |
568 | t.walk(f); | 586 | t.walk(f); |
@@ -585,12 +603,12 @@ impl Ty { | |||
585 | Ty::Tuple(0, Substs::empty()) | 603 | Ty::Tuple(0, Substs::empty()) |
586 | } | 604 | } |
587 | 605 | ||
588 | pub fn fn_ptr(sig: FnSig) -> Self { | 606 | pub fn fn_ptr(sig: CallableSig) -> Self { |
589 | Ty::FnPtr { | 607 | Ty::Function(FnPointer { |
590 | num_args: sig.params().len() as u16, | 608 | num_args: sig.params().len(), |
591 | is_varargs: sig.is_varargs, | 609 | sig: FnSig { variadic: sig.is_varargs }, |
592 | substs: Substs(sig.params_and_return), | 610 | substs: Substs(sig.params_and_return), |
593 | } | 611 | }) |
594 | } | 612 | } |
595 | 613 | ||
596 | pub fn builtin(builtin: BuiltinType) -> Self { | 614 | pub fn builtin(builtin: BuiltinType) -> Self { |
@@ -673,7 +691,7 @@ impl Ty { | |||
673 | (Ty::OpaqueType(ty_id, ..), Ty::OpaqueType(ty_id2, ..)) => ty_id == ty_id2, | 691 | (Ty::OpaqueType(ty_id, ..), Ty::OpaqueType(ty_id2, ..)) => ty_id == ty_id2, |
674 | (Ty::AssociatedType(ty_id, ..), Ty::AssociatedType(ty_id2, ..)) | 692 | (Ty::AssociatedType(ty_id, ..), Ty::AssociatedType(ty_id2, ..)) |
675 | | (Ty::ForeignType(ty_id, ..), Ty::ForeignType(ty_id2, ..)) => ty_id == ty_id2, | 693 | | (Ty::ForeignType(ty_id, ..), Ty::ForeignType(ty_id2, ..)) => ty_id == ty_id2, |
676 | (Ty::Closure { def, expr, .. }, Ty::Closure { def: def2, expr: expr2, .. }) => { | 694 | (Ty::Closure(def, expr, _), Ty::Closure(def2, expr2, _)) => { |
677 | expr == expr2 && def == def2 | 695 | expr == expr2 && def == def2 |
678 | } | 696 | } |
679 | (Ty::Ref(mutability, ..), Ty::Ref(mutability2, ..)) | 697 | (Ty::Ref(mutability, ..), Ty::Ref(mutability2, ..)) |
@@ -681,9 +699,9 @@ impl Ty { | |||
681 | mutability == mutability2 | 699 | mutability == mutability2 |
682 | } | 700 | } |
683 | ( | 701 | ( |
684 | Ty::FnPtr { num_args, is_varargs, .. }, | 702 | Ty::Function(FnPointer { num_args, sig, .. }), |
685 | Ty::FnPtr { num_args: num_args2, is_varargs: is_varargs2, .. }, | 703 | Ty::Function(FnPointer { num_args: num_args2, sig: sig2, .. }), |
686 | ) => num_args == num_args2 && is_varargs == is_varargs2, | 704 | ) => num_args == num_args2 && sig == sig2, |
687 | (Ty::Tuple(cardinality, _), Ty::Tuple(cardinality2, _)) => cardinality == cardinality2, | 705 | (Ty::Tuple(cardinality, _), Ty::Tuple(cardinality2, _)) => cardinality == cardinality2, |
688 | (Ty::Str, Ty::Str) | (Ty::Never, Ty::Never) => true, | 706 | (Ty::Str, Ty::Str) | (Ty::Never, Ty::Never) => true, |
689 | (Ty::Scalar(scalar), Ty::Scalar(scalar2)) => scalar == scalar2, | 707 | (Ty::Scalar(scalar), Ty::Scalar(scalar2)) => scalar == scalar2, |
@@ -722,17 +740,15 @@ impl Ty { | |||
722 | } | 740 | } |
723 | } | 741 | } |
724 | 742 | ||
725 | pub fn callable_sig(&self, db: &dyn HirDatabase) -> Option<FnSig> { | 743 | pub fn callable_sig(&self, db: &dyn HirDatabase) -> Option<CallableSig> { |
726 | match self { | 744 | match self { |
727 | Ty::FnPtr { is_varargs, substs: parameters, .. } => { | 745 | Ty::Function(fn_ptr) => Some(CallableSig::from_fn_ptr(fn_ptr)), |
728 | Some(FnSig::from_fn_ptr_substs(¶meters, *is_varargs)) | ||
729 | } | ||
730 | Ty::FnDef(def, parameters) => { | 746 | Ty::FnDef(def, parameters) => { |
731 | let sig = db.callable_item_signature(*def); | 747 | let sig = db.callable_item_signature(*def); |
732 | Some(sig.subst(¶meters)) | 748 | Some(sig.subst(¶meters)) |
733 | } | 749 | } |
734 | Ty::Closure { substs: parameters, .. } => { | 750 | Ty::Closure(.., substs) => { |
735 | let sig_param = ¶meters[0]; | 751 | let sig_param = &substs[0]; |
736 | sig_param.callable_sig(db) | 752 | sig_param.callable_sig(db) |
737 | } | 753 | } |
738 | _ => None, | 754 | _ => None, |
@@ -751,11 +767,11 @@ impl Ty { | |||
751 | | Ty::RawPtr(_, substs) | 767 | | Ty::RawPtr(_, substs) |
752 | | Ty::Ref(_, substs) | 768 | | Ty::Ref(_, substs) |
753 | | Ty::FnDef(_, substs) | 769 | | Ty::FnDef(_, substs) |
754 | | Ty::FnPtr { substs, .. } | 770 | | Ty::Function(FnPointer { substs, .. }) |
755 | | Ty::Tuple(_, substs) | 771 | | Ty::Tuple(_, substs) |
756 | | Ty::OpaqueType(_, substs) | 772 | | Ty::OpaqueType(_, substs) |
757 | | Ty::AssociatedType(_, substs) | 773 | | Ty::AssociatedType(_, substs) |
758 | | Ty::Closure { substs, .. } => { | 774 | | Ty::Closure(.., substs) => { |
759 | assert_eq!(substs.len(), new_substs.len()); | 775 | assert_eq!(substs.len(), new_substs.len()); |
760 | *substs = new_substs; | 776 | *substs = new_substs; |
761 | } | 777 | } |
@@ -774,11 +790,11 @@ impl Ty { | |||
774 | | Ty::RawPtr(_, substs) | 790 | | Ty::RawPtr(_, substs) |
775 | | Ty::Ref(_, substs) | 791 | | Ty::Ref(_, substs) |
776 | | Ty::FnDef(_, substs) | 792 | | Ty::FnDef(_, substs) |
777 | | Ty::FnPtr { substs, .. } | 793 | | Ty::Function(FnPointer { substs, .. }) |
778 | | Ty::Tuple(_, substs) | 794 | | Ty::Tuple(_, substs) |
779 | | Ty::OpaqueType(_, substs) | 795 | | Ty::OpaqueType(_, substs) |
780 | | Ty::AssociatedType(_, substs) | 796 | | Ty::AssociatedType(_, substs) |
781 | | Ty::Closure { substs, .. } => Some(substs), | 797 | | Ty::Closure(.., substs) => Some(substs), |
782 | _ => None, | 798 | _ => None, |
783 | } | 799 | } |
784 | } | 800 | } |
@@ -791,11 +807,11 @@ impl Ty { | |||
791 | | Ty::RawPtr(_, substs) | 807 | | Ty::RawPtr(_, substs) |
792 | | Ty::Ref(_, substs) | 808 | | Ty::Ref(_, substs) |
793 | | Ty::FnDef(_, substs) | 809 | | Ty::FnDef(_, substs) |
794 | | Ty::FnPtr { substs, .. } | 810 | | Ty::Function(FnPointer { substs, .. }) |
795 | | Ty::Tuple(_, substs) | 811 | | Ty::Tuple(_, substs) |
796 | | Ty::OpaqueType(_, substs) | 812 | | Ty::OpaqueType(_, substs) |
797 | | Ty::AssociatedType(_, substs) | 813 | | Ty::AssociatedType(_, substs) |
798 | | Ty::Closure { substs, .. } => Some(substs), | 814 | | Ty::Closure(.., substs) => Some(substs), |
799 | _ => None, | 815 | _ => None, |
800 | } | 816 | } |
801 | } | 817 | } |