mirror of
https://github.com/rust-lang/rust.git
synced 2025-01-22 04:34:51 +00:00
Merge #8039
8039: Use SmallVec for Substs r=flodiebold a=flodiebold Doesn't help as much as I hoped, but it helps a bit and I also did some refactorings that were necessary anyway. Co-authored-by: Florian Diebold <flodiebold@gmail.com>
This commit is contained in:
commit
c0a2b4e826
@ -31,6 +31,7 @@ use hir_def::{
|
|||||||
GenericDefId, HasModule, LifetimeParamId, Lookup, TraitId, TypeAliasId, TypeParamId,
|
GenericDefId, HasModule, LifetimeParamId, Lookup, TraitId, TypeAliasId, TypeParamId,
|
||||||
};
|
};
|
||||||
use itertools::Itertools;
|
use itertools::Itertools;
|
||||||
|
use smallvec::SmallVec;
|
||||||
|
|
||||||
use crate::{
|
use crate::{
|
||||||
db::HirDatabase,
|
db::HirDatabase,
|
||||||
@ -272,7 +273,7 @@ impl Ty {
|
|||||||
|
|
||||||
/// A list of substitutions for generic parameters.
|
/// A list of substitutions for generic parameters.
|
||||||
#[derive(Clone, PartialEq, Eq, Debug, Hash)]
|
#[derive(Clone, PartialEq, Eq, Debug, Hash)]
|
||||||
pub struct Substs(Arc<[Ty]>);
|
pub struct Substs(SmallVec<[Ty; 2]>);
|
||||||
|
|
||||||
impl TypeWalk for Substs {
|
impl TypeWalk for Substs {
|
||||||
fn walk(&self, f: &mut impl FnMut(&Ty)) {
|
fn walk(&self, f: &mut impl FnMut(&Ty)) {
|
||||||
@ -286,19 +287,27 @@ impl TypeWalk for Substs {
|
|||||||
f: &mut impl FnMut(&mut Ty, DebruijnIndex),
|
f: &mut impl FnMut(&mut Ty, DebruijnIndex),
|
||||||
binders: DebruijnIndex,
|
binders: DebruijnIndex,
|
||||||
) {
|
) {
|
||||||
for t in make_mut_slice(&mut self.0) {
|
for t in &mut self.0 {
|
||||||
t.walk_mut_binders(f, binders);
|
t.walk_mut_binders(f, binders);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Substs {
|
impl Substs {
|
||||||
|
pub fn interned(&self, _: &Interner) -> &[Ty] {
|
||||||
|
&self.0
|
||||||
|
}
|
||||||
|
|
||||||
pub fn empty() -> Substs {
|
pub fn empty() -> Substs {
|
||||||
Substs(Arc::new([]))
|
Substs(SmallVec::new())
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn single(ty: Ty) -> Substs {
|
pub fn single(ty: Ty) -> Substs {
|
||||||
Substs(Arc::new([ty]))
|
Substs({
|
||||||
|
let mut v = SmallVec::new();
|
||||||
|
v.push(ty);
|
||||||
|
v
|
||||||
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn prefix(&self, n: usize) -> Substs {
|
pub fn prefix(&self, n: usize) -> Substs {
|
||||||
@ -316,6 +325,10 @@ impl Substs {
|
|||||||
&self.0[0]
|
&self.0[0]
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub fn from_iter(_interner: &Interner, elements: impl IntoIterator<Item = Ty>) -> Self {
|
||||||
|
Substs(elements.into_iter().collect())
|
||||||
|
}
|
||||||
|
|
||||||
/// Return Substs that replace each parameter by itself (i.e. `Ty::Param`).
|
/// Return Substs that replace each parameter by itself (i.e. `Ty::Param`).
|
||||||
pub(crate) fn type_params_for_generics(
|
pub(crate) fn type_params_for_generics(
|
||||||
db: &dyn HirDatabase,
|
db: &dyn HirDatabase,
|
||||||
@ -600,13 +613,13 @@ impl CallableSig {
|
|||||||
|
|
||||||
pub fn from_fn_ptr(fn_ptr: &FnPointer) -> CallableSig {
|
pub fn from_fn_ptr(fn_ptr: &FnPointer) -> CallableSig {
|
||||||
CallableSig {
|
CallableSig {
|
||||||
params_and_return: Arc::clone(&fn_ptr.substs.0),
|
params_and_return: fn_ptr.substs.interned(&Interner).iter().cloned().collect(),
|
||||||
is_varargs: fn_ptr.sig.variadic,
|
is_varargs: fn_ptr.sig.variadic,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn from_substs(substs: &Substs) -> CallableSig {
|
pub fn from_substs(substs: &Substs) -> CallableSig {
|
||||||
CallableSig { params_and_return: Arc::clone(&substs.0), is_varargs: false }
|
CallableSig { params_and_return: substs.iter().cloned().collect(), is_varargs: false }
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn params(&self) -> &[Ty] {
|
pub fn params(&self) -> &[Ty] {
|
||||||
@ -649,7 +662,7 @@ impl Ty {
|
|||||||
TyKind::Function(FnPointer {
|
TyKind::Function(FnPointer {
|
||||||
num_args: sig.params().len(),
|
num_args: sig.params().len(),
|
||||||
sig: FnSig { abi: (), safety: Safety::Safe, variadic: sig.is_varargs },
|
sig: FnSig { abi: (), safety: Safety::Safe, variadic: sig.is_varargs },
|
||||||
substs: Substs(sig.params_and_return),
|
substs: Substs::from_iter(&Interner, sig.params_and_return.iter().cloned()),
|
||||||
})
|
})
|
||||||
.intern(&Interner)
|
.intern(&Interner)
|
||||||
}
|
}
|
||||||
|
@ -31,7 +31,7 @@ use crate::{
|
|||||||
traits::chalk::{Interner, ToChalk},
|
traits::chalk::{Interner, ToChalk},
|
||||||
utils::{
|
utils::{
|
||||||
all_super_trait_refs, associated_type_by_name_including_super_traits, generics,
|
all_super_trait_refs, associated_type_by_name_including_super_traits, generics,
|
||||||
make_mut_slice, variant_data,
|
variant_data,
|
||||||
},
|
},
|
||||||
AliasTy, Binders, BoundVar, CallableSig, DebruijnIndex, FnPointer, FnSig, GenericPredicate,
|
AliasTy, Binders, BoundVar, CallableSig, DebruijnIndex, FnPointer, FnSig, GenericPredicate,
|
||||||
ImplTraitId, OpaqueTy, PolyFnSig, ProjectionPredicate, ProjectionTy, ReturnTypeImplTrait,
|
ImplTraitId, OpaqueTy, PolyFnSig, ProjectionPredicate, ProjectionTy, ReturnTypeImplTrait,
|
||||||
@ -150,8 +150,9 @@ impl<'a> TyLoweringContext<'a> {
|
|||||||
let ty = match type_ref {
|
let ty = match type_ref {
|
||||||
TypeRef::Never => TyKind::Never.intern(&Interner),
|
TypeRef::Never => TyKind::Never.intern(&Interner),
|
||||||
TypeRef::Tuple(inner) => {
|
TypeRef::Tuple(inner) => {
|
||||||
let inner_tys: Arc<[Ty]> = inner.iter().map(|tr| self.lower_ty(tr)).collect();
|
let inner_tys = inner.iter().map(|tr| self.lower_ty(tr));
|
||||||
TyKind::Tuple(inner_tys.len(), Substs(inner_tys)).intern(&Interner)
|
TyKind::Tuple(inner_tys.len(), Substs::from_iter(&Interner, inner_tys))
|
||||||
|
.intern(&Interner)
|
||||||
}
|
}
|
||||||
TypeRef::Path(path) => {
|
TypeRef::Path(path) => {
|
||||||
let (ty, res_) = self.lower_path(path);
|
let (ty, res_) = self.lower_path(path);
|
||||||
@ -638,7 +639,7 @@ impl<'a> TyLoweringContext<'a> {
|
|||||||
) -> TraitRef {
|
) -> TraitRef {
|
||||||
let mut substs = self.trait_ref_substs_from_path(segment, resolved);
|
let mut substs = self.trait_ref_substs_from_path(segment, resolved);
|
||||||
if let Some(self_ty) = explicit_self_ty {
|
if let Some(self_ty) = explicit_self_ty {
|
||||||
make_mut_slice(&mut substs.0)[0] = self_ty;
|
substs.0[0] = self_ty;
|
||||||
}
|
}
|
||||||
TraitRef { trait_: resolved, substs }
|
TraitRef { trait_: resolved, substs }
|
||||||
}
|
}
|
||||||
|
@ -5,6 +5,7 @@ use super::tls;
|
|||||||
use base_db::salsa::InternId;
|
use base_db::salsa::InternId;
|
||||||
use chalk_ir::{GenericArg, Goal, GoalData};
|
use chalk_ir::{GenericArg, Goal, GoalData};
|
||||||
use hir_def::TypeAliasId;
|
use hir_def::TypeAliasId;
|
||||||
|
use smallvec::SmallVec;
|
||||||
use std::{fmt, sync::Arc};
|
use std::{fmt, sync::Arc};
|
||||||
|
|
||||||
#[derive(Debug, Copy, Clone, Hash, PartialOrd, Ord, PartialEq, Eq)]
|
#[derive(Debug, Copy, Clone, Hash, PartialOrd, Ord, PartialEq, Eq)]
|
||||||
@ -33,7 +34,7 @@ impl chalk_ir::interner::Interner for Interner {
|
|||||||
type InternedGenericArg = chalk_ir::GenericArgData<Self>;
|
type InternedGenericArg = chalk_ir::GenericArgData<Self>;
|
||||||
type InternedGoal = Arc<GoalData<Self>>;
|
type InternedGoal = Arc<GoalData<Self>>;
|
||||||
type InternedGoals = Vec<Goal<Self>>;
|
type InternedGoals = Vec<Goal<Self>>;
|
||||||
type InternedSubstitution = Vec<GenericArg<Self>>;
|
type InternedSubstitution = SmallVec<[GenericArg<Self>; 2]>;
|
||||||
type InternedProgramClause = Arc<chalk_ir::ProgramClauseData<Self>>;
|
type InternedProgramClause = Arc<chalk_ir::ProgramClauseData<Self>>;
|
||||||
type InternedProgramClauses = Arc<[chalk_ir::ProgramClause<Self>]>;
|
type InternedProgramClauses = Arc<[chalk_ir::ProgramClause<Self>]>;
|
||||||
type InternedQuantifiedWhereClauses = Vec<chalk_ir::QuantifiedWhereClause<Self>>;
|
type InternedQuantifiedWhereClauses = Vec<chalk_ir::QuantifiedWhereClause<Self>>;
|
||||||
@ -265,13 +266,13 @@ impl chalk_ir::interner::Interner for Interner {
|
|||||||
fn intern_substitution<E>(
|
fn intern_substitution<E>(
|
||||||
&self,
|
&self,
|
||||||
data: impl IntoIterator<Item = Result<GenericArg<Self>, E>>,
|
data: impl IntoIterator<Item = Result<GenericArg<Self>, E>>,
|
||||||
) -> Result<Vec<GenericArg<Self>>, E> {
|
) -> Result<Self::InternedSubstitution, E> {
|
||||||
data.into_iter().collect()
|
data.into_iter().collect()
|
||||||
}
|
}
|
||||||
|
|
||||||
fn substitution_data<'a>(
|
fn substitution_data<'a>(
|
||||||
&self,
|
&self,
|
||||||
substitution: &'a Vec<GenericArg<Self>>,
|
substitution: &'a Self::InternedSubstitution,
|
||||||
) -> &'a [GenericArg<Self>] {
|
) -> &'a [GenericArg<Self>] {
|
||||||
substitution
|
substitution
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user