aboutsummaryrefslogtreecommitdiff
path: root/crates/hir_ty/src/mapping.rs
diff options
context:
space:
mode:
Diffstat (limited to 'crates/hir_ty/src/mapping.rs')
-rw-r--r--crates/hir_ty/src/mapping.rs92
1 files changed, 32 insertions, 60 deletions
diff --git a/crates/hir_ty/src/mapping.rs b/crates/hir_ty/src/mapping.rs
index f57115de6..37c935194 100644
--- a/crates/hir_ty/src/mapping.rs
+++ b/crates/hir_ty/src/mapping.rs
@@ -3,16 +3,12 @@
3//! Chalk (in both directions); plus some helper functions for more specialized 3//! Chalk (in both directions); plus some helper functions for more specialized
4//! conversions. 4//! conversions.
5 5
6use chalk_ir::{cast::Cast, fold::Shift, DebruijnIndex};
7use chalk_solve::rust_ir; 6use chalk_solve::rust_ir;
8 7
9use base_db::salsa::InternKey; 8use base_db::salsa::InternKey;
10use hir_def::{GenericDefId, TypeAliasId}; 9use hir_def::TypeAliasId;
11 10
12use crate::{ 11use crate::{chalk_db, db::HirDatabase, CallableDefId, FnDefId, Interner, OpaqueTyId};
13 chalk_db, db::HirDatabase, AliasEq, AliasTy, CallableDefId, FnDefId, Interner, ProjectionTyExt,
14 QuantifiedWhereClause, Substitution, Ty, WhereClause,
15};
16 12
17pub(crate) trait ToChalk { 13pub(crate) trait ToChalk {
18 type Chalk; 14 type Chalk;
@@ -80,62 +76,38 @@ impl ToChalk for TypeAliasAsValue {
80 } 76 }
81} 77}
82 78
83pub(super) fn convert_where_clauses( 79impl From<FnDefId> for crate::db::InternedCallableDefId {
84 db: &dyn HirDatabase, 80 fn from(fn_def_id: FnDefId) -> Self {
85 def: GenericDefId, 81 InternKey::from_intern_id(fn_def_id.0)
86 substs: &Substitution,
87) -> Vec<chalk_ir::QuantifiedWhereClause<Interner>> {
88 let generic_predicates = db.generic_predicates(def);
89 let mut result = Vec::with_capacity(generic_predicates.len());
90 for pred in generic_predicates.iter() {
91 result.push(pred.clone().substitute(&Interner, substs));
92 } 82 }
93 result
94} 83}
95 84
96pub(super) fn generic_predicate_to_inline_bound( 85impl From<crate::db::InternedCallableDefId> for FnDefId {
97 db: &dyn HirDatabase, 86 fn from(callable_def_id: crate::db::InternedCallableDefId) -> Self {
98 pred: &QuantifiedWhereClause, 87 chalk_ir::FnDefId(callable_def_id.as_intern_id())
99 self_ty: &Ty, 88 }
100) -> Option<chalk_ir::Binders<rust_ir::InlineBound<Interner>>> { 89}
101 // An InlineBound is like a GenericPredicate, except the self type is left out. 90
102 // We don't have a special type for this, but Chalk does. 91impl From<OpaqueTyId> for crate::db::InternedOpaqueTyId {
103 let self_ty_shifted_in = self_ty.clone().shifted_in_from(&Interner, DebruijnIndex::ONE); 92 fn from(id: OpaqueTyId) -> Self {
104 let (pred, binders) = pred.as_ref().into_value_and_skipped_binders(); 93 InternKey::from_intern_id(id.0)
105 match pred { 94 }
106 WhereClause::Implemented(trait_ref) => { 95}
107 if trait_ref.self_type_parameter(&Interner) != self_ty_shifted_in { 96
108 // we can only convert predicates back to type bounds if they 97impl From<crate::db::InternedOpaqueTyId> for OpaqueTyId {
109 // have the expected self type 98 fn from(id: crate::db::InternedOpaqueTyId) -> Self {
110 return None; 99 chalk_ir::OpaqueTyId(id.as_intern_id())
111 } 100 }
112 let args_no_self = trait_ref.substitution.as_slice(&Interner)[1..] 101}
113 .iter() 102
114 .map(|ty| ty.clone().cast(&Interner)) 103impl From<chalk_ir::ClosureId<Interner>> for crate::db::InternedClosureId {
115 .collect(); 104 fn from(id: chalk_ir::ClosureId<Interner>) -> Self {
116 let trait_bound = rust_ir::TraitBound { trait_id: trait_ref.trait_id, args_no_self }; 105 Self::from_intern_id(id.0)
117 Some(chalk_ir::Binders::new(binders, rust_ir::InlineBound::TraitBound(trait_bound))) 106 }
118 } 107}
119 WhereClause::AliasEq(AliasEq { alias: AliasTy::Projection(projection_ty), ty }) => { 108
120 if projection_ty.self_type_parameter(&Interner) != self_ty_shifted_in { 109impl From<crate::db::InternedClosureId> for chalk_ir::ClosureId<Interner> {
121 return None; 110 fn from(id: crate::db::InternedClosureId) -> Self {
122 } 111 chalk_ir::ClosureId(id.as_intern_id())
123 let trait_ = projection_ty.trait_(db);
124 let args_no_self = projection_ty.substitution.as_slice(&Interner)[1..]
125 .iter()
126 .map(|ty| ty.clone().cast(&Interner))
127 .collect();
128 let alias_eq_bound = rust_ir::AliasEqBound {
129 value: ty.clone(),
130 trait_bound: rust_ir::TraitBound { trait_id: trait_.to_chalk(db), args_no_self },
131 associated_ty_id: projection_ty.associated_ty_id,
132 parameters: Vec::new(), // FIXME we don't support generic associated types yet
133 };
134 Some(chalk_ir::Binders::new(
135 binders,
136 rust_ir::InlineBound::AliasEqBound(alias_eq_bound),
137 ))
138 }
139 _ => None,
140 } 112 }
141} 113}