diff --git a/compiler/rustc_attr_parsing/src/attributes/test_attrs.rs b/compiler/rustc_attr_parsing/src/attributes/test_attrs.rs index 7f25641b948e2..ec7cdd3624dc3 100644 --- a/compiler/rustc_attr_parsing/src/attributes/test_attrs.rs +++ b/compiler/rustc_attr_parsing/src/attributes/test_attrs.rs @@ -91,3 +91,25 @@ impl SingleAttributeParser for ShouldPanicParser { }) } } + +pub(crate) struct RustcVarianceParser; + +impl NoArgsAttributeParser for RustcVarianceParser { + const PATH: &[Symbol] = &[sym::rustc_variance]; + const ON_DUPLICATE: OnDuplicate = OnDuplicate::Warn; + const ALLOWED_TARGETS: AllowedTargets = AllowedTargets::AllowList(&[ + Allow(Target::Struct), + Allow(Target::Enum), + Allow(Target::Union), + ]); + const CREATE: fn(Span) -> AttributeKind = |_| AttributeKind::RustcVariance; +} + +pub(crate) struct RustcVarianceOfOpaquesParser; + +impl NoArgsAttributeParser for RustcVarianceOfOpaquesParser { + const PATH: &[Symbol] = &[sym::rustc_variance_of_opaques]; + const ON_DUPLICATE: OnDuplicate = OnDuplicate::Warn; + const ALLOWED_TARGETS: AllowedTargets = AllowedTargets::AllowList(&[Allow(Target::Crate)]); + const CREATE: fn(Span) -> AttributeKind = |_| AttributeKind::RustcVarianceOfOpaques; +} diff --git a/compiler/rustc_attr_parsing/src/context.rs b/compiler/rustc_attr_parsing/src/context.rs index 6aae2b90a5045..26c1fc91aecf6 100644 --- a/compiler/rustc_attr_parsing/src/context.rs +++ b/compiler/rustc_attr_parsing/src/context.rs @@ -85,7 +85,9 @@ use crate::attributes::semantics::MayDangleParser; use crate::attributes::stability::{ BodyStabilityParser, ConstStabilityIndirectParser, ConstStabilityParser, StabilityParser, }; -use crate::attributes::test_attrs::{IgnoreParser, ShouldPanicParser}; +use crate::attributes::test_attrs::{ + IgnoreParser, RustcVarianceOfOpaquesParser, RustcVarianceParser, ShouldPanicParser, +}; use crate::attributes::traits::{ AllowIncoherentImplParser, CoinductiveParser, DenyExplicitImplParser, DoNotImplementViaObjectParser, FundamentalParser, MarkerParser, ParenSugarParser, @@ -300,6 +302,8 @@ attribute_parsers!( Single>, Single>, Single>, + Single>, + Single>, Single>, Single>, Single>, diff --git a/compiler/rustc_hir/src/attrs/data_structures.rs b/compiler/rustc_hir/src/attrs/data_structures.rs index 8d2baae703b8f..fe48e6f4fafd9 100644 --- a/compiler/rustc_hir/src/attrs/data_structures.rs +++ b/compiler/rustc_hir/src/attrs/data_structures.rs @@ -1007,6 +1007,12 @@ pub enum AttributeKind { /// Represents `#[rustc_simd_monomorphize_lane_limit = "N"]`. RustcSimdMonomorphizeLaneLimit(Limit), + /// Represents `#[rustc_variance]` + RustcVariance, + + /// Represents `#[rustc_variance_of_opaques]` + RustcVarianceOfOpaques, + /// Represents `#[sanitize]` /// /// the on set and off set are distjoint since there's a third option: unset. diff --git a/compiler/rustc_hir/src/attrs/encode_cross_crate.rs b/compiler/rustc_hir/src/attrs/encode_cross_crate.rs index fd764ad458b14..5b593778b75a1 100644 --- a/compiler/rustc_hir/src/attrs/encode_cross_crate.rs +++ b/compiler/rustc_hir/src/attrs/encode_cross_crate.rs @@ -129,6 +129,8 @@ impl AttributeKind { RustcScalableVector { .. } => Yes, RustcShouldNotBeCalledOnConstItems(..) => Yes, RustcSimdMonomorphizeLaneLimit(..) => Yes, // Affects layout computation, which needs to work cross-crate + RustcVariance => No, + RustcVarianceOfOpaques => No, Sanitize { .. } => No, ShouldPanic { .. } => No, SkipDuringMethodDispatch { .. } => No, diff --git a/compiler/rustc_hir_analysis/src/variance/dump.rs b/compiler/rustc_hir_analysis/src/variance/dump.rs index 31f0adf720d79..e625d9dfe3b5f 100644 --- a/compiler/rustc_hir_analysis/src/variance/dump.rs +++ b/compiler/rustc_hir_analysis/src/variance/dump.rs @@ -1,8 +1,9 @@ use std::fmt::Write; +use rustc_hir::attrs::AttributeKind; use rustc_hir::def_id::{CRATE_DEF_ID, LocalDefId}; +use rustc_hir::find_attr; use rustc_middle::ty::{GenericArgs, TyCtxt}; -use rustc_span::sym; fn format_variances(tcx: TyCtxt<'_>, def_id: LocalDefId) -> String { let variances = tcx.variances_of(def_id); @@ -25,7 +26,7 @@ fn format_variances(tcx: TyCtxt<'_>, def_id: LocalDefId) -> String { pub(crate) fn variances(tcx: TyCtxt<'_>) { let crate_items = tcx.hir_crate_items(()); - if tcx.has_attr(CRATE_DEF_ID, sym::rustc_variance_of_opaques) { + if find_attr!(tcx.get_all_attrs(CRATE_DEF_ID), AttributeKind::RustcVarianceOfOpaques) { for id in crate_items.opaques() { tcx.dcx().emit_err(crate::errors::VariancesOf { span: tcx.def_span(id), @@ -35,7 +36,7 @@ pub(crate) fn variances(tcx: TyCtxt<'_>) { } for id in crate_items.free_items() { - if !tcx.has_attr(id.owner_id, sym::rustc_variance) { + if !find_attr!(tcx.get_all_attrs(id.owner_id), AttributeKind::RustcVariance) { continue; } diff --git a/compiler/rustc_passes/src/check_attr.rs b/compiler/rustc_passes/src/check_attr.rs index 4266731cf0a22..d89a71c1deb63 100644 --- a/compiler/rustc_passes/src/check_attr.rs +++ b/compiler/rustc_passes/src/check_attr.rs @@ -274,6 +274,8 @@ impl<'tcx> CheckAttrVisitor<'tcx> { | AttributeKind::RustcScalableVector { .. } | AttributeKind::RustcSimdMonomorphizeLaneLimit(..) | AttributeKind::RustcShouldNotBeCalledOnConstItems(..) + | AttributeKind::RustcVariance + | AttributeKind::RustcVarianceOfOpaques | AttributeKind::ExportStable | AttributeKind::FfiConst(..) | AttributeKind::UnstableFeatureBound(..) @@ -378,8 +380,6 @@ impl<'tcx> CheckAttrVisitor<'tcx> { | sym::rustc_capture_analysis | sym::rustc_regions | sym::rustc_strict_coherence - | sym::rustc_variance - | sym::rustc_variance_of_opaques | sym::rustc_hidden_type_of_opaques | sym::rustc_mir | sym::rustc_effective_visibility diff --git a/tests/ui/feature-gates/feature-gate-rustc-attrs-1.rs b/tests/ui/feature-gates/feature-gate-rustc-attrs-1.rs index 17556723622ed..f3d5bcbd8d781 100644 --- a/tests/ui/feature-gates/feature-gate-rustc-attrs-1.rs +++ b/tests/ui/feature-gates/feature-gate-rustc-attrs-1.rs @@ -1,12 +1,14 @@ // Test that `#[rustc_*]` attributes are gated by `rustc_attrs` feature gate. -#[rustc_variance] -//~^ ERROR use of an internal attribute [E0658] -//~| NOTE the `#[rustc_variance]` attribute is an internal implementation detail that will never be stable -//~| NOTE the `#[rustc_variance]` attribute is used for rustc unit tests #[rustc_nonnull_optimization_guaranteed] //~^ ERROR use of an internal attribute [E0658] //~| NOTE the `#[rustc_nonnull_optimization_guaranteed]` attribute is an internal implementation detail that will never be stable //~| NOTE the `#[rustc_nonnull_optimization_guaranteed]` attribute is just used to document guaranteed niche optimizations in the standard library //~| NOTE the compiler does not even check whether the type indeed is being non-null-optimized; it is your responsibility to ensure that the attribute is only used on types that are optimized fn main() {} + +#[rustc_variance] +//~^ ERROR use of an internal attribute [E0658] +//~| NOTE the `#[rustc_variance]` attribute is an internal implementation detail that will never be stable +//~| NOTE the `#[rustc_variance]` attribute is used for rustc unit tests +enum E {} diff --git a/tests/ui/feature-gates/feature-gate-rustc-attrs-1.stderr b/tests/ui/feature-gates/feature-gate-rustc-attrs-1.stderr index 159d383e40891..6588229b7d56e 100644 --- a/tests/ui/feature-gates/feature-gate-rustc-attrs-1.stderr +++ b/tests/ui/feature-gates/feature-gate-rustc-attrs-1.stderr @@ -1,16 +1,6 @@ error[E0658]: use of an internal attribute --> $DIR/feature-gate-rustc-attrs-1.rs:3:1 | -LL | #[rustc_variance] - | ^^^^^^^^^^^^^^^^^ - | - = help: add `#![feature(rustc_attrs)]` to the crate attributes to enable - = note: the `#[rustc_variance]` attribute is an internal implementation detail that will never be stable - = note: the `#[rustc_variance]` attribute is used for rustc unit tests - -error[E0658]: use of an internal attribute - --> $DIR/feature-gate-rustc-attrs-1.rs:7:1 - | LL | #[rustc_nonnull_optimization_guaranteed] | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ | @@ -19,6 +9,16 @@ LL | #[rustc_nonnull_optimization_guaranteed] = note: the `#[rustc_nonnull_optimization_guaranteed]` attribute is just used to document guaranteed niche optimizations in the standard library = note: the compiler does not even check whether the type indeed is being non-null-optimized; it is your responsibility to ensure that the attribute is only used on types that are optimized +error[E0658]: use of an internal attribute + --> $DIR/feature-gate-rustc-attrs-1.rs:10:1 + | +LL | #[rustc_variance] + | ^^^^^^^^^^^^^^^^^ + | + = help: add `#![feature(rustc_attrs)]` to the crate attributes to enable + = note: the `#[rustc_variance]` attribute is an internal implementation detail that will never be stable + = note: the `#[rustc_variance]` attribute is used for rustc unit tests + error: aborting due to 2 previous errors For more information about this error, try `rustc --explain E0658`.