From c9c4053eed8ec7cfc66bf51743cdc144abd593f6 Mon Sep 17 00:00:00 2001 From: Lukas Wirth Date: Sat, 6 Jan 2024 16:58:15 +0100 Subject: [PATCH] More aliases --- crates/hir-ty/src/interner.rs | 232 +++++++++++++++++----------------- crates/hir-ty/src/lib.rs | 13 +- 2 files changed, 130 insertions(+), 115 deletions(-) diff --git a/crates/hir-ty/src/interner.rs b/crates/hir-ty/src/interner.rs index e4dd4b86cf..7d3539edad 100644 --- a/crates/hir-ty/src/interner.rs +++ b/crates/hir-ty/src/interner.rs @@ -1,9 +1,15 @@ //! Implementation of the Chalk `Interner` trait, which allows customizing the //! representation of the various objects Chalk deals with (types, goals etc.). -use crate::{chalk_db, tls, ConstScalar, GenericArg}; +use crate::{ + chalk_db, tls, AliasTy, CanonicalVarKind, CanonicalVarKinds, ClosureId, Const, ConstData, + ConstScalar, Constraint, Constraints, FnDefId, GenericArg, GenericArgData, Goal, GoalData, + Goals, InEnvironment, Lifetime, LifetimeData, OpaqueTy, OpaqueTyId, ProgramClause, + ProgramClauseData, ProgramClauses, ProjectionTy, QuantifiedWhereClause, QuantifiedWhereClauses, + Substitution, Ty, TyData, TyKind, VariableKind, VariableKinds, +}; use base_db::salsa::InternId; -use chalk_ir::{Goal, GoalData}; +use chalk_ir::{ProgramClauseImplication, SeparatorTraitRef, Variance}; use hir_def::TypeAliasId; use intern::{impl_internable, Interned}; use smallvec::SmallVec; @@ -30,37 +36,70 @@ impl std::ops::Deref for InternedWrapper { } } +#[derive(Eq)] +pub struct PreHashedWrapper(T, u64); + +impl fmt::Debug for PreHashedWrapper { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + fmt::Debug::fmt(&self.0, f) + } +} + +impl PartialEq for PreHashedWrapper { + fn eq(&self, other: &Self) -> bool { + self.1 == other.1 && self.0 == other.0 + } +} + +impl std::ops::Deref for PreHashedWrapper { + type Target = T; + + fn deref(&self) -> &Self::Target { + &self.0 + } +} + +impl std::hash::Hash for PreHashedWrapper { + fn hash(&self, state: &mut H) { + state.write_u64(self.1); + } +} + impl_internable!( - InternedWrapper>>, + InternedWrapper>, InternedWrapper>, - InternedWrapper>, - InternedWrapper>, - InternedWrapper>, + InternedWrapper, + InternedWrapper, + InternedWrapper, InternedWrapper, - InternedWrapper>>, - InternedWrapper>>, - InternedWrapper>>, - InternedWrapper>, + InternedWrapper>, + InternedWrapper>, + InternedWrapper>, + InternedWrapper>, + // InternedWrapper>, ); impl chalk_ir::interner::Interner for Interner { - type InternedType = Interned>>; - type InternedLifetime = Interned>>; - type InternedConst = Interned>>; + type InternedType = Interned>; + type InternedLifetime = Interned>; + type InternedConst = Interned>; type InternedConcreteConst = ConstScalar; - type InternedGenericArg = chalk_ir::GenericArgData; - type InternedGoal = Arc>; - type InternedGoals = Vec>; + type InternedGenericArg = GenericArgData; + // We could do the following, but that saves "only" 20mb on self while increasing inferecene + // time by ~2.5% + // type InternedGoal = Interned>; + // type InternedGoal = Interned>>; + type InternedGoal = Arc; + type InternedGoals = Vec; type InternedSubstitution = Interned>>; - type InternedProgramClauses = Interned>>>; - type InternedProgramClause = chalk_ir::ProgramClauseData; - type InternedQuantifiedWhereClauses = - Interned>>>; - type InternedVariableKinds = Interned>>>; - type InternedCanonicalVarKinds = - Interned>>>; - type InternedConstraints = Vec>>; - type InternedVariances = Interned>>; + type InternedProgramClauses = Interned>>; + type InternedProgramClause = ProgramClauseData; + type InternedQuantifiedWhereClauses = Interned>>; + type InternedVariableKinds = Interned>>; + type InternedCanonicalVarKinds = Interned>>; + // type InternedConstraints = SmallVec<[InEnvironment; 1]>; + type InternedConstraints = Vec>; + type InternedVariances = SmallVec<[Variance; 16]>; type DefId = InternId; type InternedAdtId = hir_def::AdtId; type Identifier = TypeAliasId; @@ -88,68 +127,51 @@ impl chalk_ir::interner::Interner for Interner { } fn debug_opaque_ty_id( - opaque_ty_id: chalk_ir::OpaqueTyId, + opaque_ty_id: OpaqueTyId, fmt: &mut fmt::Formatter<'_>, ) -> Option { Some(write!(fmt, "OpaqueTy#{}", opaque_ty_id.0)) } - fn debug_fn_def_id( - fn_def_id: chalk_ir::FnDefId, - fmt: &mut fmt::Formatter<'_>, - ) -> Option { + fn debug_fn_def_id(fn_def_id: FnDefId, fmt: &mut fmt::Formatter<'_>) -> Option { tls::with_current_program(|prog| Some(prog?.debug_fn_def_id(fn_def_id, fmt))) } fn debug_closure_id( - _fn_def_id: chalk_ir::ClosureId, + _fn_def_id: ClosureId, _fmt: &mut fmt::Formatter<'_>, ) -> Option { None } - fn debug_alias( - alias: &chalk_ir::AliasTy, - fmt: &mut fmt::Formatter<'_>, - ) -> Option { + fn debug_alias(alias: &AliasTy, fmt: &mut fmt::Formatter<'_>) -> Option { use std::fmt::Debug; match alias { - chalk_ir::AliasTy::Projection(projection_ty) => { - Interner::debug_projection_ty(projection_ty, fmt) - } - chalk_ir::AliasTy::Opaque(opaque_ty) => Some(opaque_ty.fmt(fmt)), + AliasTy::Projection(projection_ty) => Interner::debug_projection_ty(projection_ty, fmt), + AliasTy::Opaque(opaque_ty) => Some(opaque_ty.fmt(fmt)), } } fn debug_projection_ty( - proj: &chalk_ir::ProjectionTy, + proj: &ProjectionTy, fmt: &mut fmt::Formatter<'_>, ) -> Option { tls::with_current_program(|prog| Some(prog?.debug_projection_ty(proj, fmt))) } - fn debug_opaque_ty( - opaque_ty: &chalk_ir::OpaqueTy, - fmt: &mut fmt::Formatter<'_>, - ) -> Option { + fn debug_opaque_ty(opaque_ty: &OpaqueTy, fmt: &mut fmt::Formatter<'_>) -> Option { Some(write!(fmt, "{:?}", opaque_ty.opaque_ty_id)) } - fn debug_ty(ty: &chalk_ir::Ty, fmt: &mut fmt::Formatter<'_>) -> Option { + fn debug_ty(ty: &Ty, fmt: &mut fmt::Formatter<'_>) -> Option { Some(write!(fmt, "{:?}", ty.data(Interner))) } - fn debug_lifetime( - lifetime: &chalk_ir::Lifetime, - fmt: &mut fmt::Formatter<'_>, - ) -> Option { + fn debug_lifetime(lifetime: &Lifetime, fmt: &mut fmt::Formatter<'_>) -> Option { Some(write!(fmt, "{:?}", lifetime.data(Interner))) } - fn debug_const( - constant: &chalk_ir::Const, - fmt: &mut fmt::Formatter<'_>, - ) -> Option { + fn debug_const(constant: &Const, fmt: &mut fmt::Formatter<'_>) -> Option { Some(write!(fmt, "{:?}", constant.data(Interner))) } @@ -161,102 +183,99 @@ impl chalk_ir::interner::Interner for Interner { } fn debug_variable_kinds( - variable_kinds: &chalk_ir::VariableKinds, + variable_kinds: &VariableKinds, fmt: &mut fmt::Formatter<'_>, ) -> Option { Some(write!(fmt, "{:?}", variable_kinds.as_slice(Interner))) } fn debug_variable_kinds_with_angles( - variable_kinds: &chalk_ir::VariableKinds, + variable_kinds: &VariableKinds, fmt: &mut fmt::Formatter<'_>, ) -> Option { Some(write!(fmt, "{:?}", variable_kinds.inner_debug(Interner))) } fn debug_canonical_var_kinds( - canonical_var_kinds: &chalk_ir::CanonicalVarKinds, + canonical_var_kinds: &CanonicalVarKinds, fmt: &mut fmt::Formatter<'_>, ) -> Option { Some(write!(fmt, "{:?}", canonical_var_kinds.as_slice(Interner))) } - fn debug_goal(goal: &Goal, fmt: &mut fmt::Formatter<'_>) -> Option { + fn debug_goal(goal: &Goal, fmt: &mut fmt::Formatter<'_>) -> Option { let goal_data = goal.data(Interner); Some(write!(fmt, "{goal_data:?}")) } - fn debug_goals( - goals: &chalk_ir::Goals, - fmt: &mut fmt::Formatter<'_>, - ) -> Option { + fn debug_goals(goals: &Goals, fmt: &mut fmt::Formatter<'_>) -> Option { Some(write!(fmt, "{:?}", goals.debug(Interner))) } fn debug_program_clause_implication( - pci: &chalk_ir::ProgramClauseImplication, + pci: &ProgramClauseImplication, fmt: &mut fmt::Formatter<'_>, ) -> Option { Some(write!(fmt, "{:?}", pci.debug(Interner))) } fn debug_program_clause( - clause: &chalk_ir::ProgramClause, + clause: &ProgramClause, fmt: &mut fmt::Formatter<'_>, ) -> Option { Some(write!(fmt, "{:?}", clause.data(Interner))) } fn debug_program_clauses( - clauses: &chalk_ir::ProgramClauses, + clauses: &ProgramClauses, fmt: &mut fmt::Formatter<'_>, ) -> Option { Some(write!(fmt, "{:?}", clauses.as_slice(Interner))) } fn debug_substitution( - substitution: &chalk_ir::Substitution, + substitution: &Substitution, fmt: &mut fmt::Formatter<'_>, ) -> Option { Some(write!(fmt, "{:?}", substitution.debug(Interner))) } fn debug_separator_trait_ref( - separator_trait_ref: &chalk_ir::SeparatorTraitRef<'_, Interner>, + separator_trait_ref: &SeparatorTraitRef<'_, Interner>, fmt: &mut fmt::Formatter<'_>, ) -> Option { Some(write!(fmt, "{:?}", separator_trait_ref.debug(Interner))) } fn debug_quantified_where_clauses( - clauses: &chalk_ir::QuantifiedWhereClauses, + clauses: &QuantifiedWhereClauses, fmt: &mut fmt::Formatter<'_>, ) -> Option { Some(write!(fmt, "{:?}", clauses.as_slice(Interner))) } fn debug_constraints( - _clauses: &chalk_ir::Constraints, + _clauses: &Constraints, _fmt: &mut fmt::Formatter<'_>, ) -> Option { None } - fn intern_ty(self, kind: chalk_ir::TyKind) -> Self::InternedType { + fn intern_ty(self, kind: TyKind) -> Self::InternedType { let flags = kind.compute_flags(self); - Interned::new(InternedWrapper(chalk_ir::TyData { kind, flags })) + Interned::new(InternedWrapper(TyData { kind, flags })) } - fn ty_data(self, ty: &Self::InternedType) -> &chalk_ir::TyData { + fn ty_data(self, ty: &Self::InternedType) -> &TyData { &ty.0 } - fn intern_lifetime(self, lifetime: chalk_ir::LifetimeData) -> Self::InternedLifetime { + fn intern_lifetime(self, lifetime: LifetimeData) -> Self::InternedLifetime { Interned::new(InternedWrapper(lifetime)) } - fn lifetime_data(self, lifetime: &Self::InternedLifetime) -> &chalk_ir::LifetimeData { + fn lifetime_data(self, lifetime: &Self::InternedLifetime) -> &LifetimeData { &lifetime.0 } - fn intern_const(self, constant: chalk_ir::ConstData) -> Self::InternedConst { + fn intern_const(self, constant: ConstData) -> Self::InternedConst { Interned::new(InternedWrapper(constant)) } - fn const_data(self, constant: &Self::InternedConst) -> &chalk_ir::ConstData { + fn const_data(self, constant: &Self::InternedConst) -> &ConstData { &constant.0 } @@ -269,36 +288,33 @@ impl chalk_ir::interner::Interner for Interner { !matches!(c1, ConstScalar::Bytes(..)) || !matches!(c2, ConstScalar::Bytes(..)) || (c1 == c2) } - fn intern_generic_arg( - self, - parameter: chalk_ir::GenericArgData, - ) -> Self::InternedGenericArg { + fn intern_generic_arg(self, parameter: GenericArgData) -> Self::InternedGenericArg { parameter } - fn generic_arg_data( - self, - parameter: &Self::InternedGenericArg, - ) -> &chalk_ir::GenericArgData { + fn generic_arg_data(self, parameter: &Self::InternedGenericArg) -> &GenericArgData { parameter } - fn intern_goal(self, goal: GoalData) -> Self::InternedGoal { + fn intern_goal(self, goal: GoalData) -> Self::InternedGoal { Arc::new(goal) } - fn goal_data(self, goal: &Self::InternedGoal) -> &GoalData { + fn goal_data(self, goal: &Self::InternedGoal) -> &GoalData { goal } fn intern_goals( self, - data: impl IntoIterator, E>>, + data: impl IntoIterator>, ) -> Result { + // let hash = + // std::hash::BuildHasher::hash_one(&BuildHasherDefault::::default(), &goal); + // Interned::new(InternedWrapper(PreHashedWrapper(goal, hash))) data.into_iter().collect() } - fn goals_data(self, goals: &Self::InternedGoals) -> &[Goal] { + fn goals_data(self, goals: &Self::InternedGoals) -> &[Goal] { goals } @@ -313,37 +329,28 @@ impl chalk_ir::interner::Interner for Interner { &substitution.as_ref().0 } - fn intern_program_clause( - self, - data: chalk_ir::ProgramClauseData, - ) -> Self::InternedProgramClause { + fn intern_program_clause(self, data: ProgramClauseData) -> Self::InternedProgramClause { data } - fn program_clause_data( - self, - clause: &Self::InternedProgramClause, - ) -> &chalk_ir::ProgramClauseData { + fn program_clause_data(self, clause: &Self::InternedProgramClause) -> &ProgramClauseData { clause } fn intern_program_clauses( self, - data: impl IntoIterator, E>>, + data: impl IntoIterator>, ) -> Result { Ok(Interned::new(InternedWrapper(data.into_iter().collect::>()?))) } - fn program_clauses_data( - self, - clauses: &Self::InternedProgramClauses, - ) -> &[chalk_ir::ProgramClause] { + fn program_clauses_data(self, clauses: &Self::InternedProgramClauses) -> &[ProgramClause] { clauses } fn intern_quantified_where_clauses( self, - data: impl IntoIterator, E>>, + data: impl IntoIterator>, ) -> Result { Ok(Interned::new(InternedWrapper(data.into_iter().collect::>()?))) } @@ -351,27 +358,24 @@ impl chalk_ir::interner::Interner for Interner { fn quantified_where_clauses_data( self, clauses: &Self::InternedQuantifiedWhereClauses, - ) -> &[chalk_ir::QuantifiedWhereClause] { + ) -> &[QuantifiedWhereClause] { clauses } fn intern_generic_arg_kinds( self, - data: impl IntoIterator, E>>, + data: impl IntoIterator>, ) -> Result { Ok(Interned::new(InternedWrapper(data.into_iter().collect::>()?))) } - fn variable_kinds_data( - self, - parameter_kinds: &Self::InternedVariableKinds, - ) -> &[chalk_ir::VariableKind] { + fn variable_kinds_data(self, parameter_kinds: &Self::InternedVariableKinds) -> &[VariableKind] { ¶meter_kinds.as_ref().0 } fn intern_canonical_var_kinds( self, - data: impl IntoIterator, E>>, + data: impl IntoIterator>, ) -> Result { Ok(Interned::new(InternedWrapper(data.into_iter().collect::>()?))) } @@ -379,30 +383,30 @@ impl chalk_ir::interner::Interner for Interner { fn canonical_var_kinds_data( self, canonical_var_kinds: &Self::InternedCanonicalVarKinds, - ) -> &[chalk_ir::CanonicalVarKind] { + ) -> &[CanonicalVarKind] { canonical_var_kinds } fn intern_constraints( self, - data: impl IntoIterator>, E>>, + data: impl IntoIterator, E>>, ) -> Result { data.into_iter().collect() } fn constraints_data( self, constraints: &Self::InternedConstraints, - ) -> &[chalk_ir::InEnvironment>] { + ) -> &[InEnvironment] { constraints } fn intern_variances( self, - data: impl IntoIterator>, + data: impl IntoIterator>, ) -> Result { - Ok(Interned::new(InternedWrapper(data.into_iter().collect::>()?))) + data.into_iter().collect::>() } - fn variances_data(self, variances: &Self::InternedVariances) -> &[chalk_ir::Variance] { + fn variances_data(self, variances: &Self::InternedVariances) -> &[Variance] { variances } } diff --git a/crates/hir-ty/src/lib.rs b/crates/hir-ty/src/lib.rs index cf174feed2..b60fbac5af 100644 --- a/crates/hir-ty/src/lib.rs +++ b/crates/hir-ty/src/lib.rs @@ -45,7 +45,7 @@ use chalk_ir::{ fold::{Shift, TypeFoldable}, interner::HasInterner, visit::{TypeSuperVisitable, TypeVisitable, TypeVisitor}, - NoSolution, TyData, + NoSolution, }; use either::Either; use hir_def::{hir::ExprId, type_ref::Rawness, GeneralConstId, TypeOrConstParamId}; @@ -152,10 +152,21 @@ pub type DomainGoal = chalk_ir::DomainGoal; pub type Goal = chalk_ir::Goal; pub type AliasEq = chalk_ir::AliasEq; pub type Solution = chalk_solve::Solution; +pub type Constraint = chalk_ir::Constraint; +pub type Constraints = chalk_ir::Constraints; pub type ConstrainedSubst = chalk_ir::ConstrainedSubst; pub type Guidance = chalk_solve::Guidance; pub type WhereClause = chalk_ir::WhereClause; +pub type CanonicalVarKind = chalk_ir::CanonicalVarKind; +pub type GoalData = chalk_ir::GoalData; +pub type Goals = chalk_ir::Goals; +pub type ProgramClauseData = chalk_ir::ProgramClauseData; +pub type ProgramClause = chalk_ir::ProgramClause; +pub type ProgramClauses = chalk_ir::ProgramClauses; +pub type TyData = chalk_ir::TyData; +pub type Variances = chalk_ir::Variances; + /// A constant can have reference to other things. Memory map job is holding /// the necessary bits of memory of the const eval session to keep the constant /// meaningful.