rustc_hir_analysis/variance/
dump.rs1use std::fmt::Write;
2
3use rustc_hir::def_id::LocalDefId;
4use rustc_hir::find_attr;
5use rustc_middle::ty::{GenericArgs, TyCtxt};
6
7fn format_variances(tcx: TyCtxt<'_>, def_id: LocalDefId) -> String {
8 let variances = tcx.variances_of(def_id);
9 let generics = GenericArgs::identity_for_item(tcx, def_id);
10 let mut ret = String::with_capacity(2 + 7 * variances.len());
12 ret.push('[');
13 for (arg, variance) in generics.iter().zip(variances.iter()) {
14 ret.write_fmt(format_args!("{0}: {1:?}, ", arg, variance))write!(ret, "{arg}: {variance:?}, ").unwrap();
15 }
16 if !variances.is_empty() {
18 ret.pop();
19 ret.pop();
20 }
21 ret.push(']');
22 ret
23}
24
25pub(crate) fn variances(tcx: TyCtxt<'_>) {
26 let crate_items = tcx.hir_crate_items(());
27
28 if {
'done:
{
for i in tcx.hir_krate_attrs() {
#[allow(unused_imports)]
use rustc_hir::attrs::AttributeKind::*;
let i: &rustc_hir::Attribute = i;
match i {
rustc_hir::Attribute::Parsed(RustcVarianceOfOpaques) => {
break 'done Some(());
}
rustc_hir::Attribute::Unparsed(..) =>
{}
#[deny(unreachable_patterns)]
_ => {}
}
}
None
}
}.is_some()find_attr!(tcx, crate, RustcVarianceOfOpaques) {
29 for id in crate_items.opaques() {
30 tcx.dcx().emit_err(crate::errors::VariancesOf {
31 span: tcx.def_span(id),
32 variances: format_variances(tcx, id),
33 });
34 }
35 }
36
37 for id in crate_items.free_items() {
38 if !{
#[allow(deprecated)]
{
{
'done:
{
for i in tcx.get_all_attrs(id.owner_id) {
#[allow(unused_imports)]
use rustc_hir::attrs::AttributeKind::*;
let i: &rustc_hir::Attribute = i;
match i {
rustc_hir::Attribute::Parsed(RustcVariance) => {
break 'done Some(());
}
rustc_hir::Attribute::Unparsed(..) =>
{}
#[deny(unreachable_patterns)]
_ => {}
}
}
None
}
}
}
}.is_some()find_attr!(tcx, id.owner_id, RustcVariance) {
39 continue;
40 }
41
42 tcx.dcx().emit_err(crate::errors::VariancesOf {
43 span: tcx.def_span(id.owner_id),
44 variances: format_variances(tcx, id.owner_id.def_id),
45 });
46 }
47}