1 //! Walks the crate looking for items/impl-items/trait-items that have
2 //! either a `rustc_symbol_name` or `rustc_def_path` attribute and
3 //! generates an error giving, respectively, the symbol name or
4 //! def-path. This is used for unit testing the code that generates
5 //! paths etc in all kinds of annoying scenarios.
8 use rustc_hir
::def_id
::LocalDefId
;
9 use rustc_middle
::ty
::print
::with_no_trimmed_paths
;
10 use rustc_middle
::ty
::{subst::InternalSubsts, Instance, TyCtxt}
;
11 use rustc_span
::symbol
::{sym, Symbol}
;
13 const SYMBOL_NAME
: Symbol
= sym
::rustc_symbol_name
;
14 const DEF_PATH
: Symbol
= sym
::rustc_def_path
;
16 pub fn report_symbol_names(tcx
: TyCtxt
<'_
>) {
17 // if the `rustc_attrs` feature is not enabled, then the
18 // attributes we are interested in cannot be present anyway, so
20 if !tcx
.features().rustc_attrs
{
24 tcx
.dep_graph
.with_ignore(|| {
25 let mut visitor
= SymbolNamesTest { tcx }
;
26 tcx
.hir().krate().visit_all_item_likes(&mut visitor
);
30 struct SymbolNamesTest
<'tcx
> {
34 impl SymbolNamesTest
<'tcx
> {
35 fn process_attrs(&mut self, def_id
: LocalDefId
) {
37 for attr
in tcx
.get_attrs(def_id
.to_def_id()).iter() {
38 if tcx
.sess
.check_name(attr
, SYMBOL_NAME
) {
39 let def_id
= def_id
.to_def_id();
40 let instance
= Instance
::new(
42 tcx
.erase_regions(InternalSubsts
::identity_for_item(tcx
, def_id
)),
44 let mangled
= tcx
.symbol_name(instance
);
45 tcx
.sess
.span_err(attr
.span
, &format
!("symbol-name({})", mangled
));
46 if let Ok(demangling
) = rustc_demangle
::try_demangle(mangled
.name
) {
47 tcx
.sess
.span_err(attr
.span
, &format
!("demangling({})", demangling
));
48 tcx
.sess
.span_err(attr
.span
, &format
!("demangling-alt({:#})", demangling
));
50 } else if tcx
.sess
.check_name(attr
, DEF_PATH
) {
51 let path
= with_no_trimmed_paths(|| tcx
.def_path_str(def_id
.to_def_id()));
52 tcx
.sess
.span_err(attr
.span
, &format
!("def-path({})", path
));
55 // (*) The formatting of `tag({})` is chosen so that tests can elect
56 // to test the entirety of the string, if they choose, or else just
62 impl hir
::itemlikevisit
::ItemLikeVisitor
<'tcx
> for SymbolNamesTest
<'tcx
> {
63 fn visit_item(&mut self, item
: &'tcx hir
::Item
<'tcx
>) {
64 self.process_attrs(item
.def_id
);
67 fn visit_trait_item(&mut self, trait_item
: &'tcx hir
::TraitItem
<'tcx
>) {
68 self.process_attrs(trait_item
.def_id
);
71 fn visit_impl_item(&mut self, impl_item
: &'tcx hir
::ImplItem
<'tcx
>) {
72 self.process_attrs(impl_item
.def_id
);
75 fn visit_foreign_item(&mut self, foreign_item
: &'tcx hir
::ForeignItem
<'tcx
>) {
76 self.process_attrs(foreign_item
.def_id
);