Do not fetch HIR to monomorphize impls.

This commit is contained in:
Camille GILLOT 2023-02-12 19:46:51 +00:00
parent facecf6e1b
commit 0d39f9d94d

View File

@ -1191,28 +1191,14 @@ impl<'v> RootCollector<'_, 'v> {
fn process_item(&mut self, id: hir::ItemId) {
match self.tcx.def_kind(id.owner_id) {
DefKind::Enum | DefKind::Struct | DefKind::Union => {
let item = self.tcx.hir().item(id);
match item.kind {
hir::ItemKind::Enum(_, ref generics)
| hir::ItemKind::Struct(_, ref generics)
| hir::ItemKind::Union(_, ref generics) => {
if generics.params.is_empty() {
if self.mode == MonoItemCollectionMode::Eager {
debug!(
"RootCollector: ADT drop-glue for {}",
self.tcx.def_path_str(item.owner_id.to_def_id())
);
if self.tcx.generics_of(id.owner_id).count() == 0
&& self.mode == MonoItemCollectionMode::Eager
{
debug!("RootCollector: ADT drop-glue for `{id:?}`",);
let ty = Instance::new(
item.owner_id.to_def_id(),
InternalSubsts::empty(),
)
.ty(self.tcx, ty::ParamEnv::reveal_all());
visit_drop_use(self.tcx, ty, true, DUMMY_SP, self.output);
}
}
}
_ => bug!(),
let ty =
self.tcx.bound_type_of(id.owner_id.to_def_id()).no_bound_vars().unwrap();
visit_drop_use(self.tcx, ty, true, DUMMY_SP, self.output);
}
}
DefKind::GlobalAsm => {
@ -1240,8 +1226,7 @@ impl<'v> RootCollector<'_, 'v> {
}
DefKind::Impl { .. } => {
if self.mode == MonoItemCollectionMode::Eager {
let item = self.tcx.hir().item(id);
create_mono_items_for_default_impls(self.tcx, item, self.output);
create_mono_items_for_default_impls(self.tcx, id, self.output);
}
}
DefKind::Fn => {
@ -1326,66 +1311,51 @@ fn item_requires_monomorphization(tcx: TyCtxt<'_>, def_id: LocalDefId) -> bool {
generics.requires_monomorphization(tcx)
}
#[instrument(level = "debug", skip(tcx, output))]
fn create_mono_items_for_default_impls<'tcx>(
tcx: TyCtxt<'tcx>,
item: &'tcx hir::Item<'tcx>,
item: hir::ItemId,
output: &mut MonoItems<'tcx>,
) {
match item.kind {
hir::ItemKind::Impl(ref impl_) => {
if matches!(impl_.polarity, hir::ImplPolarity::Negative(_)) {
return;
}
let polarity = tcx.impl_polarity(item.owner_id);
if matches!(polarity, ty::ImplPolarity::Negative) {
return;
}
for param in impl_.generics.params {
match param.kind {
hir::GenericParamKind::Lifetime { .. } => {}
hir::GenericParamKind::Type { .. } | hir::GenericParamKind::Const { .. } => {
return;
}
}
}
if tcx.generics_of(item.owner_id).own_requires_monomorphization() {
return;
}
debug!(
"create_mono_items_for_default_impls(item={})",
tcx.def_path_str(item.owner_id.to_def_id())
);
let Some(trait_ref) = tcx.impl_trait_ref(item.owner_id) else {
return;
};
if let Some(trait_ref) = tcx.impl_trait_ref(item.owner_id) {
let trait_ref = trait_ref.subst_identity();
let trait_ref = trait_ref.subst_identity();
let param_env = ty::ParamEnv::reveal_all();
let trait_ref = tcx.normalize_erasing_regions(param_env, trait_ref);
let overridden_methods = tcx.impl_item_implementor_ids(item.owner_id);
for method in tcx.provided_trait_methods(trait_ref.def_id) {
if overridden_methods.contains_key(&method.def_id) {
continue;
}
if tcx.generics_of(method.def_id).own_requires_monomorphization() {
continue;
}
let substs =
InternalSubsts::for_item(tcx, method.def_id, |param, _| match param.kind {
GenericParamDefKind::Lifetime => tcx.lifetimes.re_erased.into(),
GenericParamDefKind::Type { .. }
| GenericParamDefKind::Const { .. } => {
trait_ref.substs[param.index as usize]
}
});
let instance =
ty::Instance::expect_resolve(tcx, param_env, method.def_id, substs);
let mono_item = create_fn_mono_item(tcx, instance, DUMMY_SP);
if mono_item.node.is_instantiable(tcx) && should_codegen_locally(tcx, &instance)
{
output.push(mono_item);
}
}
}
let param_env = ty::ParamEnv::reveal_all();
let trait_ref = tcx.normalize_erasing_regions(param_env, trait_ref);
let overridden_methods = tcx.impl_item_implementor_ids(item.owner_id);
for method in tcx.provided_trait_methods(trait_ref.def_id) {
if overridden_methods.contains_key(&method.def_id) {
continue;
}
if tcx.generics_of(method.def_id).own_requires_monomorphization() {
continue;
}
let substs = InternalSubsts::for_item(tcx, method.def_id, |param, _| match param.kind {
GenericParamDefKind::Lifetime => tcx.lifetimes.re_erased.into(),
GenericParamDefKind::Type { .. } | GenericParamDefKind::Const { .. } => {
trait_ref.substs[param.index as usize]
}
});
let instance = ty::Instance::expect_resolve(tcx, param_env, method.def_id, substs);
let mono_item = create_fn_mono_item(tcx, instance, DUMMY_SP);
if mono_item.node.is_instantiable(tcx) && should_codegen_locally(tcx, &instance) {
output.push(mono_item);
}
_ => bug!(),
}
}