Auto merge of #139018 - oli-obk:incremental-trait-impls, r=compiler-errors
Various local trait item iteration cleanups
Adding a trait impl for `Foo` unconditionally affected all queries that are interested in a completely independent trait `Bar`. Perf has no effect on this. We probably don't have a good perf test for this tho.
r? `@compiler-errors`
I am unsure about https://github.com/rust-lang/rust/pull/139018/commits/9d05efb66f7b599eeacb5d2456f844fe4768e865 as it doesn't improve anything wrt incremental, because we still do all the checks for valid `Drop` impls, which subsequently will still invoke many queries and basically keep the depgraph the same.
I want to do
9549077a47/compiler/rustc_middle/src/ty/trait_def.rs (L141)
but would leave that to a follow-up PR, this one changes enough things as it is
This commit is contained in:
commit
ae9173d7dd
26 changed files with 96 additions and 93 deletions
|
@ -36,10 +36,8 @@ use crate::hir::def_id::{DefId, LocalDefId};
|
|||
/// cannot do `struct S<T>; impl<T:Clone> Drop for S<T> { ... }`).
|
||||
pub(crate) fn check_drop_impl(
|
||||
tcx: TyCtxt<'_>,
|
||||
drop_impl_did: DefId,
|
||||
drop_impl_did: LocalDefId,
|
||||
) -> Result<(), ErrorGuaranteed> {
|
||||
let drop_impl_did = drop_impl_did.expect_local();
|
||||
|
||||
match tcx.impl_polarity(drop_impl_did) {
|
||||
ty::ImplPolarity::Positive => {}
|
||||
ty::ImplPolarity::Negative => {
|
||||
|
@ -56,9 +54,9 @@ pub(crate) fn check_drop_impl(
|
|||
|
||||
tcx.ensure_ok().orphan_check_impl(drop_impl_did)?;
|
||||
|
||||
let dtor_impl_trait_ref = tcx.impl_trait_ref(drop_impl_did).unwrap().instantiate_identity();
|
||||
let self_ty = tcx.type_of(drop_impl_did).instantiate_identity();
|
||||
|
||||
match dtor_impl_trait_ref.self_ty().kind() {
|
||||
match self_ty.kind() {
|
||||
ty::Adt(adt_def, adt_to_impl_args) => {
|
||||
ensure_impl_params_and_item_params_correspond(
|
||||
tcx,
|
||||
|
|
|
@ -114,11 +114,11 @@ pub fn provide(providers: &mut Providers) {
|
|||
}
|
||||
|
||||
fn adt_destructor(tcx: TyCtxt<'_>, def_id: LocalDefId) -> Option<ty::Destructor> {
|
||||
tcx.calculate_dtor(def_id.to_def_id(), always_applicable::check_drop_impl)
|
||||
tcx.calculate_dtor(def_id, always_applicable::check_drop_impl)
|
||||
}
|
||||
|
||||
fn adt_async_destructor(tcx: TyCtxt<'_>, def_id: LocalDefId) -> Option<ty::AsyncDestructor> {
|
||||
tcx.calculate_async_dtor(def_id.to_def_id(), always_applicable::check_drop_impl)
|
||||
tcx.calculate_async_dtor(def_id, always_applicable::check_drop_impl)
|
||||
}
|
||||
|
||||
/// Given a `DefId` for an opaque type in return position, find its parent item's return
|
||||
|
|
|
@ -153,9 +153,12 @@ pub(crate) fn provide(providers: &mut Providers) {
|
|||
}
|
||||
|
||||
fn coherent_trait(tcx: TyCtxt<'_>, def_id: DefId) -> Result<(), ErrorGuaranteed> {
|
||||
let impls = tcx.local_trait_impls(def_id);
|
||||
// If there are no impls for the trait, then "all impls" are trivially coherent and we won't check anything
|
||||
// anyway. Thus we bail out even before the specialization graph, avoiding the dep_graph edge.
|
||||
let Some(impls) = tcx.all_local_trait_impls(()).get(&def_id) else { return Ok(()) };
|
||||
if impls.is_empty() {
|
||||
return Ok(());
|
||||
}
|
||||
// Trigger building the specialization graph for the trait. This will detect and report any
|
||||
// overlap errors.
|
||||
let mut res = tcx.ensure_ok().specialization_graph_of(def_id);
|
||||
|
|
|
@ -1730,25 +1730,23 @@ impl<'tcx> dyn HirTyLowerer<'tcx> + '_ {
|
|||
.is_accessible_from(self.item_def_id(), tcx)
|
||||
&& tcx.all_impls(*trait_def_id)
|
||||
.any(|impl_def_id| {
|
||||
let impl_header = tcx.impl_trait_header(impl_def_id);
|
||||
impl_header.is_some_and(|header| {
|
||||
let trait_ref = header.trait_ref.instantiate(
|
||||
tcx,
|
||||
infcx.fresh_args_for_item(DUMMY_SP, impl_def_id),
|
||||
);
|
||||
let header = tcx.impl_trait_header(impl_def_id).unwrap();
|
||||
let trait_ref = header.trait_ref.instantiate(
|
||||
tcx,
|
||||
infcx.fresh_args_for_item(DUMMY_SP, impl_def_id),
|
||||
);
|
||||
|
||||
let value = fold_regions(tcx, qself_ty, |_, _| tcx.lifetimes.re_erased);
|
||||
// FIXME: Don't bother dealing with non-lifetime binders here...
|
||||
if value.has_escaping_bound_vars() {
|
||||
return false;
|
||||
}
|
||||
infcx
|
||||
.can_eq(
|
||||
ty::ParamEnv::empty(),
|
||||
trait_ref.self_ty(),
|
||||
value,
|
||||
) && header.polarity != ty::ImplPolarity::Negative
|
||||
})
|
||||
let value = fold_regions(tcx, qself_ty, |_, _| tcx.lifetimes.re_erased);
|
||||
// FIXME: Don't bother dealing with non-lifetime binders here...
|
||||
if value.has_escaping_bound_vars() {
|
||||
return false;
|
||||
}
|
||||
infcx
|
||||
.can_eq(
|
||||
ty::ParamEnv::empty(),
|
||||
trait_ref.self_ty(),
|
||||
value,
|
||||
) && header.polarity != ty::ImplPolarity::Negative
|
||||
})
|
||||
})
|
||||
.map(|trait_def_id| tcx.def_path_str(trait_def_id))
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue