Push resolver further up
This commit is contained in:
parent
7ec62ea5e6
commit
21c5fd8b1b
@ -358,10 +358,17 @@ impl SourceAnalyzer {
|
||||
// FIXME check that?
|
||||
// FIXME replace Unknown by bound vars here
|
||||
let canonical = Canonical { value: ty.ty.value.clone(), num_vars: 0 };
|
||||
|
||||
let env = TraitEnvironment::lower(db, &self.resolver);
|
||||
let krate = self.resolver.krate()?;
|
||||
let traits_in_scope = self.resolver.traits_in_scope(db);
|
||||
|
||||
method_resolution::iterate_method_candidates(
|
||||
&canonical,
|
||||
db,
|
||||
&self.resolver,
|
||||
env,
|
||||
krate,
|
||||
&traits_in_scope,
|
||||
name,
|
||||
method_resolution::LookupMode::MethodCall,
|
||||
|ty, it| match it {
|
||||
@ -382,10 +389,17 @@ impl SourceAnalyzer {
|
||||
// FIXME check that?
|
||||
// FIXME replace Unknown by bound vars here
|
||||
let canonical = Canonical { value: ty.ty.value.clone(), num_vars: 0 };
|
||||
|
||||
let env = TraitEnvironment::lower(db, &self.resolver);
|
||||
let krate = self.resolver.krate()?;
|
||||
let traits_in_scope = self.resolver.traits_in_scope(db);
|
||||
|
||||
method_resolution::iterate_method_candidates(
|
||||
&canonical,
|
||||
db,
|
||||
&self.resolver,
|
||||
env,
|
||||
krate,
|
||||
&traits_in_scope,
|
||||
name,
|
||||
method_resolution::LookupMode::Path,
|
||||
|ty, it| callback(ty, it.into()),
|
||||
|
@ -569,12 +569,19 @@ impl<'a, D: HirDatabase> InferenceContext<'a, D> {
|
||||
) -> Ty {
|
||||
let receiver_ty = self.infer_expr(receiver, &Expectation::none());
|
||||
let canonicalized_receiver = self.canonicalizer().canonicalize_ty(receiver_ty.clone());
|
||||
let resolved = method_resolution::lookup_method(
|
||||
&canonicalized_receiver.value,
|
||||
self.db,
|
||||
method_name,
|
||||
&self.resolver,
|
||||
);
|
||||
|
||||
let traits_in_scope = self.resolver.traits_in_scope(self.db);
|
||||
|
||||
let resolved = self.resolver.krate().and_then(|krate| {
|
||||
method_resolution::lookup_method(
|
||||
&canonicalized_receiver.value,
|
||||
self.db,
|
||||
self.trait_env.clone(),
|
||||
krate,
|
||||
&traits_in_scope,
|
||||
method_name,
|
||||
)
|
||||
});
|
||||
let (derefed_receiver_ty, method_ty, def_generics) = match resolved {
|
||||
Some((ty, func)) => {
|
||||
let ty = canonicalized_receiver.decanonicalize_ty(ty);
|
||||
|
@ -11,7 +11,7 @@ use hir_expand::name::Name;
|
||||
|
||||
use crate::{db::HirDatabase, method_resolution, Substs, Ty, TypeWalk, ValueTyDefId};
|
||||
|
||||
use super::{ExprOrPatId, InferenceContext, TraitRef};
|
||||
use super::{ExprOrPatId, InferenceContext, TraitEnvironment, TraitRef};
|
||||
|
||||
impl<'a, D: HirDatabase> InferenceContext<'a, D> {
|
||||
pub(super) fn infer_path(
|
||||
@ -193,11 +193,16 @@ impl<'a, D: HirDatabase> InferenceContext<'a, D> {
|
||||
}
|
||||
|
||||
let canonical_ty = self.canonicalizer().canonicalize_ty(ty.clone());
|
||||
let env = TraitEnvironment::lower(self.db, &self.resolver);
|
||||
let krate = self.resolver.krate()?;
|
||||
let traits_in_scope = self.resolver.traits_in_scope(self.db);
|
||||
|
||||
method_resolution::iterate_method_candidates(
|
||||
&canonical_ty.value,
|
||||
self.db,
|
||||
&self.resolver.clone(),
|
||||
env,
|
||||
krate,
|
||||
&traits_in_scope,
|
||||
Some(name),
|
||||
method_resolution::LookupMode::Path,
|
||||
move |_ty, item| {
|
||||
|
@ -6,8 +6,8 @@ use std::sync::Arc;
|
||||
|
||||
use arrayvec::ArrayVec;
|
||||
use hir_def::{
|
||||
lang_item::LangItemTarget, resolver::Resolver, type_ref::Mutability, AssocContainerId,
|
||||
AssocItemId, FunctionId, HasModule, ImplId, Lookup, TraitId,
|
||||
lang_item::LangItemTarget, type_ref::Mutability, AssocContainerId, AssocItemId, FunctionId,
|
||||
HasModule, ImplId, Lookup, TraitId,
|
||||
};
|
||||
use hir_expand::name::Name;
|
||||
use ra_db::CrateId;
|
||||
@ -144,14 +144,24 @@ impl Ty {
|
||||
pub(crate) fn lookup_method(
|
||||
ty: &Canonical<Ty>,
|
||||
db: &impl HirDatabase,
|
||||
env: Arc<TraitEnvironment>,
|
||||
krate: CrateId,
|
||||
traits_in_scope: &FxHashSet<TraitId>,
|
||||
name: &Name,
|
||||
resolver: &Resolver,
|
||||
) -> Option<(Ty, FunctionId)> {
|
||||
iterate_method_candidates(ty, db, resolver, Some(name), LookupMode::MethodCall, |ty, f| match f
|
||||
{
|
||||
AssocItemId::FunctionId(f) => Some((ty.clone(), f)),
|
||||
_ => None,
|
||||
})
|
||||
iterate_method_candidates(
|
||||
ty,
|
||||
db,
|
||||
env,
|
||||
krate,
|
||||
&traits_in_scope,
|
||||
Some(name),
|
||||
LookupMode::MethodCall,
|
||||
|ty, f| match f {
|
||||
AssocItemId::FunctionId(f) => Some((ty.clone(), f)),
|
||||
_ => None,
|
||||
},
|
||||
)
|
||||
}
|
||||
|
||||
/// Whether we're looking up a dotted method call (like `v.len()`) or a path
|
||||
@ -172,14 +182,13 @@ pub enum LookupMode {
|
||||
pub fn iterate_method_candidates<T>(
|
||||
ty: &Canonical<Ty>,
|
||||
db: &impl HirDatabase,
|
||||
resolver: &Resolver,
|
||||
env: Arc<TraitEnvironment>,
|
||||
krate: CrateId,
|
||||
traits_in_scope: &FxHashSet<TraitId>,
|
||||
name: Option<&Name>,
|
||||
mode: LookupMode,
|
||||
mut callback: impl FnMut(&Ty, AssocItemId) -> Option<T>,
|
||||
) -> Option<T> {
|
||||
let traits_in_scope = resolver.traits_in_scope(db);
|
||||
let krate = resolver.krate()?;
|
||||
let env = TraitEnvironment::lower(db, resolver);
|
||||
match mode {
|
||||
LookupMode::MethodCall => {
|
||||
// For method calls, rust first does any number of autoderef, and then one
|
||||
@ -190,9 +199,7 @@ pub fn iterate_method_candidates<T>(
|
||||
// Also note that when we've got a receiver like &S, even if the method we
|
||||
// find in the end takes &self, we still do the autoderef step (just as
|
||||
// rustc does an autoderef and then autoref again).
|
||||
let environment = TraitEnvironment::lower(db, resolver);
|
||||
let ty = InEnvironment { value: ty.clone(), environment };
|
||||
let krate = resolver.krate()?;
|
||||
let ty = InEnvironment { value: ty.clone(), environment: env.clone() };
|
||||
|
||||
// We have to be careful about the order we're looking at candidates
|
||||
// in here. Consider the case where we're resolving `x.clone()`
|
||||
@ -214,7 +221,7 @@ pub fn iterate_method_candidates<T>(
|
||||
db,
|
||||
env.clone(),
|
||||
krate,
|
||||
&traits_in_scope,
|
||||
traits_in_scope,
|
||||
name,
|
||||
&mut callback,
|
||||
) {
|
||||
@ -230,7 +237,7 @@ pub fn iterate_method_candidates<T>(
|
||||
db,
|
||||
env,
|
||||
krate,
|
||||
&traits_in_scope,
|
||||
traits_in_scope,
|
||||
name,
|
||||
&mut callback,
|
||||
)
|
||||
|
Loading…
x
Reference in New Issue
Block a user