summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorOli Scherer <git-spam-no-reply9815368754983@oli-obk.de>2024-01-22 12:23:50 +0000
committerOli Scherer <git-spam-no-reply9815368754983@oli-obk.de>2024-01-24 08:55:16 +0000
commit166fb652e4150eda7132293a2e293911a99ed1f3 (patch)
treeec8cf9fe65e21bc9efdb5457b3fe3b0d1a5fc7b5
parente8b6db72515807fa301ff8d39b8ac058d5653fd1 (diff)
Revert "Auto merge of #118133 - Urgau:stabilize_trait_upcasting, r=WaffleLapkin"
This reverts commit 6d2b84b3ed7848fd91b8d6151d4451b3103ed816, reversing changes made to 73bc12199ea8c7651ed98b069c0dd6b0bb5fabcf.
-rw-r--r--compiler/rustc_feature/src/accepted.rs3
-rw-r--r--compiler/rustc_feature/src/unstable.rs3
-rw-r--r--compiler/rustc_hir_typeck/src/coercion.rs23
-rw-r--r--compiler/rustc_lint/src/deref_into_dyn_supertrait.rs13
-rw-r--r--compiler/rustc_lint/src/lib.rs2
-rw-r--r--compiler/rustc_lint/src/lints.rs1
-rw-r--r--compiler/rustc_middle/src/lib.rs2
-rw-r--r--compiler/rustc_trait_selection/src/traits/select/candidate_assembly.rs51
-rw-r--r--library/core/tests/lib.rs2
-rw-r--r--src/doc/unstable-book/src/language-features/trait-upcasting.md27
-rw-r--r--src/tools/miri/src/lib.rs2
-rw-r--r--src/tools/miri/tests/fail/dyn-upcast-trait-mismatch.rs3
-rw-r--r--src/tools/miri/tests/pass/box-custom-alloc.rs3
-rw-r--r--src/tools/miri/tests/pass/dyn-upcast.rs3
-rw-r--r--tests/ui/codegen/issue-99551.rs1
-rw-r--r--tests/ui/dyn-star/no-unsize-coerce-dyn-trait.rs2
-rw-r--r--tests/ui/dyn-star/no-unsize-coerce-dyn-trait.stderr2
-rw-r--r--tests/ui/dyn-star/upcast.rs2
-rw-r--r--tests/ui/dyn-star/upcast.stderr2
-rw-r--r--tests/ui/feature-gates/feature-gate-trait_upcasting.rs13
-rw-r--r--tests/ui/feature-gates/feature-gate-trait_upcasting.stderr13
-rw-r--r--tests/ui/traits/next-solver/normalize-unsize-rhs.rs1
-rw-r--r--tests/ui/traits/next-solver/trait-upcast-lhs-needs-normalization.rs1
-rw-r--r--tests/ui/traits/next-solver/upcast-right-substs.rs1
-rw-r--r--tests/ui/traits/trait-upcasting/alias-where-clause-isnt-supertrait.rs1
-rw-r--r--tests/ui/traits/trait-upcasting/alias-where-clause-isnt-supertrait.stderr2
-rw-r--r--tests/ui/traits/trait-upcasting/basic.rs2
-rw-r--r--tests/ui/traits/trait-upcasting/correct-supertrait-substitution.rs1
-rw-r--r--tests/ui/traits/trait-upcasting/deref-lint-regions.stderr14
-rw-r--r--tests/ui/traits/trait-upcasting/deref-lint.stderr14
-rw-r--r--tests/ui/traits/trait-upcasting/deref-upcast-behavioral-change.rs3
-rw-r--r--tests/ui/traits/trait-upcasting/deref-upcast-behavioral-change.stderr23
-rw-r--r--tests/ui/traits/trait-upcasting/diamond.rs2
-rw-r--r--tests/ui/traits/trait-upcasting/fewer-associated.rs2
-rw-r--r--tests/ui/traits/trait-upcasting/illegal-upcast-from-impl.current.stderr2
-rw-r--r--tests/ui/traits/trait-upcasting/illegal-upcast-from-impl.next.stderr2
-rw-r--r--tests/ui/traits/trait-upcasting/illegal-upcast-from-impl.rs2
-rw-r--r--tests/ui/traits/trait-upcasting/inference-behavior-change-deref.rs1
-rw-r--r--tests/ui/traits/trait-upcasting/inference-behavior-change-deref.stderr2
-rw-r--r--tests/ui/traits/trait-upcasting/invalid-upcast.rs2
-rw-r--r--tests/ui/traits/trait-upcasting/invalid-upcast.stderr30
-rw-r--r--tests/ui/traits/trait-upcasting/issue-11515-upcast-fn_mut-fn.rs1
-rw-r--r--tests/ui/traits/trait-upcasting/issue-11515.current.stderr13
-rw-r--r--tests/ui/traits/trait-upcasting/issue-11515.next.stderr13
-rw-r--r--tests/ui/traits/trait-upcasting/issue-11515.rs3
-rw-r--r--tests/ui/traits/trait-upcasting/lifetime.rs2
-rw-r--r--tests/ui/traits/trait-upcasting/migrate-lint-deny-regions.rs (renamed from tests/ui/traits/trait-upcasting/deref-lint-regions.rs)5
-rw-r--r--tests/ui/traits/trait-upcasting/migrate-lint-deny-regions.stderr19
-rw-r--r--tests/ui/traits/trait-upcasting/migrate-lint-deny.rs (renamed from tests/ui/traits/trait-upcasting/deref-lint.rs)5
-rw-r--r--tests/ui/traits/trait-upcasting/migrate-lint-deny.stderr19
-rw-r--r--tests/ui/traits/trait-upcasting/migrate-lint-different-substs.rs1
-rw-r--r--tests/ui/traits/trait-upcasting/migrate-lint-different-substs.stderr5
-rw-r--r--tests/ui/traits/trait-upcasting/multiple-occurrence-ambiguousity.rs1
-rw-r--r--tests/ui/traits/trait-upcasting/multiple-occurrence-ambiguousity.stderr2
-rw-r--r--tests/ui/traits/trait-upcasting/normalization.rs2
-rw-r--r--tests/ui/traits/trait-upcasting/replace-vptr.rs2
-rw-r--r--tests/ui/traits/trait-upcasting/struct.rs2
-rw-r--r--tests/ui/traits/trait-upcasting/subtrait-method.rs2
-rw-r--r--tests/ui/traits/trait-upcasting/subtrait-method.stderr20
-rw-r--r--tests/ui/traits/trait-upcasting/type-checking-test-1.current.stderr2
-rw-r--r--tests/ui/traits/trait-upcasting/type-checking-test-1.next.stderr2
-rw-r--r--tests/ui/traits/trait-upcasting/type-checking-test-1.rs2
-rw-r--r--tests/ui/traits/trait-upcasting/type-checking-test-2.rs2
-rw-r--r--tests/ui/traits/trait-upcasting/type-checking-test-2.stderr4
-rw-r--r--tests/ui/traits/trait-upcasting/type-checking-test-3.rs2
-rw-r--r--tests/ui/traits/trait-upcasting/type-checking-test-3.stderr4
-rw-r--r--tests/ui/traits/trait-upcasting/type-checking-test-4.rs2
-rw-r--r--tests/ui/traits/trait-upcasting/type-checking-test-4.stderr12
-rw-r--r--tests/ui/traits/trait-upcasting/upcast-through-struct-tail.current.stderr13
-rw-r--r--tests/ui/traits/trait-upcasting/upcast-through-struct-tail.next.stderr13
-rw-r--r--tests/ui/traits/trait-upcasting/upcast-through-struct-tail.rs2
71 files changed, 353 insertions, 105 deletions
diff --git a/compiler/rustc_feature/src/accepted.rs b/compiler/rustc_feature/src/accepted.rs
index 51ee56080a2..be04fa7436b 100644
--- a/compiler/rustc_feature/src/accepted.rs
+++ b/compiler/rustc_feature/src/accepted.rs
@@ -337,9 +337,6 @@ declare_features! (
/// Allows `#[track_caller]` to be used which provides
/// accurate caller location reporting during panic (RFC 2091).
(accepted, track_caller, "1.46.0", Some(47809)),
- /// Allows dyn upcasting trait objects via supertraits.
- /// Dyn upcasting is casting, e.g., `dyn Foo -> dyn Bar` where `Foo: Bar`.
- (accepted, trait_upcasting, "1.76.0", Some(65991)),
/// Allows #[repr(transparent)] on univariant enums (RFC 2645).
(accepted, transparent_enums, "1.42.0", Some(60405)),
/// Allows indexing tuples.
diff --git a/compiler/rustc_feature/src/unstable.rs b/compiler/rustc_feature/src/unstable.rs
index 1ad75a692c7..eadb19f6fc3 100644
--- a/compiler/rustc_feature/src/unstable.rs
+++ b/compiler/rustc_feature/src/unstable.rs
@@ -580,6 +580,9 @@ declare_features! (
(unstable, thread_local, "1.0.0", Some(29594)),
/// Allows defining `trait X = A + B;` alias items.
(unstable, trait_alias, "1.24.0", Some(41517)),
+ /// Allows dyn upcasting trait objects via supertraits.
+ /// Dyn upcasting is casting, e.g., `dyn Foo -> dyn Bar` where `Foo: Bar`.
+ (unstable, trait_upcasting, "1.56.0", Some(65991)),
/// Allows for transmuting between arrays with sizes that contain generic consts.
(unstable, transmute_generic_consts, "1.70.0", Some(109929)),
/// Allows #[repr(transparent)] on unions (RFC 2645).
diff --git a/compiler/rustc_hir_typeck/src/coercion.rs b/compiler/rustc_hir_typeck/src/coercion.rs
index 61236c07135..f08af9edcbb 100644
--- a/compiler/rustc_hir_typeck/src/coercion.rs
+++ b/compiler/rustc_hir_typeck/src/coercion.rs
@@ -627,6 +627,7 @@ impl<'f, 'tcx> Coerce<'f, 'tcx> {
)];
let mut has_unsized_tuple_coercion = false;
+ let mut has_trait_upcasting_coercion = None;
// Keep resolving `CoerceUnsized` and `Unsize` predicates to avoid
// emitting a coercion in cases like `Foo<$1>` -> `Foo<$2>`, where
@@ -694,6 +695,13 @@ impl<'f, 'tcx> Coerce<'f, 'tcx> {
// these here and emit a feature error if coercion doesn't fail
// due to another reason.
match impl_source {
+ traits::ImplSource::Builtin(
+ BuiltinImplSource::TraitUpcasting { .. },
+ _,
+ ) => {
+ has_trait_upcasting_coercion =
+ Some((trait_pred.self_ty(), trait_pred.trait_ref.args.type_at(1)));
+ }
traits::ImplSource::Builtin(BuiltinImplSource::TupleUnsizing, _) => {
has_unsized_tuple_coercion = true;
}
@@ -704,6 +712,21 @@ impl<'f, 'tcx> Coerce<'f, 'tcx> {
}
}
+ if let Some((sub, sup)) = has_trait_upcasting_coercion
+ && !self.tcx().features().trait_upcasting
+ {
+ // Renders better when we erase regions, since they're not really the point here.
+ let (sub, sup) = self.tcx.erase_regions((sub, sup));
+ let mut err = feature_err(
+ &self.tcx.sess.parse_sess,
+ sym::trait_upcasting,
+ self.cause.span,
+ format!("cannot cast `{sub}` to `{sup}`, trait upcasting coercion is experimental"),
+ );
+ err.note(format!("required when coercing `{source}` into `{target}`"));
+ err.emit();
+ }
+
if has_unsized_tuple_coercion && !self.tcx.features().unsized_tuple_coercion {
feature_err(
&self.tcx.sess.parse_sess,
diff --git a/compiler/rustc_lint/src/deref_into_dyn_supertrait.rs b/compiler/rustc_lint/src/deref_into_dyn_supertrait.rs
index 98bafc0f263..4673b801dc1 100644
--- a/compiler/rustc_lint/src/deref_into_dyn_supertrait.rs
+++ b/compiler/rustc_lint/src/deref_into_dyn_supertrait.rs
@@ -5,6 +5,7 @@ use crate::{
use rustc_hir as hir;
use rustc_middle::ty;
+use rustc_session::lint::FutureIncompatibilityReason;
use rustc_span::sym;
use rustc_trait_selection::traits::supertraits;
@@ -12,6 +13,9 @@ declare_lint! {
/// The `deref_into_dyn_supertrait` lint is output whenever there is a use of the
/// `Deref` implementation with a `dyn SuperTrait` type as `Output`.
///
+ /// These implementations will become shadowed when the `trait_upcasting` feature is stabilized.
+ /// The `deref` functions will no longer be called implicitly, so there might be behavior change.
+ ///
/// ### Example
///
/// ```rust,compile_fail
@@ -40,10 +44,15 @@ declare_lint! {
///
/// ### Explanation
///
- /// The implicit dyn upcasting coercion take priority over those `Deref` impls.
+ /// The dyn upcasting coercion feature adds new coercion rules, taking priority
+ /// over certain other coercion rules, which will cause some behavior change.
pub DEREF_INTO_DYN_SUPERTRAIT,
Warn,
- "`Deref` implementation usage with a supertrait trait object for output are shadow by implicit coercion",
+ "`Deref` implementation usage with a supertrait trait object for output might be shadowed in the future",
+ @future_incompatible = FutureIncompatibleInfo {
+ reason: FutureIncompatibilityReason::FutureReleaseSemanticsChange,
+ reference: "issue #89460 <https://github.com/rust-lang/rust/issues/89460>",
+ };
}
declare_lint_pass!(DerefIntoDynSupertrait => [DEREF_INTO_DYN_SUPERTRAIT]);
diff --git a/compiler/rustc_lint/src/lib.rs b/compiler/rustc_lint/src/lib.rs
index a4ab5527e3f..066c88cc652 100644
--- a/compiler/rustc_lint/src/lib.rs
+++ b/compiler/rustc_lint/src/lib.rs
@@ -39,7 +39,7 @@
#![feature(min_specialization)]
#![feature(never_type)]
#![feature(rustc_attrs)]
-#![cfg_attr(bootstrap, feature(trait_upcasting))]
+#![feature(trait_upcasting)]
#![recursion_limit = "256"]
#![deny(rustc::untranslatable_diagnostic)]
#![deny(rustc::diagnostic_outside_of_impl)]
diff --git a/compiler/rustc_lint/src/lints.rs b/compiler/rustc_lint/src/lints.rs
index ca6408bdf3d..9c0d3be0318 100644
--- a/compiler/rustc_lint/src/lints.rs
+++ b/compiler/rustc_lint/src/lints.rs
@@ -544,7 +544,6 @@ pub enum BuiltinSpecialModuleNameUsed {
// deref_into_dyn_supertrait.rs
#[derive(LintDiagnostic)]
#[diag(lint_supertrait_as_deref_target)]
-#[help]
pub struct SupertraitAsDerefTarget<'a> {
pub self_ty: Ty<'a>,
pub supertrait_principal: PolyExistentialTraitRef<'a>,
diff --git a/compiler/rustc_middle/src/lib.rs b/compiler/rustc_middle/src/lib.rs
index e048268fad1..3206c6cf650 100644
--- a/compiler/rustc_middle/src/lib.rs
+++ b/compiler/rustc_middle/src/lib.rs
@@ -49,7 +49,7 @@
#![feature(associated_type_bounds)]
#![feature(rustc_attrs)]
#![feature(control_flow_enum)]
-#![cfg_attr(bootstrap, feature(trait_upcasting))]
+#![feature(trait_upcasting)]
#![feature(trusted_step)]
#![feature(try_blocks)]
#![feature(try_reserve_kind)]
diff --git a/compiler/rustc_trait_selection/src/traits/select/candidate_assembly.rs b/compiler/rustc_trait_selection/src/traits/select/candidate_assembly.rs
index 73e06b84085..38b1046ac53 100644
--- a/compiler/rustc_trait_selection/src/traits/select/candidate_assembly.rs
+++ b/compiler/rustc_trait_selection/src/traits/select/candidate_assembly.rs
@@ -9,10 +9,13 @@
use hir::def_id::DefId;
use hir::LangItem;
use rustc_hir as hir;
+use rustc_infer::traits::ObligationCause;
use rustc_infer::traits::{Obligation, PolyTraitObligation, SelectionError};
use rustc_middle::ty::fast_reject::{DeepRejectCtxt, TreatParams};
use rustc_middle::ty::{self, Ty, TypeVisitableExt};
+use crate::traits;
+use crate::traits::query::evaluate_obligation::InferCtxtExt;
use crate::traits::util;
use super::BuiltinImplConditions;
@@ -723,6 +726,45 @@ impl<'cx, 'tcx> SelectionContext<'cx, 'tcx> {
})
}
+ /// Temporary migration for #89190
+ fn need_migrate_deref_output_trait_object(
+ &mut self,
+ ty: Ty<'tcx>,
+ param_env: ty::ParamEnv<'tcx>,
+ cause: &ObligationCause<'tcx>,
+ ) -> Option<ty::PolyExistentialTraitRef<'tcx>> {
+ let tcx = self.tcx();
+ if tcx.features().trait_upcasting {
+ return None;
+ }
+
+ // <ty as Deref>
+ let trait_ref = ty::TraitRef::new(tcx, tcx.lang_items().deref_trait()?, [ty]);
+
+ let obligation =
+ traits::Obligation::new(tcx, cause.clone(), param_env, ty::Binder::dummy(trait_ref));
+ if !self.infcx.predicate_may_hold(&obligation) {
+ return None;
+ }
+
+ self.infcx.probe(|_| {
+ let ty = traits::normalize_projection_type(
+ self,
+ param_env,
+ ty::AliasTy::new(tcx, tcx.lang_items().deref_target()?, trait_ref.args),
+ cause.clone(),
+ 0,
+ // We're *intentionally* throwing these away,
+ // since we don't actually use them.
+ &mut vec![],
+ )
+ .ty()
+ .unwrap();
+
+ if let ty::Dynamic(data, ..) = ty.kind() { data.principal() } else { None }
+ })
+ }
+
/// Searches for unsizing that might apply to `obligation`.
fn assemble_candidates_for_unsizing(
&mut self,
@@ -780,6 +822,15 @@ impl<'cx, 'tcx> SelectionContext<'cx, 'tcx> {
let principal_a = a_data.principal().unwrap();
let target_trait_did = principal_def_id_b.unwrap();
let source_trait_ref = principal_a.with_self_ty(self.tcx(), source);
+ if let Some(deref_trait_ref) = self.need_migrate_deref_output_trait_object(
+ source,
+ obligation.param_env,
+ &obligation.cause,
+ ) {
+ if deref_trait_ref.def_id() == target_trait_did {
+ return;
+ }
+ }
for (idx, upcast_trait_ref) in
util::supertraits(self.tcx(), source_trait_ref).enumerate()
diff --git a/library/core/tests/lib.rs b/library/core/tests/lib.rs
index c531117bed5..ac8b6f6b567 100644
--- a/library/core/tests/lib.rs
+++ b/library/core/tests/lib.rs
@@ -111,7 +111,7 @@
#![feature(slice_flatten)]
#![feature(error_generic_member_access)]
#![feature(error_in_core)]
-#![cfg_attr(bootstrap, feature(trait_upcasting))]
+#![feature(trait_upcasting)]
#![feature(utf8_chunks)]
#![feature(is_ascii_octdigit)]
#![feature(get_many_mut)]
diff --git a/src/doc/unstable-book/src/language-features/trait-upcasting.md b/src/doc/unstable-book/src/language-features/trait-upcasting.md
new file mode 100644
index 00000000000..3697ae38f9d
--- /dev/null
+++ b/src/doc/unstable-book/src/language-features/trait-upcasting.md
@@ -0,0 +1,27 @@
+# `trait_upcasting`
+
+The tracking issue for this feature is: [#65991]
+
+[#65991]: https://github.com/rust-lang/rust/issues/65991
+
+------------------------
+
+The `trait_upcasting` feature adds support for trait upcasting coercion. This allows a
+trait object of type `dyn Bar` to be cast to a trait object of type `dyn Foo`
+so long as `Bar: Foo`.
+
+```rust,edition2018
+#![feature(trait_upcasting)]
+#![allow(incomplete_features)]
+
+trait Foo {}
+
+trait Bar: Foo {}
+
+impl Foo for i32 {}
+
+impl<T: Foo + ?Sized> Bar for T {}
+
+let bar: &dyn Bar = &123;
+let foo: &dyn Foo = bar;
+```
diff --git a/src/tools/miri/src/lib.rs b/src/tools/miri/src/lib.rs
index 1eb40ab826c..70e9c443e90 100644
--- a/src/tools/miri/src/lib.rs
+++ b/src/tools/miri/src/lib.rs
@@ -11,7 +11,7 @@
#![feature(round_ties_even)]
#![feature(let_chains)]
#![feature(lint_reasons)]
-#![cfg_attr(bootstrap, feature(trait_upcasting))]
+#![feature(trait_upcasting)]
// Configure clippy and other lints
#![allow(
clippy::collapsible_else_if,
diff --git a/src/tools/miri/tests/fail/dyn-upcast-trait-mismatch.rs b/src/tools/miri/tests/fail/dyn-upcast-trait-mismatch.rs
index 7d46ecd8f6e..648ac07c43e 100644
--- a/src/tools/miri/tests/fail/dyn-upcast-trait-mismatch.rs
+++ b/src/tools/miri/tests/fail/dyn-upcast-trait-mismatch.rs
@@ -1,3 +1,6 @@
+#![feature(trait_upcasting)]
+#![allow(incomplete_features)]
+
trait Foo: PartialEq<i32> + std::fmt::Debug + Send + Sync {
fn a(&self) -> i32 {
10
diff --git a/src/tools/miri/tests/pass/box-custom-alloc.rs b/src/tools/miri/tests/pass/box-custom-alloc.rs
index 3d055961d15..155e3d74ab9 100644
--- a/src/tools/miri/tests/pass/box-custom-alloc.rs
+++ b/src/tools/miri/tests/pass/box-custom-alloc.rs
@@ -1,6 +1,7 @@
//@revisions: stack tree
//@[tree]compile-flags: -Zmiri-tree-borrows
-#![feature(allocator_api)]
+#![allow(incomplete_features)] // for trait upcasting
+#![feature(allocator_api, trait_upcasting)]
use std::alloc::Layout;
use std::alloc::{AllocError, Allocator};
diff --git a/src/tools/miri/tests/pass/dyn-upcast.rs b/src/tools/miri/tests/pass/dyn-upcast.rs
index ddaefeca3a3..8432012a9ba 100644
--- a/src/tools/miri/tests/pass/dyn-upcast.rs
+++ b/src/tools/miri/tests/pass/dyn-upcast.rs
@@ -1,3 +1,6 @@
+#![feature(trait_upcasting)]
+#![allow(incomplete_features)]
+
fn main() {
basic();
diamond();
diff --git a/tests/ui/codegen/issue-99551.rs b/tests/ui/codegen/issue-99551.rs
index 9e203fba113..b223aff4e94 100644
--- a/tests/ui/codegen/issue-99551.rs
+++ b/tests/ui/codegen/issue-99551.rs
@@ -1,4 +1,5 @@
// build-pass
+#![feature(trait_upcasting)]
pub trait A {}
pub trait B {}
diff --git a/tests/ui/dyn-star/no-unsize-coerce-dyn-trait.rs b/tests/ui/dyn-star/no-unsize-coerce-dyn-trait.rs
index 0201c889706..a4eb669e321 100644
--- a/tests/ui/dyn-star/no-unsize-coerce-dyn-trait.rs
+++ b/tests/ui/dyn-star/no-unsize-coerce-dyn-trait.rs
@@ -1,4 +1,4 @@
-#![feature(dyn_star)]
+#![feature(dyn_star, trait_upcasting)]
//~^ WARN the feature `dyn_star` is incomplete and may not be safe to use and/or cause compiler crashes
trait A: B {}
diff --git a/tests/ui/dyn-star/no-unsize-coerce-dyn-trait.stderr b/tests/ui/dyn-star/no-unsize-coerce-dyn-trait.stderr
index 7e2cf661369..1f7bfb1d5bd 100644
--- a/tests/ui/dyn-star/no-unsize-coerce-dyn-trait.stderr
+++ b/tests/ui/dyn-star/no-unsize-coerce-dyn-trait.stderr
@@ -1,7 +1,7 @@
warning: the feature `dyn_star` is incomplete and may not be safe to use and/or cause compiler crashes
--> $DIR/no-unsize-coerce-dyn-trait.rs:1:12
|
-LL | #![feature(dyn_star)]
+LL | #![feature(dyn_star, trait_upcasting)]
| ^^^^^^^^
|
= note: see issue #102425 <https://github.com/rust-lang/rust/issues/102425> for more information
diff --git a/tests/ui/dyn-star/upcast.rs b/tests/ui/dyn-star/upcast.rs
index 7748cdda943..c667ac143a3 100644
--- a/tests/ui/dyn-star/upcast.rs
+++ b/tests/ui/dyn-star/upcast.rs
@@ -1,6 +1,6 @@
// known-bug: #104800
-#![feature(dyn_star)]
+#![feature(dyn_star, trait_upcasting)]
trait Foo: Bar {
fn hello(&self);
diff --git a/tests/ui/dyn-star/upcast.stderr b/tests/ui/dyn-star/upcast.stderr
index bdf77da713a..adef9525bf1 100644
--- a/tests/ui/dyn-star/upcast.stderr
+++ b/tests/ui/dyn-star/upcast.stderr
@@ -1,7 +1,7 @@
warning: the feature `dyn_star` is incomplete and may not be safe to use and/or cause compiler crashes
--> $DIR/upcast.rs:3:12
|
-LL | #![feature(dyn_star)]
+LL | #![feature(dyn_star, trait_upcasting)]
| ^^^^^^^^
|
= note: see issue #102425 <https://github.com/rust-lang/rust/issues/102425> for more information
diff --git a/tests/ui/feature-gates/feature-gate-trait_upcasting.rs b/tests/ui/feature-gates/feature-gate-trait_upcasting.rs
new file mode 100644
index 00000000000..e4102f1cfa7
--- /dev/null
+++ b/tests/ui/feature-gates/feature-gate-trait_upcasting.rs
@@ -0,0 +1,13 @@
+trait Foo {}
+
+trait Bar: Foo {}
+
+impl Foo for () {}
+
+impl Bar for () {}
+
+fn main() {
+ let bar: &dyn Bar = &();
+ let foo: &dyn Foo = bar;
+ //~^ ERROR trait upcasting coercion is experimental [E0658]
+}
diff --git a/tests/ui/feature-gates/feature-gate-trait_upcasting.stderr b/tests/ui/feature-gates/feature-gate-trait_upcasting.stderr
new file mode 100644
index 00000000000..ce2f3c0a808
--- /dev/null
+++ b/tests/ui/feature-gates/feature-gate-trait_upcasting.stderr
@@ -0,0 +1,13 @@
+error[E0658]: cannot cast `dyn Bar` to `dyn Foo`, trait upcasting coercion is experimental
+ --> $DIR/feature-gate-trait_upcasting.rs:11:25
+ |
+LL | let foo: &dyn Foo = bar;
+ | ^^^
+ |
+ = note: see issue #65991 <https://github.com/rust-lang/rust/issues/65991> for more information
+ = help: add `#![feature(trait_upcasting)]` to the crate attributes to enable
+ = note: required when coercing `&dyn Bar` into `&dyn Foo`
+
+error: aborting due to 1 previous error
+
+For more information about this error, try `rustc --explain E0658`.
diff --git a/tests/ui/traits/next-solver/normalize-unsize-rhs.rs b/tests/ui/traits/next-solver/normalize-unsize-rhs.rs
index 6ca82d1b872..08bb0cf42e8 100644
--- a/tests/ui/traits/next-solver/normalize-unsize-rhs.rs
+++ b/tests/ui/traits/next-solver/normalize-unsize-rhs.rs
@@ -1,5 +1,6 @@
// compile-flags: -Znext-solver
// check-pass
+#![feature(trait_upcasting)]
trait A {}
trait B: A {}
diff --git a/tests/ui/traits/next-solver/trait-upcast-lhs-needs-normalization.rs b/tests/ui/traits/next-solver/trait-upcast-lhs-needs-normalization.rs
index 2a482f74668..8e0378e94f0 100644
--- a/tests/ui/traits/next-solver/trait-upcast-lhs-needs-normalization.rs
+++ b/tests/ui/traits/next-solver/trait-upcast-lhs-needs-normalization.rs
@@ -1,5 +1,6 @@
// check-pass
// compile-flags: -Znext-solver
+#![feature(trait_upcasting)]
pub trait A {}
pub trait B: A {}
diff --git a/tests/ui/traits/next-solver/upcast-right-substs.rs b/tests/ui/traits/next-solver/upcast-right-substs.rs
index 5e4d958c895..5b4f6d4be0c 100644
--- a/tests/ui/traits/next-solver/upcast-right-substs.rs
+++ b/tests/ui/traits/next-solver/upcast-right-substs.rs
@@ -1,5 +1,6 @@
// compile-flags: -Znext-solver
// check-pass
+#![feature(trait_upcasting)]
trait Foo: Bar<i32> + Bar<u32> {}
diff --git a/tests/ui/traits/trait-upcasting/alias-where-clause-isnt-supertrait.rs b/tests/ui/traits/trait-upcasting/alias-where-clause-isnt-supertrait.rs
index 927a9d6b94f..4a5e445d1ef 100644
--- a/tests/ui/traits/trait-upcasting/alias-where-clause-isnt-supertrait.rs
+++ b/tests/ui/traits/trait-upcasting/alias-where-clause-isnt-supertrait.rs
@@ -1,3 +1,4 @@
+#![feature(trait_upcasting)]
#![feature(trait_alias)]
// Although we *elaborate* `T: Alias` to `i32: B`, we should
diff --git a/tests/ui/traits/trait-upcasting/alias-where-clause-isnt-supertrait.stderr b/tests/ui/traits/trait-upcasting/alias-where-clause-isnt-supertrait.stderr
index 1a410519a4e..99c82b88d9c 100644
--- a/tests/ui/traits/trait-upcasting/alias-where-clause-isnt-supertrait.stderr
+++ b/tests/ui/traits/trait-upcasting/alias-where-clause-isnt-supertrait.stderr
@@ -1,5 +1,5 @@
error[E0308]: mismatched types
- --> $DIR/alias-where-clause-isnt-supertrait.rs:26:5
+ --> $DIR/alias-where-clause-isnt-supertrait.rs:27:5
|
LL | fn test(x: &dyn C) -> &dyn B {
| ------ expected `&dyn B` because of return type
diff --git a/tests/ui/traits/trait-upcasting/basic.rs b/tests/ui/traits/trait-upcasting/basic.rs
index 538cd8329cc..570ec5160bf 100644
--- a/tests/ui/traits/trait-upcasting/basic.rs
+++ b/tests/ui/traits/trait-upcasting/basic.rs
@@ -1,5 +1,7 @@
// run-pass
+#![feature(trait_upcasting)]
+
trait Foo: PartialEq<i32> + std::fmt::Debug + Send + Sync {
fn a(&self) -> i32 {
10
diff --git a/tests/ui/traits/trait-upcasting/correct-supertrait-substitution.rs b/tests/ui/traits/trait-upcasting/correct-supertrait-substitution.rs
index 4a379d9f875..eae5cf8d58d 100644
--- a/tests/ui/traits/trait-upcasting/correct-supertrait-substitution.rs
+++ b/tests/ui/traits/trait-upcasting/correct-supertrait-substitution.rs
@@ -1,4 +1,5 @@
// run-pass
+#![feature(trait_upcasting)]
trait Foo<T: Default + ToString>: Bar<i32> + Bar<T> {}
trait Bar<T: Default + ToString> {
diff --git a/tests/ui/traits/trait-upcasting/deref-lint-regions.stderr b/tests/ui/traits/trait-upcasting/deref-lint-regions.stderr
deleted file mode 100644
index 557a4420a3d..00000000000
--- a/tests/ui/traits/trait-upcasting/deref-lint-regions.stderr
+++ /dev/null
@@ -1,14 +0,0 @@
-warning: this `Deref` implementation is covered by an implicit supertrait coercion
- --> $DIR/deref-lint-regions.rs:8:1
- |
-LL | impl<'a> Deref for dyn Foo<'a> {
- | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ `dyn Foo<'_>` implements `Deref<Target = dyn Bar<'_>>` which conflicts with supertrait `Bar<'_>`
-LL |
-LL | type Target = dyn Bar<'a>;
- | -------------------------- target type is a supertrait of `dyn Foo<'_>`
- |
- = help: consider removing this implementation or replacing it with a method instead
- = note: `#[warn(deref_into_dyn_supertrait)]` on by default
-
-warning: 1 warning emitted
-
diff --git a/tests/ui/traits/trait-upcasting/deref-lint.stderr b/tests/ui/traits/trait-upcasting/deref-lint.stderr
deleted file mode 100644
index 5a13659edf5..00000000000
--- a/tests/ui/traits/trait-upcasting/deref-lint.stderr
+++ /dev/null
@@ -1,14 +0,0 @@
-warning: this `Deref` implementation is covered by an implicit supertrait coercion
- --> $DIR/deref-lint.rs:9:1
- |
-LL | impl<'a> Deref for dyn 'a + B {
- | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ `dyn B` implements `Deref<Target = dyn A>` which conflicts with supertrait `A`
-...
-LL | type Target = dyn A;
- | -------------------- target type is a supertrait of `dyn B`
- |
- = help: consider removing this implementation or replacing it with a method instead
- = note: `#[warn(deref_into_dyn_supertrait)]` on by default
-
-warning: 1 warning emitted
-
diff --git a/tests/ui/traits/trait-upcasting/deref-upcast-behavioral-change.rs b/tests/ui/traits/trait-upcasting/deref-upcast-behavioral-change.rs
index 366eae1a58a..e4784fa4101 100644
--- a/tests/ui/traits/trait-upcasting/deref-upcast-behavioral-change.rs
+++ b/tests/ui/traits/trait-upcasting/deref-upcast-behavioral-change.rs
@@ -15,6 +15,8 @@ impl Foo for () {
}
impl<'a> Deref for dyn Foo + 'a {
+ //~^ ERROR this `Deref` implementation is covered by an implicit supertrait coercion
+ //~| WARN this will change its meaning in a future release!
type Target = dyn Bar<u32> + 'a;
fn deref(&self) -> &Self::Target {
@@ -30,5 +32,4 @@ fn main() {
let x: &dyn Foo = &();
let y = take_dyn(x);
let z: u32 = y;
- //~^ ERROR mismatched types
}
diff --git a/tests/ui/traits/trait-upcasting/deref-upcast-behavioral-change.stderr b/tests/ui/traits/trait-upcasting/deref-upcast-behavioral-change.stderr
index 193d09e3501..fa93e28c73b 100644
--- a/tests/ui/traits/trait-upcasting/deref-upcast-behavioral-change.stderr
+++ b/tests/ui/traits/trait-upcasting/deref-upcast-behavioral-change.stderr
@@ -1,16 +1,19 @@
-error[E0308]: mismatched types
- --> $DIR/deref-upcast-behavioral-change.rs:32:18
+error: this `Deref` implementation is covered by an implicit supertrait coercion
+ --> $DIR/deref-upcast-behavioral-change.rs:17:1
|
-LL | let z: u32 = y;
- | --- ^ expected `u32`, found `i32`
- | |
- | expected due to this
+LL | impl<'a> Deref for dyn Foo + 'a {
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ `dyn Foo` implements `Deref<Target = dyn Bar<u32>>` which conflicts with supertrait `Bar<i32>`
+...
+LL | type Target = dyn Bar<u32> + 'a;
+ | -------------------------------- target type is a supertrait of `dyn Foo`
|
-help: you can convert an `i32` to a `u32` and panic if the converted value doesn't fit
+ = warning: this will change its meaning in a future release!
+ = note: for more information, see issue #89460 <https://github.com/rust-lang/rust/issues/89460>
+note: the lint level is defined here
+ --> $DIR/deref-upcast-behavioral-change.rs:1:9
|
-LL | let z: u32 = y.try_into().unwrap();
- | ++++++++++++++++++++
+LL | #![deny(deref_into_dyn_supertrait)]
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^
error: aborting due to 1 previous error
-For more information about this error, try `rustc --explain E0308`.
diff --git a/tests/ui/traits/trait-upcasting/diamond.rs b/tests/ui/traits/trait-upcasting/diamond.rs
index 9a78339a4ec..a4f81c464b4 100644
--- a/tests/ui/traits/trait-upcasting/diamond.rs
+++ b/tests/ui/traits/trait-upcasting/diamond.rs
@@ -1,5 +1,7 @@
// run-pass
+#![feature(trait_upcasting)]
+
trait Foo: PartialEq<i32> + std::fmt::Debug + Send + Sync {
fn a(&self) -> i32 {
10
diff --git a/tests/ui/traits/trait-upcasting/fewer-associated.rs b/tests/ui/traits/trait-upcasting/fewer-associated.rs
index e7ca6fa5208..58e72d9d7ef 100644
--- a/tests/ui/traits/trait-upcasting/fewer-associated.rs
+++ b/tests/ui/traits/trait-upcasting/fewer-associated.rs
@@ -3,6 +3,8 @@
// revisions: current next
//[next] compile-flags: -Znext-solver
+#![feature(trait_upcasting)]
+
trait A: B {
type Assoc;
}
diff --git a/tests/ui/traits/trait-upcasting/illegal-upcast-from-impl.current.stderr b/tests/ui/traits/trait-upcasting/illegal-upcast-from-impl.current.stderr
index 119b3109c63..1538e2f3fd7 100644
--- a/tests/ui/traits/trait-upcasting/illegal-upcast-from-impl.current.stderr
+++ b/tests/ui/traits/trait-upcasting/illegal-upcast-from-impl.current.stderr
@@ -1,5 +1,5 @@
error[E0308]: mismatched types
- --> $DIR/illegal-upcast-from-impl.rs:14:66
+ --> $DIR/illegal-upcast-from-impl.rs:16:66
|
LL | fn illegal(x: &dyn Sub<Assoc = ()>) -> &dyn Super<Assoc = i32> { x }
| ----------------------- ^ expected trait `Super`, found trait `Sub`
diff --git a/tests/ui/traits/trait-upcasting/illegal-upcast-from-impl.next.stderr b/tests/ui/traits/trait-upcasting/illegal-upcast-from-impl.next.stderr
index 119b3109c63..1538e2f3fd7 100644
--- a/tests/ui/traits/trait-upcasting/illegal-upcast-from-impl.next.stderr
+++ b/tests/ui/traits/trait-upcasting/illegal-upcast-from-impl.next.stderr
@@ -1,5 +1,5 @@
error[E0308]: mismatched types
- --> $DIR/illegal-upcast-from-impl.rs:14:66
+ --> $DIR/illegal-upcast-from-impl.rs:16:66
|
LL | fn illegal(x: &dyn Sub<Assoc = ()>) -> &dyn Super<Assoc = i32> { x }
| ----------------------- ^ expected trait `Super`, found trait `Sub`
diff --git a/tests/ui/traits/trait-upcasting/illegal-upcast-from-impl.rs b/tests/ui/traits/trait-upcasting/illegal-upcast-from-impl.rs
index 5a493fd48b3..ffed8beb448 100644
--- a/tests/ui/traits/trait-upcasting/illegal-upcast-from-impl.rs
+++ b/tests/ui/traits/trait-upcasting/illegal-upcast-from-impl.rs
@@ -1,6 +1,8 @@
// revisions: current next
//[next] compile-flags: -Znext-solver
+#![feature(trait_upcasting)]
+
trait Super {
type Assoc;
}
diff --git a/tests/ui/traits/trait-upcasting/inference-behavior-change-deref.rs b/tests/ui/traits/trait-upcasting/inference-behavior-change-deref.rs
index 999f3b16f50..79fb643eacd 100644
--- a/tests/ui/traits/trait-upcasting/inference-behavior-change-deref.rs
+++ b/tests/ui/traits/trait-upcasting/inference-behavior-change-deref.rs
@@ -1,4 +1,5 @@
#![deny(deref_into_dyn_supertrait)]
+#![feature(trait_upcasting)] // remove this and the test compiles
use std::ops::Deref;
diff --git a/tests/ui/traits/trait-upcasting/inference-behavior-change-deref.stderr b/tests/ui/traits/trait-upcasting/inference-behavior-change-deref.stderr
index fcc80c6148f..6b6a26d1593 100644
--- a/tests/ui/traits/trait-upcasting/inference-behavior-change-deref.stderr
+++ b/tests/ui/traits/trait-upcasting/inference-behavior-change-deref.stderr
@@ -1,5 +1,5 @@
error[E0308]: mismatched types
- --> $DIR/inference-behavior-change-deref.rs:33:18
+ --> $DIR/inference-behavior-change-deref.rs:34:18
|
LL | let z: u32 = y;
| --- ^ expected `u32`, found `i32`
diff --git a/tests/ui/traits/trait-upcasting/invalid-upcast.rs b/tests/ui/traits/trait-upcasting/invalid-upcast.rs
index 9269a5e3e9f..e634bbd5ac6 100644
--- a/tests/ui/traits/trait-upcasting/invalid-upcast.rs
+++ b/tests/ui/traits/trait-upcasting/invalid-upcast.rs
@@ -1,3 +1,5 @@
+#![feature(trait_upcasting)]
+
trait Foo {
fn a(&self) -> i32 {
10
diff --git a/tests/ui/traits/trait-upcasting/invalid-upcast.stderr b/tests/ui/traits/trait-upcasting/invalid-upcast.stderr
index e70b99d28c7..3aa21ee3ddd 100644
--- a/tests/ui/traits/trait-upcasting/invalid-upcast.stderr
+++ b/tests/ui/traits/trait-upcasting/invalid-upcast.stderr
@@ -1,5 +1,5 @@
error[E0308]: mismatched types
- --> $DIR/invalid-upcast.rs:51:35
+ --> $DIR/invalid-upcast.rs:53:35
|
LL | let _: &dyn std::fmt::Debug = baz;
| -------------------- ^^^ expected trait `Debug`, found trait `Baz`
@@ -10,7 +10,7 @@ LL | let _: &dyn std::fmt::Debug = baz;
found reference `&dyn Baz`
error[E0308]: mismatched types
- --> $DIR/invalid-upcast.rs:53:24
+ --> $DIR/invalid-upcast.rs:55:24
|
LL | let _: &dyn Send = baz;
| --------- ^^^ expected trait `Send`, found trait `Baz`
@@ -21,7 +21,7 @@ LL | let _: &dyn Send = baz;
found reference `&dyn Baz`
error[E0308]: mismatched types
- --> $DIR/invalid-upcast.rs:55:24
+ --> $DIR/invalid-upcast.rs:57:24
|
LL | let _: &dyn Sync = baz;
| --------- ^^^ expected trait `Sync`, found trait `Baz`
@@ -32,7 +32,7 @@ LL | let _: &dyn Sync = baz;
found reference `&dyn Baz`
error[E0308]: mismatched types
- --> $DIR/invalid-upcast.rs:58:25
+ --> $DIR/invalid-upcast.rs:60:25
|
LL | let bar: &dyn Bar = baz;
| -------- ^^^ expected trait `Bar`, found trait `Baz`
@@ -43,7 +43,7 @@ LL | let bar: &dyn Bar = baz;
found reference `&dyn Baz`
error[E0308]: mismatched types
- --> $DIR/invalid-upcast.rs:60:35
+ --> $DIR/invalid-upcast.rs:62:35
|
LL | let _: &dyn std::fmt::Debug = bar;
| -------------------- ^^^ expected trait `Debug`, found trait `Bar`
@@ -54,7 +54,7 @@ LL | let _: &dyn std::fmt::Debug = bar;
found reference `&dyn Bar`
error[E0308]: mismatched types
- --> $DIR/invalid-upcast.rs:62:24
+ --> $DIR/invalid-upcast.rs:64:24
|
LL | let _: &dyn Send = bar;
| --------- ^^^ expected trait `Send`, found trait `Bar`
@@ -65,7 +65,7 @@ LL | let _: &dyn Send = bar;
found reference `&dyn Bar`
error[E0308]: mismatched types
- --> $DIR/invalid-upcast.rs:64:24
+ --> $DIR/invalid-upcast.rs:66:24
|
LL | let _: &dyn Sync = bar;
| --------- ^^^ expected trait `Sync`, found trait `Bar`
@@ -76,7 +76,7 @@ LL | let _: &dyn Sync = bar;
found reference `&dyn Bar`
error[E0308]: mismatched types
- --> $DIR/invalid-upcast.rs:67:25
+ --> $DIR/invalid-upcast.rs:69:25
|
LL | let foo: &dyn Foo = baz;
| -------- ^^^ expected trait `Foo`, found trait `Baz`
@@ -87,7 +87,7 @@ LL | let foo: &dyn Foo = baz;
found reference `&dyn Baz`
error[E0308]: mismatched types
- --> $DIR/invalid-upcast.rs:69:35
+ --> $DIR/invalid-upcast.rs:71:35
|
LL | let _: &dyn std::fmt::Debug = foo;
| -------------------- ^^^ expected trait `Debug`, found trait `Foo`
@@ -98,7 +98,7 @@ LL | let _: &dyn std::fmt::Debug = foo;
found reference `&dyn Foo`
error[E0308]: mismatched types
- --> $DIR/invalid-upcast.rs:71:24
+ --> $DIR/invalid-upcast.rs:73:24
|
LL | let _: &dyn Send = foo;
| --------- ^^^ expected trait `Send`, found trait `Foo`
@@ -109,7 +109,7 @@ LL | let _: &dyn Send = foo;
found reference `&dyn Foo`
error[E0308]: mismatched types
- --> $DIR/invalid-upcast.rs:73:24
+ --> $DIR/invalid-upcast.rs:75:24
|
LL | let _: &dyn Sync = foo;
| --------- ^^^ expected trait `Sync`, found trait `Foo`
@@ -120,7 +120,7 @@ LL | let _: &dyn Sync = foo;
found reference `&dyn Foo`
error[E0308]: mismatched types
- --> $DIR/invalid-upcast.rs:76:25
+ --> $DIR/invalid-upcast.rs:78:25
|
LL | let foo: &dyn Foo = bar;
| -------- ^^^ expected trait `Foo`, found trait `Bar`
@@ -131,7 +131,7 @@ LL | let foo: &dyn Foo = bar;
found reference `&dyn Bar`
error[E0308]: mismatched types
- --> $DIR/invalid-upcast.rs:78:35
+ --> $DIR/invalid-upcast.rs:80:35
|
LL | let _: &dyn std::fmt::Debug = foo;
| -------------------- ^^^ expected trait `Debug`, found trait `Foo`
@@ -142,7 +142,7 @@ LL | let _: &dyn std::fmt::Debug = foo;
found reference `&dyn Foo`
error[E0308]: mismatched types
- --> $DIR/invalid-upcast.rs:80:24
+ --> $DIR/invalid-upcast.rs:82:24
|
LL | let _: &dyn Send = foo;
| --------- ^^^ expected trait `Send`, found trait `Foo`
@@ -153,7 +153,7 @@ LL | let _: &dyn Send = foo;
found reference `&dyn Foo`
error[E0308]: mismatched types
- --> $DIR/invalid-upcast.rs:82:24
+ --> $DIR/invalid-upcast.rs:84:24
|
LL | let _: &dyn Sync = foo;
| --------- ^^^ expected trait `Sync`, found trait `Foo`
diff --git a/tests/ui/traits/trait-upcasting/issue-11515-upcast-fn_mut-fn.rs b/tests/ui/traits/trait-upcasting/issue-11515-upcast-fn_mut-fn.rs
index 77ce627078f..b672963ae98 100644
--- a/tests/ui/traits/trait-upcasting/issue-11515-upcast-fn_mut-fn.rs
+++ b/tests/ui/traits/trait-upcasting/issue-11515-upcast-fn_mut-fn.rs
@@ -1,4 +1,5 @@
// run-pass
+#![feature(trait_upcasting)]
struct Test {
func: Box<dyn FnMut() + 'static>,
diff --git a/tests/ui/traits/trait-upcasting/issue-11515.current.stderr b/tests/ui/traits/trait-upcasting/issue-11515.current.stderr
new file mode 100644
index 00000000000..da7ac4cc04e
--- /dev/null
+++ b/tests/ui/traits/trait-upcasting/issue-11515.current.stderr
@@ -0,0 +1,13 @@
+error[E0658]: cannot cast `dyn Fn()` to `dyn FnMut()`, trait upcasting coercion is experimental
+ --> $DIR/issue-11515.rs:10:38
+ |
+LL | let test = Box::new(Test { func: closure });
+ | ^^^^^^^
+ |
+ = note: see issue #65991 <https://github.com/rust-lang/rust/issues/65991> for more information
+ = help: add `#![feature(trait_upcasting)]` to the crate attributes to enable
+ = note: required when coercing `Box<(dyn Fn() + 'static)>` into `Box<(dyn FnMut() + 'static)>`
+
+error: aborting due to 1 previous error
+
+For more information about this error, try `rustc --explain E0658`.
diff --git a/tests/ui/traits/trait-upcasting/issue-11515.next.stderr b/tests/ui/traits/trait-upcasting/issue-11515.next.stderr
new file mode 100644
index 00000000000..da7ac4cc04e
--- /dev/null
+++ b/tests/ui/traits/trait-upcasting/issue-11515.next.stderr
@@ -0,0 +1,13 @@
+error[E0658]: cannot cast `dyn Fn()` to `dyn FnMut()`, trait upcasting coercion is experimental
+ --> $DIR/issue-11515.rs:10:38
+ |
+LL | let test = Box::new(Test { func: closure });
+ | ^^^^^^^
+ |
+ = note: see issue #65991 <https://github.com/rust-lang/rust/issues/65991> for more information
+ = help: add `#![feature(trait_upcasting)]` to the crate attributes to enable
+ = note: required when coercing `Box<(dyn Fn() + 'static)>` into `Box<(dyn FnMut() + 'static)>`
+
+error: aborting due to 1 previous error
+
+For more information about this error, try `rustc --explain E0658`.
diff --git a/tests/ui/traits/trait-upcasting/issue-11515.rs b/tests/ui/traits/trait-upcasting/issue-11515.rs
index a1edb53ec37..31ea2fb353c 100644
--- a/tests/ui/traits/trait-upcasting/issue-11515.rs
+++ b/tests/ui/traits/trait-upcasting/issue-11515.rs
@@ -1,4 +1,3 @@
-// check-pass
// revisions: current next
//[next] compile-flags: -Znext-solver
@@ -8,5 +7,5 @@ struct Test {
fn main() {
let closure: Box<dyn Fn() + 'static> = Box::new(|| ());
- let test = Box::new(Test { func: closure });
+ let test = Box::new(Test { func: closure }); //~ ERROR trait upcasting coercion is experimental [E0658]
}
diff --git a/tests/ui/traits/trait-upcasting/lifetime.rs b/tests/ui/traits/trait-upcasting/lifetime.rs
index 6c65c38870f..9825158c2dd 100644
--- a/tests/ui/traits/trait-upcasting/lifetime.rs
+++ b/tests/ui/traits/trait-upcasting/lifetime.rs
@@ -1,5 +1,7 @@
// run-pass
+#![feature(trait_upcasting)]
+
trait Foo: PartialEq<i32> + std::fmt::Debug + Send + Sync {
fn a(&self) -> i32 {
10
diff --git a/tests/ui/traits/trait-upcasting/deref-lint-regions.rs b/tests/ui/traits/trait-upcasting/migrate-lint-deny-regions.rs
index 946305cbb2b..da1a9cc2775 100644
--- a/tests/ui/traits/trait-upcasting/deref-lint-regions.rs
+++ b/tests/ui/traits/trait-upcasting/migrate-lint-deny-regions.rs
@@ -1,4 +1,4 @@
-// check-pass
+#![deny(deref_into_dyn_supertrait)]
use std::ops::Deref;
@@ -6,7 +6,8 @@ trait Bar<'a> {}
trait Foo<'a>: Bar<'a> {}
impl<'a> Deref for dyn Foo<'a> {
- //~^ WARN this `Deref` implementation is covered by an implicit supertrait coercion
+ //~^ ERROR this `Deref` implementation is covered by an implicit supertrait coercion
+ //~| WARN this will change its meaning in a future release!
type Target = dyn Bar<'a>;
fn deref(&self) -> &Self::Target {
diff --git a/tests/ui/traits/trait-upcasting/migrate-lint-deny-regions.stderr b/tests/ui/traits/trait-upcasting/migrate-lint-deny-regions.stderr
new file mode 100644
index 00000000000..a5f3660d4bc
--- /dev/null
+++ b/tests/ui/traits/trait-upcasting/migrate-lint-deny-regions.stderr
@@ -0,0 +1,19 @@
+error: this `Deref` implementation is covered by an implicit supertrait coercion
+ --> $DIR/migrate-lint-deny-regions.rs:8:1
+ |
+LL | impl<'a> Deref for dyn Foo<'a> {
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ `dyn Foo<'_>` implements `Deref<Target = dyn Bar<'_>>` which conflicts with supertrait `Bar<'_>`
+...
+LL | type Target = dyn Bar<'a>;
+ | -------------------------- target type is a supertrait of `dyn Foo<'_>`
+ |
+ = warning: this will change its meaning in a future release!
+ = note: for more information, see issue #89460 <https://github.com/rust-lang/rust/issues/89460>
+note: the lint level is defined here
+ --> $DIR/migrate-lint-deny-regions.rs:1:9
+ |
+LL | #![deny(deref_into_dyn_supertrait)]
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^
+
+error: aborting due to 1 previous error
+
diff --git a/tests/ui/traits/trait-upcasting/deref-lint.rs b/tests/ui/traits/trait-upcasting/migrate-lint-deny.rs
index 68838d2ae20..926b3649e01 100644
--- a/tests/ui/traits/trait-upcasting/deref-lint.rs
+++ b/tests/ui/traits/trait-upcasting/migrate-lint-deny.rs
@@ -1,4 +1,4 @@
-// check-pass
+#![deny(deref_into_dyn_supertrait)]
use std::ops::Deref;
@@ -7,7 +7,8 @@ trait A {}
trait B: A {}
impl<'a> Deref for dyn 'a + B {
- //~^ WARN this `Deref` implementation is covered by an implicit supertrait coercion
+ //~^ ERROR this `Deref` implementation is covered by an implicit supertrait coercion
+ //~| WARN this will change its meaning in a future release!
type Target = dyn A;
fn deref(&self) -> &Self::Target {
diff --git a/tests/ui/traits/trait-upcasting/migrate-lint-deny.stderr b/tests/ui/traits/trait-upcasting/migrate-lint-deny.stderr
new file mode 100644
index 00000000000..29997a9b3d9
--- /dev/null
+++ b/tests/ui/traits/trait-upcasting/migrate-lint-deny.stderr
@@ -0,0 +1,19 @@
+error: this `Deref` implementation is covered by an implicit supertrait coercion
+ --> $DIR/migrate-lint-deny.rs:9:1
+ |
+LL | impl<'a> Deref for dyn 'a + B {
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ `dyn B` implements `Deref<Target = dyn A>` which conflicts with supertrait `A`
+...
+LL | type Target = dyn A;
+ | -------------------- target type is a supertrait of `dyn B`
+ |
+ = warning: this will change its meaning in a future release!
+ = note: for more information, see issue #89460 <https://github.com/rust-lang/rust/issues/89460>
+note: the lint level is defined here
+ --> $DIR/migrate-lint-deny.rs:1:9
+ |
+LL | #![deny(deref_into_dyn_supertrait)]
+ | ^^^^^^^^^^^^^^^^^^^^^^^^^
+
+error: aborting due to 1 previous error
+
diff --git a/tests/ui/traits/trait-upcasting/migrate-lint-different-substs.rs b/tests/ui/traits/trait-upcasting/migrate-lint-different-substs.rs
index 2c9126c863d..8a90a09ff04 100644
--- a/tests/ui/traits/trait-upcasting/migrate-lint-different-substs.rs
+++ b/tests/ui/traits/trait-upcasting/migrate-lint-different-substs.rs
@@ -10,6 +10,7 @@ trait Foo: Bar<i32> {
impl<'a> Deref for dyn Foo + 'a {
//~^ WARN this `Deref` implementation is covered by an implicit supertrait coercion
+ //~| WARN this will change its meaning in a future release!
type Target = dyn Bar<u32> + 'a;
fn deref(&self) -> &Self::Target {
diff --git a/tests/ui/traits/trait-upcasting/migrate-lint-different-substs.stderr b/tests/ui/traits/trait-upcasting/migrate-lint-different-substs.stderr
index a447f9cf83b..6245da5a176 100644
--- a/tests/ui/traits/trait-upcasting/migrate-lint-different-substs.stderr
+++ b/tests/ui/traits/trait-upcasting/migrate-lint-different-substs.stderr
@@ -3,11 +3,12 @@ warning: this `Deref` implementation is covered by an implicit supertrait coerci
|
LL | impl<'a> Deref for dyn Foo + 'a {
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ `dyn Foo` implements `Deref<Target = dyn Bar<u32>>` which conflicts with supertrait `Bar<i32>`
-LL |
+...
LL | type Target = dyn Bar<u32> + 'a;
| -------------------------------- target type is a supertrait of `dyn Foo`
|
- = help: consider removing this implementation or replacing it with a method instead
+ = warning: this will change its meaning in a future release!
+ = note: for more information, see issue #89460 <https://github.com/rust-lang/rust/issues/89460>
= note: `#[warn(deref_into_dyn_supertrait)]` on by default
warning: 1 warning emitted
diff --git a/tests/ui/traits/trait-upcasting/multiple-occurrence-ambiguousity.rs b/tests/ui/traits/trait-upcasting/multiple-occurrence-ambiguousity.rs
index 0e17c276717..2e53a00a90e 100644
--- a/tests/ui/traits/trait-upcasting/multiple-occurrence-ambiguousity.rs
+++ b/tests/ui/traits/trait-upcasting/multiple-occurrence-ambiguousity.rs
@@ -1,4 +1,5 @@
// check-fail
+#![feature(trait_upcasting)]
trait Bar<T> {
fn bar(&self, _: T) {}
diff --git a/tests/ui/traits/trait-upcasting/multiple-occurrence-ambiguousity.stderr b/tests/ui/traits/trait-upcasting/multiple-occurrence-ambiguousity.stderr
index c888ccc1ebb..70ba1fcaf38 100644
--- a/tests/ui/traits/trait-upcasting/multiple-occurrence-ambiguousity.stderr
+++ b/tests/ui/traits/trait-upcasting/multiple-occurrence-ambiguousity.stderr
@@ -1,5 +1,5 @@
error[E0308]: mismatched types
- --> $DIR/multiple-occurrence-ambiguousity.rs:19:26
+ --> $DIR/multiple-occurrence-ambiguousity.rs:20:26
|
LL | let t: &dyn Bar<_> = s;
| ----------- ^ expected trait `Bar`, found trait `Foo`
diff --git a/tests/ui/traits/trait-upcasting/normalization.rs b/tests/ui/traits/trait-upcasting/normalization.rs
index b594969483a..24da1ec5dfb 100644
--- a/tests/ui/traits/trait-upcasting/normalization.rs
+++ b/tests/ui/traits/trait-upcasting/normalization.rs
@@ -3,6 +3,8 @@
// revisions: current next
//[next] compile-flags: -Znext-solver
+#![feature(trait_upcasting)]
+
trait Mirror {
type Assoc;
}
diff --git a/tests/ui/traits/trait-upcasting/replace-vptr.rs b/tests/ui/traits/trait-upcasting/replace-vptr.rs
index 4a7304ec2d7..9ccfc9306ac 100644
--- a/tests/ui/traits/trait-upcasting/replace-vptr.rs
+++ b/tests/ui/traits/trait-upcasting/replace-vptr.rs
@@ -1,5 +1,7 @@
// run-pass
+#![feature(trait_upcasting)]
+
trait A {
fn foo_a(&self);
}
diff --git a/tests/ui/traits/trait-upcasting/struct.rs b/tests/ui/traits/trait-upcasting/struct.rs
index 64fa9ca1b5f..a3e41696956 100644
--- a/tests/ui/traits/trait-upcasting/struct.rs
+++ b/tests/ui/traits/trait-upcasting/struct.rs
@@ -1,5 +1,7 @@
// run-pass
+#![feature(trait_upcasting)]
+
use std::rc::Rc;
use std::sync::Arc;
diff --git a/tests/ui/traits/trait-upcasting/subtrait-method.rs b/tests/ui/traits/trait-upcasting/subtrait-method.rs
index 20277280440..136d15af0e8 100644
--- a/tests/ui/traits/trait-upcasting/subtrait-method.rs
+++ b/tests/ui/traits/trait-upcasting/subtrait-method.rs
@@ -1,3 +1,5 @@
+#![feature(trait_upcasting)]
+
trait Foo: PartialEq<i32> + std::fmt::Debug + Send + Sync {
fn a(&self) -> i32 {
10
diff --git a/tests/ui/traits/trait-upcasting/subtrait-method.stderr b/tests/ui/traits/trait-upcasting/subtrait-method.stderr
index 3fdf3f48161..918159e845b 100644
--- a/tests/ui/traits/trait-upcasting/subtrait-method.stderr
+++ b/tests/ui/traits/trait-upcasting/subtrait-method.stderr
@@ -1,64 +1,64 @@
error[E0599]: no method named `c` found for reference `&dyn Bar` in the current scope
- --> $DIR/subtrait-method.rs:53:9
+ --> $DIR/subtrait-method.rs:55:9
|
LL | bar.c();
| ^ help: there is a method with a similar name: `a`
|
= help: items from traits can only be used if the trait is implemented and in scope
note: `Baz` defines an item `c`, perhaps you need to implement it
- --> $DIR/subtrait-method.rs:25:1
+ --> $DIR/subtrait-method.rs:27:1
|
LL | trait Baz: Bar {
| ^^^^^^^^^^^^^^
error[E0599]: no method named `b` found for reference `&dyn Foo` in the current scope
- --> $DIR/subtrait-method.rs:57:9
+ --> $DIR/subtrait-method.rs:59:9
|
LL | foo.b();
| ^ help: there is a method with a similar name: `a`
|
= help: items from traits can only be used if the trait is implemented and in scope
note: `Bar` defines an item `b`, perhaps you need to implement it
- --> $DIR/subtrait-method.rs:15:1
+ --> $DIR/subtrait-method.rs:17:1
|
LL | trait Bar: Foo {
| ^^^^^^^^^^^^^^
error[E0599]: no method named `c` found for reference `&dyn Foo` in the current scope
- --> $DIR/subtrait-method.rs:59:9
+ --> $DIR/subtrait-method.rs:61:9
|
LL | foo.c();
| ^ help: there is a method with a similar name: `a`
|
= help: items from traits can only be used if the trait is implemented and in scope
note: `Baz` defines an item `c`, perhaps you need to implement it
- --> $DIR/subtrait-method.rs:25:1
+ --> $DIR/subtrait-method.rs:27:1
|
LL | trait Baz: Bar {
| ^^^^^^^^^^^^^^
error[E0599]: no method named `b` found for reference `&dyn Foo` in the current scope
- --> $DIR/subtrait-method.rs:63:9
+ --> $DIR/subtrait-method.rs:65:9
|
LL | foo.b();
| ^ help: there is a method with a similar name: `a`
|
= help: items from traits can only be used if the trait is implemented and in scope
note: `Bar` defines an item `b`, perhaps you need to implement it
- --> $DIR/subtrait-method.rs:15:1
+ --> $DIR/subtrait-method.rs:17:1
|
LL | trait Bar: Foo {
| ^^^^^^^^^^^^^^
error[E0599]: no method named `c` found for reference `&dyn Foo` in the current scope
- --> $DIR/subtrait-method.rs:65:9
+ --> $DIR/subtrait-method.rs:67:9
|
LL | foo.c();
| ^ help: there is a method with a similar name: `a`
|
= help: items from traits can only be used if the trait is implemented and in scope
note: `Baz` defines an item `c`, perhaps you need to implement it
- --> $DIR/subtrait-method.rs:25:1
+ --> $DIR/subtrait-method.rs:27:1
|
LL | trait Baz: Bar {
| ^^^^^^^^^^^^^^
diff --git a/tests/ui/traits/trait-upcasting/type-checking-test-1.current.stderr b/tests/ui/traits/trait-upcasting/type-checking-test-1.current.stderr
index 47ffa68b8ff..10c22440a83 100644
--- a/tests/ui/traits/trait-upcasting/type-checking-test-1.current.stderr
+++ b/tests/ui/traits/trait-upcasting/type-checking-test-1.current.stderr
@@ -1,5 +1,5 @@
error[E0605]: non-primitive cast: `&dyn Foo` as `&dyn Bar<_>`
- --> $DIR/type-checking-test-1.rs:17:13
+ --> $DIR/type-checking-test-1.rs:19:13
|
LL | let _ = x as &dyn Bar<_>; // Ambiguous
| ^^^^^^^^^^^^^^^^ an `as` expression can only be used to convert between primitive types or to coerce to a specific trait object
diff --git a/tests/ui/traits/trait-upcasting/type-checking-test-1.next.stderr b/tests/ui/traits/trait-upcasting/type-checking-test-1.next.stderr
index 47ffa68b8ff..10c22440a83 100644
--- a/tests/ui/traits/trait-upcasting/type-checking-test-1.next.stderr
+++ b/tests/ui/traits/trait-upcasting/type-checking-test-1.next.stderr
@@ -1,5 +1,5 @@
error[E0605]: non-primitive cast: `&dyn Foo` as `&dyn Bar<_>`
- --> $DIR/type-checking-test-1.rs:17:13
+ --> $DIR/type-checking-test-1.rs:19:13
|
LL | let _ = x as &dyn Bar<_>; // Ambiguous
| ^^^^^^^^^^^^^^^^ an `as` expression can only be used to convert between primitive types or to coerce to a specific trait object
diff --git a/tests/ui/traits/trait-upcasting/type-checking-test-1.rs b/tests/ui/traits/trait-upcasting/type-checking-test-1.rs
index 7d3deeeaa61..54c3c5e0c28 100644
--- a/tests/ui/traits/trait-upcasting/type-checking-test-1.rs
+++ b/tests/ui/traits/trait-upcasting/type-checking-test-1.rs
@@ -1,6 +1,8 @@
// revisions: current next
//[next] compile-flags: -Znext-solver
+#![feature(trait_upcasting)]
+
trait Foo: Bar<i32> + Bar<u32> {}
trait Bar<T> {
fn bar(&self) -> Option<T> {
diff --git a/tests/ui/traits/trait-upcasting/type-checking-test-2.rs b/tests/ui/traits/trait-upcasting/type-checking-test-2.rs
index b4df0f5a902..b024b27750b 100644
--- a/tests/ui/traits/trait-upcasting/type-checking-test-2.rs
+++ b/tests/ui/traits/trait-upcasting/type-checking-test-2.rs
@@ -1,3 +1,5 @@
+#![feature(trait_upcasting)]
+
trait Foo<T>: Bar<i32> + Bar<T> {}
trait Bar<T> {
fn bar(&self) -> Option<T> {
diff --git a/tests/ui/traits/trait-upcasting/type-checking-test-2.stderr b/tests/ui/traits/trait-upcasting/type-checking-test-2.stderr
index f84ea93dc67..3e59b9d3363 100644
--- a/tests/ui/traits/trait-upcasting/type-checking-test-2.stderr
+++ b/tests/ui/traits/trait-upcasting/type-checking-test-2.stderr
@@ -1,11 +1,11 @@
error[E0605]: non-primitive cast: `&dyn Foo<i32>` as `&dyn Bar<u32>`
- --> $DIR/type-checking-test-2.rs:17:13
+ --> $DIR/type-checking-test-2.rs:19:13
|
LL | let _ = x as &dyn Bar<u32>; // Error
| ^^^^^^^^^^^^^^^^^^ an `as` expression can only be used to convert between primitive types or to coerce to a specific trait object
error[E0605]: non-primitive cast: `&dyn Foo<u32>` as `&dyn Bar<_>`
- --> $DIR/type-checking-test-2.rs:22:13
+ --> $DIR/type-checking-test-2.rs:24:13
|
LL | let a = x as &dyn Bar<_>; // Ambiguous
| ^^^^^^^^^^^^^^^^ an `as` expression can only be used to convert between primitive types or to coerce to a specific trait object
diff --git a/tests/ui/traits/trait-upcasting/type-checking-test-3.rs b/tests/ui/traits/trait-upcasting/type-checking-test-3.rs
index 3685569d98d..b2db3a12797 100644
--- a/tests/ui/traits/trait-upcasting/type-checking-test-3.rs
+++ b/tests/ui/traits/trait-upcasting/type-checking-test-3.rs
@@ -1,3 +1,5 @@
+#![feature(trait_upcasting)]
+
trait Foo<'a>: Bar<'a> {}
trait Bar<'a> {}
diff --git a/tests/ui/traits/trait-upcasting/type-checking-test-3.stderr b/tests/ui/traits/trait-upcasting/type-checking-test-3.stderr
index 640a6066268..e6cb6a75399 100644
--- a/tests/ui/traits/trait-upcasting/type-checking-test-3.stderr
+++ b/tests/ui/traits/trait-upcasting/type-checking-test-3.stderr
@@ -1,5 +1,5 @@
error: lifetime may not live long enough
- --> $DIR/type-checking-test-3.rs:9:13
+ --> $DIR/type-checking-test-3.rs:11:13
|
LL | fn test_wrong1<'a>(x: &dyn Foo<'static>, y: &'a u32) {
| -- lifetime `'a` defined here
@@ -7,7 +7,7 @@ LL | let _ = x as &dyn Bar<'a>; // Error
| ^^^^^^^^^^^^^^^^^ type annotation requires that `'a` must outlive `'static`
error: lifetime may not live long enough
- --> $DIR/type-checking-test-3.rs:14:13
+ --> $DIR/type-checking-test-3.rs:16:13
|
LL | fn test_wrong2<'a>(x: &dyn Foo<'a>) {
| -- lifetime `'a` defined here
diff --git a/tests/ui/traits/trait-upcasting/type-checking-test-4.rs b/tests/ui/traits/trait-upcasting/type-checking-test-4.rs
index 65391502386..f40c48f0d12 100644
--- a/tests/ui/traits/trait-upcasting/type-checking-test-4.rs
+++ b/tests/ui/traits/trait-upcasting/type-checking-test-4.rs
@@ -1,3 +1,5 @@
+#![feature(trait_upcasting)]
+
trait Foo<'a>: Bar<'a, 'a> {}
trait Bar<'a, 'b> {
fn get_b(&self) -> Option<&'a u32> {
diff --git a/tests/ui/traits/trait-upcasting/type-checking-test-4.stderr b/tests/ui/traits/trait-upcasting/type-checking-test-4.stderr
index 7e7548955d3..8d506e5807e 100644
--- a/tests/ui/traits/trait-upcasting/type-checking-test-4.stderr
+++ b/tests/ui/traits/trait-upcasting/type-checking-test-4.stderr
@@ -1,5 +1,5 @@
error: lifetime may not live long enough
- --> $DIR/type-checking-test-4.rs:13:13
+ --> $DIR/type-checking-test-4.rs:15:13
|
LL | fn test_wrong1<'a>(x: &dyn Foo<'static>, y: &'a u32) {
| -- lifetime `'a` defined here
@@ -7,7 +7,7 @@ LL | let _ = x as &dyn Bar<'static, 'a>; // Error
| ^^^^^^^^^^^^^^^^^^^^^^^^^^ type annotation requires that `'a` must outlive `'static`
error: lifetime may not live long enough
- --> $DIR/type-checking-test-4.rs:18:13
+ --> $DIR/type-checking-test-4.rs:20:13
|
LL | fn test_wrong2<'a>(x: &dyn Foo<'static>, y: &'a u32) {
| -- lifetime `'a` defined here
@@ -15,7 +15,7 @@ LL | let _ = x as &dyn Bar<'a, 'static>; // Error
| ^^^^^^^^^^^^^^^^^^^^^^^^^^ type annotation requires that `'a` must outlive `'static`
error: lifetime may not live long enough
- --> $DIR/type-checking-test-4.rs:24:5
+ --> $DIR/type-checking-test-4.rs:26:5
|
LL | fn test_wrong3<'a>(x: &dyn Foo<'a>) -> Option<&'static u32> {
| -- lifetime `'a` defined here
@@ -24,7 +24,7 @@ LL | y.get_b() // ERROR
| ^^^^^^^^^ returning this value requires that `'a` must outlive `'static`
error: lifetime may not live long enough
- --> $DIR/type-checking-test-4.rs:29:5
+ --> $DIR/type-checking-test-4.rs:31:5
|
LL | fn test_wrong4<'a>(x: &dyn Foo<'a>) -> Option<&'static u32> {
| -- lifetime `'a` defined here
@@ -32,7 +32,7 @@ LL | <_ as Bar>::get_b(x) // ERROR
| ^^^^^^^^^^^^^^^^^^^^ returning this value requires that `'a` must outlive `'static`
error: lifetime may not live long enough
- --> $DIR/type-checking-test-4.rs:34:5
+ --> $DIR/type-checking-test-4.rs:36:5
|
LL | fn test_wrong5<'a>(x: &dyn Foo<'a>) -> Option<&'static u32> {
| -- lifetime `'a` defined here
@@ -40,7 +40,7 @@ LL | <_ as Bar<'_, '_>>::get_b(x) // ERROR
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ returning this value requires that `'a` must outlive `'static`
error: lifetime may not live long enough
- --> $DIR/type-checking-test-4.rs:42:5
+ --> $DIR/type-checking-test-4.rs:44:5
|
LL | fn test_wrong6<'a>(x: &dyn Foo<'a>) -> Option<&'static u32> {
| -- lifetime `'a` defined here
diff --git a/tests/ui/traits/trait-upcasting/upcast-through-struct-tail.current.stderr b/tests/ui/traits/trait-upcasting/upcast-through-struct-tail.current.stderr
new file mode 100644
index 00000000000..f1f0cd30957
--- /dev/null
+++ b/tests/ui/traits/trait-upcasting/upcast-through-struct-tail.current.stderr
@@ -0,0 +1,13 @@
+error[E0658]: cannot cast `dyn A` to `dyn B`, trait upcasting coercion is experimental
+ --> $DIR/upcast-through-struct-tail.rs:10:5
+ |
+LL | x
+ | ^
+ |
+ = note: see issue #65991 <https://github.com/rust-lang/rust/issues/65991> for more information
+ = help: add `#![feature(trait_upcasting)]` to the crate attributes to enable
+ = note: required when coercing `Box<Wrapper<(dyn A + 'a)>>` into `Box<Wrapper<(dyn B + 'a)>>`
+
+error: aborting due to 1 previous error
+
+For more information about this error, try `rustc --explain E0658`.
diff --git a/tests/ui/traits/trait-upcasting/upcast-through-struct-tail.next.stderr b/tests/ui/traits/trait-upcasting/upcast-through-struct-tail.next.stderr
new file mode 100644
index 00000000000..f1f0cd30957
--- /dev/null
+++ b/tests/ui/traits/trait-upcasting/upcast-through-struct-tail.next.stderr
@@ -0,0 +1,13 @@
+error[E0658]: cannot cast `dyn A` to `dyn B`, trait upcasting coercion is experimental
+ --> $DIR/upcast-through-struct-tail.rs:10:5
+ |
+LL | x
+ | ^
+ |
+ = note: see issue #65991 <https://github.com/rust-lang/rust/issues/65991> for more information
+ = help: add `#![feature(trait_upcasting)]` to the crate attributes to enable
+ = note: required when coercing `Box<Wrapper<(dyn A + 'a)>>` into `Box<Wrapper<(dyn B + 'a)>>`
+
+error: aborting due to 1 previous error
+
+For more information about this error, try `rustc --explain E0658`.
diff --git a/tests/ui/traits/trait-upcasting/upcast-through-struct-tail.rs b/tests/ui/traits/trait-upcasting/upcast-through-struct-tail.rs
index f8cf793e4a4..948f058e528 100644
--- a/tests/ui/traits/trait-upcasting/upcast-through-struct-tail.rs
+++ b/tests/ui/traits/trait-upcasting/upcast-through-struct-tail.rs
@@ -1,4 +1,3 @@
-// check-pass
// revisions: current next
//[next] compile-flags: -Znext-solver
@@ -9,6 +8,7 @@ trait B {}
fn test<'a>(x: Box<Wrapper<dyn A + 'a>>) -> Box<Wrapper<dyn B + 'a>> {
x
+ //~^ ERROR cannot cast `dyn A` to `dyn B`, trait upcasting coercion is experimental
}
fn main() {}