diff options
Diffstat (limited to 'crates/hir_ty/src/types.rs')
-rw-r--r-- | crates/hir_ty/src/types.rs | 31 |
1 files changed, 30 insertions, 1 deletions
diff --git a/crates/hir_ty/src/types.rs b/crates/hir_ty/src/types.rs index dc64e6e2b..4a626d5e7 100644 --- a/crates/hir_ty/src/types.rs +++ b/crates/hir_ty/src/types.rs | |||
@@ -4,7 +4,7 @@ | |||
4 | use std::sync::Arc; | 4 | use std::sync::Arc; |
5 | 5 | ||
6 | use chalk_ir::{ | 6 | use chalk_ir::{ |
7 | cast::{CastTo, Caster}, | 7 | cast::{Cast, CastTo, Caster}, |
8 | BoundVar, Mutability, Scalar, TyVariableKind, | 8 | BoundVar, Mutability, Scalar, TyVariableKind, |
9 | }; | 9 | }; |
10 | use smallvec::SmallVec; | 10 | use smallvec::SmallVec; |
@@ -29,6 +29,12 @@ pub struct ProjectionTy { | |||
29 | pub substitution: Substitution, | 29 | pub substitution: Substitution, |
30 | } | 30 | } |
31 | 31 | ||
32 | impl ProjectionTy { | ||
33 | pub fn self_type_parameter(&self, interner: &Interner) -> &Ty { | ||
34 | &self.substitution.interned()[0].assert_ty_ref(interner) | ||
35 | } | ||
36 | } | ||
37 | |||
32 | #[derive(Clone, PartialEq, Eq, Debug, Hash)] | 38 | #[derive(Clone, PartialEq, Eq, Debug, Hash)] |
33 | pub struct DynTy { | 39 | pub struct DynTy { |
34 | /// The unknown self type. | 40 | /// The unknown self type. |
@@ -272,6 +278,14 @@ impl Substitution { | |||
272 | self.0.iter() | 278 | self.0.iter() |
273 | } | 279 | } |
274 | 280 | ||
281 | pub fn from1(_interner: &Interner, ty: Ty) -> Substitution { | ||
282 | Substitution::intern({ | ||
283 | let mut v = SmallVec::new(); | ||
284 | v.push(ty.cast(&Interner)); | ||
285 | v | ||
286 | }) | ||
287 | } | ||
288 | |||
275 | pub fn from_iter( | 289 | pub fn from_iter( |
276 | interner: &Interner, | 290 | interner: &Interner, |
277 | elements: impl IntoIterator<Item = impl CastTo<GenericArg>>, | 291 | elements: impl IntoIterator<Item = impl CastTo<GenericArg>>, |
@@ -346,6 +360,15 @@ impl<T: Clone> Binders<&T> { | |||
346 | } | 360 | } |
347 | } | 361 | } |
348 | 362 | ||
363 | impl<T: TypeWalk> Binders<T> { | ||
364 | /// Substitutes all variables. | ||
365 | pub fn substitute(self, interner: &Interner, subst: &Substitution) -> T { | ||
366 | let (value, binders) = self.into_value_and_skipped_binders(); | ||
367 | assert_eq!(subst.len(interner), binders.len(interner)); | ||
368 | value.subst_bound_vars(subst) | ||
369 | } | ||
370 | } | ||
371 | |||
349 | impl<T: std::fmt::Debug> std::fmt::Debug for Binders<T> { | 372 | impl<T: std::fmt::Debug> std::fmt::Debug for Binders<T> { |
350 | fn fmt(&self, fmt: &mut std::fmt::Formatter<'_>) -> Result<(), std::fmt::Error> { | 373 | fn fmt(&self, fmt: &mut std::fmt::Formatter<'_>) -> Result<(), std::fmt::Error> { |
351 | let Binders { ref binders, ref value } = *self; | 374 | let Binders { ref binders, ref value } = *self; |
@@ -361,6 +384,12 @@ pub struct TraitRef { | |||
361 | pub substitution: Substitution, | 384 | pub substitution: Substitution, |
362 | } | 385 | } |
363 | 386 | ||
387 | impl TraitRef { | ||
388 | pub fn self_type_parameter(&self, interner: &Interner) -> &Ty { | ||
389 | &self.substitution.at(interner, 0).assert_ty_ref(interner) | ||
390 | } | ||
391 | } | ||
392 | |||
364 | /// Like `generics::WherePredicate`, but with resolved types: A condition on the | 393 | /// Like `generics::WherePredicate`, but with resolved types: A condition on the |
365 | /// parameters of a generic item. | 394 | /// parameters of a generic item. |
366 | #[derive(Debug, Clone, PartialEq, Eq, Hash)] | 395 | #[derive(Debug, Clone, PartialEq, Eq, Hash)] |