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.
7 use crate::errors
::{Kind, TestOutput}
;
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 symbol_names
= SymbolNamesTest { tcx }
;
26 let crate_items
= tcx
.hir_crate_items(());
28 for id
in crate_items
.items() {
29 symbol_names
.process_attrs(id
.owner_id
.def_id
);
32 for id
in crate_items
.trait_items() {
33 symbol_names
.process_attrs(id
.owner_id
.def_id
);
36 for id
in crate_items
.impl_items() {
37 symbol_names
.process_attrs(id
.owner_id
.def_id
);
40 for id
in crate_items
.foreign_items() {
41 symbol_names
.process_attrs(id
.owner_id
.def_id
);
46 struct SymbolNamesTest
<'tcx
> {
50 impl SymbolNamesTest
<'_
> {
51 fn process_attrs(&mut self, def_id
: LocalDefId
) {
53 // The formatting of `tag({})` is chosen so that tests can elect
54 // to test the entirety of the string, if they choose, or else just
56 for attr
in tcx
.get_attrs(def_id
.to_def_id(), SYMBOL_NAME
) {
57 let def_id
= def_id
.to_def_id();
58 let instance
= Instance
::new(
60 tcx
.erase_regions(InternalSubsts
::identity_for_item(tcx
, def_id
)),
62 let mangled
= tcx
.symbol_name(instance
);
63 tcx
.sess
.emit_err(TestOutput
{
65 kind
: Kind
::SymbolName
,
66 content
: format
!("{mangled}"),
68 if let Ok(demangling
) = rustc_demangle
::try_demangle(mangled
.name
) {
69 tcx
.sess
.emit_err(TestOutput
{
71 kind
: Kind
::Demangling
,
72 content
: format
!("{demangling}"),
74 tcx
.sess
.emit_err(TestOutput
{
76 kind
: Kind
::DemanglingAlt
,
77 content
: format
!("{:#}", demangling
),
82 for attr
in tcx
.get_attrs(def_id
.to_def_id(), DEF_PATH
) {
83 tcx
.sess
.emit_err(TestOutput
{
86 content
: with_no_trimmed_paths
!(tcx
.def_path_str(def_id
.to_def_id())),