mirror of
https://github.com/rust-lang/rust-analyzer
synced 2024-12-26 13:03:31 +00:00
Decouple
This commit is contained in:
parent
d770f22c53
commit
cace49e9a7
5 changed files with 42 additions and 45 deletions
|
@ -945,7 +945,7 @@ impl ImplBlock {
|
|||
}
|
||||
pub fn for_trait(db: &impl HirDatabase, krate: Crate, trait_: Trait) -> Vec<ImplBlock> {
|
||||
let impls = db.impls_in_crate(krate.crate_id);
|
||||
impls.lookup_impl_blocks_for_trait(trait_).map(Self::from).collect()
|
||||
impls.lookup_impl_blocks_for_trait(trait_.id).map(Self::from).collect()
|
||||
}
|
||||
|
||||
pub fn target_trait(&self, db: &impl DefDatabase) -> Option<TypeRef> {
|
||||
|
|
|
@ -2,6 +2,7 @@
|
|||
|
||||
use std::sync::Arc;
|
||||
|
||||
use hir_def::{GenericDefId, LocalStructFieldId, TraitId, VariantId};
|
||||
use ra_arena::map::ArenaMap;
|
||||
use ra_db::{salsa, CrateId};
|
||||
|
||||
|
@ -12,19 +13,15 @@ use crate::{
|
|||
CallableDef, FnSig, GenericPredicate, InferenceResult, Substs, Ty, TyDefId, TypeCtor,
|
||||
ValueTyDefId,
|
||||
},
|
||||
Crate, DefWithBody, ImplBlock, Trait,
|
||||
Crate, DefWithBody, ImplBlock,
|
||||
};
|
||||
|
||||
pub use hir_def::{
|
||||
db::{
|
||||
BodyQuery, BodyWithSourceMapQuery, ConstDataQuery, CrateDefMapQuery, CrateLangItemsQuery,
|
||||
DefDatabase, DefDatabaseStorage, DocumentationQuery, EnumDataQuery, ExprScopesQuery,
|
||||
FunctionDataQuery, GenericParamsQuery, ImplDataQuery, InternDatabase,
|
||||
InternDatabaseStorage, LangItemQuery, ModuleLangItemsQuery, RawItemsQuery,
|
||||
RawItemsWithSourceMapQuery, StaticDataQuery, StructDataQuery, TraitDataQuery,
|
||||
TypeAliasDataQuery,
|
||||
},
|
||||
GenericDefId, LocalStructFieldId, VariantId,
|
||||
pub use hir_def::db::{
|
||||
BodyQuery, BodyWithSourceMapQuery, ConstDataQuery, CrateDefMapQuery, CrateLangItemsQuery,
|
||||
DefDatabase, DefDatabaseStorage, DocumentationQuery, EnumDataQuery, ExprScopesQuery,
|
||||
FunctionDataQuery, GenericParamsQuery, ImplDataQuery, InternDatabase, InternDatabaseStorage,
|
||||
LangItemQuery, ModuleLangItemsQuery, RawItemsQuery, RawItemsWithSourceMapQuery,
|
||||
StaticDataQuery, StructDataQuery, TraitDataQuery, TypeAliasDataQuery,
|
||||
};
|
||||
pub use hir_expand::db::{
|
||||
AstDatabase, AstDatabaseStorage, AstIdMapQuery, MacroArgQuery, MacroDefQuery, MacroExpandQuery,
|
||||
|
@ -66,7 +63,7 @@ pub trait HirDatabase: DefDatabase {
|
|||
fn impls_in_crate(&self, krate: CrateId) -> Arc<CrateImplBlocks>;
|
||||
|
||||
#[salsa::invoke(crate::ty::traits::impls_for_trait_query)]
|
||||
fn impls_for_trait(&self, krate: Crate, trait_: Trait) -> Arc<[ImplBlock]>;
|
||||
fn impls_for_trait(&self, krate: CrateId, trait_: TraitId) -> Arc<[ImplBlock]>;
|
||||
|
||||
/// This provides the Chalk trait solver instance. Because Chalk always
|
||||
/// works from a specific crate, this query is keyed on the crate; and
|
||||
|
|
|
@ -6,9 +6,10 @@ use std::sync::Arc;
|
|||
|
||||
use arrayvec::ArrayVec;
|
||||
use hir_def::{
|
||||
lang_item::LangItemTarget, resolver::HasResolver, resolver::Resolver, AssocItemId, AstItemDef,
|
||||
HasModule, ImplId, TraitId,
|
||||
lang_item::LangItemTarget, resolver::HasResolver, resolver::Resolver, type_ref::Mutability,
|
||||
AssocItemId, AstItemDef, HasModule, ImplId, TraitId,
|
||||
};
|
||||
use hir_expand::name::Name;
|
||||
use ra_db::CrateId;
|
||||
use ra_prof::profile;
|
||||
use rustc_hash::FxHashMap;
|
||||
|
@ -17,7 +18,7 @@ use crate::{
|
|||
db::HirDatabase,
|
||||
ty::primitive::{FloatBitness, Uncertain},
|
||||
ty::{utils::all_super_traits, Ty, TypeCtor},
|
||||
AssocItem, Crate, Function, Mutability, Name, Trait,
|
||||
AssocItem, Function,
|
||||
};
|
||||
|
||||
use super::{autoderef, Canonical, InEnvironment, TraitEnvironment, TraitRef};
|
||||
|
@ -87,8 +88,8 @@ impl CrateImplBlocks {
|
|||
fingerprint.and_then(|f| self.impls.get(&f)).into_iter().flatten().copied()
|
||||
}
|
||||
|
||||
pub fn lookup_impl_blocks_for_trait(&self, tr: Trait) -> impl Iterator<Item = ImplId> + '_ {
|
||||
self.impls_by_trait.get(&tr.id).into_iter().flatten().copied()
|
||||
pub fn lookup_impl_blocks_for_trait(&self, tr: TraitId) -> impl Iterator<Item = ImplId> + '_ {
|
||||
self.impls_by_trait.get(&tr).into_iter().flatten().copied()
|
||||
}
|
||||
|
||||
pub fn all_impls<'a>(&'a self) -> impl Iterator<Item = ImplId> + 'a {
|
||||
|
@ -96,14 +97,18 @@ impl CrateImplBlocks {
|
|||
}
|
||||
}
|
||||
|
||||
fn def_crates(db: &impl HirDatabase, cur_crate: Crate, ty: &Ty) -> Option<ArrayVec<[Crate; 2]>> {
|
||||
fn def_crates(
|
||||
db: &impl HirDatabase,
|
||||
cur_crate: CrateId,
|
||||
ty: &Ty,
|
||||
) -> Option<ArrayVec<[CrateId; 2]>> {
|
||||
// Types like slice can have inherent impls in several crates, (core and alloc).
|
||||
// The corresponding impls are marked with lang items, so we can use them to find the required crates.
|
||||
macro_rules! lang_item_crate {
|
||||
($($name:expr),+ $(,)?) => {{
|
||||
let mut v = ArrayVec::<[LangItemTarget; 2]>::new();
|
||||
$(
|
||||
v.extend(db.lang_item(cur_crate.crate_id, $name.into()));
|
||||
v.extend(db.lang_item(cur_crate, $name.into()));
|
||||
)+
|
||||
v
|
||||
}};
|
||||
|
@ -112,7 +117,7 @@ fn def_crates(db: &impl HirDatabase, cur_crate: Crate, ty: &Ty) -> Option<ArrayV
|
|||
let lang_item_targets = match ty {
|
||||
Ty::Apply(a_ty) => match a_ty.ctor {
|
||||
TypeCtor::Adt(def_id) => {
|
||||
return Some(std::iter::once(def_id.module(db).krate.into()).collect())
|
||||
return Some(std::iter::once(def_id.module(db).krate).collect())
|
||||
}
|
||||
TypeCtor::Bool => lang_item_crate!("bool"),
|
||||
TypeCtor::Char => lang_item_crate!("char"),
|
||||
|
@ -136,7 +141,7 @@ fn def_crates(db: &impl HirDatabase, cur_crate: Crate, ty: &Ty) -> Option<ArrayV
|
|||
LangItemTarget::ImplBlockId(it) => Some(it),
|
||||
_ => None,
|
||||
})
|
||||
.map(|it| it.module(db).krate.into())
|
||||
.map(|it| it.module(db).krate)
|
||||
.collect();
|
||||
Some(res)
|
||||
}
|
||||
|
@ -193,14 +198,9 @@ pub(crate) fn iterate_method_candidates<T>(
|
|||
let environment = TraitEnvironment::lower(db, resolver);
|
||||
let ty = InEnvironment { value: ty.clone(), environment };
|
||||
for derefed_ty in autoderef::autoderef(db, resolver.krate(), ty) {
|
||||
if let Some(result) = iterate_inherent_methods(
|
||||
&derefed_ty,
|
||||
db,
|
||||
name,
|
||||
mode,
|
||||
krate.into(),
|
||||
&mut callback,
|
||||
) {
|
||||
if let Some(result) =
|
||||
iterate_inherent_methods(&derefed_ty, db, name, mode, krate, &mut callback)
|
||||
{
|
||||
return Some(result);
|
||||
}
|
||||
if let Some(result) = iterate_trait_method_candidates(
|
||||
|
@ -283,11 +283,11 @@ fn iterate_inherent_methods<T>(
|
|||
db: &impl HirDatabase,
|
||||
name: Option<&Name>,
|
||||
mode: LookupMode,
|
||||
krate: Crate,
|
||||
krate: CrateId,
|
||||
mut callback: impl FnMut(&Ty, AssocItem) -> Option<T>,
|
||||
) -> Option<T> {
|
||||
for krate in def_crates(db, krate, &ty.value)? {
|
||||
let impls = db.impls_in_crate(krate.crate_id);
|
||||
let impls = db.impls_in_crate(krate);
|
||||
|
||||
for impl_block in impls.lookup_impl_blocks(&ty.value) {
|
||||
for &item in db.impl_data(impl_block).items.iter() {
|
||||
|
@ -327,7 +327,7 @@ pub(crate) fn implements_trait(
|
|||
ty: &Canonical<Ty>,
|
||||
db: &impl HirDatabase,
|
||||
resolver: &Resolver,
|
||||
krate: Crate,
|
||||
krate: CrateId,
|
||||
trait_: TraitId,
|
||||
) -> bool {
|
||||
if ty.value.inherent_trait() == Some(trait_) {
|
||||
|
@ -337,7 +337,7 @@ pub(crate) fn implements_trait(
|
|||
}
|
||||
let env = TraitEnvironment::lower(db, resolver);
|
||||
let goal = generic_implements_goal(db, env, trait_, ty.clone());
|
||||
let solution = db.trait_solve(krate, goal);
|
||||
let solution = db.trait_solve(krate.into(), goal);
|
||||
|
||||
solution.is_some()
|
||||
}
|
||||
|
@ -348,11 +348,11 @@ impl Ty {
|
|||
pub fn iterate_impl_items<T>(
|
||||
self,
|
||||
db: &impl HirDatabase,
|
||||
krate: Crate,
|
||||
krate: CrateId,
|
||||
mut callback: impl FnMut(AssocItem) -> Option<T>,
|
||||
) -> Option<T> {
|
||||
for krate in def_crates(db, krate, &self)? {
|
||||
let impls = db.impls_in_crate(krate.crate_id);
|
||||
let impls = db.impls_in_crate(krate);
|
||||
|
||||
for impl_block in impls.lookup_impl_blocks(&self) {
|
||||
for &item in db.impl_data(impl_block).items.iter() {
|
||||
|
|
|
@ -2,13 +2,13 @@
|
|||
use std::sync::{Arc, Mutex};
|
||||
|
||||
use chalk_ir::{cast::Cast, family::ChalkIr};
|
||||
use hir_def::{expr::ExprId, DefWithBodyId};
|
||||
use hir_def::{expr::ExprId, DefWithBodyId, TraitId};
|
||||
use log::debug;
|
||||
use ra_db::{impl_intern_key, salsa};
|
||||
use ra_db::{impl_intern_key, salsa, CrateId};
|
||||
use ra_prof::profile;
|
||||
use rustc_hash::FxHashSet;
|
||||
|
||||
use crate::{db::HirDatabase, Crate, ImplBlock, Trait, TypeAlias};
|
||||
use crate::{db::HirDatabase, Crate, ImplBlock, TypeAlias};
|
||||
|
||||
use super::{Canonical, GenericPredicate, HirDisplay, ProjectionTy, TraitRef, Ty, TypeWalk};
|
||||
|
||||
|
@ -77,8 +77,8 @@ pub(crate) fn trait_solver_query(
|
|||
/// Collects impls for the given trait in the whole dependency tree of `krate`.
|
||||
pub(crate) fn impls_for_trait_query(
|
||||
db: &impl HirDatabase,
|
||||
krate: Crate,
|
||||
trait_: Trait,
|
||||
krate: CrateId,
|
||||
trait_: TraitId,
|
||||
) -> Arc<[ImplBlock]> {
|
||||
let mut impls = FxHashSet::default();
|
||||
// We call the query recursively here. On the one hand, this means we can
|
||||
|
@ -86,10 +86,10 @@ pub(crate) fn impls_for_trait_query(
|
|||
// will only ever get called for a few crates near the root of the tree (the
|
||||
// ones the user is editing), so this may actually be a waste of memory. I'm
|
||||
// doing it like this mainly for simplicity for now.
|
||||
for dep in krate.dependencies(db) {
|
||||
impls.extend(db.impls_for_trait(dep.krate, trait_).iter());
|
||||
for dep in db.crate_graph().dependencies(krate) {
|
||||
impls.extend(db.impls_for_trait(dep.crate_id, trait_).iter());
|
||||
}
|
||||
let crate_impl_blocks = db.impls_in_crate(krate.crate_id);
|
||||
let crate_impl_blocks = db.impls_in_crate(krate);
|
||||
impls.extend(crate_impl_blocks.lookup_impl_blocks_for_trait(trait_).map(ImplBlock::from));
|
||||
impls.into_iter().collect()
|
||||
}
|
||||
|
|
|
@ -448,7 +448,7 @@ where
|
|||
let trait_: TraitId = from_chalk(self.db, trait_id);
|
||||
let mut result: Vec<_> = self
|
||||
.db
|
||||
.impls_for_trait(self.krate, trait_.into())
|
||||
.impls_for_trait(self.krate.crate_id, trait_.into())
|
||||
.iter()
|
||||
.copied()
|
||||
.map(Impl::ImplBlock)
|
||||
|
|
Loading…
Reference in a new issue