mirror of
https://github.com/rust-lang/rust-analyzer.git
synced 2025-09-29 21:35:20 +00:00
Merge #6376
6376: Avoid impls_fnonce to return true when the trait solving is ambiguous r=flodiebold a=GrayJack This PR should fix #6375 This adds a variation of `method_resolution::implements_trait` called `method_resolution::implements_trait_unique`, that only returns true when the trait solving is unique, and also change `impls_fnonce` to use the later instead. I also added a test just to be sure. Co-authored-by: GrayJack <gr41.j4ck@gmail.com>
This commit is contained in:
commit
8cfc1cd95b
4 changed files with 26 additions and 1 deletions
|
@ -1398,7 +1398,7 @@ impl Type {
|
||||||
};
|
};
|
||||||
|
|
||||||
let canonical_ty = Canonical { value: self.ty.value.clone(), kinds: Arc::new([]) };
|
let canonical_ty = Canonical { value: self.ty.value.clone(), kinds: Arc::new([]) };
|
||||||
method_resolution::implements_trait(
|
method_resolution::implements_trait_unique(
|
||||||
&canonical_ty,
|
&canonical_ty,
|
||||||
db,
|
db,
|
||||||
self.ty.environment.clone(),
|
self.ty.environment.clone(),
|
||||||
|
|
|
@ -740,6 +740,19 @@ pub fn implements_trait(
|
||||||
solution.is_some()
|
solution.is_some()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub fn implements_trait_unique(
|
||||||
|
ty: &Canonical<Ty>,
|
||||||
|
db: &dyn HirDatabase,
|
||||||
|
env: Arc<TraitEnvironment>,
|
||||||
|
krate: CrateId,
|
||||||
|
trait_: TraitId,
|
||||||
|
) -> bool {
|
||||||
|
let goal = generic_implements_goal(db, env, trait_, ty.clone());
|
||||||
|
let solution = db.trait_solve(krate, goal);
|
||||||
|
|
||||||
|
matches!(solution, Some(crate::traits::Solution::Unique(_)))
|
||||||
|
}
|
||||||
|
|
||||||
/// This creates Substs for a trait with the given Self type and type variables
|
/// This creates Substs for a trait with the given Self type and type variables
|
||||||
/// for all other parameters, to query Chalk with it.
|
/// for all other parameters, to query Chalk with it.
|
||||||
fn generic_implements_goal(
|
fn generic_implements_goal(
|
||||||
|
|
|
@ -115,6 +115,12 @@ pre { color: #DCDCCC; background: #3F3F3F; font-size: 22px; padd
|
||||||
<span class="value_param callable">f</span><span class="punctuation">(</span><span class="punctuation">)</span>
|
<span class="value_param callable">f</span><span class="punctuation">(</span><span class="punctuation">)</span>
|
||||||
<span class="punctuation">}</span>
|
<span class="punctuation">}</span>
|
||||||
|
|
||||||
|
<span class="keyword">fn</span> <span class="function declaration">foobar</span><span class="punctuation">(</span><span class="punctuation">)</span> <span class="operator">-></span> <span class="keyword">impl</span> <span class="unresolved_reference">Copy</span> <span class="punctuation">{</span><span class="punctuation">}</span>
|
||||||
|
|
||||||
|
<span class="keyword">fn</span> <span class="function declaration">foo</span><span class="punctuation">(</span><span class="punctuation">)</span> <span class="punctuation">{</span>
|
||||||
|
<span class="keyword">let</span> <span class="variable declaration">bar</span> <span class="operator">=</span> <span class="function">foobar</span><span class="punctuation">(</span><span class="punctuation">)</span><span class="punctuation">;</span>
|
||||||
|
<span class="punctuation">}</span>
|
||||||
|
|
||||||
<span class="macro">macro_rules!</span> <span class="macro declaration">def_fn</span> <span class="punctuation">{</span>
|
<span class="macro">macro_rules!</span> <span class="macro declaration">def_fn</span> <span class="punctuation">{</span>
|
||||||
<span class="punctuation">(</span><span class="punctuation">$</span><span class="punctuation">(</span><span class="punctuation">$</span>tt<span class="punctuation">:</span>tt<span class="punctuation">)</span><span class="punctuation">*</span><span class="punctuation">)</span> <span class="operator">=</span><span class="punctuation">></span> <span class="punctuation">{</span><span class="punctuation">$</span><span class="punctuation">(</span><span class="punctuation">$</span>tt<span class="punctuation">)</span><span class="punctuation">*</span><span class="punctuation">}</span>
|
<span class="punctuation">(</span><span class="punctuation">$</span><span class="punctuation">(</span><span class="punctuation">$</span>tt<span class="punctuation">:</span>tt<span class="punctuation">)</span><span class="punctuation">*</span><span class="punctuation">)</span> <span class="operator">=</span><span class="punctuation">></span> <span class="punctuation">{</span><span class="punctuation">$</span><span class="punctuation">(</span><span class="punctuation">$</span>tt<span class="punctuation">)</span><span class="punctuation">*</span><span class="punctuation">}</span>
|
||||||
<span class="punctuation">}</span>
|
<span class="punctuation">}</span>
|
||||||
|
|
|
@ -89,6 +89,12 @@ fn baz<F: Fn() -> ()>(f: F) {
|
||||||
f()
|
f()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn foobar() -> impl Copy {}
|
||||||
|
|
||||||
|
fn foo() {
|
||||||
|
let bar = foobar();
|
||||||
|
}
|
||||||
|
|
||||||
macro_rules! def_fn {
|
macro_rules! def_fn {
|
||||||
($($tt:tt)*) => {$($tt)*}
|
($($tt:tt)*) => {$($tt)*}
|
||||||
}
|
}
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue