Skip to content

Commit fcd67f1

Browse files
authored
Rollup merge of rust-lang#134367 - WaffleLapkin:trait_upcasting_as_a_treat, r=compiler-errors
Stabilize `feature(trait_upcasting)` This feature was "done" for a while now, I think it's finally time to stabilize it! Stabilization report: rust-lang#134367 (comment). cc reference PR: rust-lang/reference#1622. Closes rust-lang#65991 (tracking issue), closes rust-lang#89460 (the lint is no longer future incompat). r? compiler-errors
2 parents f37c190 + 4915995 commit fcd67f1

File tree

94 files changed

+140
-479
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

94 files changed

+140
-479
lines changed

Diff for: compiler/rustc_feature/src/accepted.rs

+3
Original file line numberDiff line numberDiff line change
@@ -400,6 +400,9 @@ declare_features! (
400400
/// Allows `#[track_caller]` to be used which provides
401401
/// accurate caller location reporting during panic (RFC 2091).
402402
(accepted, track_caller, "1.46.0", Some(47809)),
403+
/// Allows dyn upcasting trait objects via supertraits.
404+
/// Dyn upcasting is casting, e.g., `dyn Foo -> dyn Bar` where `Foo: Bar`.
405+
(accepted, trait_upcasting, "CURRENT_RUSTC_VERSION", Some(65991)),
403406
/// Allows #[repr(transparent)] on univariant enums (RFC 2645).
404407
(accepted, transparent_enums, "1.42.0", Some(60405)),
405408
/// Allows indexing tuples.

Diff for: compiler/rustc_feature/src/unstable.rs

-3
Original file line numberDiff line numberDiff line change
@@ -634,9 +634,6 @@ declare_features! (
634634
(unstable, thread_local, "1.0.0", Some(29594)),
635635
/// Allows defining `trait X = A + B;` alias items.
636636
(unstable, trait_alias, "1.24.0", Some(41517)),
637-
/// Allows dyn upcasting trait objects via supertraits.
638-
/// Dyn upcasting is casting, e.g., `dyn Foo -> dyn Bar` where `Foo: Bar`.
639-
(unstable, trait_upcasting, "1.56.0", Some(65991)),
640637
/// Allows for transmuting between arrays with sizes that contain generic consts.
641638
(unstable, transmute_generic_consts, "1.70.0", Some(109929)),
642639
/// Allows #[repr(transparent)] on unions (RFC 2645).

Diff for: compiler/rustc_hir_typeck/src/coercion.rs

-23
Original file line numberDiff line numberDiff line change
@@ -605,7 +605,6 @@ impl<'f, 'tcx> Coerce<'f, 'tcx> {
605605
)];
606606

607607
let mut has_unsized_tuple_coercion = false;
608-
let mut has_trait_upcasting_coercion = None;
609608

610609
// Keep resolving `CoerceUnsized` and `Unsize` predicates to avoid
611610
// emitting a coercion in cases like `Foo<$1>` -> `Foo<$2>`, where
@@ -690,13 +689,6 @@ impl<'f, 'tcx> Coerce<'f, 'tcx> {
690689
// these here and emit a feature error if coercion doesn't fail
691690
// due to another reason.
692691
match impl_source {
693-
traits::ImplSource::Builtin(
694-
BuiltinImplSource::TraitUpcasting { .. },
695-
_,
696-
) => {
697-
has_trait_upcasting_coercion =
698-
Some((trait_pred.self_ty(), trait_pred.trait_ref.args.type_at(1)));
699-
}
700692
traits::ImplSource::Builtin(BuiltinImplSource::TupleUnsizing, _) => {
701693
has_unsized_tuple_coercion = true;
702694
}
@@ -707,21 +699,6 @@ impl<'f, 'tcx> Coerce<'f, 'tcx> {
707699
}
708700
}
709701

710-
if let Some((sub, sup)) = has_trait_upcasting_coercion
711-
&& !self.tcx().features().trait_upcasting()
712-
{
713-
// Renders better when we erase regions, since they're not really the point here.
714-
let (sub, sup) = self.tcx.erase_regions((sub, sup));
715-
let mut err = feature_err(
716-
&self.tcx.sess,
717-
sym::trait_upcasting,
718-
self.cause.span,
719-
format!("cannot cast `{sub}` to `{sup}`, trait upcasting coercion is experimental"),
720-
);
721-
err.note(format!("required when coercing `{source}` into `{target}`"));
722-
err.emit();
723-
}
724-
725702
if has_unsized_tuple_coercion && !self.tcx.features().unsized_tuple_coercion() {
726703
feature_err(
727704
&self.tcx.sess,

Diff for: compiler/rustc_lint/src/deref_into_dyn_supertrait.rs

+12-13
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,5 @@
11
use rustc_hir::{self as hir, LangItem};
22
use rustc_middle::ty;
3-
use rustc_session::lint::FutureIncompatibilityReason;
43
use rustc_session::{declare_lint, declare_lint_pass};
54
use rustc_span::sym;
65
use rustc_trait_selection::traits::supertraits;
@@ -9,11 +8,12 @@ use crate::lints::{SupertraitAsDerefTarget, SupertraitAsDerefTargetLabel};
98
use crate::{LateContext, LateLintPass, LintContext};
109

1110
declare_lint! {
12-
/// The `deref_into_dyn_supertrait` lint is output whenever there is a use of the
13-
/// `Deref` implementation with a `dyn SuperTrait` type as `Output`.
11+
/// The `deref_into_dyn_supertrait` lint is emitted whenever there is a `Deref` implementation
12+
/// for `dyn SubTrait` with a `dyn SuperTrait` type as the `Output` type.
1413
///
15-
/// These implementations will become shadowed when the `trait_upcasting` feature is stabilized.
16-
/// The `deref` functions will no longer be called implicitly, so there might be behavior change.
14+
/// These implementations are "shadowed" by trait upcasting (stabilized since
15+
/// CURRENT_RUSTC_VERSION). The `deref` functions is no longer called implicitly, which might
16+
/// change behavior compared to previous rustc versions.
1717
///
1818
/// ### Example
1919
///
@@ -43,15 +43,14 @@ declare_lint! {
4343
///
4444
/// ### Explanation
4545
///
46-
/// The dyn upcasting coercion feature adds new coercion rules, taking priority
47-
/// over certain other coercion rules, which will cause some behavior change.
46+
/// The trait upcasting coercion added a new coercion rule, taking priority over certain other
47+
/// coercion rules, which causes some behavior change compared to older `rustc` versions.
48+
///
49+
/// `deref` can be still called explicitly, it just isn't called as part of a deref coercion
50+
/// (since trait upcasting coercion takes priority).
4851
pub DEREF_INTO_DYN_SUPERTRAIT,
49-
Warn,
50-
"`Deref` implementation usage with a supertrait trait object for output might be shadowed in the future",
51-
@future_incompatible = FutureIncompatibleInfo {
52-
reason: FutureIncompatibilityReason::FutureReleaseSemanticsChange,
53-
reference: "issue #89460 <https://github.com/rust-lang/rust/issues/89460>",
54-
};
52+
Allow,
53+
"`Deref` implementation with a supertrait trait object for output is shadowed by trait upcasting",
5554
}
5655

5756
declare_lint_pass!(DerefIntoDynSupertrait => [DEREF_INTO_DYN_SUPERTRAIT]);

Diff for: compiler/rustc_lint/src/lib.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@
2121
2222
// tidy-alphabetical-start
2323
#![allow(internal_features)]
24+
#![cfg_attr(bootstrap, feature(trait_upcasting))]
2425
#![doc(html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/")]
2526
#![doc(rust_logo)]
2627
#![feature(array_windows)]
@@ -32,7 +33,6 @@
3233
#![feature(let_chains)]
3334
#![feature(rustc_attrs)]
3435
#![feature(rustdoc_internals)]
35-
#![feature(trait_upcasting)]
3636
#![warn(unreachable_pub)]
3737
// tidy-alphabetical-end
3838

Diff for: compiler/rustc_middle/src/lib.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -29,6 +29,7 @@
2929
#![allow(rustc::diagnostic_outside_of_impl)]
3030
#![allow(rustc::potential_query_instability)]
3131
#![allow(rustc::untranslatable_diagnostic)]
32+
#![cfg_attr(bootstrap, feature(trait_upcasting))]
3233
#![doc(html_root_url = "https://doc.rust-lang.org/nightly/nightly-rustc/")]
3334
#![doc(rust_logo)]
3435
#![feature(allocator_api)]
@@ -56,7 +57,6 @@
5657
#![feature(ptr_alignment_type)]
5758
#![feature(rustc_attrs)]
5859
#![feature(rustdoc_internals)]
59-
#![feature(trait_upcasting)]
6060
#![feature(trusted_len)]
6161
#![feature(try_blocks)]
6262
#![feature(try_trait_v2)]

Diff for: compiler/rustc_trait_selection/src/traits/select/candidate_assembly.rs

+1-62
Original file line numberDiff line numberDiff line change
@@ -12,9 +12,7 @@ use hir::LangItem;
1212
use hir::def_id::DefId;
1313
use rustc_data_structures::fx::{FxHashSet, FxIndexSet};
1414
use rustc_hir as hir;
15-
use rustc_infer::traits::{
16-
Obligation, ObligationCause, PolyTraitObligation, PredicateObligations, SelectionError,
17-
};
15+
use rustc_infer::traits::{Obligation, PolyTraitObligation, SelectionError};
1816
use rustc_middle::ty::fast_reject::DeepRejectCtxt;
1917
use rustc_middle::ty::{self, Ty, TypeVisitableExt, TypingMode};
2018
use rustc_middle::{bug, span_bug};
@@ -23,8 +21,6 @@ use tracing::{debug, instrument, trace};
2321

2422
use super::SelectionCandidate::*;
2523
use super::{BuiltinImplConditions, SelectionCandidateSet, SelectionContext, TraitObligationStack};
26-
use crate::traits;
27-
use crate::traits::query::evaluate_obligation::InferCtxtExt;
2824
use crate::traits::util;
2925

3026
impl<'cx, 'tcx> SelectionContext<'cx, 'tcx> {
@@ -904,54 +900,6 @@ impl<'cx, 'tcx> SelectionContext<'cx, 'tcx> {
904900
})
905901
}
906902

907-
/// Temporary migration for #89190
908-
fn need_migrate_deref_output_trait_object(
909-
&mut self,
910-
ty: Ty<'tcx>,
911-
param_env: ty::ParamEnv<'tcx>,
912-
cause: &ObligationCause<'tcx>,
913-
) -> Option<ty::PolyExistentialTraitRef<'tcx>> {
914-
// Don't drop any candidates in intercrate mode, as it's incomplete.
915-
// (Not that it matters, since `Unsize` is not a stable trait.)
916-
//
917-
// FIXME(@lcnr): This should probably only trigger during analysis,
918-
// disabling candidates during codegen is also questionable.
919-
if let TypingMode::Coherence = self.infcx.typing_mode() {
920-
return None;
921-
}
922-
923-
let tcx = self.tcx();
924-
if tcx.features().trait_upcasting() {
925-
return None;
926-
}
927-
928-
// <ty as Deref>
929-
let trait_ref = ty::TraitRef::new(tcx, tcx.lang_items().deref_trait()?, [ty]);
930-
931-
let obligation =
932-
traits::Obligation::new(tcx, cause.clone(), param_env, ty::Binder::dummy(trait_ref));
933-
if !self.infcx.predicate_may_hold(&obligation) {
934-
return None;
935-
}
936-
937-
self.infcx.probe(|_| {
938-
let ty = traits::normalize_projection_ty(
939-
self,
940-
param_env,
941-
ty::AliasTy::new_from_args(tcx, tcx.lang_items().deref_target()?, trait_ref.args),
942-
cause.clone(),
943-
0,
944-
// We're *intentionally* throwing these away,
945-
// since we don't actually use them.
946-
&mut PredicateObligations::new(),
947-
)
948-
.as_type()
949-
.unwrap();
950-
951-
if let ty::Dynamic(data, ..) = ty.kind() { data.principal() } else { None }
952-
})
953-
}
954-
955903
/// Searches for unsizing that might apply to `obligation`.
956904
fn assemble_candidates_for_unsizing(
957905
&mut self,
@@ -1019,15 +967,6 @@ impl<'cx, 'tcx> SelectionContext<'cx, 'tcx> {
1019967
let principal_a = a_data.principal().unwrap();
1020968
let target_trait_did = principal_def_id_b.unwrap();
1021969
let source_trait_ref = principal_a.with_self_ty(self.tcx(), source);
1022-
if let Some(deref_trait_ref) = self.need_migrate_deref_output_trait_object(
1023-
source,
1024-
obligation.param_env,
1025-
&obligation.cause,
1026-
) {
1027-
if deref_trait_ref.def_id() == target_trait_did {
1028-
return;
1029-
}
1030-
}
1031970

1032971
for (idx, upcast_trait_ref) in
1033972
util::supertraits(self.tcx(), source_trait_ref).enumerate()

Diff for: compiler/rustc_type_ir/src/solve/mod.rs

+1-3
Original file line numberDiff line numberDiff line change
@@ -179,9 +179,7 @@ pub enum BuiltinImplSource {
179179
Object(usize),
180180
/// A built-in implementation of `Upcast` for trait objects to other trait objects.
181181
///
182-
/// This can be removed when `feature(dyn_upcasting)` is stabilized, since we only
183-
/// use it to detect when upcasting traits in hir typeck. The index is only used
184-
/// for winnowing.
182+
/// The index is only used for winnowing.
185183
TraitUpcasting(usize),
186184
/// Unsizing a tuple like `(A, B, ..., X)` to `(A, B, ..., Y)` if `X` unsizes to `Y`.
187185
///

Diff for: library/coretests/tests/lib.rs

-1
Original file line numberDiff line numberDiff line change
@@ -81,7 +81,6 @@
8181
#![feature(strict_provenance_atomic_ptr)]
8282
#![feature(strict_provenance_lints)]
8383
#![feature(test)]
84-
#![feature(trait_upcasting)]
8584
#![feature(trusted_len)]
8685
#![feature(trusted_random_access)]
8786
#![feature(try_blocks)]

Diff for: src/doc/unstable-book/src/language-features/trait-upcasting.md

-26
This file was deleted.

Diff for: src/tools/miri/src/lib.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,4 @@
1+
#![cfg_attr(bootstrap, feature(trait_upcasting))]
12
#![feature(rustc_private)]
23
#![feature(cell_update)]
34
#![feature(float_gamma)]
@@ -9,7 +10,6 @@
910
#![feature(yeet_expr)]
1011
#![feature(nonzero_ops)]
1112
#![feature(let_chains)]
12-
#![feature(trait_upcasting)]
1313
#![feature(strict_overflow_ops)]
1414
#![feature(pointer_is_aligned_to)]
1515
#![feature(unqualified_local_imports)]

Diff for: src/tools/miri/tests/fail/dyn-upcast-trait-mismatch.rs

-3
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,6 @@
11
// Validation stops this too early.
22
//@compile-flags: -Zmiri-disable-validation
33

4-
#![feature(trait_upcasting)]
5-
#![allow(incomplete_features)]
6-
74
trait Foo: PartialEq<i32> + std::fmt::Debug + Send + Sync {
85
#[allow(dead_code)]
96
fn a(&self) -> i32 {

Diff for: src/tools/miri/tests/pass/box-custom-alloc.rs

+1-2
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,6 @@
11
//@revisions: stack tree
22
//@[tree]compile-flags: -Zmiri-tree-borrows
3-
#![allow(incomplete_features)] // for trait upcasting
4-
#![feature(allocator_api, trait_upcasting)]
3+
#![feature(allocator_api)]
54

65
use std::alloc::{AllocError, Allocator, Layout};
76
use std::cell::Cell;

Diff for: src/tools/miri/tests/pass/dyn-upcast.rs

-3
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,3 @@
1-
#![feature(trait_upcasting)]
2-
#![allow(incomplete_features)]
3-
41
use std::fmt;
52

63
fn main() {

Diff for: tests/codegen/vtable-upcast.rs

-1
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,6 @@
22
//@ compile-flags: -C no-prepopulate-passes -Copt-level=0
33

44
#![crate_type = "lib"]
5-
#![feature(trait_upcasting)]
65

76
pub trait Base {
87
fn base(&self);

Diff for: tests/crashes/131886.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
//@ known-bug: #131886
22
//@ compile-flags: -Zvalidate-mir --crate-type=lib
3-
#![feature(trait_upcasting, type_alias_impl_trait)]
3+
#![feature(type_alias_impl_trait)]
44

55
type Tait = impl Sized;
66

Diff for: tests/ui/codegen/issue-99551.rs

-1
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,4 @@
11
//@ build-pass
2-
#![feature(trait_upcasting)]
32

43
pub trait A {}
54
pub trait B {}

Diff for: tests/ui/dyn-star/no-unsize-coerce-dyn-trait.rs

+2-2
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
1-
#![feature(dyn_star, trait_upcasting)]
2-
//~^ WARN the feature `dyn_star` is incomplete and may not be safe to use and/or cause compiler crashes
1+
#![expect(incomplete_features)]
2+
#![feature(dyn_star)]
33

44
trait A: B {}
55
trait B {}

Diff for: tests/ui/dyn-star/no-unsize-coerce-dyn-trait.stderr

+1-10
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,3 @@
1-
warning: the feature `dyn_star` is incomplete and may not be safe to use and/or cause compiler crashes
2-
--> $DIR/no-unsize-coerce-dyn-trait.rs:1:12
3-
|
4-
LL | #![feature(dyn_star, trait_upcasting)]
5-
| ^^^^^^^^
6-
|
7-
= note: see issue #102425 <https://github.com/rust-lang/rust/issues/102425> for more information
8-
= note: `#[warn(incomplete_features)]` on by default
9-
101
error[E0308]: mismatched types
112
--> $DIR/no-unsize-coerce-dyn-trait.rs:11:26
123
|
@@ -18,6 +9,6 @@ LL | let y: Box<dyn* B> = x;
189
= note: expected struct `Box<dyn* B>`
1910
found struct `Box<dyn* A>`
2011

21-
error: aborting due to 1 previous error; 1 warning emitted
12+
error: aborting due to 1 previous error
2213

2314
For more information about this error, try `rustc --explain E0308`.

Diff for: tests/ui/dyn-star/upcast.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
//@ known-bug: #104800
22

3-
#![feature(dyn_star, trait_upcasting)]
3+
#![feature(dyn_star)]
44

55
trait Foo: Bar {
66
fn hello(&self);

Diff for: tests/ui/dyn-star/upcast.stderr

+1-1
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
warning: the feature `dyn_star` is incomplete and may not be safe to use and/or cause compiler crashes
22
--> $DIR/upcast.rs:3:12
33
|
4-
LL | #![feature(dyn_star, trait_upcasting)]
4+
LL | #![feature(dyn_star)]
55
| ^^^^^^^^
66
|
77
= note: see issue #102425 <https://github.com/rust-lang/rust/issues/102425> for more information

0 commit comments

Comments
 (0)