Skip to content

Commit bd2b210

Browse files
committed
Remove CheckConstTraitVisitor
Signed-off-by: Miguel Guarniz <[email protected]>
1 parent a7d6408 commit bd2b210

File tree

1 file changed

+54
-68
lines changed

1 file changed

+54
-68
lines changed

compiler/rustc_passes/src/check_const.rs

Lines changed: 54 additions & 68 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@
1010
use rustc_attr as attr;
1111
use rustc_errors::struct_span_err;
1212
use rustc_hir as hir;
13+
use rustc_hir::def::DefKind;
1314
use rustc_hir::def_id::LocalDefId;
1415
use rustc_hir::intravisit::{self, Visitor};
1516
use rustc_middle::hir::nested_filter;
@@ -58,88 +59,73 @@ impl NonConstExpr {
5859
fn check_mod_const_bodies(tcx: TyCtxt<'_>, module_def_id: LocalDefId) {
5960
let mut vis = CheckConstVisitor::new(tcx);
6061
tcx.hir().visit_item_likes_in_module(module_def_id, &mut vis.as_deep_visitor());
61-
tcx.hir().visit_item_likes_in_module(module_def_id, &mut CheckConstTraitVisitor::new(tcx));
62+
for id in tcx.hir_module_items(module_def_id).items() {
63+
check_item(tcx, id);
64+
}
6265
}
6366

6467
pub(crate) fn provide(providers: &mut Providers) {
6568
*providers = Providers { check_mod_const_bodies, ..*providers };
6669
}
6770

68-
struct CheckConstTraitVisitor<'tcx> {
69-
tcx: TyCtxt<'tcx>,
70-
}
71+
fn check_item<'tcx>(tcx: TyCtxt<'tcx>, id: hir::ItemId) {
72+
let _: Option<_> = try {
73+
if !matches!(tcx.hir().def_kind(id.def_id), DefKind::Impl) {
74+
None?
75+
}
7176

72-
impl<'tcx> CheckConstTraitVisitor<'tcx> {
73-
fn new(tcx: TyCtxt<'tcx>) -> Self {
74-
CheckConstTraitVisitor { tcx }
75-
}
76-
}
77+
let item = tcx.hir().item(id);
78+
if let hir::ItemKind::Impl(ref imp) = item.kind && let hir::Constness::Const = imp.constness {
79+
let trait_def_id = imp.of_trait.as_ref()?.trait_def_id()?;
80+
let ancestors = tcx
81+
.trait_def(trait_def_id)
82+
.ancestors(tcx, item.def_id.to_def_id())
83+
.ok()?;
84+
let mut to_implement = Vec::new();
7785

78-
impl<'tcx> hir::itemlikevisit::ItemLikeVisitor<'tcx> for CheckConstTraitVisitor<'tcx> {
79-
/// check for const trait impls, and errors if the impl uses provided/default functions
80-
/// of the trait being implemented; as those provided functions can be non-const.
81-
fn visit_item<'hir>(&mut self, item: &'hir hir::Item<'hir>) {
82-
let _: Option<_> = try {
83-
if let hir::ItemKind::Impl(ref imp) = item.kind && let hir::Constness::Const = imp.constness {
84-
let trait_def_id = imp.of_trait.as_ref()?.trait_def_id()?;
85-
let ancestors = self
86-
.tcx
87-
.trait_def(trait_def_id)
88-
.ancestors(self.tcx, item.def_id.to_def_id())
89-
.ok()?;
90-
let mut to_implement = Vec::new();
91-
92-
for trait_item in self.tcx.associated_items(trait_def_id).in_definition_order()
86+
for trait_item in tcx.associated_items(trait_def_id).in_definition_order()
87+
{
88+
if let ty::AssocItem {
89+
kind: ty::AssocKind::Fn,
90+
defaultness,
91+
def_id: trait_item_id,
92+
..
93+
} = *trait_item
94+
{
95+
// we can ignore functions that do not have default bodies:
96+
// if those are unimplemented it will be caught by typeck.
97+
if !defaultness.has_value()
98+
|| tcx
99+
.has_attr(trait_item_id, sym::default_method_body_is_const)
93100
{
94-
if let ty::AssocItem {
95-
kind: ty::AssocKind::Fn,
96-
defaultness,
97-
def_id: trait_item_id,
98-
..
99-
} = *trait_item
100-
{
101-
// we can ignore functions that do not have default bodies:
102-
// if those are unimplemented it will be caught by typeck.
103-
if !defaultness.has_value()
104-
|| self
105-
.tcx
106-
.has_attr(trait_item_id, sym::default_method_body_is_const)
107-
{
108-
continue;
109-
}
110-
111-
let is_implemented = ancestors
112-
.leaf_def(self.tcx, trait_item_id)
113-
.map(|node_item| !node_item.defining_node.is_from_trait())
114-
.unwrap_or(false);
115-
116-
if !is_implemented {
117-
to_implement.push(self.tcx.item_name(trait_item_id).to_string());
118-
}
119-
}
101+
continue;
120102
}
121103

122-
// all nonconst trait functions (not marked with #[default_method_body_is_const])
123-
// must be implemented
124-
if !to_implement.is_empty() {
125-
self.tcx
126-
.sess
127-
.struct_span_err(
128-
item.span,
129-
"const trait implementations may not use non-const default functions",
130-
)
131-
.note(&format!("`{}` not implemented", to_implement.join("`, `")))
132-
.emit();
104+
let is_implemented = ancestors
105+
.leaf_def(tcx, trait_item_id)
106+
.map(|node_item| !node_item.defining_node.is_from_trait())
107+
.unwrap_or(false);
108+
109+
if !is_implemented {
110+
to_implement.push(tcx.item_name(trait_item_id).to_string());
133111
}
112+
}
134113
}
135-
};
136-
}
137114

138-
fn visit_trait_item<'hir>(&mut self, _: &'hir hir::TraitItem<'hir>) {}
139-
140-
fn visit_impl_item<'hir>(&mut self, _: &'hir hir::ImplItem<'hir>) {}
141-
142-
fn visit_foreign_item<'hir>(&mut self, _: &'hir hir::ForeignItem<'hir>) {}
115+
// all nonconst trait functions (not marked with #[default_method_body_is_const])
116+
// must be implemented
117+
if !to_implement.is_empty() {
118+
tcx
119+
.sess
120+
.struct_span_err(
121+
item.span,
122+
"const trait implementations may not use non-const default functions",
123+
)
124+
.note(&format!("`{}` not implemented", to_implement.join("`, `")))
125+
.emit();
126+
}
127+
}
128+
};
143129
}
144130

145131
#[derive(Copy, Clone)]

0 commit comments

Comments
 (0)