aboutsummaryrefslogtreecommitdiff
path: root/crates/hir/src/lib.rs
diff options
context:
space:
mode:
Diffstat (limited to 'crates/hir/src/lib.rs')
-rw-r--r--crates/hir/src/lib.rs256
1 files changed, 173 insertions, 83 deletions
diff --git a/crates/hir/src/lib.rs b/crates/hir/src/lib.rs
index 8d082994a..f0bc2c7b9 100644
--- a/crates/hir/src/lib.rs
+++ b/crates/hir/src/lib.rs
@@ -29,6 +29,8 @@ mod has_source;
29pub mod diagnostics; 29pub mod diagnostics;
30pub mod db; 30pub mod db;
31 31
32mod display;
33
32use std::{iter, sync::Arc}; 34use std::{iter, sync::Arc};
33 35
34use arrayvec::ArrayVec; 36use arrayvec::ArrayVec;
@@ -50,12 +52,13 @@ use hir_def::{
50use hir_expand::{diagnostics::DiagnosticSink, name::name, MacroDefKind}; 52use hir_expand::{diagnostics::DiagnosticSink, name::name, MacroDefKind};
51use hir_ty::{ 53use hir_ty::{
52 autoderef, 54 autoderef,
53 display::{write_bounds_like_dyn_trait_with_prefix, HirDisplayError, HirFormatter}, 55 method_resolution::{self, TyFingerprint},
54 method_resolution, 56 primitive::UintTy,
57 to_assoc_type_id,
55 traits::{FnTrait, Solution, SolutionVariables}, 58 traits::{FnTrait, Solution, SolutionVariables},
56 AliasTy, BoundVar, CallableDefId, CallableSig, Canonical, DebruijnIndex, GenericPredicate, 59 AliasTy, BoundVar, CallableDefId, CallableSig, Canonical, DebruijnIndex, GenericPredicate,
57 InEnvironment, Obligation, ProjectionPredicate, ProjectionTy, Scalar, Substs, TraitEnvironment, 60 InEnvironment, Interner, Obligation, ProjectionPredicate, ProjectionTy, Scalar, Substs, Ty,
58 Ty, TyDefId, TyVariableKind, 61 TyDefId, TyKind, TyVariableKind,
59}; 62};
60use rustc_hash::FxHashSet; 63use rustc_hash::FxHashSet;
61use stdx::{format_to, impl_from}; 64use stdx::{format_to, impl_from};
@@ -266,8 +269,7 @@ impl ModuleDef {
266 } 269 }
267 270
268 pub fn canonical_path(&self, db: &dyn HirDatabase) -> Option<String> { 271 pub fn canonical_path(&self, db: &dyn HirDatabase) -> Option<String> {
269 let mut segments = Vec::new(); 272 let mut segments = vec![self.name(db)?.to_string()];
270 segments.push(self.name(db)?.to_string());
271 for m in self.module(db)?.path_to_root(db) { 273 for m in self.module(db)?.path_to_root(db) {
272 segments.extend(m.name(db).map(|it| it.to_string())) 274 segments.extend(m.name(db).map(|it| it.to_string()))
273 } 275 }
@@ -571,6 +573,12 @@ impl Struct {
571 } 573 }
572} 574}
573 575
576impl HasVisibility for Struct {
577 fn visibility(&self, db: &dyn HirDatabase) -> Visibility {
578 db.struct_data(self.id).visibility.resolve(db.upcast(), &self.id.resolver(db.upcast()))
579 }
580}
581
574#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)] 582#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
575pub struct Union { 583pub struct Union {
576 pub(crate) id: UnionId, 584 pub(crate) id: UnionId,
@@ -603,6 +611,12 @@ impl Union {
603 } 611 }
604} 612}
605 613
614impl HasVisibility for Union {
615 fn visibility(&self, db: &dyn HirDatabase) -> Visibility {
616 db.union_data(self.id).visibility.resolve(db.upcast(), &self.id.resolver(db.upcast()))
617 }
618}
619
606#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)] 620#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
607pub struct Enum { 621pub struct Enum {
608 pub(crate) id: EnumId, 622 pub(crate) id: EnumId,
@@ -630,6 +644,12 @@ impl Enum {
630 } 644 }
631} 645}
632 646
647impl HasVisibility for Enum {
648 fn visibility(&self, db: &dyn HirDatabase) -> Visibility {
649 db.enum_data(self.id).visibility.resolve(db.upcast(), &self.id.resolver(db.upcast()))
650 }
651}
652
633#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)] 653#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
634pub struct Variant { 654pub struct Variant {
635 pub(crate) parent: Enum, 655 pub(crate) parent: Enum,
@@ -677,7 +697,7 @@ impl_from!(Struct, Union, Enum for Adt);
677impl Adt { 697impl Adt {
678 pub fn has_non_default_type_params(self, db: &dyn HirDatabase) -> bool { 698 pub fn has_non_default_type_params(self, db: &dyn HirDatabase) -> bool {
679 let subst = db.generic_defaults(self.into()); 699 let subst = db.generic_defaults(self.into());
680 subst.iter().any(|ty| &ty.value == &Ty::Unknown) 700 subst.iter().any(|ty| ty.value.is_unknown())
681 } 701 }
682 702
683 /// Turns this ADT into a type. Any type parameters of the ADT will be 703 /// Turns this ADT into a type. Any type parameters of the ADT will be
@@ -696,8 +716,8 @@ impl Adt {
696 } 716 }
697 } 717 }
698 718
699 pub fn krate(self, db: &dyn HirDatabase) -> Option<Crate> { 719 pub fn krate(self, db: &dyn HirDatabase) -> Crate {
700 Some(self.module(db).krate()) 720 self.module(db).krate()
701 } 721 }
702 722
703 pub fn name(self, db: &dyn HirDatabase) -> Name { 723 pub fn name(self, db: &dyn HirDatabase) -> Name {
@@ -802,7 +822,7 @@ impl Function {
802 let krate = self.id.lookup(db.upcast()).container.module(db.upcast()).krate(); 822 let krate = self.id.lookup(db.upcast()).container.module(db.upcast()).krate();
803 let ret_type = &db.function_data(self.id).ret_type; 823 let ret_type = &db.function_data(self.id).ret_type;
804 let ctx = hir_ty::TyLoweringContext::new(db, &resolver); 824 let ctx = hir_ty::TyLoweringContext::new(db, &resolver);
805 let ty = Ty::from_hir_ext(&ctx, ret_type).0; 825 let ty = ctx.lower_ty(ret_type);
806 Type::new_with_resolver_inner(db, krate, &resolver, ty) 826 Type::new_with_resolver_inner(db, krate, &resolver, ty)
807 } 827 }
808 828
@@ -817,19 +837,20 @@ impl Function {
817 let resolver = self.id.resolver(db.upcast()); 837 let resolver = self.id.resolver(db.upcast());
818 let krate = self.id.lookup(db.upcast()).container.module(db.upcast()).krate(); 838 let krate = self.id.lookup(db.upcast()).container.module(db.upcast()).krate();
819 let ctx = hir_ty::TyLoweringContext::new(db, &resolver); 839 let ctx = hir_ty::TyLoweringContext::new(db, &resolver);
820 let environment = TraitEnvironment::lower(db, &resolver); 840 let environment = db.trait_environment(self.id.into());
821 db.function_data(self.id) 841 db.function_data(self.id)
822 .params 842 .params
823 .iter() 843 .iter()
824 .map(|type_ref| { 844 .enumerate()
845 .map(|(idx, type_ref)| {
825 let ty = Type { 846 let ty = Type {
826 krate, 847 krate,
827 ty: InEnvironment { 848 ty: InEnvironment {
828 value: Ty::from_hir_ext(&ctx, type_ref).0, 849 value: ctx.lower_ty(type_ref),
829 environment: environment.clone(), 850 environment: environment.clone(),
830 }, 851 },
831 }; 852 };
832 Param { ty } 853 Param { func: self, ty, idx }
833 }) 854 })
834 .collect() 855 .collect()
835 } 856 }
@@ -843,7 +864,7 @@ impl Function {
843 } 864 }
844 865
845 pub fn is_unsafe(self, db: &dyn HirDatabase) -> bool { 866 pub fn is_unsafe(self, db: &dyn HirDatabase) -> bool {
846 db.function_data(self.id).is_unsafe 867 db.function_data(self.id).qualifier.is_unsafe
847 } 868 }
848 869
849 pub fn diagnostics(self, db: &dyn HirDatabase, sink: &mut DiagnosticSink) { 870 pub fn diagnostics(self, db: &dyn HirDatabase, sink: &mut DiagnosticSink) {
@@ -892,6 +913,9 @@ impl From<hir_ty::Mutability> for Access {
892 913
893#[derive(Debug)] 914#[derive(Debug)]
894pub struct Param { 915pub struct Param {
916 func: Function,
917 /// The index in parameter list, including self parameter.
918 idx: usize,
895 ty: Type, 919 ty: Type,
896} 920}
897 921
@@ -899,6 +923,15 @@ impl Param {
899 pub fn ty(&self) -> &Type { 923 pub fn ty(&self) -> &Type {
900 &self.ty 924 &self.ty
901 } 925 }
926
927 pub fn pattern_source(&self, db: &dyn HirDatabase) -> Option<ast::Pat> {
928 let params = self.func.source(db)?.value.param_list()?;
929 if params.self_param().is_some() {
930 params.params().nth(self.idx.checked_sub(1)?)?.pat()
931 } else {
932 params.params().nth(self.idx)?.pat()
933 }
934 }
902} 935}
903 936
904#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)] 937#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
@@ -956,6 +989,10 @@ impl Const {
956 pub fn name(self, db: &dyn HirDatabase) -> Option<Name> { 989 pub fn name(self, db: &dyn HirDatabase) -> Option<Name> {
957 db.const_data(self.id).name.clone() 990 db.const_data(self.id).name.clone()
958 } 991 }
992
993 pub fn type_ref(self, db: &dyn HirDatabase) -> TypeRef {
994 db.const_data(self.id).type_ref.clone()
995 }
959} 996}
960 997
961impl HasVisibility for Const { 998impl HasVisibility for Const {
@@ -989,6 +1026,12 @@ impl Static {
989 } 1026 }
990} 1027}
991 1028
1029impl HasVisibility for Static {
1030 fn visibility(&self, db: &dyn HirDatabase) -> Visibility {
1031 db.static_data(self.id).visibility.resolve(db.upcast(), &self.id.resolver(db.upcast()))
1032 }
1033}
1034
992#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)] 1035#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
993pub struct Trait { 1036pub struct Trait {
994 pub(crate) id: TraitId, 1037 pub(crate) id: TraitId,
@@ -1008,7 +1051,13 @@ impl Trait {
1008 } 1051 }
1009 1052
1010 pub fn is_auto(self, db: &dyn HirDatabase) -> bool { 1053 pub fn is_auto(self, db: &dyn HirDatabase) -> bool {
1011 db.trait_data(self.id).auto 1054 db.trait_data(self.id).is_auto
1055 }
1056}
1057
1058impl HasVisibility for Trait {
1059 fn visibility(&self, db: &dyn HirDatabase) -> Visibility {
1060 db.trait_data(self.id).visibility.resolve(db.upcast(), &self.id.resolver(db.upcast()))
1012 } 1061 }
1013} 1062}
1014 1063
@@ -1020,15 +1069,15 @@ pub struct TypeAlias {
1020impl TypeAlias { 1069impl TypeAlias {
1021 pub fn has_non_default_type_params(self, db: &dyn HirDatabase) -> bool { 1070 pub fn has_non_default_type_params(self, db: &dyn HirDatabase) -> bool {
1022 let subst = db.generic_defaults(self.id.into()); 1071 let subst = db.generic_defaults(self.id.into());
1023 subst.iter().any(|ty| &ty.value == &Ty::Unknown) 1072 subst.iter().any(|ty| ty.value.is_unknown())
1024 } 1073 }
1025 1074
1026 pub fn module(self, db: &dyn HirDatabase) -> Module { 1075 pub fn module(self, db: &dyn HirDatabase) -> Module {
1027 Module { id: self.id.lookup(db.upcast()).module(db.upcast()) } 1076 Module { id: self.id.lookup(db.upcast()).module(db.upcast()) }
1028 } 1077 }
1029 1078
1030 pub fn krate(self, db: &dyn HirDatabase) -> Option<Crate> { 1079 pub fn krate(self, db: &dyn HirDatabase) -> Crate {
1031 Some(self.module(db).krate()) 1080 self.module(db).krate()
1032 } 1081 }
1033 1082
1034 pub fn type_ref(self, db: &dyn HirDatabase) -> Option<TypeRef> { 1083 pub fn type_ref(self, db: &dyn HirDatabase) -> Option<TypeRef> {
@@ -1392,7 +1441,7 @@ impl TypeParam {
1392 pub fn ty(self, db: &dyn HirDatabase) -> Type { 1441 pub fn ty(self, db: &dyn HirDatabase) -> Type {
1393 let resolver = self.id.parent.resolver(db.upcast()); 1442 let resolver = self.id.parent.resolver(db.upcast());
1394 let krate = self.id.parent.module(db.upcast()).krate(); 1443 let krate = self.id.parent.module(db.upcast()).krate();
1395 let ty = Ty::Placeholder(self.id); 1444 let ty = TyKind::Placeholder(hir_ty::to_placeholder_idx(db, self.id)).intern(&Interner);
1396 Type::new_with_resolver_inner(db, krate, &resolver, ty) 1445 Type::new_with_resolver_inner(db, krate, &resolver, ty)
1397 } 1446 }
1398 1447
@@ -1420,19 +1469,6 @@ impl TypeParam {
1420 } 1469 }
1421} 1470}
1422 1471
1423impl HirDisplay for TypeParam {
1424 fn hir_fmt(&self, f: &mut HirFormatter) -> Result<(), HirDisplayError> {
1425 write!(f, "{}", self.name(f.db))?;
1426 let bounds = f.db.generic_predicates_for_param(self.id);
1427 let substs = Substs::type_params(f.db, self.id.parent);
1428 let predicates = bounds.iter().cloned().map(|b| b.subst(&substs)).collect::<Vec<_>>();
1429 if !(predicates.is_empty() || f.omit_verbose_types()) {
1430 write_bounds_like_dyn_trait_with_prefix(":", &predicates, f)?;
1431 }
1432 Ok(())
1433 }
1434}
1435
1436#[derive(Clone, Copy, Debug, PartialEq, Eq, Hash)] 1472#[derive(Clone, Copy, Debug, PartialEq, Eq, Hash)]
1437pub struct LifetimeParam { 1473pub struct LifetimeParam {
1438 pub(crate) id: LifetimeParamId, 1474 pub(crate) id: LifetimeParamId,
@@ -1491,9 +1527,44 @@ impl Impl {
1491 1527
1492 inherent.all_impls().chain(trait_.all_impls()).map(Self::from).collect() 1528 inherent.all_impls().chain(trait_.all_impls()).map(Self::from).collect()
1493 } 1529 }
1494 pub fn for_trait(db: &dyn HirDatabase, krate: Crate, trait_: Trait) -> Vec<Impl> { 1530
1495 let impls = db.trait_impls_in_crate(krate.id); 1531 pub fn all_for_type(db: &dyn HirDatabase, Type { krate, ty }: Type) -> Vec<Impl> {
1496 impls.for_trait(trait_.id).map(Self::from).collect() 1532 let def_crates = match ty.value.def_crates(db, krate) {
1533 Some(def_crates) => def_crates,
1534 None => return Vec::new(),
1535 };
1536
1537 let filter = |impl_def: &Impl| {
1538 let target_ty = impl_def.target_ty(db);
1539 let rref = target_ty.remove_ref();
1540 ty.value.equals_ctor(rref.as_ref().map_or(&target_ty.ty.value, |it| &it.ty.value))
1541 };
1542
1543 let mut all = Vec::new();
1544 def_crates.into_iter().for_each(|id| {
1545 all.extend(db.inherent_impls_in_crate(id).all_impls().map(Self::from).filter(filter))
1546 });
1547 let fp = TyFingerprint::for_impl(&ty.value);
1548 for id in db.crate_graph().iter() {
1549 match fp {
1550 Some(fp) => all.extend(
1551 db.trait_impls_in_crate(id).for_self_ty(fp).map(Self::from).filter(filter),
1552 ),
1553 None => all
1554 .extend(db.trait_impls_in_crate(id).all_impls().map(Self::from).filter(filter)),
1555 }
1556 }
1557 all
1558 }
1559
1560 pub fn all_for_trait(db: &dyn HirDatabase, trait_: Trait) -> Vec<Impl> {
1561 let krate = trait_.module(db).krate();
1562 let mut all = Vec::new();
1563 for Crate { id } in krate.reverse_dependencies(db).into_iter().chain(Some(krate)) {
1564 let impls = db.trait_impls_in_crate(id);
1565 all.extend(impls.for_trait(trait_.id).map(Self::from))
1566 }
1567 all
1497 } 1568 }
1498 1569
1499 // FIXME: the return type is wrong. This should be a hir version of 1570 // FIXME: the return type is wrong. This should be a hir version of
@@ -1507,7 +1578,7 @@ impl Impl {
1507 let resolver = self.id.resolver(db.upcast()); 1578 let resolver = self.id.resolver(db.upcast());
1508 let krate = self.id.lookup(db.upcast()).container.krate(); 1579 let krate = self.id.lookup(db.upcast()).container.krate();
1509 let ctx = hir_ty::TyLoweringContext::new(db, &resolver); 1580 let ctx = hir_ty::TyLoweringContext::new(db, &resolver);
1510 let ty = Ty::from_hir(&ctx, &impl_data.target_type); 1581 let ty = ctx.lower_ty(&impl_data.target_type);
1511 Type::new_with_resolver_inner(db, krate, &resolver, ty) 1582 Type::new_with_resolver_inner(db, krate, &resolver, ty)
1512 } 1583 }
1513 1584
@@ -1571,13 +1642,15 @@ impl Type {
1571 resolver: &Resolver, 1642 resolver: &Resolver,
1572 ty: Ty, 1643 ty: Ty,
1573 ) -> Type { 1644 ) -> Type {
1574 let environment = TraitEnvironment::lower(db, &resolver); 1645 let environment =
1646 resolver.generic_def().map_or_else(Default::default, |d| db.trait_environment(d));
1575 Type { krate, ty: InEnvironment { value: ty, environment } } 1647 Type { krate, ty: InEnvironment { value: ty, environment } }
1576 } 1648 }
1577 1649
1578 fn new(db: &dyn HirDatabase, krate: CrateId, lexical_env: impl HasResolver, ty: Ty) -> Type { 1650 fn new(db: &dyn HirDatabase, krate: CrateId, lexical_env: impl HasResolver, ty: Ty) -> Type {
1579 let resolver = lexical_env.resolver(db.upcast()); 1651 let resolver = lexical_env.resolver(db.upcast());
1580 let environment = TraitEnvironment::lower(db, &resolver); 1652 let environment =
1653 resolver.generic_def().map_or_else(Default::default, |d| db.trait_environment(d));
1581 Type { krate, ty: InEnvironment { value: ty, environment } } 1654 Type { krate, ty: InEnvironment { value: ty, environment } }
1582 } 1655 }
1583 1656
@@ -1592,25 +1665,29 @@ impl Type {
1592 } 1665 }
1593 1666
1594 pub fn is_unit(&self) -> bool { 1667 pub fn is_unit(&self) -> bool {
1595 matches!(self.ty.value, Ty::Tuple(0, ..)) 1668 matches!(self.ty.value.interned(&Interner), TyKind::Tuple(0, ..))
1596 } 1669 }
1597 pub fn is_bool(&self) -> bool { 1670 pub fn is_bool(&self) -> bool {
1598 matches!(self.ty.value, Ty::Scalar(Scalar::Bool)) 1671 matches!(self.ty.value.interned(&Interner), TyKind::Scalar(Scalar::Bool))
1599 } 1672 }
1600 1673
1601 pub fn is_mutable_reference(&self) -> bool { 1674 pub fn is_mutable_reference(&self) -> bool {
1602 matches!(self.ty.value, Ty::Ref(hir_ty::Mutability::Mut, ..)) 1675 matches!(self.ty.value.interned(&Interner), TyKind::Ref(hir_ty::Mutability::Mut, ..))
1676 }
1677
1678 pub fn is_usize(&self) -> bool {
1679 matches!(self.ty.value.interned(&Interner), TyKind::Scalar(Scalar::Uint(UintTy::Usize)))
1603 } 1680 }
1604 1681
1605 pub fn remove_ref(&self) -> Option<Type> { 1682 pub fn remove_ref(&self) -> Option<Type> {
1606 match &self.ty.value { 1683 match &self.ty.value.interned(&Interner) {
1607 Ty::Ref(.., substs) => Some(self.derived(substs[0].clone())), 1684 TyKind::Ref(.., ty) => Some(self.derived(ty.clone())),
1608 _ => None, 1685 _ => None,
1609 } 1686 }
1610 } 1687 }
1611 1688
1612 pub fn is_unknown(&self) -> bool { 1689 pub fn is_unknown(&self) -> bool {
1613 matches!(self.ty.value, Ty::Unknown) 1690 self.ty.value.is_unknown()
1614 } 1691 }
1615 1692
1616 /// Checks that particular type `ty` implements `std::future::Future`. 1693 /// Checks that particular type `ty` implements `std::future::Future`.
@@ -1691,8 +1768,11 @@ impl Type {
1691 .fill(args.iter().map(|t| t.ty.value.clone())) 1768 .fill(args.iter().map(|t| t.ty.value.clone()))
1692 .build(); 1769 .build();
1693 let predicate = ProjectionPredicate { 1770 let predicate = ProjectionPredicate {
1694 projection_ty: ProjectionTy { associated_ty: alias.id, parameters: subst }, 1771 projection_ty: ProjectionTy {
1695 ty: Ty::BoundVar(BoundVar::new(DebruijnIndex::INNERMOST, 0)), 1772 associated_ty_id: to_assoc_type_id(alias.id),
1773 substitution: subst,
1774 },
1775 ty: TyKind::BoundVar(BoundVar::new(DebruijnIndex::INNERMOST, 0)).intern(&Interner),
1696 }; 1776 };
1697 let goal = Canonical { 1777 let goal = Canonical {
1698 value: InEnvironment::new( 1778 value: InEnvironment::new(
@@ -1720,26 +1800,23 @@ impl Type {
1720 } 1800 }
1721 1801
1722 pub fn as_callable(&self, db: &dyn HirDatabase) -> Option<Callable> { 1802 pub fn as_callable(&self, db: &dyn HirDatabase) -> Option<Callable> {
1723 let def = match self.ty.value { 1803 let def = self.ty.value.callable_def(db);
1724 Ty::FnDef(def, _) => Some(def),
1725 _ => None,
1726 };
1727 1804
1728 let sig = self.ty.value.callable_sig(db)?; 1805 let sig = self.ty.value.callable_sig(db)?;
1729 Some(Callable { ty: self.clone(), sig, def, is_bound_method: false }) 1806 Some(Callable { ty: self.clone(), sig, def, is_bound_method: false })
1730 } 1807 }
1731 1808
1732 pub fn is_closure(&self) -> bool { 1809 pub fn is_closure(&self) -> bool {
1733 matches!(&self.ty.value, Ty::Closure { .. }) 1810 matches!(&self.ty.value.interned(&Interner), TyKind::Closure { .. })
1734 } 1811 }
1735 1812
1736 pub fn is_fn(&self) -> bool { 1813 pub fn is_fn(&self) -> bool {
1737 matches!(&self.ty.value, Ty::FnDef(..) | Ty::Function { .. }) 1814 matches!(&self.ty.value.interned(&Interner), TyKind::FnDef(..) | TyKind::Function { .. })
1738 } 1815 }
1739 1816
1740 pub fn is_packed(&self, db: &dyn HirDatabase) -> bool { 1817 pub fn is_packed(&self, db: &dyn HirDatabase) -> bool {
1741 let adt_id = match self.ty.value { 1818 let adt_id = match self.ty.value.interned(&Interner) {
1742 Ty::Adt(hir_ty::AdtId(adt_id), ..) => adt_id, 1819 &TyKind::Adt(hir_ty::AdtId(adt_id), ..) => adt_id,
1743 _ => return false, 1820 _ => return false,
1744 }; 1821 };
1745 1822
@@ -1751,24 +1828,45 @@ impl Type {
1751 } 1828 }
1752 1829
1753 pub fn is_raw_ptr(&self) -> bool { 1830 pub fn is_raw_ptr(&self) -> bool {
1754 matches!(&self.ty.value, Ty::Raw(..)) 1831 matches!(&self.ty.value.interned(&Interner), TyKind::Raw(..))
1755 } 1832 }
1756 1833
1757 pub fn contains_unknown(&self) -> bool { 1834 pub fn contains_unknown(&self) -> bool {
1758 return go(&self.ty.value); 1835 return go(&self.ty.value);
1759 1836
1760 fn go(ty: &Ty) -> bool { 1837 fn go(ty: &Ty) -> bool {
1761 match ty { 1838 match ty.interned(&Interner) {
1762 Ty::Unknown => true, 1839 TyKind::Unknown => true,
1763 _ => ty.substs().map_or(false, |substs| substs.iter().any(go)), 1840
1841 TyKind::Adt(_, substs)
1842 | TyKind::AssociatedType(_, substs)
1843 | TyKind::Tuple(_, substs)
1844 | TyKind::OpaqueType(_, substs)
1845 | TyKind::FnDef(_, substs)
1846 | TyKind::Closure(_, substs) => substs.iter().any(go),
1847
1848 TyKind::Array(ty) | TyKind::Slice(ty) | TyKind::Raw(_, ty) | TyKind::Ref(_, ty) => {
1849 go(ty)
1850 }
1851
1852 TyKind::Scalar(_)
1853 | TyKind::Str
1854 | TyKind::Never
1855 | TyKind::Placeholder(_)
1856 | TyKind::BoundVar(_)
1857 | TyKind::InferenceVar(_, _)
1858 | TyKind::Dyn(_)
1859 | TyKind::Function(_)
1860 | TyKind::Alias(_)
1861 | TyKind::ForeignType(_) => false,
1764 } 1862 }
1765 } 1863 }
1766 } 1864 }
1767 1865
1768 pub fn fields(&self, db: &dyn HirDatabase) -> Vec<(Field, Type)> { 1866 pub fn fields(&self, db: &dyn HirDatabase) -> Vec<(Field, Type)> {
1769 let (variant_id, substs) = match self.ty.value { 1867 let (variant_id, substs) = match self.ty.value.interned(&Interner) {
1770 Ty::Adt(hir_ty::AdtId(AdtId::StructId(s)), ref substs) => (s.into(), substs), 1868 &TyKind::Adt(hir_ty::AdtId(AdtId::StructId(s)), ref substs) => (s.into(), substs),
1771 Ty::Adt(hir_ty::AdtId(AdtId::UnionId(u)), ref substs) => (u.into(), substs), 1869 &TyKind::Adt(hir_ty::AdtId(AdtId::UnionId(u)), ref substs) => (u.into(), substs),
1772 _ => return Vec::new(), 1870 _ => return Vec::new(),
1773 }; 1871 };
1774 1872
@@ -1783,7 +1881,7 @@ impl Type {
1783 } 1881 }
1784 1882
1785 pub fn tuple_fields(&self, _db: &dyn HirDatabase) -> Vec<Type> { 1883 pub fn tuple_fields(&self, _db: &dyn HirDatabase) -> Vec<Type> {
1786 if let Ty::Tuple(_, substs) = &self.ty.value { 1884 if let TyKind::Tuple(_, substs) = &self.ty.value.interned(&Interner) {
1787 substs.iter().map(|ty| self.derived(ty.clone())).collect() 1885 substs.iter().map(|ty| self.derived(ty.clone())).collect()
1788 } else { 1886 } else {
1789 Vec::new() 1887 Vec::new()
@@ -1918,12 +2016,6 @@ impl Type {
1918 self.ty.value.associated_type_parent_trait(db).map(Into::into) 2016 self.ty.value.associated_type_parent_trait(db).map(Into::into)
1919 } 2017 }
1920 2018
1921 // FIXME: provide required accessors such that it becomes implementable from outside.
1922 pub fn is_equal_for_find_impls(&self, other: &Type) -> bool {
1923 let rref = other.remove_ref();
1924 self.ty.value.equals_ctor(rref.as_ref().map_or(&other.ty.value, |it| &it.ty.value))
1925 }
1926
1927 fn derived(&self, ty: Ty) -> Type { 2019 fn derived(&self, ty: Ty) -> Type {
1928 Type { 2020 Type {
1929 krate: self.krate, 2021 krate: self.krate,
@@ -1965,36 +2057,40 @@ impl Type {
1965 2057
1966 fn walk_type(db: &dyn HirDatabase, type_: &Type, cb: &mut impl FnMut(Type)) { 2058 fn walk_type(db: &dyn HirDatabase, type_: &Type, cb: &mut impl FnMut(Type)) {
1967 let ty = type_.ty.value.strip_references(); 2059 let ty = type_.ty.value.strip_references();
1968 match ty { 2060 match ty.interned(&Interner) {
1969 Ty::Adt(..) => { 2061 TyKind::Adt(..) => {
1970 cb(type_.derived(ty.clone())); 2062 cb(type_.derived(ty.clone()));
1971 } 2063 }
1972 Ty::AssociatedType(..) => { 2064 TyKind::AssociatedType(..) => {
1973 if let Some(_) = ty.associated_type_parent_trait(db) { 2065 if let Some(_) = ty.associated_type_parent_trait(db) {
1974 cb(type_.derived(ty.clone())); 2066 cb(type_.derived(ty.clone()));
1975 } 2067 }
1976 } 2068 }
1977 Ty::OpaqueType(..) => { 2069 TyKind::OpaqueType(..) => {
1978 if let Some(bounds) = ty.impl_trait_bounds(db) { 2070 if let Some(bounds) = ty.impl_trait_bounds(db) {
1979 walk_bounds(db, &type_.derived(ty.clone()), &bounds, cb); 2071 walk_bounds(db, &type_.derived(ty.clone()), &bounds, cb);
1980 } 2072 }
1981 } 2073 }
1982 Ty::Alias(AliasTy::Opaque(opaque_ty)) => { 2074 TyKind::Alias(AliasTy::Opaque(opaque_ty)) => {
1983 if let Some(bounds) = ty.impl_trait_bounds(db) { 2075 if let Some(bounds) = ty.impl_trait_bounds(db) {
1984 walk_bounds(db, &type_.derived(ty.clone()), &bounds, cb); 2076 walk_bounds(db, &type_.derived(ty.clone()), &bounds, cb);
1985 } 2077 }
1986 2078
1987 walk_substs(db, type_, &opaque_ty.parameters, cb); 2079 walk_substs(db, type_, &opaque_ty.substitution, cb);
1988 } 2080 }
1989 Ty::Placeholder(_) => { 2081 TyKind::Placeholder(_) => {
1990 if let Some(bounds) = ty.impl_trait_bounds(db) { 2082 if let Some(bounds) = ty.impl_trait_bounds(db) {
1991 walk_bounds(db, &type_.derived(ty.clone()), &bounds, cb); 2083 walk_bounds(db, &type_.derived(ty.clone()), &bounds, cb);
1992 } 2084 }
1993 } 2085 }
1994 Ty::Dyn(bounds) => { 2086 TyKind::Dyn(bounds) => {
1995 walk_bounds(db, &type_.derived(ty.clone()), bounds.as_ref(), cb); 2087 walk_bounds(db, &type_.derived(ty.clone()), bounds.as_ref(), cb);
1996 } 2088 }
1997 2089
2090 TyKind::Ref(_, ty) | TyKind::Raw(_, ty) | TyKind::Array(ty) | TyKind::Slice(ty) => {
2091 walk_type(db, &type_.derived(ty.clone()), cb);
2092 }
2093
1998 _ => {} 2094 _ => {}
1999 } 2095 }
2000 if let Some(substs) = ty.substs() { 2096 if let Some(substs) = ty.substs() {
@@ -2006,12 +2102,6 @@ impl Type {
2006 } 2102 }
2007} 2103}
2008 2104
2009impl HirDisplay for Type {
2010 fn hir_fmt(&self, f: &mut HirFormatter) -> Result<(), HirDisplayError> {
2011 self.ty.value.hir_fmt(f)
2012 }
2013}
2014
2015// FIXME: closures 2105// FIXME: closures
2016#[derive(Debug)] 2106#[derive(Debug)]
2017pub struct Callable { 2107pub struct Callable {