Skip to content

Commit 14f2524

Browse files
committed
Replace #[rustc_do_not_implement_via_object] with #[rustc_dyn_incompatible_trait], which makes the marked trait dyn-incompatible.
Removes the attribute from `MetaSized` and `PointeeSized`, with a special case in the trait solvers for `MetaSized`. `dyn MetaSized` is a perfectly cromulent type, and seems to only have had #[rustc_do_not_implement_via_object] so the builtin object candidate does not overlap with the builtin MetaSized impl that all `dyn` types get. Resolves this with a special case by checking `is_sizedness_trait` where the trait solvers previously checked `implement_via_object`. `dyn PointeeSized` alone is rejected for other reasons (since `dyn PointeeSized` is considered to have no principal trait because `PointeeSized` is removed at an earlier stage of the compiler), but `(dyn PointeeSized + Send)` is valid and equivalent to `dyn Send`.
1 parent 1279939 commit 14f2524

35 files changed

Lines changed: 384 additions & 155 deletions

File tree

compiler/rustc_attr_parsing/src/attributes/traits.rs

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -94,12 +94,12 @@ impl<S: Stage> NoArgsAttributeParser<S> for DenyExplicitImplParser {
9494
const CREATE: fn(Span) -> AttributeKind = AttributeKind::DenyExplicitImpl;
9595
}
9696

97-
pub(crate) struct DoNotImplementViaObjectParser;
98-
impl<S: Stage> NoArgsAttributeParser<S> for DoNotImplementViaObjectParser {
99-
const PATH: &[Symbol] = &[sym::rustc_do_not_implement_via_object];
97+
pub(crate) struct DynIncompatibleTraitParser;
98+
impl<S: Stage> NoArgsAttributeParser<S> for DynIncompatibleTraitParser {
99+
const PATH: &[Symbol] = &[sym::rustc_dyn_incompatible_trait];
100100
const ON_DUPLICATE: OnDuplicate<S> = OnDuplicate::Error;
101101
const ALLOWED_TARGETS: AllowedTargets = AllowedTargets::AllowList(&[Allow(Target::Trait)]);
102-
const CREATE: fn(Span) -> AttributeKind = AttributeKind::DoNotImplementViaObject;
102+
const CREATE: fn(Span) -> AttributeKind = AttributeKind::DynIncompatibleTrait;
103103
}
104104

105105
// Specialization

compiler/rustc_attr_parsing/src/context.rs

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -77,8 +77,8 @@ use crate::attributes::stability::{
7777
use crate::attributes::test_attrs::{IgnoreParser, ShouldPanicParser};
7878
use crate::attributes::traits::{
7979
AllowIncoherentImplParser, CoinductiveParser, DenyExplicitImplParser,
80-
DoNotImplementViaObjectParser, FundamentalParser, MarkerParser, ParenSugarParser,
81-
PointeeParser, SkipDuringMethodDispatchParser, SpecializationTraitParser, TypeConstParser,
80+
DynIncompatibleTraitParser, FundamentalParser, MarkerParser, ParenSugarParser, PointeeParser,
81+
SkipDuringMethodDispatchParser, SpecializationTraitParser, TypeConstParser,
8282
UnsafeSpecializationMarkerParser,
8383
};
8484
use crate::attributes::transparency::TransparencyParser;
@@ -240,7 +240,7 @@ attribute_parsers!(
240240
Single<WithoutArgs<ConstStabilityIndirectParser>>,
241241
Single<WithoutArgs<CoroutineParser>>,
242242
Single<WithoutArgs<DenyExplicitImplParser>>,
243-
Single<WithoutArgs<DoNotImplementViaObjectParser>>,
243+
Single<WithoutArgs<DynIncompatibleTraitParser>>,
244244
Single<WithoutArgs<EiiExternItemParser>>,
245245
Single<WithoutArgs<ExportStableParser>>,
246246
Single<WithoutArgs<FfiConstParser>>,

compiler/rustc_feature/src/builtin_attrs.rs

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1321,13 +1321,13 @@ pub static BUILTIN_ATTRIBUTES: &[BuiltinAttribute] = &[
13211321
"`#[rustc_deny_explicit_impl]` enforces that a trait can have no user-provided impls"
13221322
),
13231323
rustc_attr!(
1324-
rustc_do_not_implement_via_object,
1324+
rustc_dyn_incompatible_trait,
13251325
AttributeType::Normal,
13261326
template!(Word),
13271327
ErrorFollowing,
13281328
EncodeCrossCrate::No,
1329-
"`#[rustc_do_not_implement_via_object]` opts out of the automatic trait impl for trait objects \
1330-
(`impl Trait for dyn Trait`)"
1329+
"`#[rustc_dyn_incompatible_trait]` marks a trait as dyn-incompatible, \
1330+
even if it otherwise satisfies the requirements to be dyn-compatible."
13311331
),
13321332
rustc_attr!(
13331333
rustc_has_incoherent_inherent_impls, AttributeType::Normal, template!(Word),

compiler/rustc_hir/src/attrs/data_structures.rs

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -705,9 +705,6 @@ pub enum AttributeKind {
705705
/// Represents [`#[deprecated]`](https://doc.rust-lang.org/stable/reference/attributes/diagnostics.html#the-deprecated-attribute).
706706
Deprecation { deprecation: Deprecation, span: Span },
707707

708-
/// Represents `#[rustc_do_not_implement_via_object]`.
709-
DoNotImplementViaObject(Span),
710-
711708
/// Represents [`#[doc]`](https://doc.rust-lang.org/stable/rustdoc/write-documentation/the-doc-attribute.html).
712709
/// Represents all other uses of the [`#[doc]`](https://doc.rust-lang.org/stable/rustdoc/write-documentation/the-doc-attribute.html)
713710
/// attribute.
@@ -720,6 +717,9 @@ pub enum AttributeKind {
720717
/// Represents `#[rustc_dummy]`.
721718
Dummy,
722719

720+
/// Represents `#[rustc_dyn_incompatible_trait]`.
721+
DynIncompatibleTrait(Span),
722+
723723
/// Implementation detail of `#[eii]`
724724
EiiExternItem,
725725

compiler/rustc_hir/src/attrs/encode_cross_crate.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -42,10 +42,10 @@ impl AttributeKind {
4242
DebuggerVisualizer(..) => No,
4343
DenyExplicitImpl(..) => No,
4444
Deprecation { .. } => Yes,
45-
DoNotImplementViaObject(..) => No,
4645
Doc(_) => Yes,
4746
DocComment { .. } => Yes,
4847
Dummy => No,
48+
DynIncompatibleTrait(..) => No,
4949
EiiExternItem => No,
5050
EiiExternTarget(_) => Yes,
5151
EiiImpls(..) => No,

compiler/rustc_hir_analysis/src/coherence/mod.rs

Lines changed: 1 addition & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -211,9 +211,7 @@ fn check_object_overlap<'tcx>(
211211
// This is a WF error tested by `coherence-impl-trait-for-trait-dyn-compatible.rs`.
212212
} else {
213213
let mut supertrait_def_ids = elaborate::supertrait_def_ids(tcx, component_def_id);
214-
if supertrait_def_ids
215-
.any(|d| d == trait_def_id && tcx.trait_def(d).implement_via_object)
216-
{
214+
if supertrait_def_ids.any(|d| d == trait_def_id) {
217215
let span = tcx.def_span(impl_def_id);
218216
return Err(struct_span_code_err!(
219217
tcx.dcx(),

compiler/rustc_hir_analysis/src/collect.rs

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -926,7 +926,8 @@ fn trait_def(tcx: TyCtxt<'_>, def_id: LocalDefId) -> ty::TraitDef {
926926
);
927927

928928
let deny_explicit_impl = find_attr!(attrs, AttributeKind::DenyExplicitImpl(_));
929-
let implement_via_object = !find_attr!(attrs, AttributeKind::DoNotImplementViaObject(_));
929+
let force_dyn_incompatible =
930+
find_attr!(attrs, AttributeKind::DynIncompatibleTrait(span) => *span);
930931

931932
ty::TraitDef {
932933
def_id: def_id.to_def_id(),
@@ -941,7 +942,7 @@ fn trait_def(tcx: TyCtxt<'_>, def_id: LocalDefId) -> ty::TraitDef {
941942
skip_boxed_slice_during_method_dispatch,
942943
specialization_kind,
943944
must_implement_one_of,
944-
implement_via_object,
945+
force_dyn_incompatible,
945946
deny_explicit_impl,
946947
}
947948
}

compiler/rustc_middle/src/traits/mod.rs

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -764,6 +764,9 @@ pub enum DynCompatibilityViolation {
764764
/// `Self: Sized` declared on the trait.
765765
SizedSelf(SmallVec<[Span; 1]>),
766766

767+
/// Trait is marked `#[rustc_dyn_incompatible_trait]`.
768+
ExplicitlyDynIncompatible(SmallVec<[Span; 1]>),
769+
767770
/// Supertrait reference references `Self` an in illegal location
768771
/// (e.g., `trait Foo : Bar<Self>`).
769772
SupertraitSelf(SmallVec<[Span; 1]>),
@@ -788,6 +791,9 @@ impl DynCompatibilityViolation {
788791
pub fn error_msg(&self) -> Cow<'static, str> {
789792
match self {
790793
DynCompatibilityViolation::SizedSelf(_) => "it requires `Self: Sized`".into(),
794+
DynCompatibilityViolation::ExplicitlyDynIncompatible(_) => {
795+
"it opted out of dyn-compatibility".into()
796+
}
791797
DynCompatibilityViolation::SupertraitSelf(spans) => {
792798
if spans.iter().any(|sp| *sp != DUMMY_SP) {
793799
"it uses `Self` as a type parameter".into()
@@ -861,6 +867,7 @@ impl DynCompatibilityViolation {
861867
pub fn solution(&self) -> DynCompatibilityViolationSolution {
862868
match self {
863869
DynCompatibilityViolation::SizedSelf(_)
870+
| DynCompatibilityViolation::ExplicitlyDynIncompatible(_)
864871
| DynCompatibilityViolation::SupertraitSelf(_)
865872
| DynCompatibilityViolation::SupertraitNonLifetimeBinder(..)
866873
| DynCompatibilityViolation::SupertraitConst(_) => {
@@ -894,6 +901,7 @@ impl DynCompatibilityViolation {
894901
match self {
895902
DynCompatibilityViolation::SupertraitSelf(spans)
896903
| DynCompatibilityViolation::SizedSelf(spans)
904+
| DynCompatibilityViolation::ExplicitlyDynIncompatible(spans)
897905
| DynCompatibilityViolation::SupertraitNonLifetimeBinder(spans)
898906
| DynCompatibilityViolation::SupertraitConst(spans) => spans.clone(),
899907
DynCompatibilityViolation::AssocConst(_, span)

compiler/rustc_middle/src/ty/context.rs

Lines changed: 0 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -710,10 +710,6 @@ impl<'tcx> Interner for TyCtxt<'tcx> {
710710
self.trait_def(def_id).is_fundamental
711711
}
712712

713-
fn trait_may_be_implemented_via_object(self, trait_def_id: DefId) -> bool {
714-
self.trait_def(trait_def_id).implement_via_object
715-
}
716-
717713
fn trait_is_unsafe(self, trait_def_id: Self::DefId) -> bool {
718714
self.trait_def(trait_def_id).safety.is_unsafe()
719715
}

compiler/rustc_middle/src/ty/trait_def.rs

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@ use rustc_hir::def::DefKind;
77
use rustc_hir::def_id::{DefId, LOCAL_CRATE};
88
use rustc_hir::{self as hir, find_attr};
99
use rustc_macros::{Decodable, Encodable, HashStable};
10+
use rustc_span::Span;
1011
use tracing::debug;
1112

1213
use crate::query::LocalCrate;
@@ -69,10 +70,9 @@ pub struct TraitDef {
6970
/// must be implemented.
7071
pub must_implement_one_of: Option<Box<[Ident]>>,
7172

72-
/// Whether to add a builtin `dyn Trait: Trait` implementation.
73-
/// This is enabled for all traits except ones marked with
74-
/// `#[rustc_do_not_implement_via_object]`.
75-
pub implement_via_object: bool,
73+
/// Whether the trait should be considered dyn-incompatible, even if it otherwise
74+
/// satisfies the requirements to be dyn-compatible.
75+
pub force_dyn_incompatible: Option<Span>,
7676

7777
/// Whether a trait is fully built-in, and any implementation is disallowed.
7878
/// This only applies to built-in traits, and is marked via

0 commit comments

Comments
 (0)