diff --git a/compiler/rustc_hir_typeck/src/pat.rs b/compiler/rustc_hir_typeck/src/pat.rs index fb78da0a86c..423ffced897 100644 --- a/compiler/rustc_hir_typeck/src/pat.rs +++ b/compiler/rustc_hir_typeck/src/pat.rs @@ -690,16 +690,29 @@ fn check_pat_ident( BindingMode(def_br, Mutability::Mut) } else { - // `mut` resets binding mode on edition <= 2021 - self.typeck_results + // `mut` resets the binding mode on edition <= 2021 + *self + .typeck_results .borrow_mut() .rust_2024_migration_desugared_pats_mut() - .insert(pat_info.top_info.hir_id); + .entry(pat_info.top_info.hir_id) + .or_default() |= pat.span.at_least_rust_2024(); BindingMode(ByRef::No, Mutability::Mut) } } BindingMode(ByRef::No, mutbl) => BindingMode(def_br, mutbl), - BindingMode(ByRef::Yes(_), _) => user_bind_annot, + BindingMode(ByRef::Yes(_), _) => { + if matches!(def_br, ByRef::Yes(_)) { + // `ref`/`ref mut` overrides the binding mode on edition <= 2021 + *self + .typeck_results + .borrow_mut() + .rust_2024_migration_desugared_pats_mut() + .entry(pat_info.top_info.hir_id) + .or_default() |= pat.span.at_least_rust_2024(); + } + user_bind_annot + } }; if bm.0 == ByRef::Yes(Mutability::Mut) @@ -2204,14 +2217,14 @@ fn check_pat_ref( } } else { // Reset binding mode on old editions - if pat_info.binding_mode != ByRef::No { pat_info.binding_mode = ByRef::No; - - self.typeck_results + *self + .typeck_results .borrow_mut() .rust_2024_migration_desugared_pats_mut() - .insert(pat_info.top_info.hir_id); + .entry(pat_info.top_info.hir_id) + .or_default() |= pat.span.at_least_rust_2024(); } } @@ -2262,6 +2275,7 @@ fn check_pat_ref( (err, err) } }; + self.check_pat(inner, inner_ty, pat_info); ref_ty } diff --git a/compiler/rustc_hir_typeck/src/writeback.rs b/compiler/rustc_hir_typeck/src/writeback.rs index b193b81f6de..d3d092be222 100644 --- a/compiler/rustc_hir_typeck/src/writeback.rs +++ b/compiler/rustc_hir_typeck/src/writeback.rs @@ -635,7 +635,7 @@ fn visit_adjustments(&mut self, span: Span, hir_id: HirId) { #[instrument(skip(self), level = "debug")] fn visit_rust_2024_migration_desugared_pats(&mut self, hir_id: hir::HirId) { - if self + if let Some(is_hard_error) = self .fcx .typeck_results .borrow_mut() @@ -645,7 +645,9 @@ fn visit_rust_2024_migration_desugared_pats(&mut self, hir_id: hir::HirId) { debug!( "node is a pat whose match ergonomics are desugared by the Rust 2024 migration lint" ); - self.typeck_results.rust_2024_migration_desugared_pats_mut().insert(hir_id); + self.typeck_results + .rust_2024_migration_desugared_pats_mut() + .insert(hir_id, is_hard_error); } } diff --git a/compiler/rustc_lint_defs/src/builtin.rs b/compiler/rustc_lint_defs/src/builtin.rs index f532b9b153b..45a5ce0ca20 100644 --- a/compiler/rustc_lint_defs/src/builtin.rs +++ b/compiler/rustc_lint_defs/src/builtin.rs @@ -1651,7 +1651,6 @@ /// ### Example /// /// ```rust,edition2021 - /// #![feature(ref_pat_eat_one_layer_2024)] /// #![warn(rust_2024_incompatible_pat)] /// /// if let Some(&a) = &Some(&0u8) { @@ -1672,12 +1671,10 @@ pub RUST_2024_INCOMPATIBLE_PAT, Allow, "detects patterns whose meaning will change in Rust 2024", - @feature_gate = ref_pat_eat_one_layer_2024; - // FIXME uncomment below upon stabilization - /*@future_incompatible = FutureIncompatibleInfo { + @future_incompatible = FutureIncompatibleInfo { reason: FutureIncompatibilityReason::EditionSemanticsChange(Edition::Edition2024), reference: "123076", - };*/ + }; } declare_lint! { diff --git a/compiler/rustc_middle/src/ty/typeck_results.rs b/compiler/rustc_middle/src/ty/typeck_results.rs index c01d2120111..6aa2b2cd480 100644 --- a/compiler/rustc_middle/src/ty/typeck_results.rs +++ b/compiler/rustc_middle/src/ty/typeck_results.rs @@ -73,9 +73,10 @@ pub struct TypeckResults<'tcx> { /// Stores the actual binding mode for all instances of [`BindingMode`]. pat_binding_modes: ItemLocalMap, - /// Top-level patterns whose match ergonomics need to be desugared - /// by the Rust 2021 -> 2024 migration lint. - rust_2024_migration_desugared_pats: ItemLocalSet, + /// Top-level patterns whose match ergonomics need to be desugared by the Rust 2021 -> 2024 + /// migration lint. The boolean indicates whether the emitted diagnostic should be a hard error + /// (if any of the incompatible pattern elements are in edition 2024). + rust_2024_migration_desugared_pats: ItemLocalMap, /// Stores the types which were implicitly dereferenced in pattern binding modes /// for later usage in THIR lowering. For example, @@ -418,15 +419,15 @@ pub fn pat_adjustments_mut(&mut self) -> LocalTableInContextMut<'_, Vec LocalTableInContextMut { hir_owner: self.hir_owner, data: &mut self.pat_adjustments } } - pub fn rust_2024_migration_desugared_pats(&self) -> LocalSetInContext<'_> { - LocalSetInContext { + pub fn rust_2024_migration_desugared_pats(&self) -> LocalTableInContext<'_, bool> { + LocalTableInContext { hir_owner: self.hir_owner, data: &self.rust_2024_migration_desugared_pats, } } - pub fn rust_2024_migration_desugared_pats_mut(&mut self) -> LocalSetInContextMut<'_> { - LocalSetInContextMut { + pub fn rust_2024_migration_desugared_pats_mut(&mut self) -> LocalTableInContextMut<'_, bool> { + LocalTableInContextMut { hir_owner: self.hir_owner, data: &mut self.rust_2024_migration_desugared_pats, } diff --git a/compiler/rustc_mir_build/messages.ftl b/compiler/rustc_mir_build/messages.ftl index 1c4e9fd11cb..55149570dbc 100644 --- a/compiler/rustc_mir_build/messages.ftl +++ b/compiler/rustc_mir_build/messages.ftl @@ -265,7 +265,7 @@ mir_build_pointer_pattern = function pointers and raw pointers not derived from mir_build_privately_uninhabited = pattern `{$witness_1}` is currently uninhabited, but this variant contains private fields which may become inhabited in the future -mir_build_rust_2024_incompatible_pat = the semantics of this pattern will change in edition 2024 +mir_build_rust_2024_incompatible_pat = patterns are not allowed to reset the default binding mode in edition 2024 mir_build_rustc_box_attribute_error = `#[rustc_box]` attribute used incorrectly .attributes = no other attributes may be applied diff --git a/compiler/rustc_mir_build/src/errors.rs b/compiler/rustc_mir_build/src/errors.rs index 42be7f9402e..00f65e0c7d0 100644 --- a/compiler/rustc_mir_build/src/errors.rs +++ b/compiler/rustc_mir_build/src/errors.rs @@ -983,6 +983,8 @@ pub(crate) struct Rust2024IncompatiblePat { pub(crate) struct Rust2024IncompatiblePatSugg { pub(crate) suggestion: Vec<(Span, String)>, + /// Whether the incompatibility is a hard error because a relevant span is in edition 2024. + pub(crate) is_hard_error: bool, } impl Subdiagnostic for Rust2024IncompatiblePatSugg { diff --git a/compiler/rustc_mir_build/src/thir/pattern/mod.rs b/compiler/rustc_mir_build/src/thir/pattern/mod.rs index 04e921ecc2e..56e5156a91f 100644 --- a/compiler/rustc_mir_build/src/thir/pattern/mod.rs +++ b/compiler/rustc_mir_build/src/thir/pattern/mod.rs @@ -25,6 +25,7 @@ pub(crate) use self::check_match::check_match; use crate::errors::*; +use crate::fluent_generated as fluent; use crate::thir::util::UserAnnotatedTyHelpers; struct PatCtxt<'a, 'tcx> { @@ -48,18 +49,28 @@ pub(super) fn pat_from_hir<'a, 'tcx>( typeck_results, rust_2024_migration_suggestion: typeck_results .rust_2024_migration_desugared_pats() - .contains(pat.hir_id) - .then_some(Rust2024IncompatiblePatSugg { suggestion: Vec::new() }), + .get(pat.hir_id) + .map(|&is_hard_error| Rust2024IncompatiblePatSugg { + suggestion: Vec::new(), + is_hard_error, + }), }; let result = pcx.lower_pattern(pat); debug!("pat_from_hir({:?}) = {:?}", pat, result); if let Some(sugg) = pcx.rust_2024_migration_suggestion { - tcx.emit_node_span_lint( - lint::builtin::RUST_2024_INCOMPATIBLE_PAT, - pat.hir_id, - pat.span, - Rust2024IncompatiblePat { sugg }, - ); + if sugg.is_hard_error { + let mut err = + tcx.dcx().struct_span_err(pat.span, fluent::mir_build_rust_2024_incompatible_pat); + err.subdiagnostic(sugg); + err.emit(); + } else { + tcx.emit_node_span_lint( + lint::builtin::RUST_2024_INCOMPATIBLE_PAT, + pat.hir_id, + pat.span, + Rust2024IncompatiblePat { sugg }, + ); + } } result } diff --git a/compiler/rustc_monomorphize/src/partitioning.rs b/compiler/rustc_monomorphize/src/partitioning.rs index 5bd484d7bb0..9bf7e67417e 100644 --- a/compiler/rustc_monomorphize/src/partitioning.rs +++ b/compiler/rustc_monomorphize/src/partitioning.rs @@ -119,6 +119,7 @@ use rustc_session::CodegenUnits; use rustc_session::config::{DumpMonoStatsFormat, SwitchWithOptPath}; use rustc_span::symbol::Symbol; +use rustc_target::spec::SymbolVisibility; use tracing::debug; use crate::collector::{self, MonoItemCollectionStrategy, UsageMap}; @@ -904,6 +905,11 @@ fn mono_item_visibility<'tcx>( } fn default_visibility(tcx: TyCtxt<'_>, id: DefId, is_generic: bool) -> Visibility { + // Fast-path to avoid expensive query call below + if tcx.sess.default_visibility() == SymbolVisibility::Interposable { + return Visibility::Default; + } + let export_level = if is_generic { // Generic functions never have export-level C. SymbolExportLevel::Rust @@ -913,6 +919,7 @@ fn default_visibility(tcx: TyCtxt<'_>, id: DefId, is_generic: bool) -> Visibilit _ => SymbolExportLevel::Rust, } }; + match export_level { // C-export level items remain at `Default` to allow C code to // access and interpose them. diff --git a/compiler/rustc_next_trait_solver/src/solve/assembly/mod.rs b/compiler/rustc_next_trait_solver/src/solve/assembly/mod.rs index cebeef76bfc..c9c0d6391fc 100644 --- a/compiler/rustc_next_trait_solver/src/solve/assembly/mod.rs +++ b/compiler/rustc_next_trait_solver/src/solve/assembly/mod.rs @@ -6,6 +6,7 @@ use rustc_type_ir::fold::TypeFoldable; use rustc_type_ir::inherent::*; use rustc_type_ir::lang_items::TraitSolverLangItem; +use rustc_type_ir::solve::inspect; use rustc_type_ir::visit::TypeVisitableExt as _; use rustc_type_ir::{self as ty, Interner, Upcast as _, elaborate}; use tracing::{debug, instrument}; @@ -288,6 +289,25 @@ pub(super) fn assemble_and_evaluate_candidates>( let Ok(normalized_self_ty) = self.structurally_normalize_ty(goal.param_env, goal.predicate.self_ty()) else { + // FIXME: We register a fake candidate when normalization fails so that + // we can point at the reason for *why*. I'm tempted to say that this + // is the wrong way to do this, though. + let result = + self.probe(|&result| inspect::ProbeKind::RigidAlias { result }).enter(|this| { + let normalized_ty = this.next_ty_infer(); + let alias_relate_goal = Goal::new( + this.cx(), + goal.param_env, + ty::PredicateKind::AliasRelate( + goal.predicate.self_ty().into(), + normalized_ty.into(), + ty::AliasRelationDirection::Equate, + ), + ); + this.add_goal(GoalSource::AliasWellFormed, alias_relate_goal); + this.evaluate_added_goals_and_make_canonical_response(Certainty::AMBIGUOUS) + }); + assert_eq!(result, Err(NoSolution)); return vec![]; }; diff --git a/compiler/rustc_next_trait_solver/src/solve/eval_ctxt/mod.rs b/compiler/rustc_next_trait_solver/src/solve/eval_ctxt/mod.rs index daacc669118..0f8b796d602 100644 --- a/compiler/rustc_next_trait_solver/src/solve/eval_ctxt/mod.rs +++ b/compiler/rustc_next_trait_solver/src/solve/eval_ctxt/mod.rs @@ -983,7 +983,7 @@ pub(super) fn add_item_bounds_for_hidden_type( hidden_ty, &mut goals, ); - self.add_goals(GoalSource::Misc, goals); + self.add_goals(GoalSource::AliasWellFormed, goals); } // Do something for each opaque/hidden pair defined with `def_id` in the diff --git a/compiler/rustc_next_trait_solver/src/solve/normalizes_to/mod.rs b/compiler/rustc_next_trait_solver/src/solve/normalizes_to/mod.rs index 005b293621a..4d8b193ee49 100644 --- a/compiler/rustc_next_trait_solver/src/solve/normalizes_to/mod.rs +++ b/compiler/rustc_next_trait_solver/src/solve/normalizes_to/mod.rs @@ -15,7 +15,7 @@ use crate::solve::inspect::ProbeKind; use crate::solve::{ BuiltinImplSource, CandidateSource, Certainty, EvalCtxt, Goal, GoalSource, MaybeCause, - NoSolution, QueryResult, + NoSolution, QueryResult, Reveal, }; impl EvalCtxt<'_, D> @@ -37,13 +37,64 @@ pub(super) fn compute_normalizes_to_goal( match normalize_result { Ok(res) => Ok(res), Err(NoSolution) => { - let Goal { param_env, predicate: NormalizesTo { alias, term } } = goal; - self.relate_rigid_alias_non_alias(param_env, alias, ty::Invariant, term)?; - self.evaluate_added_goals_and_make_canonical_response(Certainty::Yes) + self.probe(|&result| ProbeKind::RigidAlias { result }).enter(|this| { + let Goal { param_env, predicate: NormalizesTo { alias, term } } = goal; + this.add_rigid_constraints(param_env, alias)?; + this.relate_rigid_alias_non_alias(param_env, alias, ty::Invariant, term)?; + this.evaluate_added_goals_and_make_canonical_response(Certainty::Yes) + }) } } } + /// Register any obligations that are used to validate that an alias should be + /// treated as rigid. + /// + /// An alias may be considered rigid if it fails normalization, but we also don't + /// want to consider aliases that are not well-formed to be rigid simply because + /// they fail normalization. + /// + /// For example, some `::Assoc` where `T: Trait` does not hold, or an + /// opaque type whose hidden type doesn't actually satisfy the opaque item bounds. + fn add_rigid_constraints( + &mut self, + param_env: I::ParamEnv, + rigid_alias: ty::AliasTerm, + ) -> Result<(), NoSolution> { + let cx = self.cx(); + match rigid_alias.kind(cx) { + // Projections are rigid only if their trait ref holds, + // and the GAT where-clauses hold. + ty::AliasTermKind::ProjectionTy | ty::AliasTermKind::ProjectionConst => { + let trait_ref = rigid_alias.trait_ref(cx); + self.add_goal(GoalSource::AliasWellFormed, Goal::new(cx, param_env, trait_ref)); + Ok(()) + } + ty::AliasTermKind::OpaqueTy => { + match param_env.reveal() { + // In user-facing mode, paques are only rigid if we may not define it. + Reveal::UserFacing => { + if rigid_alias + .def_id + .as_local() + .is_some_and(|def_id| self.can_define_opaque_ty(def_id)) + { + Err(NoSolution) + } else { + Ok(()) + } + } + // Opaques are never rigid in reveal-all mode. + Reveal::All => Err(NoSolution), + } + } + // FIXME(generic_const_exprs): we would need to support generic consts here + ty::AliasTermKind::UnevaluatedConst => Err(NoSolution), + // Inherent and weak types are never rigid. This type must not be well-formed. + ty::AliasTermKind::WeakTy | ty::AliasTermKind::InherentTy => Err(NoSolution), + } + } + /// Normalize the given alias by at least one step. If the alias is rigid, this /// returns `NoSolution`. #[instrument(level = "trace", skip(self), ret)] @@ -124,6 +175,7 @@ fn probe_and_match_goal_against_assumption( ecx.instantiate_normalizes_to_term(goal, assumption_projection_pred.term); // Add GAT where clauses from the trait's definition + // FIXME: We don't need these, since these are the type's own WF obligations. ecx.add_goals( GoalSource::Misc, cx.own_predicates_of(goal.predicate.def_id()) @@ -179,7 +231,8 @@ fn consider_impl_candidate( .map(|pred| goal.with(cx, pred)); ecx.add_goals(GoalSource::ImplWhereBound, where_clause_bounds); - // Add GAT where clauses from the trait's definition + // Add GAT where clauses from the trait's definition. + // FIXME: We don't need these, since these are the type's own WF obligations. ecx.add_goals( GoalSource::Misc, cx.own_predicates_of(goal.predicate.def_id()) diff --git a/compiler/rustc_serialize/src/serialize.rs b/compiler/rustc_serialize/src/serialize.rs index bae5f259fcc..db8555edd0f 100644 --- a/compiler/rustc_serialize/src/serialize.rs +++ b/compiler/rustc_serialize/src/serialize.rs @@ -288,7 +288,7 @@ fn decode(d: &mut D) -> Rc { impl> Encodable for [T] { default fn encode(&self, s: &mut S) { s.emit_usize(self.len()); - for e in self.iter() { + for e in self { e.encode(s); } } @@ -527,7 +527,7 @@ fn decode(d: &mut D) -> ThinVec { impl> Encodable for VecDeque { fn encode(&self, s: &mut S) { s.emit_usize(self.len()); - for e in self.iter() { + for e in self { e.encode(s); } } @@ -547,7 +547,7 @@ impl Encodable for BTreeMap { fn encode(&self, e: &mut S) { e.emit_usize(self.len()); - for (key, val) in self.iter() { + for (key, val) in self { key.encode(e); val.encode(e); } @@ -571,7 +571,7 @@ impl Encodable for BTreeSet { fn encode(&self, s: &mut S) { s.emit_usize(self.len()); - for e in self.iter() { + for e in self { e.encode(s); } } @@ -595,7 +595,7 @@ impl Encodable for HashMap { fn encode(&self, e: &mut E) { e.emit_usize(self.len()); - for (key, val) in self.iter() { + for (key, val) in self { key.encode(e); val.encode(e); } @@ -621,7 +621,7 @@ impl Encodable for HashSet { fn encode(&self, s: &mut E) { s.emit_usize(self.len()); - for e in self.iter() { + for e in self { e.encode(s); } } @@ -646,7 +646,7 @@ impl Encodable for indexmap::IndexMap { fn encode(&self, e: &mut E) { e.emit_usize(self.len()); - for (key, val) in self.iter() { + for (key, val) in self { key.encode(e); val.encode(e); } @@ -672,7 +672,7 @@ impl Encodable for indexmap::IndexSet { fn encode(&self, s: &mut E) { s.emit_usize(self.len()); - for e in self.iter() { + for e in self { e.encode(s); } } diff --git a/compiler/rustc_trait_selection/src/solve/fulfill.rs b/compiler/rustc_trait_selection/src/solve/fulfill.rs index d9dc772eca9..53e5420d27a 100644 --- a/compiler/rustc_trait_selection/src/solve/fulfill.rs +++ b/compiler/rustc_trait_selection/src/solve/fulfill.rs @@ -14,7 +14,7 @@ use rustc_middle::ty::error::{ExpectedFound, TypeError}; use rustc_middle::ty::{self, TyCtxt}; use rustc_next_trait_solver::solve::{GenerateProofTree, HasChanged, SolverDelegateEvalExt as _}; -use tracing::instrument; +use tracing::{instrument, trace}; use super::Certainty; use super::delegate::SolverDelegate; @@ -401,6 +401,7 @@ fn non_trivial_candidates<'a>( nested_goal.source(), GoalSource::ImplWhereBound | GoalSource::InstantiateHigherRanked + | GoalSource::AliasWellFormed ) && match self.consider_ambiguities { true => { matches!( @@ -415,6 +416,13 @@ fn non_trivial_candidates<'a>( }) }); } + + // Prefer a non-rigid candidate if there is one. + if candidates.len() > 1 { + candidates.retain(|candidate| { + !matches!(candidate.kind(), inspect::ProbeKind::RigidAlias { .. }) + }); + } } } @@ -429,8 +437,11 @@ fn span(&self) -> rustc_span::Span { self.obligation.cause.span } + #[instrument(level = "trace", skip(self, goal), fields(goal = ?goal.goal()))] fn visit_goal(&mut self, goal: &inspect::InspectGoal<'_, 'tcx>) -> Self::Result { let candidates = self.non_trivial_candidates(goal); + trace!(candidates = ?candidates.iter().map(|c| c.kind()).collect::>()); + let [candidate] = candidates.as_slice() else { return ControlFlow::Break(self.obligation.clone()); }; @@ -464,17 +475,13 @@ fn visit_goal(&mut self, goal: &inspect::InspectGoal<'_, 'tcx>) -> Self::Result polarity: ty::PredicatePolarity::Positive, })) } - ty::PredicateKind::Clause( - ty::ClauseKind::WellFormed(_) | ty::ClauseKind::Projection(..), - ) - | ty::PredicateKind::AliasRelate(..) => ChildMode::PassThrough, - _ => { - return ControlFlow::Break(self.obligation.clone()); - } + _ => ChildMode::PassThrough, }; let mut impl_where_bound_count = 0; for nested_goal in candidate.instantiate_nested_goals(self.span()) { + trace!(nested_goal = ?(nested_goal.goal(), nested_goal.source(), nested_goal.result())); + let make_obligation = |cause| Obligation { cause, param_env: nested_goal.goal().param_env, @@ -501,7 +508,7 @@ fn visit_goal(&mut self, goal: &inspect::InspectGoal<'_, 'tcx>) -> Self::Result (_, GoalSource::InstantiateHigherRanked) => { obligation = self.obligation.clone(); } - (ChildMode::PassThrough, _) => { + (ChildMode::PassThrough, _) | (_, GoalSource::AliasWellFormed) => { obligation = make_obligation(self.obligation.cause.clone()); } } diff --git a/compiler/rustc_trait_selection/src/solve/inspect/analyse.rs b/compiler/rustc_trait_selection/src/solve/inspect/analyse.rs index 254620e0b59..4975a9ce0c7 100644 --- a/compiler/rustc_trait_selection/src/solve/inspect/analyse.rs +++ b/compiler/rustc_trait_selection/src/solve/inspect/analyse.rs @@ -292,7 +292,8 @@ fn candidates_recur( | inspect::ProbeKind::Root { .. } | inspect::ProbeKind::TryNormalizeNonRigid { .. } | inspect::ProbeKind::TraitCandidate { .. } - | inspect::ProbeKind::OpaqueTypeStorageLookup { .. } => { + | inspect::ProbeKind::OpaqueTypeStorageLookup { .. } + | inspect::ProbeKind::RigidAlias { .. } => { // Nested probes have to prove goals added in their parent // but do not leak them, so we truncate the added goals // afterwards. @@ -316,7 +317,8 @@ fn candidates_recur( inspect::ProbeKind::Root { result } | inspect::ProbeKind::TryNormalizeNonRigid { result } | inspect::ProbeKind::TraitCandidate { source: _, result } - | inspect::ProbeKind::OpaqueTypeStorageLookup { result } => { + | inspect::ProbeKind::OpaqueTypeStorageLookup { result } + | inspect::ProbeKind::RigidAlias { result } => { // We only add a candidate if `shallow_certainty` was set, which means // that we ended up calling `evaluate_added_goals_and_make_canonical_response`. if let Some(shallow_certainty) = shallow_certainty { diff --git a/compiler/rustc_trait_selection/src/solve/select.rs b/compiler/rustc_trait_selection/src/solve/select.rs index 257fd263b94..1661852903c 100644 --- a/compiler/rustc_trait_selection/src/solve/select.rs +++ b/compiler/rustc_trait_selection/src/solve/select.rs @@ -177,7 +177,8 @@ fn to_selection<'tcx>( | ProbeKind::UpcastProjectionCompatibility | ProbeKind::OpaqueTypeStorageLookup { result: _ } | ProbeKind::Root { result: _ } - | ProbeKind::ShadowedEnvProbing => { + | ProbeKind::ShadowedEnvProbing + | ProbeKind::RigidAlias { result: _ } => { span_bug!(span, "didn't expect to assemble trait candidate from {:#?}", cand.kind()) } }) diff --git a/compiler/rustc_type_ir/src/solve/inspect.rs b/compiler/rustc_type_ir/src/solve/inspect.rs index 099c66f6bdc..138ba8bac88 100644 --- a/compiler/rustc_type_ir/src/solve/inspect.rs +++ b/compiler/rustc_type_ir/src/solve/inspect.rs @@ -135,4 +135,6 @@ pub enum ProbeKind { ShadowedEnvProbing, /// Try to unify an opaque type with an existing key in the storage. OpaqueTypeStorageLookup { result: QueryResult }, + /// Checking that a rigid alias is well-formed. + RigidAlias { result: QueryResult }, } diff --git a/compiler/rustc_type_ir/src/solve/mod.rs b/compiler/rustc_type_ir/src/solve/mod.rs index a0f7658212f..f02c7a32071 100644 --- a/compiler/rustc_type_ir/src/solve/mod.rs +++ b/compiler/rustc_type_ir/src/solve/mod.rs @@ -130,6 +130,10 @@ pub enum GoalSource { ImplWhereBound, /// Instantiating a higher-ranked goal and re-proving it. InstantiateHigherRanked, + /// Predicate required for an alias projection to be well-formed. + /// This is used in two places: projecting to an opaque whose hidden type + /// is already registered in the opaque type storage, and for rigid projections. + AliasWellFormed, } #[derive_where(Clone; I: Interner, Goal: Clone)] diff --git a/library/core/src/lib.rs b/library/core/src/lib.rs index 7060da172f3..6ed9ccaa694 100644 --- a/library/core/src/lib.rs +++ b/library/core/src/lib.rs @@ -153,6 +153,7 @@ #![feature(isqrt)] #![feature(lazy_get)] #![feature(link_cfg)] +#![feature(non_null_from_ref)] #![feature(offset_of_enum)] #![feature(panic_internals)] #![feature(ptr_alignment_type)] diff --git a/library/core/src/ptr/non_null.rs b/library/core/src/ptr/non_null.rs index dfd0bd8fd1e..3e4cae2b3ca 100644 --- a/library/core/src/ptr/non_null.rs +++ b/library/core/src/ptr/non_null.rs @@ -230,6 +230,24 @@ pub const fn new(ptr: *mut T) -> Option { } } + /// Converts a reference to a `NonNull` pointer. + #[unstable(feature = "non_null_from_ref", issue = "130823")] + #[rustc_const_unstable(feature = "non_null_from_ref", issue = "130823")] + #[inline] + pub const fn from_ref(r: &T) -> Self { + // SAFETY: A reference cannot be null. + unsafe { NonNull { pointer: r as *const T } } + } + + /// Converts a mutable reference to a `NonNull` pointer. + #[unstable(feature = "non_null_from_ref", issue = "130823")] + #[rustc_const_unstable(feature = "non_null_from_ref", issue = "130823")] + #[inline] + pub const fn from_mut(r: &mut T) -> Self { + // SAFETY: A mutable reference cannot be null. + unsafe { NonNull { pointer: r as *mut T } } + } + /// Performs the same functionality as [`std::ptr::from_raw_parts`], except that a /// `NonNull` pointer is returned, as opposed to a raw `*const` pointer. /// @@ -1749,9 +1767,8 @@ impl From<&mut T> for NonNull { /// /// This conversion is safe and infallible since references cannot be null. #[inline] - fn from(reference: &mut T) -> Self { - // SAFETY: A mutable reference cannot be null. - unsafe { NonNull { pointer: reference as *mut T } } + fn from(r: &mut T) -> Self { + NonNull::from_mut(r) } } @@ -1761,8 +1778,7 @@ impl From<&T> for NonNull { /// /// This conversion is safe and infallible since references cannot be null. #[inline] - fn from(reference: &T) -> Self { - // SAFETY: A reference cannot be null. - unsafe { NonNull { pointer: reference as *const T } } + fn from(r: &T) -> Self { + NonNull::from_ref(r) } } diff --git a/src/librustdoc/clean/types.rs b/src/librustdoc/clean/types.rs index bc5bf4c0583..44295fa0cd9 100644 --- a/src/librustdoc/clean/types.rs +++ b/src/librustdoc/clean/types.rs @@ -1450,7 +1450,7 @@ pub(crate) fn is_notable_trait(&self, tcx: TyCtxt<'_>) -> bool { pub(crate) fn safety(&self, tcx: TyCtxt<'_>) -> hir::Safety { tcx.trait_def(self.def_id).safety } - pub(crate) fn is_object_safe(&self, tcx: TyCtxt<'_>) -> bool { + pub(crate) fn is_dyn_compatible(&self, tcx: TyCtxt<'_>) -> bool { tcx.is_dyn_compatible(self.def_id) } } diff --git a/src/librustdoc/html/markdown.rs b/src/librustdoc/html/markdown.rs index 5dacabd031e..315b7742a4c 100644 --- a/src/librustdoc/html/markdown.rs +++ b/src/librustdoc/html/markdown.rs @@ -2002,7 +2002,7 @@ fn init_id_map() -> FxHashMap, usize> { map.insert("required-associated-consts".into(), 1); map.insert("required-methods".into(), 1); map.insert("provided-methods".into(), 1); - map.insert("object-safety".into(), 1); + map.insert("dyn-compatibility".into(), 1); map.insert("implementors".into(), 1); map.insert("synthetic-implementors".into(), 1); map.insert("implementations-list".into(), 1); diff --git a/src/librustdoc/html/render/print_item.rs b/src/librustdoc/html/render/print_item.rs index 3c96f873681..5e9cbef99a9 100644 --- a/src/librustdoc/html/render/print_item.rs +++ b/src/librustdoc/html/render/print_item.rs @@ -934,16 +934,18 @@ fn trait_item(w: &mut Buffer, cx: &mut Context<'_>, m: &clean::Item, t: &clean:: let cache = &cloned_shared.cache; let mut extern_crates = FxIndexSet::default(); - if !t.is_object_safe(cx.tcx()) { + if !t.is_dyn_compatible(cx.tcx()) { + // FIXME(dyn_compat_renaming): Update the URL once the Reference is updated. write_section_heading( w, - "Object Safety", - "object-safety", + "Dyn Compatibility", + "dyn-compatibility", None, &format!( - "
This trait is not \ - \ - object safe.
", + "

This trait is not \ + dyn compatible.

\ +

In older versions of Rust, dyn compatibility was called \"object safety\", \ + so this trait is not object safe.

", base = crate::clean::utils::DOC_RUST_LANG_ORG_CHANNEL ), ); diff --git a/src/librustdoc/html/render/sidebar.rs b/src/librustdoc/html/render/sidebar.rs index e7706e7fdea..6df9486e658 100644 --- a/src/librustdoc/html/render/sidebar.rs +++ b/src/librustdoc/html/render/sidebar.rs @@ -315,10 +315,10 @@ fn filter_items<'a>( ); sidebar_assoc_items(cx, it, blocks); - if !t.is_object_safe(cx.tcx()) { + if !t.is_dyn_compatible(cx.tcx()) { blocks.push(LinkBlock::forced( - Link::new("object-safety", "Object Safety"), - "object-safety-note", + Link::new("dyn-compatibility", "Dyn Compatibility"), + "dyn-compatibility-note", )); } diff --git a/src/librustdoc/json/conversions.rs b/src/librustdoc/json/conversions.rs index b8791c9918b..77e7d83090b 100644 --- a/src/librustdoc/json/conversions.rs +++ b/src/librustdoc/json/conversions.rs @@ -672,7 +672,7 @@ fn from_clean(trait_: clean::Trait, renderer: &JsonRenderer<'_>) -> Self { let tcx = renderer.tcx; let is_auto = trait_.is_auto(tcx); let is_unsafe = trait_.safety(tcx) == rustc_hir::Safety::Unsafe; - let is_object_safe = trait_.is_object_safe(tcx); + let is_object_safe = trait_.is_dyn_compatible(tcx); let clean::Trait { items, generics, bounds, .. } = trait_; Trait { is_auto, diff --git a/tests/mir-opt/pre-codegen/slice_iter.enumerated_loop.PreCodegen.after.panic-abort.mir b/tests/mir-opt/pre-codegen/slice_iter.enumerated_loop.PreCodegen.after.panic-abort.mir index 3aa483ed1ae..bd56ab67e00 100644 --- a/tests/mir-opt/pre-codegen/slice_iter.enumerated_loop.PreCodegen.after.panic-abort.mir +++ b/tests/mir-opt/pre-codegen/slice_iter.enumerated_loop.PreCodegen.after.panic-abort.mir @@ -19,30 +19,30 @@ fn enumerated_loop(_1: &[T], _2: impl Fn(usize, &T)) -> () { debug i => _22; debug x => _23; } - scope 17 (inlined > as Iterator>::next) { + scope 18 (inlined > as Iterator>::next) { let mut _14: &mut std::slice::Iter<'_, T>; let mut _15: std::option::Option<&T>; let mut _19: (usize, bool); let mut _20: (usize, &T); - scope 18 { + scope 19 { let _18: usize; - scope 23 { + scope 24 { } } - scope 19 { - scope 20 { - scope 26 (inlined as FromResidual>>::from_residual) { + scope 20 { + scope 21 { + scope 27 (inlined as FromResidual>>::from_residual) { } } } - scope 21 { - scope 22 { + scope 22 { + scope 23 { } } - scope 24 (inlined as Try>::branch) { + scope 25 (inlined as Try>::branch) { let mut _16: isize; let _17: &T; - scope 25 { + scope 26 { } } } @@ -59,29 +59,31 @@ fn enumerated_loop(_1: &[T], _2: impl Fn(usize, &T)) -> () { let _9: *const T; scope 7 { } - scope 11 (inlined without_provenance::) { + scope 12 (inlined without_provenance::) { } - scope 12 (inlined NonNull::::as_ptr) { + scope 13 (inlined NonNull::::as_ptr) { } - scope 13 (inlined std::ptr::mut_ptr::::add) { + scope 14 (inlined std::ptr::mut_ptr::::add) { } } scope 8 (inlined as From<&[T]>>::from) { - let mut _4: *const [T]; + scope 9 (inlined NonNull::<[T]>::from_ref) { + let mut _4: *const [T]; + } } - scope 9 (inlined NonNull::<[T]>::cast::) { + scope 10 (inlined NonNull::<[T]>::cast::) { let mut _5: *const T; - scope 10 (inlined NonNull::<[T]>::as_ptr) { + scope 11 (inlined NonNull::<[T]>::as_ptr) { } } } } } - scope 14 (inlined as Iterator>::enumerate) { - scope 15 (inlined Enumerate::>::new) { + scope 15 (inlined as Iterator>::enumerate) { + scope 16 (inlined Enumerate::>::new) { } } - scope 16 (inlined > as IntoIterator>::into_iter) { + scope 17 (inlined > as IntoIterator>::into_iter) { } bb0: { diff --git a/tests/mir-opt/pre-codegen/slice_iter.enumerated_loop.PreCodegen.after.panic-unwind.mir b/tests/mir-opt/pre-codegen/slice_iter.enumerated_loop.PreCodegen.after.panic-unwind.mir index 4cc0aa0ed78..57f09a4631b 100644 --- a/tests/mir-opt/pre-codegen/slice_iter.enumerated_loop.PreCodegen.after.panic-unwind.mir +++ b/tests/mir-opt/pre-codegen/slice_iter.enumerated_loop.PreCodegen.after.panic-unwind.mir @@ -34,29 +34,31 @@ fn enumerated_loop(_1: &[T], _2: impl Fn(usize, &T)) -> () { let _9: *const T; scope 7 { } - scope 11 (inlined without_provenance::) { + scope 12 (inlined without_provenance::) { } - scope 12 (inlined NonNull::::as_ptr) { + scope 13 (inlined NonNull::::as_ptr) { } - scope 13 (inlined std::ptr::mut_ptr::::add) { + scope 14 (inlined std::ptr::mut_ptr::::add) { } } scope 8 (inlined as From<&[T]>>::from) { - let mut _4: *const [T]; + scope 9 (inlined NonNull::<[T]>::from_ref) { + let mut _4: *const [T]; + } } - scope 9 (inlined NonNull::<[T]>::cast::) { + scope 10 (inlined NonNull::<[T]>::cast::) { let mut _5: *const T; - scope 10 (inlined NonNull::<[T]>::as_ptr) { + scope 11 (inlined NonNull::<[T]>::as_ptr) { } } } } } - scope 14 (inlined as Iterator>::enumerate) { - scope 15 (inlined Enumerate::>::new) { + scope 15 (inlined as Iterator>::enumerate) { + scope 16 (inlined Enumerate::>::new) { } } - scope 16 (inlined > as IntoIterator>::into_iter) { + scope 17 (inlined > as IntoIterator>::into_iter) { } bb0: { diff --git a/tests/mir-opt/pre-codegen/slice_iter.forward_loop.PreCodegen.after.panic-abort.mir b/tests/mir-opt/pre-codegen/slice_iter.forward_loop.PreCodegen.after.panic-abort.mir index 507afa63c68..4050304f469 100644 --- a/tests/mir-opt/pre-codegen/slice_iter.forward_loop.PreCodegen.after.panic-abort.mir +++ b/tests/mir-opt/pre-codegen/slice_iter.forward_loop.PreCodegen.after.panic-abort.mir @@ -31,25 +31,27 @@ fn forward_loop(_1: &[T], _2: impl Fn(&T)) -> () { let _9: *const T; scope 7 { } - scope 11 (inlined without_provenance::) { + scope 12 (inlined without_provenance::) { } - scope 12 (inlined NonNull::::as_ptr) { + scope 13 (inlined NonNull::::as_ptr) { } - scope 13 (inlined std::ptr::mut_ptr::::add) { + scope 14 (inlined std::ptr::mut_ptr::::add) { } } scope 8 (inlined as From<&[T]>>::from) { - let mut _4: *const [T]; + scope 9 (inlined NonNull::<[T]>::from_ref) { + let mut _4: *const [T]; + } } - scope 9 (inlined NonNull::<[T]>::cast::) { + scope 10 (inlined NonNull::<[T]>::cast::) { let mut _5: *const T; - scope 10 (inlined NonNull::<[T]>::as_ptr) { + scope 11 (inlined NonNull::<[T]>::as_ptr) { } } } } } - scope 14 (inlined as IntoIterator>::into_iter) { + scope 15 (inlined as IntoIterator>::into_iter) { } bb0: { diff --git a/tests/mir-opt/pre-codegen/slice_iter.forward_loop.PreCodegen.after.panic-unwind.mir b/tests/mir-opt/pre-codegen/slice_iter.forward_loop.PreCodegen.after.panic-unwind.mir index a25f12edc28..2c3d7ab1e4a 100644 --- a/tests/mir-opt/pre-codegen/slice_iter.forward_loop.PreCodegen.after.panic-unwind.mir +++ b/tests/mir-opt/pre-codegen/slice_iter.forward_loop.PreCodegen.after.panic-unwind.mir @@ -31,25 +31,27 @@ fn forward_loop(_1: &[T], _2: impl Fn(&T)) -> () { let _9: *const T; scope 7 { } - scope 11 (inlined without_provenance::) { + scope 12 (inlined without_provenance::) { } - scope 12 (inlined NonNull::::as_ptr) { + scope 13 (inlined NonNull::::as_ptr) { } - scope 13 (inlined std::ptr::mut_ptr::::add) { + scope 14 (inlined std::ptr::mut_ptr::::add) { } } scope 8 (inlined as From<&[T]>>::from) { - let mut _4: *const [T]; + scope 9 (inlined NonNull::<[T]>::from_ref) { + let mut _4: *const [T]; + } } - scope 9 (inlined NonNull::<[T]>::cast::) { + scope 10 (inlined NonNull::<[T]>::cast::) { let mut _5: *const T; - scope 10 (inlined NonNull::<[T]>::as_ptr) { + scope 11 (inlined NonNull::<[T]>::as_ptr) { } } } } } - scope 14 (inlined as IntoIterator>::into_iter) { + scope 15 (inlined as IntoIterator>::into_iter) { } bb0: { diff --git a/tests/mir-opt/pre-codegen/slice_iter.reverse_loop.PreCodegen.after.panic-abort.mir b/tests/mir-opt/pre-codegen/slice_iter.reverse_loop.PreCodegen.after.panic-abort.mir index 1b397a4e4cd..a6ccd435c40 100644 --- a/tests/mir-opt/pre-codegen/slice_iter.reverse_loop.PreCodegen.after.panic-abort.mir +++ b/tests/mir-opt/pre-codegen/slice_iter.reverse_loop.PreCodegen.after.panic-abort.mir @@ -18,7 +18,7 @@ fn reverse_loop(_1: &[T], _2: impl Fn(&T)) -> () { scope 2 { debug x => _17; } - scope 17 (inlined > as Iterator>::next) { + scope 18 (inlined > as Iterator>::next) { let mut _14: &mut std::slice::Iter<'_, T>; } } @@ -34,29 +34,31 @@ fn reverse_loop(_1: &[T], _2: impl Fn(&T)) -> () { let _9: *const T; scope 7 { } - scope 11 (inlined without_provenance::) { + scope 12 (inlined without_provenance::) { } - scope 12 (inlined NonNull::::as_ptr) { + scope 13 (inlined NonNull::::as_ptr) { } - scope 13 (inlined std::ptr::mut_ptr::::add) { + scope 14 (inlined std::ptr::mut_ptr::::add) { } } scope 8 (inlined as From<&[T]>>::from) { - let mut _4: *const [T]; + scope 9 (inlined NonNull::<[T]>::from_ref) { + let mut _4: *const [T]; + } } - scope 9 (inlined NonNull::<[T]>::cast::) { + scope 10 (inlined NonNull::<[T]>::cast::) { let mut _5: *const T; - scope 10 (inlined NonNull::<[T]>::as_ptr) { + scope 11 (inlined NonNull::<[T]>::as_ptr) { } } } } } - scope 14 (inlined as Iterator>::rev) { - scope 15 (inlined Rev::>::new) { + scope 15 (inlined as Iterator>::rev) { + scope 16 (inlined Rev::>::new) { } } - scope 16 (inlined > as IntoIterator>::into_iter) { + scope 17 (inlined > as IntoIterator>::into_iter) { } bb0: { diff --git a/tests/mir-opt/pre-codegen/slice_iter.reverse_loop.PreCodegen.after.panic-unwind.mir b/tests/mir-opt/pre-codegen/slice_iter.reverse_loop.PreCodegen.after.panic-unwind.mir index 77689dd9b51..df11c8e3b49 100644 --- a/tests/mir-opt/pre-codegen/slice_iter.reverse_loop.PreCodegen.after.panic-unwind.mir +++ b/tests/mir-opt/pre-codegen/slice_iter.reverse_loop.PreCodegen.after.panic-unwind.mir @@ -18,7 +18,7 @@ fn reverse_loop(_1: &[T], _2: impl Fn(&T)) -> () { scope 2 { debug x => _17; } - scope 17 (inlined > as Iterator>::next) { + scope 18 (inlined > as Iterator>::next) { let mut _14: &mut std::slice::Iter<'_, T>; } } @@ -34,29 +34,31 @@ fn reverse_loop(_1: &[T], _2: impl Fn(&T)) -> () { let _9: *const T; scope 7 { } - scope 11 (inlined without_provenance::) { + scope 12 (inlined without_provenance::) { } - scope 12 (inlined NonNull::::as_ptr) { + scope 13 (inlined NonNull::::as_ptr) { } - scope 13 (inlined std::ptr::mut_ptr::::add) { + scope 14 (inlined std::ptr::mut_ptr::::add) { } } scope 8 (inlined as From<&[T]>>::from) { - let mut _4: *const [T]; + scope 9 (inlined NonNull::<[T]>::from_ref) { + let mut _4: *const [T]; + } } - scope 9 (inlined NonNull::<[T]>::cast::) { + scope 10 (inlined NonNull::<[T]>::cast::) { let mut _5: *const T; - scope 10 (inlined NonNull::<[T]>::as_ptr) { + scope 11 (inlined NonNull::<[T]>::as_ptr) { } } } } } - scope 14 (inlined as Iterator>::rev) { - scope 15 (inlined Rev::>::new) { + scope 15 (inlined as Iterator>::rev) { + scope 16 (inlined Rev::>::new) { } } - scope 16 (inlined > as IntoIterator>::into_iter) { + scope 17 (inlined > as IntoIterator>::into_iter) { } bb0: { diff --git a/tests/rustdoc/dyn-compatibility.rs b/tests/rustdoc/dyn-compatibility.rs new file mode 100644 index 00000000000..9115f93bc3b --- /dev/null +++ b/tests/rustdoc/dyn-compatibility.rs @@ -0,0 +1,27 @@ +#![crate_name = "foo"] + +//@ has 'foo/trait.DynIncompatible.html' +//@ has - '//*[@class="dyn-compatibility-info"]' 'This trait is not dyn compatible.' +//@ has - '//*[@id="dyn-compatibility"]' 'Dyn Compatibility' +pub trait DynIncompatible { + fn foo() -> Self; +} + +//@ has 'foo/trait.DynIncompatible2.html' +//@ has - '//*[@class="dyn-compatibility-info"]' 'This trait is not dyn compatible.' +//@ has - '//*[@id="dyn-compatibility"]' 'Dyn Compatibility' +pub trait DynIncompatible2 { + fn foo(i: T); +} + +//@ has 'foo/trait.DynCompatible.html' +//@ !has - '//*[@class="dyn-compatibility-info"]' '' +//@ !has - '//*[@id="dyn-compatibility"]' '' +pub trait DynCompatible { + fn foo(&self); +} + +//@ has 'foo/struct.Foo.html' +//@ count - '//*[@class="dyn-compatibility-info"]' 0 +//@ count - '//*[@id="dyn-compatibility"]' 0 +pub struct Foo; diff --git a/tests/rustdoc/sidebar/sidebar-items.rs b/tests/rustdoc/sidebar/sidebar-items.rs index f3812143a7d..57c2eee91a9 100644 --- a/tests/rustdoc/sidebar/sidebar-items.rs +++ b/tests/rustdoc/sidebar/sidebar-items.rs @@ -14,7 +14,7 @@ //@ has - '//*[@class="sidebar-elems"]//section//a' 'Output' //@ has - '//div[@class="sidebar-elems"]//h3/a[@href="#provided-associated-types"]' 'Provided Associated Types' //@ has - '//*[@class="sidebar-elems"]//section//a' 'Extra' -//@ has - '//div[@class="sidebar-elems"]//h3/a[@href="#object-safety"]' 'Object Safety' +//@ has - '//div[@class="sidebar-elems"]//h3/a[@href="#dyn-compatibility"]' 'Dyn Compatibility' pub trait Foo { const FOO: usize; const BAR: u32 = 0; @@ -25,9 +25,9 @@ fn foo() {} fn bar() -> Self::Output; } -//@ has foo/trait.Safe.html +//@ has foo/trait.DynCompatible.html //@ !has - '//div[@class="sidebar-elems"]//h3/a[@href="#object-safety"]' '' -pub trait Safe { +pub trait DynCompatible { fn access(&self); } diff --git a/tests/rustdoc/trait-object-safe.rs b/tests/rustdoc/trait-object-safe.rs deleted file mode 100644 index b4e986c8f69..00000000000 --- a/tests/rustdoc/trait-object-safe.rs +++ /dev/null @@ -1,27 +0,0 @@ -#![crate_name = "foo"] - -//@ has 'foo/trait.Unsafe.html' -//@ has - '//*[@class="object-safety-info"]' 'This trait is not object safe.' -//@ has - '//*[@id="object-safety"]' 'Object Safety' -pub trait Unsafe { - fn foo() -> Self; -} - -//@ has 'foo/trait.Unsafe2.html' -//@ has - '//*[@class="object-safety-info"]' 'This trait is not object safe.' -//@ has - '//*[@id="object-safety"]' 'Object Safety' -pub trait Unsafe2 { - fn foo(i: T); -} - -//@ has 'foo/trait.Safe.html' -//@ !has - '//*[@class="object-safety-info"]' '' -//@ !has - '//*[@id="object-safety"]' '' -pub trait Safe { - fn foo(&self); -} - -//@ has 'foo/struct.Foo.html' -//@ count - '//*[@class="object-safety-info"]' 0 -//@ count - '//*[@id="object-safety"]' 0 -pub struct Foo; diff --git a/tests/ui/for/issue-20605.next.stderr b/tests/ui/for/issue-20605.next.stderr index 98609211865..1a66cb41464 100644 --- a/tests/ui/for/issue-20605.next.stderr +++ b/tests/ui/for/issue-20605.next.stderr @@ -11,13 +11,6 @@ help: consider mutably borrowing here LL | for item in &mut *things { *item = 0 } | ++++ -error[E0614]: type ` as IntoIterator>::Item` cannot be dereferenced - --> $DIR/issue-20605.rs:6:27 - | -LL | for item in *things { *item = 0 } - | ^^^^^ +error: aborting due to 1 previous error -error: aborting due to 2 previous errors - -Some errors have detailed explanations: E0277, E0614. -For more information about an error, try `rustc --explain E0277`. +For more information about this error, try `rustc --explain E0277`. diff --git a/tests/ui/for/issue-20605.rs b/tests/ui/for/issue-20605.rs index 647dc84028c..5c56e64a017 100644 --- a/tests/ui/for/issue-20605.rs +++ b/tests/ui/for/issue-20605.rs @@ -4,12 +4,7 @@ fn changer<'a>(mut things: Box>) { for item in *things { *item = 0 } - //[current]~^ ERROR `dyn Iterator` is not an iterator - //[next]~^^ ERROR `dyn Iterator` is not an iterator - //[next]~| ERROR type ` as IntoIterator>::Item` cannot be dereferenced - - // FIXME(-Znext-solver): these error messages are horrible and have to be - // improved before we stabilize the new solver. + //~^ ERROR `dyn Iterator` is not an iterator } fn main() {} diff --git a/tests/ui/generic-associated-types/ambig-hr-projection-issue-93340.next.stderr b/tests/ui/generic-associated-types/ambig-hr-projection-issue-93340.next.stderr index d913b2e91ca..d624fb1e42b 100644 --- a/tests/ui/generic-associated-types/ambig-hr-projection-issue-93340.next.stderr +++ b/tests/ui/generic-associated-types/ambig-hr-projection-issue-93340.next.stderr @@ -1,5 +1,5 @@ error[E0283]: type annotations needed - --> $DIR/ambig-hr-projection-issue-93340.rs:16:5 + --> $DIR/ambig-hr-projection-issue-93340.rs:17:5 | LL | cmp_eq | ^^^^^^ cannot infer type of the type parameter `A` declared on the function `cmp_eq` @@ -15,6 +15,16 @@ help: consider specifying the generic arguments LL | cmp_eq:: | +++++++++++ -error: aborting due to 1 previous error +error[E0277]: expected a `Fn(::RefType<'_>, ::RefType<'_>)` closure, found `for<'a, 'b> fn(::RefType<'a>, <_ as Scalar>::RefType<'b>) -> O {cmp_eq::}` + --> $DIR/ambig-hr-projection-issue-93340.rs:14:1 + | +LL | / fn build_expression( +LL | | ) -> impl Fn(A::RefType<'_>, B::RefType<'_>) -> O { + | |_________________________________________________^ expected an `Fn(::RefType<'_>, ::RefType<'_>)` closure, found `for<'a, 'b> fn(::RefType<'a>, <_ as Scalar>::RefType<'b>) -> O {cmp_eq::}` + | + = help: the trait `for<'a, 'b> Fn(::RefType<'a>, ::RefType<'b>)` is not implemented for fn item `for<'a, 'b> fn(::RefType<'a>, <_ as Scalar>::RefType<'b>) -> O {cmp_eq::}` -For more information about this error, try `rustc --explain E0283`. +error: aborting due to 2 previous errors + +Some errors have detailed explanations: E0277, E0283. +For more information about an error, try `rustc --explain E0277`. diff --git a/tests/ui/generic-associated-types/ambig-hr-projection-issue-93340.old.stderr b/tests/ui/generic-associated-types/ambig-hr-projection-issue-93340.old.stderr index d913b2e91ca..4a293d44e0e 100644 --- a/tests/ui/generic-associated-types/ambig-hr-projection-issue-93340.old.stderr +++ b/tests/ui/generic-associated-types/ambig-hr-projection-issue-93340.old.stderr @@ -1,5 +1,5 @@ error[E0283]: type annotations needed - --> $DIR/ambig-hr-projection-issue-93340.rs:16:5 + --> $DIR/ambig-hr-projection-issue-93340.rs:17:5 | LL | cmp_eq | ^^^^^^ cannot infer type of the type parameter `A` declared on the function `cmp_eq` diff --git a/tests/ui/generic-associated-types/ambig-hr-projection-issue-93340.rs b/tests/ui/generic-associated-types/ambig-hr-projection-issue-93340.rs index acfebad38db..5f2e134109e 100644 --- a/tests/ui/generic-associated-types/ambig-hr-projection-issue-93340.rs +++ b/tests/ui/generic-associated-types/ambig-hr-projection-issue-93340.rs @@ -13,6 +13,7 @@ fn cmp_eq<'a, 'b, A: Scalar, B: Scalar, O: Scalar>(a: A::RefType<'a>, b: B::RefT fn build_expression( ) -> impl Fn(A::RefType<'_>, B::RefType<'_>) -> O { + //[next]~^^ expected a `Fn(::RefType<'_>, ::RefType<'_>)` closure cmp_eq //~^ ERROR type annotations needed } diff --git a/tests/ui/higher-ranked/structually-relate-aliases.rs b/tests/ui/higher-ranked/structually-relate-aliases.rs index 69882450961..73c2cd23d86 100644 --- a/tests/ui/higher-ranked/structually-relate-aliases.rs +++ b/tests/ui/higher-ranked/structually-relate-aliases.rs @@ -11,6 +11,7 @@ trait Overlap {} impl Overlap for T {} impl Overlap fn(&'a (), Assoc<'a, T>)> for T {} -//~^ ERROR conflicting implementations of trait `Overlap fn(&'a (), _)>` +//~^ ERROR the trait bound `for<'a> T: ToUnit<'a>` is not satisfied +//~| ERROR the trait bound `for<'a> T: ToUnit<'a>` is not satisfied fn main() {} diff --git a/tests/ui/higher-ranked/structually-relate-aliases.stderr b/tests/ui/higher-ranked/structually-relate-aliases.stderr index 4ecd5829bc3..e9d91e45e21 100644 --- a/tests/ui/higher-ranked/structually-relate-aliases.stderr +++ b/tests/ui/higher-ranked/structually-relate-aliases.stderr @@ -1,18 +1,26 @@ WARN rustc_infer::infer::relate::generalize may incompletely handle alias type: AliasTy { args: [?1t, '^0.Named(DefId(0:15 ~ structually_relate_aliases[de75]::{impl#1}::'a), "'a")], def_id: DefId(0:5 ~ structually_relate_aliases[de75]::ToUnit::Unit), .. } - WARN rustc_infer::infer::relate::generalize may incompletely handle alias type: AliasTy { args: [?1t, '^0.Named(DefId(0:15 ~ structually_relate_aliases[de75]::{impl#1}::'a), "'a")], def_id: DefId(0:5 ~ structually_relate_aliases[de75]::ToUnit::Unit), .. } - WARN rustc_infer::infer::relate::generalize may incompletely handle alias type: AliasTy { args: [?1t, '^0.Named(DefId(0:15 ~ structually_relate_aliases[de75]::{impl#1}::'a), "'a")], def_id: DefId(0:5 ~ structually_relate_aliases[de75]::ToUnit::Unit), .. } - WARN rustc_infer::infer::relate::generalize may incompletely handle alias type: AliasTy { args: [?1t, '^0.Named(DefId(0:15 ~ structually_relate_aliases[de75]::{impl#1}::'a), "'a")], def_id: DefId(0:5 ~ structually_relate_aliases[de75]::ToUnit::Unit), .. } -error[E0119]: conflicting implementations of trait `Overlap fn(&'a (), _)>` for type `for<'a> fn(&'a (), _)` - --> $DIR/structually-relate-aliases.rs:13:1 +error[E0277]: the trait bound `for<'a> T: ToUnit<'a>` is not satisfied + --> $DIR/structually-relate-aliases.rs:13:36 | -LL | impl Overlap for T {} - | ------------------------ first implementation here -LL | LL | impl Overlap fn(&'a (), Assoc<'a, T>)> for T {} - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation for `for<'a> fn(&'a (), _)` + | ^^^^^^^^^^^^ the trait `for<'a> ToUnit<'a>` is not implemented for `T` | - = note: this behavior recently changed as a result of a bug fix; see rust-lang/rust#56105 for details +help: consider restricting type parameter `T` + | +LL | impl ToUnit<'a>> Overlap fn(&'a (), Assoc<'a, T>)> for T {} + | ++++++++++++++++++++ -error: aborting due to 1 previous error +error[E0277]: the trait bound `for<'a> T: ToUnit<'a>` is not satisfied + --> $DIR/structually-relate-aliases.rs:13:17 + | +LL | impl Overlap fn(&'a (), Assoc<'a, T>)> for T {} + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `for<'a> ToUnit<'a>` is not implemented for `T` + | +help: consider restricting type parameter `T` + | +LL | impl ToUnit<'a>> Overlap fn(&'a (), Assoc<'a, T>)> for T {} + | ++++++++++++++++++++ -For more information about this error, try `rustc --explain E0119`. +error: aborting due to 2 previous errors + +For more information about this error, try `rustc --explain E0277`. diff --git a/tests/ui/impl-trait/in-trait/alias-bounds-when-not-wf.rs b/tests/ui/impl-trait/in-trait/alias-bounds-when-not-wf.rs index 5a6bf9bfaef..351cdad4ee1 100644 --- a/tests/ui/impl-trait/in-trait/alias-bounds-when-not-wf.rs +++ b/tests/ui/impl-trait/in-trait/alias-bounds-when-not-wf.rs @@ -14,6 +14,8 @@ trait Foo {} // `usize: Foo` doesn't hold. Therefore we ICE, because we don't expect to still // encounter weak types in `assemble_alias_bound_candidates_recur`. fn hello(_: W>) {} -//~^ ERROR the size for values of type `A` cannot be known at compilation time +//~^ ERROR the trait bound `usize: Foo` is not satisfied +//~| ERROR the trait bound `usize: Foo` is not satisfied +//~| ERROR the trait bound `usize: Foo` is not satisfied fn main() {} diff --git a/tests/ui/impl-trait/in-trait/alias-bounds-when-not-wf.stderr b/tests/ui/impl-trait/in-trait/alias-bounds-when-not-wf.stderr index 9663fab3d8c..79581066a3a 100644 --- a/tests/ui/impl-trait/in-trait/alias-bounds-when-not-wf.stderr +++ b/tests/ui/impl-trait/in-trait/alias-bounds-when-not-wf.stderr @@ -7,14 +7,42 @@ LL | #![feature(lazy_type_alias)] = note: see issue #112792 for more information = note: `#[warn(incomplete_features)]` on by default -error[E0277]: the size for values of type `A` cannot be known at compilation time +error[E0277]: the trait bound `usize: Foo` is not satisfied --> $DIR/alias-bounds-when-not-wf.rs:16:13 | LL | fn hello(_: W>) {} - | ^^^^^^^^^^^ doesn't have a size known at compile-time + | ^^^^^^^^^^^ the trait `Foo` is not implemented for `usize` | - = help: the trait `Sized` is not implemented for `A` +help: this trait has no implementations, consider adding one + --> $DIR/alias-bounds-when-not-wf.rs:6:1 + | +LL | trait Foo {} + | ^^^^^^^^^ -error: aborting due to 1 previous error; 1 warning emitted +error[E0277]: the trait bound `usize: Foo` is not satisfied + --> $DIR/alias-bounds-when-not-wf.rs:16:10 + | +LL | fn hello(_: W>) {} + | ^ the trait `Foo` is not implemented for `usize` + | +help: this trait has no implementations, consider adding one + --> $DIR/alias-bounds-when-not-wf.rs:6:1 + | +LL | trait Foo {} + | ^^^^^^^^^ + +error[E0277]: the trait bound `usize: Foo` is not satisfied + --> $DIR/alias-bounds-when-not-wf.rs:16:1 + | +LL | fn hello(_: W>) {} + | ^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Foo` is not implemented for `usize` + | +help: this trait has no implementations, consider adding one + --> $DIR/alias-bounds-when-not-wf.rs:6:1 + | +LL | trait Foo {} + | ^^^^^^^^^ + +error: aborting due to 3 previous errors; 1 warning emitted For more information about this error, try `rustc --explain E0277`. diff --git a/tests/ui/impl-trait/method-resolution4.next.stderr b/tests/ui/impl-trait/method-resolution4.next.stderr index b48de0af357..0524f49f98e 100644 --- a/tests/ui/impl-trait/method-resolution4.next.stderr +++ b/tests/ui/impl-trait/method-resolution4.next.stderr @@ -4,19 +4,6 @@ error[E0282]: type annotations needed LL | foo(false).next().unwrap(); | ^^^^^^^^^^ cannot infer type -error[E0308]: mismatched types - --> $DIR/method-resolution4.rs:16:5 - | -LL | fn foo(b: bool) -> impl Iterator { - | ------------------------ the expected opaque type -... -LL | std::iter::empty() - | ^^^^^^^^^^^^^^^^^^ types differ - | - = note: expected opaque type `impl Iterator` - found struct `std::iter::Empty<_>` +error: aborting due to 1 previous error -error: aborting due to 2 previous errors - -Some errors have detailed explanations: E0282, E0308. -For more information about an error, try `rustc --explain E0282`. +For more information about this error, try `rustc --explain E0282`. diff --git a/tests/ui/impl-trait/method-resolution4.rs b/tests/ui/impl-trait/method-resolution4.rs index 91884eb59fd..5c8813ed792 100644 --- a/tests/ui/impl-trait/method-resolution4.rs +++ b/tests/ui/impl-trait/method-resolution4.rs @@ -14,7 +14,6 @@ fn foo(b: bool) -> impl Iterator { //[next]~^ type annotations needed } std::iter::empty() - //[next]~^ mismatched types } fn main() {} diff --git a/tests/ui/impl-trait/recursive-coroutine-boxed.next.stderr b/tests/ui/impl-trait/recursive-coroutine-boxed.next.stderr index 96db2030a40..132f7de4ef2 100644 --- a/tests/ui/impl-trait/recursive-coroutine-boxed.next.stderr +++ b/tests/ui/impl-trait/recursive-coroutine-boxed.next.stderr @@ -1,5 +1,5 @@ error[E0282]: type annotations needed - --> $DIR/recursive-coroutine-boxed.rs:15:23 + --> $DIR/recursive-coroutine-boxed.rs:14:23 | LL | let mut gen = Box::pin(foo()); | ^^^^^^^^ cannot infer type of the type parameter `T` declared on the struct `Box` @@ -12,29 +12,6 @@ help: consider specifying the generic argument LL | let mut gen = Box::::pin(foo()); | +++++ -error[E0308]: mismatched types - --> $DIR/recursive-coroutine-boxed.rs:14:18 - | -LL | fn foo() -> impl Coroutine { - | --------------------------------------- - | | - | the expected opaque type - | expected `impl Coroutine` because of return type -... -LL | #[coroutine] || { - | __________________^ -LL | | let mut gen = Box::pin(foo()); -LL | | -LL | | let mut r = gen.as_mut().resume(()); -... | -LL | | } -LL | | } - | |_____^ types differ - | - = note: expected opaque type `impl Coroutine` - found coroutine `{coroutine@$DIR/recursive-coroutine-boxed.rs:14:18: 14:20}` +error: aborting due to 1 previous error -error: aborting due to 2 previous errors - -Some errors have detailed explanations: E0282, E0308. -For more information about an error, try `rustc --explain E0282`. +For more information about this error, try `rustc --explain E0282`. diff --git a/tests/ui/impl-trait/recursive-coroutine-boxed.rs b/tests/ui/impl-trait/recursive-coroutine-boxed.rs index 24a77d73114..8d38e6aed12 100644 --- a/tests/ui/impl-trait/recursive-coroutine-boxed.rs +++ b/tests/ui/impl-trait/recursive-coroutine-boxed.rs @@ -10,8 +10,7 @@ fn foo() -> impl Coroutine { // FIXME(-Znext-solver): this fails with a mismatched types as the // hidden type of the opaque ends up as {type error}. We should not // emit errors for such goals. - - #[coroutine] || { //[next]~ ERROR mismatched types + #[coroutine] || { let mut gen = Box::pin(foo()); //[next]~^ ERROR type annotations needed let mut r = gen.as_mut().resume(()); diff --git a/tests/ui/impl-trait/unsized_coercion.next.stderr b/tests/ui/impl-trait/unsized_coercion.next.stderr index 49ac3f1845f..4cebd26a5be 100644 --- a/tests/ui/impl-trait/unsized_coercion.next.stderr +++ b/tests/ui/impl-trait/unsized_coercion.next.stderr @@ -1,26 +1,35 @@ -error[E0271]: type mismatch resolving `impl Trait <: dyn Trait` - --> $DIR/unsized_coercion.rs:14:17 +error[E0277]: the size for values of type `dyn Trait` cannot be known at compilation time + --> $DIR/unsized_coercion.rs:15:17 | LL | let x = hello(); - | ^^^^^^^ types differ + | ^^^^^^^ doesn't have a size known at compile-time + | + = help: the trait `Sized` is not implemented for `dyn Trait` error[E0308]: mismatched types - --> $DIR/unsized_coercion.rs:18:14 + --> $DIR/unsized_coercion.rs:19:5 | LL | fn hello() -> Box { - | ---------- the expected opaque type + | --------------- + | | | + | | the expected opaque type + | expected `Box` because of return type ... LL | Box::new(1u32) - | -------- ^^^^ types differ - | | - | arguments to this function are incorrect + | ^^^^^^^^^^^^^^ types differ | - = note: expected opaque type `impl Trait` - found type `u32` -note: associated function defined here - --> $SRC_DIR/alloc/src/boxed.rs:LL:COL + = note: expected struct `Box` + found struct `Box` -error: aborting due to 2 previous errors +error[E0277]: the size for values of type `dyn Trait` cannot be known at compilation time + --> $DIR/unsized_coercion.rs:12:1 + | +LL | fn hello() -> Box { + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ doesn't have a size known at compile-time + | + = help: the trait `Sized` is not implemented for `dyn Trait` -Some errors have detailed explanations: E0271, E0308. -For more information about an error, try `rustc --explain E0271`. +error: aborting due to 3 previous errors + +Some errors have detailed explanations: E0277, E0308. +For more information about an error, try `rustc --explain E0277`. diff --git a/tests/ui/impl-trait/unsized_coercion.rs b/tests/ui/impl-trait/unsized_coercion.rs index 46e040c1428..b3791b38abc 100644 --- a/tests/ui/impl-trait/unsized_coercion.rs +++ b/tests/ui/impl-trait/unsized_coercion.rs @@ -10,9 +10,10 @@ trait Trait {} impl Trait for u32 {} fn hello() -> Box { + //[next]~^ ERROR the size for values of type `dyn Trait` cannot be known at compilation time if true { let x = hello(); - //[next]~^ ERROR: type mismatch resolving `impl Trait <: dyn Trait` + //[next]~^ ERROR: the size for values of type `dyn Trait` cannot be known at compilation time let y: Box = x; } Box::new(1u32) //[next]~ ERROR: mismatched types diff --git a/tests/ui/impl-trait/unsized_coercion3.next.stderr b/tests/ui/impl-trait/unsized_coercion3.next.stderr index 586ae076028..d1e1809cf16 100644 --- a/tests/ui/impl-trait/unsized_coercion3.next.stderr +++ b/tests/ui/impl-trait/unsized_coercion3.next.stderr @@ -1,38 +1,35 @@ -error[E0271]: type mismatch resolving `impl Trait + ?Sized <: dyn Send` - --> $DIR/unsized_coercion3.rs:13:17 +error[E0277]: the trait bound `dyn Send: Trait` is not satisfied + --> $DIR/unsized_coercion3.rs:14:17 | LL | let x = hello(); - | ^^^^^^^ types differ + | ^^^^^^^ the trait `Trait` is not implemented for `dyn Send` + | + = help: the trait `Trait` is implemented for `u32` error[E0308]: mismatched types - --> $DIR/unsized_coercion3.rs:18:14 + --> $DIR/unsized_coercion3.rs:19:5 | LL | fn hello() -> Box { - | ------------------- the expected opaque type + | ------------------------ + | | | + | | the expected opaque type + | expected `Box` because of return type ... LL | Box::new(1u32) - | -------- ^^^^ types differ - | | - | arguments to this function are incorrect + | ^^^^^^^^^^^^^^ types differ | - = note: expected opaque type `impl Trait + ?Sized` - found type `u32` -note: associated function defined here - --> $SRC_DIR/alloc/src/boxed.rs:LL:COL + = note: expected struct `Box` + found struct `Box` -error[E0277]: the size for values of type `impl Trait + ?Sized` cannot be known at compilation time - --> $DIR/unsized_coercion3.rs:18:14 +error[E0277]: the trait bound `dyn Send: Trait` is not satisfied + --> $DIR/unsized_coercion3.rs:11:1 | -LL | Box::new(1u32) - | -------- ^^^^ doesn't have a size known at compile-time - | | - | required by a bound introduced by this call +LL | fn hello() -> Box { + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Trait` is not implemented for `dyn Send` | - = help: the trait `Sized` is not implemented for `impl Trait + ?Sized` -note: required by a bound in `Box::::new` - --> $SRC_DIR/alloc/src/boxed.rs:LL:COL + = help: the trait `Trait` is implemented for `u32` error: aborting due to 3 previous errors -Some errors have detailed explanations: E0271, E0277, E0308. -For more information about an error, try `rustc --explain E0271`. +Some errors have detailed explanations: E0277, E0308. +For more information about an error, try `rustc --explain E0277`. diff --git a/tests/ui/impl-trait/unsized_coercion3.old.stderr b/tests/ui/impl-trait/unsized_coercion3.old.stderr index 52a72b84a8d..3bb9f9c2095 100644 --- a/tests/ui/impl-trait/unsized_coercion3.old.stderr +++ b/tests/ui/impl-trait/unsized_coercion3.old.stderr @@ -1,5 +1,5 @@ error[E0277]: the size for values of type `impl Trait + ?Sized` cannot be known at compilation time - --> $DIR/unsized_coercion3.rs:15:32 + --> $DIR/unsized_coercion3.rs:16:32 | LL | let y: Box = x; | ^ doesn't have a size known at compile-time diff --git a/tests/ui/impl-trait/unsized_coercion3.rs b/tests/ui/impl-trait/unsized_coercion3.rs index 7e862de2157..c1dd5350e22 100644 --- a/tests/ui/impl-trait/unsized_coercion3.rs +++ b/tests/ui/impl-trait/unsized_coercion3.rs @@ -9,15 +9,15 @@ trait Trait {} impl Trait for u32 {} fn hello() -> Box { + //[next]~^ ERROR: the trait bound `dyn Send: Trait` is not satisfied if true { let x = hello(); - //[next]~^ ERROR: type mismatch resolving `impl Trait + ?Sized <: dyn Send` + //[next]~^ ERROR: the trait bound `dyn Send: Trait` is not satisfied let y: Box = x; //[old]~^ ERROR: the size for values of type `impl Trait + ?Sized` cannot be know } Box::new(1u32) //[next]~^ ERROR: mismatched types - //[next]~| ERROR: the size for values of type `impl Trait + ?Sized` cannot be know } fn main() {} diff --git a/tests/ui/lint/non-snake-case/lint-non-snake-case-crate.cdylib_.stderr b/tests/ui/lint/non-snake-case/lint-non-snake-case-crate.cdylib_.stderr index 9bccb270627..140d72b9742 100644 --- a/tests/ui/lint/non-snake-case/lint-non-snake-case-crate.cdylib_.stderr +++ b/tests/ui/lint/non-snake-case/lint-non-snake-case-crate.cdylib_.stderr @@ -1,11 +1,11 @@ error: crate `NonSnakeCase` should have a snake case name - --> $DIR/lint-non-snake-case-crate.rs:25:18 + --> $DIR/lint-non-snake-case-crate.rs:29:18 | LL | #![crate_name = "NonSnakeCase"] | ^^^^^^^^^^^^ help: convert the identifier to snake case: `non_snake_case` | note: the lint level is defined here - --> $DIR/lint-non-snake-case-crate.rs:27:9 + --> $DIR/lint-non-snake-case-crate.rs:31:9 | LL | #![deny(non_snake_case)] | ^^^^^^^^^^^^^^ diff --git a/tests/ui/lint/non-snake-case/lint-non-snake-case-crate.dylib_.stderr b/tests/ui/lint/non-snake-case/lint-non-snake-case-crate.dylib_.stderr index 9bccb270627..140d72b9742 100644 --- a/tests/ui/lint/non-snake-case/lint-non-snake-case-crate.dylib_.stderr +++ b/tests/ui/lint/non-snake-case/lint-non-snake-case-crate.dylib_.stderr @@ -1,11 +1,11 @@ error: crate `NonSnakeCase` should have a snake case name - --> $DIR/lint-non-snake-case-crate.rs:25:18 + --> $DIR/lint-non-snake-case-crate.rs:29:18 | LL | #![crate_name = "NonSnakeCase"] | ^^^^^^^^^^^^ help: convert the identifier to snake case: `non_snake_case` | note: the lint level is defined here - --> $DIR/lint-non-snake-case-crate.rs:27:9 + --> $DIR/lint-non-snake-case-crate.rs:31:9 | LL | #![deny(non_snake_case)] | ^^^^^^^^^^^^^^ diff --git a/tests/ui/lint/non-snake-case/lint-non-snake-case-crate.lib_.stderr b/tests/ui/lint/non-snake-case/lint-non-snake-case-crate.lib_.stderr index 9bccb270627..140d72b9742 100644 --- a/tests/ui/lint/non-snake-case/lint-non-snake-case-crate.lib_.stderr +++ b/tests/ui/lint/non-snake-case/lint-non-snake-case-crate.lib_.stderr @@ -1,11 +1,11 @@ error: crate `NonSnakeCase` should have a snake case name - --> $DIR/lint-non-snake-case-crate.rs:25:18 + --> $DIR/lint-non-snake-case-crate.rs:29:18 | LL | #![crate_name = "NonSnakeCase"] | ^^^^^^^^^^^^ help: convert the identifier to snake case: `non_snake_case` | note: the lint level is defined here - --> $DIR/lint-non-snake-case-crate.rs:27:9 + --> $DIR/lint-non-snake-case-crate.rs:31:9 | LL | #![deny(non_snake_case)] | ^^^^^^^^^^^^^^ diff --git a/tests/ui/lint/non-snake-case/lint-non-snake-case-crate.proc_macro_.stderr b/tests/ui/lint/non-snake-case/lint-non-snake-case-crate.proc_macro_.stderr index 9bccb270627..140d72b9742 100644 --- a/tests/ui/lint/non-snake-case/lint-non-snake-case-crate.proc_macro_.stderr +++ b/tests/ui/lint/non-snake-case/lint-non-snake-case-crate.proc_macro_.stderr @@ -1,11 +1,11 @@ error: crate `NonSnakeCase` should have a snake case name - --> $DIR/lint-non-snake-case-crate.rs:25:18 + --> $DIR/lint-non-snake-case-crate.rs:29:18 | LL | #![crate_name = "NonSnakeCase"] | ^^^^^^^^^^^^ help: convert the identifier to snake case: `non_snake_case` | note: the lint level is defined here - --> $DIR/lint-non-snake-case-crate.rs:27:9 + --> $DIR/lint-non-snake-case-crate.rs:31:9 | LL | #![deny(non_snake_case)] | ^^^^^^^^^^^^^^ diff --git a/tests/ui/lint/non-snake-case/lint-non-snake-case-crate.rlib_.stderr b/tests/ui/lint/non-snake-case/lint-non-snake-case-crate.rlib_.stderr index 9bccb270627..140d72b9742 100644 --- a/tests/ui/lint/non-snake-case/lint-non-snake-case-crate.rlib_.stderr +++ b/tests/ui/lint/non-snake-case/lint-non-snake-case-crate.rlib_.stderr @@ -1,11 +1,11 @@ error: crate `NonSnakeCase` should have a snake case name - --> $DIR/lint-non-snake-case-crate.rs:25:18 + --> $DIR/lint-non-snake-case-crate.rs:29:18 | LL | #![crate_name = "NonSnakeCase"] | ^^^^^^^^^^^^ help: convert the identifier to snake case: `non_snake_case` | note: the lint level is defined here - --> $DIR/lint-non-snake-case-crate.rs:27:9 + --> $DIR/lint-non-snake-case-crate.rs:31:9 | LL | #![deny(non_snake_case)] | ^^^^^^^^^^^^^^ diff --git a/tests/ui/lint/non-snake-case/lint-non-snake-case-crate.rs b/tests/ui/lint/non-snake-case/lint-non-snake-case-crate.rs index 57604d99a07..097b246c165 100644 --- a/tests/ui/lint/non-snake-case/lint-non-snake-case-crate.rs +++ b/tests/ui/lint/non-snake-case/lint-non-snake-case-crate.rs @@ -22,6 +22,10 @@ //@[rlib_] compile-flags: --crate-type=rlib //@[staticlib_] compile-flags: --crate-type=staticlib +// The compiler may emit a warning that causes stderr output +// that contains a warning this test does not wish to check. +//@[proc_macro_] needs-unwind + #![crate_name = "NonSnakeCase"] //[cdylib_,dylib_,lib_,proc_macro_,rlib_,staticlib_]~^ ERROR crate `NonSnakeCase` should have a snake case name #![deny(non_snake_case)] diff --git a/tests/ui/lint/non-snake-case/lint-non-snake-case-crate.staticlib_.stderr b/tests/ui/lint/non-snake-case/lint-non-snake-case-crate.staticlib_.stderr index 9bccb270627..140d72b9742 100644 --- a/tests/ui/lint/non-snake-case/lint-non-snake-case-crate.staticlib_.stderr +++ b/tests/ui/lint/non-snake-case/lint-non-snake-case-crate.staticlib_.stderr @@ -1,11 +1,11 @@ error: crate `NonSnakeCase` should have a snake case name - --> $DIR/lint-non-snake-case-crate.rs:25:18 + --> $DIR/lint-non-snake-case-crate.rs:29:18 | LL | #![crate_name = "NonSnakeCase"] | ^^^^^^^^^^^^ help: convert the identifier to snake case: `non_snake_case` | note: the lint level is defined here - --> $DIR/lint-non-snake-case-crate.rs:27:9 + --> $DIR/lint-non-snake-case-crate.rs:31:9 | LL | #![deny(non_snake_case)] | ^^^^^^^^^^^^^^ diff --git a/tests/ui/mir/mir-inlining/always-encode-mirs.rs b/tests/ui/mir/mir-inlining/always-encode-mirs.rs index 9029ff6499b..4553560baaa 100644 --- a/tests/ui/mir/mir-inlining/always-encode-mirs.rs +++ b/tests/ui/mir/mir-inlining/always-encode-mirs.rs @@ -1,6 +1,6 @@ // Regression test for MIR inlining with -Zalways-encode-mir enabled in the auxiliary crate. // Previously we inlined function not eligible for inlining which lead to linking error: -// undefined reference to `internal::S' +// undefined reference to `internal::S` // //@ aux-build:internal.rs //@ build-pass diff --git a/tests/ui/pattern/match_ergonomics_2024.fixed b/tests/ui/pattern/match_ergonomics_2024.fixed deleted file mode 100644 index 1ec2b5a214b..00000000000 --- a/tests/ui/pattern/match_ergonomics_2024.fixed +++ /dev/null @@ -1,57 +0,0 @@ -//@ edition: 2021 -//@ run-rustfix -//@ rustfix-only-machine-applicable -//@ aux-build:match_ergonomics_2024_macros.rs -#![feature(mut_ref, ref_pat_eat_one_layer_2024)] -#![allow(incomplete_features, unused)] -#![deny(rust_2024_incompatible_pat)] - -extern crate match_ergonomics_2024_macros; - -struct Foo(u8); - -fn main() { - let &Foo(mut a) = &Foo(0); - //~^ ERROR: the semantics of this pattern will change in edition 2024 - a = 42; - - let &mut Foo(mut a) = &mut Foo(0); - //~^ ERROR: the semantics of this pattern will change in edition 2024 - a = 42; - - if let &&&&&Some(&_) = &&&&&Some(&0u8) {} - //~^ ERROR: the semantics of this pattern will change in edition 2024 - - if let &&&&&Some(&mut _) = &&&&&Some(&mut 0u8) {} - //~^ ERROR: the semantics of this pattern will change in edition 2024 - - if let &&&&&mut Some(&_) = &&&&&mut Some(&0u8) {} - //~^ ERROR: the semantics of this pattern will change in edition 2024 - - if let &mut Some(&mut Some(&mut Some(_))) = &mut Some(&mut Some(&mut Some(0u8))) {} - //~^ ERROR: the semantics of this pattern will change in edition 2024 - - if let &mut Some(&mut Some(&mut Some(ref mut _a))) = &mut Some(&mut Some(&mut Some(0u8))) {} - //~^ ERROR: the semantics of this pattern will change in edition 2024 - - struct Struct { - a: u32, - b: u32, - c: u32, - } - let s = Struct { a: 0, b: 0, c: 0 }; - let &Struct { ref a, mut b, ref c } = &s; - //~^ ERROR: the semantics of this pattern will change in edition 2024 - - #[warn(rust_2024_incompatible_pat)] - match &(Some(0), Some(0)) { - // The two patterns are the same syntactically, but because they're defined in different - // editions they don't mean the same thing. - (Some(mut _x), match_ergonomics_2024_macros::mixed_edition_pat!(_y)) => { - //~^ WARN: the semantics of this pattern will change in edition 2024 - _x = 4; - _y = &7; - } - _ => {} - } -} diff --git a/tests/ui/pattern/match_ergonomics_2024.rs b/tests/ui/pattern/match_ergonomics_2024.rs deleted file mode 100644 index c9f992c12d4..00000000000 --- a/tests/ui/pattern/match_ergonomics_2024.rs +++ /dev/null @@ -1,57 +0,0 @@ -//@ edition: 2021 -//@ run-rustfix -//@ rustfix-only-machine-applicable -//@ aux-build:match_ergonomics_2024_macros.rs -#![feature(mut_ref, ref_pat_eat_one_layer_2024)] -#![allow(incomplete_features, unused)] -#![deny(rust_2024_incompatible_pat)] - -extern crate match_ergonomics_2024_macros; - -struct Foo(u8); - -fn main() { - let Foo(mut a) = &Foo(0); - //~^ ERROR: the semantics of this pattern will change in edition 2024 - a = 42; - - let Foo(mut a) = &mut Foo(0); - //~^ ERROR: the semantics of this pattern will change in edition 2024 - a = 42; - - if let Some(&_) = &&&&&Some(&0u8) {} - //~^ ERROR: the semantics of this pattern will change in edition 2024 - - if let Some(&mut _) = &&&&&Some(&mut 0u8) {} - //~^ ERROR: the semantics of this pattern will change in edition 2024 - - if let Some(&_) = &&&&&mut Some(&0u8) {} - //~^ ERROR: the semantics of this pattern will change in edition 2024 - - if let Some(&mut Some(Some(_))) = &mut Some(&mut Some(&mut Some(0u8))) {} - //~^ ERROR: the semantics of this pattern will change in edition 2024 - - if let Some(&mut Some(Some(_a))) = &mut Some(&mut Some(&mut Some(0u8))) {} - //~^ ERROR: the semantics of this pattern will change in edition 2024 - - struct Struct { - a: u32, - b: u32, - c: u32, - } - let s = Struct { a: 0, b: 0, c: 0 }; - let Struct { a, mut b, c } = &s; - //~^ ERROR: the semantics of this pattern will change in edition 2024 - - #[warn(rust_2024_incompatible_pat)] - match &(Some(0), Some(0)) { - // The two patterns are the same syntactically, but because they're defined in different - // editions they don't mean the same thing. - (Some(mut _x), match_ergonomics_2024_macros::mixed_edition_pat!(_y)) => { - //~^ WARN: the semantics of this pattern will change in edition 2024 - _x = 4; - _y = &7; - } - _ => {} - } -} diff --git a/tests/ui/pattern/match_ergonomics_2024.stderr b/tests/ui/pattern/match_ergonomics_2024.stderr deleted file mode 100644 index 11844434ad2..00000000000 --- a/tests/ui/pattern/match_ergonomics_2024.stderr +++ /dev/null @@ -1,97 +0,0 @@ -error: the semantics of this pattern will change in edition 2024 - --> $DIR/match_ergonomics_2024.rs:14:9 - | -LL | let Foo(mut a) = &Foo(0); - | -^^^^^^^^^ - | | - | help: desugar the match ergonomics: `&` - | -note: the lint level is defined here - --> $DIR/match_ergonomics_2024.rs:7:9 - | -LL | #![deny(rust_2024_incompatible_pat)] - | ^^^^^^^^^^^^^^^^^^^^^^^^^^ - -error: the semantics of this pattern will change in edition 2024 - --> $DIR/match_ergonomics_2024.rs:18:9 - | -LL | let Foo(mut a) = &mut Foo(0); - | -^^^^^^^^^ - | | - | help: desugar the match ergonomics: `&mut` - -error: the semantics of this pattern will change in edition 2024 - --> $DIR/match_ergonomics_2024.rs:22:12 - | -LL | if let Some(&_) = &&&&&Some(&0u8) {} - | -^^^^^^^ - | | - | help: desugar the match ergonomics: `&&&&&` - -error: the semantics of this pattern will change in edition 2024 - --> $DIR/match_ergonomics_2024.rs:25:12 - | -LL | if let Some(&mut _) = &&&&&Some(&mut 0u8) {} - | -^^^^^^^^^^^ - | | - | help: desugar the match ergonomics: `&&&&&` - -error: the semantics of this pattern will change in edition 2024 - --> $DIR/match_ergonomics_2024.rs:28:12 - | -LL | if let Some(&_) = &&&&&mut Some(&0u8) {} - | -^^^^^^^ - | | - | help: desugar the match ergonomics: `&&&&&mut` - -error: the semantics of this pattern will change in edition 2024 - --> $DIR/match_ergonomics_2024.rs:31:12 - | -LL | if let Some(&mut Some(Some(_))) = &mut Some(&mut Some(&mut Some(0u8))) {} - | ^^^^^^^^^^^^^^^^^^^^^^^^ - | -help: desugar the match ergonomics - | -LL | if let &mut Some(&mut Some(&mut Some(_))) = &mut Some(&mut Some(&mut Some(0u8))) {} - | ++++ ++++ - -error: the semantics of this pattern will change in edition 2024 - --> $DIR/match_ergonomics_2024.rs:34:12 - | -LL | if let Some(&mut Some(Some(_a))) = &mut Some(&mut Some(&mut Some(0u8))) {} - | ^^^^^^^^^^^^^^^^^^^^^^^^^ - | -help: desugar the match ergonomics - | -LL | if let &mut Some(&mut Some(&mut Some(ref mut _a))) = &mut Some(&mut Some(&mut Some(0u8))) {} - | ++++ ++++ +++++++ - -error: the semantics of this pattern will change in edition 2024 - --> $DIR/match_ergonomics_2024.rs:43:9 - | -LL | let Struct { a, mut b, c } = &s; - | ^^^^^^^^^^^^^^^^^^^^^^ - | -help: desugar the match ergonomics - | -LL | let &Struct { ref a, mut b, ref c } = &s; - | + +++ +++ - -warning: the semantics of this pattern will change in edition 2024 - --> $DIR/match_ergonomics_2024.rs:50:9 - | -LL | (Some(mut _x), match_ergonomics_2024_macros::mixed_edition_pat!(_y)) => { - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ - | -note: the lint level is defined here - --> $DIR/match_ergonomics_2024.rs:46:12 - | -LL | #[warn(rust_2024_incompatible_pat)] - | ^^^^^^^^^^^^^^^^^^^^^^^^^^ -help: desugar the match ergonomics - | -LL | &(Some(mut _x), match_ergonomics_2024_macros::mixed_edition_pat!(ref _y)) => { - | + +++ - -error: aborting due to 8 previous errors; 1 warning emitted - diff --git a/tests/ui/pattern/auxiliary/match_ergonomics_2024_macros.rs b/tests/ui/pattern/rfc-3627-match-ergonomics-2024/auxiliary/migration_lint_macros.rs similarity index 100% rename from tests/ui/pattern/auxiliary/match_ergonomics_2024_macros.rs rename to tests/ui/pattern/rfc-3627-match-ergonomics-2024/auxiliary/migration_lint_macros.rs diff --git a/tests/ui/pattern/rfc-3627-match-ergonomics-2024/migration_lint.fixed b/tests/ui/pattern/rfc-3627-match-ergonomics-2024/migration_lint.fixed new file mode 100644 index 00000000000..086671e69cb --- /dev/null +++ b/tests/ui/pattern/rfc-3627-match-ergonomics-2024/migration_lint.fixed @@ -0,0 +1,144 @@ +//@ edition: 2021 +//@ run-rustfix +//@ rustfix-only-machine-applicable +//@ aux-build:migration_lint_macros.rs +#![feature(mut_ref)] +#![allow(incomplete_features, unused)] +#![deny(rust_2024_incompatible_pat)] + +extern crate migration_lint_macros; + +struct Foo(T); + +// Tests type equality in a way that avoids coercing `&&T` to `&T`. +trait Eq {} +impl Eq for T {} +fn assert_type_eq>(_: T, _: U) {} + +fn main() { + let Foo(x) = &Foo(0); + assert_type_eq(x, &0u8); + + let Foo(x) = &mut Foo(0); + assert_type_eq(x, &mut 0u8); + + let &Foo(mut x) = &Foo(0); + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, 0u8); + + let &mut Foo(mut x) = &mut Foo(0); + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, 0u8); + + let &Foo(ref x) = &Foo(0); + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, &0u8); + + let &mut Foo(ref x) = &mut Foo(0); + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, &0u8); + + let &Foo(x) = &Foo(0); + assert_type_eq(x, 0u8); + + let &mut Foo(x) = &mut Foo(0); + assert_type_eq(x, 0u8); + + let &Foo(x) = &Foo(&0); + assert_type_eq(x, &0u8); + + let &mut Foo(x) = &mut Foo(&0); + assert_type_eq(x, &0u8); + + let &Foo(&x) = &Foo(&0); + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, 0u8); + + let &Foo(&mut x) = &Foo(&mut 0); + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, 0u8); + + let &mut Foo(&x) = &mut Foo(&0); + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, 0u8); + + let &mut Foo(&mut x) = &mut Foo(&mut 0); + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, 0u8); + + if let Some(x) = &&&&&Some(&0u8) { + assert_type_eq(x, &&0u8); + } + + if let &&&&&Some(&x) = &&&&&Some(&0u8) { + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, 0u8); + } + + if let &&&&&Some(&mut x) = &&&&&Some(&mut 0u8) { + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, 0u8); + } + + if let &&&&&mut Some(&x) = &&&&&mut Some(&0u8) { + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, 0u8); + } + + if let &mut Some(&mut Some(&mut Some(ref mut x))) = &mut Some(&mut Some(&mut Some(0u8))) { + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, &mut 0u8); + } + + struct Struct { + a: A, + b: B, + c: C, + } + + let &Struct { ref a, mut b, ref c } = &Struct { a: 0, b: 0, c: 0 }; + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(a, &0u32); + assert_type_eq(b, 0u32); + + let &Struct { a: &a, ref b, ref c } = &Struct { a: &0, b: &0, c: &0 }; + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(a, 0u32); + assert_type_eq(b, &&0u32); + assert_type_eq(c, &&0u32); + + if let &Struct { a: &Some(a), b: &Some(&b), c: &Some(ref c) } = + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + &(Struct { a: &Some(&0), b: &Some(&0), c: &Some(&0) }) + { + assert_type_eq(a, &0u32); + assert_type_eq(b, 0u32); + assert_type_eq(c, &&0u32); + } + + match &(Some(0), Some(0)) { + // The two patterns are the same syntactically, but because they're defined in different + // editions they don't mean the same thing. + &(Some(mut x), migration_lint_macros::mixed_edition_pat!(y)) => { + //~^ ERROR: patterns are not allowed to reset the default binding mode + assert_type_eq(x, 0u32); + assert_type_eq(y, 0u32); + } + _ => {} + } +} diff --git a/tests/ui/pattern/rfc-3627-match-ergonomics-2024/migration_lint.rs b/tests/ui/pattern/rfc-3627-match-ergonomics-2024/migration_lint.rs new file mode 100644 index 00000000000..acceafdb7ec --- /dev/null +++ b/tests/ui/pattern/rfc-3627-match-ergonomics-2024/migration_lint.rs @@ -0,0 +1,144 @@ +//@ edition: 2021 +//@ run-rustfix +//@ rustfix-only-machine-applicable +//@ aux-build:migration_lint_macros.rs +#![feature(mut_ref)] +#![allow(incomplete_features, unused)] +#![deny(rust_2024_incompatible_pat)] + +extern crate migration_lint_macros; + +struct Foo(T); + +// Tests type equality in a way that avoids coercing `&&T` to `&T`. +trait Eq {} +impl Eq for T {} +fn assert_type_eq>(_: T, _: U) {} + +fn main() { + let Foo(x) = &Foo(0); + assert_type_eq(x, &0u8); + + let Foo(x) = &mut Foo(0); + assert_type_eq(x, &mut 0u8); + + let Foo(mut x) = &Foo(0); + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, 0u8); + + let Foo(mut x) = &mut Foo(0); + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, 0u8); + + let Foo(ref x) = &Foo(0); + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, &0u8); + + let Foo(ref x) = &mut Foo(0); + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, &0u8); + + let &Foo(x) = &Foo(0); + assert_type_eq(x, 0u8); + + let &mut Foo(x) = &mut Foo(0); + assert_type_eq(x, 0u8); + + let &Foo(x) = &Foo(&0); + assert_type_eq(x, &0u8); + + let &mut Foo(x) = &mut Foo(&0); + assert_type_eq(x, &0u8); + + let Foo(&x) = &Foo(&0); + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, 0u8); + + let Foo(&mut x) = &Foo(&mut 0); + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, 0u8); + + let Foo(&x) = &mut Foo(&0); + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, 0u8); + + let Foo(&mut x) = &mut Foo(&mut 0); + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, 0u8); + + if let Some(x) = &&&&&Some(&0u8) { + assert_type_eq(x, &&0u8); + } + + if let Some(&x) = &&&&&Some(&0u8) { + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, 0u8); + } + + if let Some(&mut x) = &&&&&Some(&mut 0u8) { + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, 0u8); + } + + if let Some(&x) = &&&&&mut Some(&0u8) { + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, 0u8); + } + + if let Some(&mut Some(Some(x))) = &mut Some(&mut Some(&mut Some(0u8))) { + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(x, &mut 0u8); + } + + struct Struct { + a: A, + b: B, + c: C, + } + + let Struct { a, mut b, c } = &Struct { a: 0, b: 0, c: 0 }; + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(a, &0u32); + assert_type_eq(b, 0u32); + + let Struct { a: &a, b, ref c } = &Struct { a: &0, b: &0, c: &0 }; + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + assert_type_eq(a, 0u32); + assert_type_eq(b, &&0u32); + assert_type_eq(c, &&0u32); + + if let Struct { a: &Some(a), b: Some(&b), c: Some(c) } = + //~^ ERROR: patterns are not allowed to reset the default binding mode + //~| WARN: this changes meaning in Rust 2024 + &(Struct { a: &Some(&0), b: &Some(&0), c: &Some(&0) }) + { + assert_type_eq(a, &0u32); + assert_type_eq(b, 0u32); + assert_type_eq(c, &&0u32); + } + + match &(Some(0), Some(0)) { + // The two patterns are the same syntactically, but because they're defined in different + // editions they don't mean the same thing. + (Some(mut x), migration_lint_macros::mixed_edition_pat!(y)) => { + //~^ ERROR: patterns are not allowed to reset the default binding mode + assert_type_eq(x, 0u32); + assert_type_eq(y, 0u32); + } + _ => {} + } +} diff --git a/tests/ui/pattern/rfc-3627-match-ergonomics-2024/migration_lint.stderr b/tests/ui/pattern/rfc-3627-match-ergonomics-2024/migration_lint.stderr new file mode 100644 index 00000000000..1c9a469e6ee --- /dev/null +++ b/tests/ui/pattern/rfc-3627-match-ergonomics-2024/migration_lint.stderr @@ -0,0 +1,188 @@ +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/migration_lint.rs:25:9 + | +LL | let Foo(mut x) = &Foo(0); + | -^^^^^^^^^ + | | + | help: desugar the match ergonomics: `&` + | + = warning: this changes meaning in Rust 2024 + = note: for more information, see 123076 +note: the lint level is defined here + --> $DIR/migration_lint.rs:7:9 + | +LL | #![deny(rust_2024_incompatible_pat)] + | ^^^^^^^^^^^^^^^^^^^^^^^^^^ + +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/migration_lint.rs:30:9 + | +LL | let Foo(mut x) = &mut Foo(0); + | -^^^^^^^^^ + | | + | help: desugar the match ergonomics: `&mut` + | + = warning: this changes meaning in Rust 2024 + = note: for more information, see 123076 + +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/migration_lint.rs:35:9 + | +LL | let Foo(ref x) = &Foo(0); + | -^^^^^^^^^ + | | + | help: desugar the match ergonomics: `&` + | + = warning: this changes meaning in Rust 2024 + = note: for more information, see 123076 + +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/migration_lint.rs:40:9 + | +LL | let Foo(ref x) = &mut Foo(0); + | -^^^^^^^^^ + | | + | help: desugar the match ergonomics: `&mut` + | + = warning: this changes meaning in Rust 2024 + = note: for more information, see 123076 + +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/migration_lint.rs:57:9 + | +LL | let Foo(&x) = &Foo(&0); + | -^^^^^^ + | | + | help: desugar the match ergonomics: `&` + | + = warning: this changes meaning in Rust 2024 + = note: for more information, see 123076 + +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/migration_lint.rs:62:9 + | +LL | let Foo(&mut x) = &Foo(&mut 0); + | -^^^^^^^^^^ + | | + | help: desugar the match ergonomics: `&` + | + = warning: this changes meaning in Rust 2024 + = note: for more information, see 123076 + +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/migration_lint.rs:67:9 + | +LL | let Foo(&x) = &mut Foo(&0); + | -^^^^^^ + | | + | help: desugar the match ergonomics: `&mut` + | + = warning: this changes meaning in Rust 2024 + = note: for more information, see 123076 + +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/migration_lint.rs:72:9 + | +LL | let Foo(&mut x) = &mut Foo(&mut 0); + | -^^^^^^^^^^ + | | + | help: desugar the match ergonomics: `&mut` + | + = warning: this changes meaning in Rust 2024 + = note: for more information, see 123076 + +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/migration_lint.rs:81:12 + | +LL | if let Some(&x) = &&&&&Some(&0u8) { + | -^^^^^^^ + | | + | help: desugar the match ergonomics: `&&&&&` + | + = warning: this changes meaning in Rust 2024 + = note: for more information, see 123076 + +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/migration_lint.rs:87:12 + | +LL | if let Some(&mut x) = &&&&&Some(&mut 0u8) { + | -^^^^^^^^^^^ + | | + | help: desugar the match ergonomics: `&&&&&` + | + = warning: this changes meaning in Rust 2024 + = note: for more information, see 123076 + +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/migration_lint.rs:93:12 + | +LL | if let Some(&x) = &&&&&mut Some(&0u8) { + | -^^^^^^^ + | | + | help: desugar the match ergonomics: `&&&&&mut` + | + = warning: this changes meaning in Rust 2024 + = note: for more information, see 123076 + +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/migration_lint.rs:99:12 + | +LL | if let Some(&mut Some(Some(x))) = &mut Some(&mut Some(&mut Some(0u8))) { + | ^^^^^^^^^^^^^^^^^^^^^^^^ + | + = warning: this changes meaning in Rust 2024 + = note: for more information, see 123076 +help: desugar the match ergonomics + | +LL | if let &mut Some(&mut Some(&mut Some(ref mut x))) = &mut Some(&mut Some(&mut Some(0u8))) { + | ++++ ++++ +++++++ + +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/migration_lint.rs:111:9 + | +LL | let Struct { a, mut b, c } = &Struct { a: 0, b: 0, c: 0 }; + | ^^^^^^^^^^^^^^^^^^^^^^ + | + = warning: this changes meaning in Rust 2024 + = note: for more information, see 123076 +help: desugar the match ergonomics + | +LL | let &Struct { ref a, mut b, ref c } = &Struct { a: 0, b: 0, c: 0 }; + | + +++ +++ + +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/migration_lint.rs:117:9 + | +LL | let Struct { a: &a, b, ref c } = &Struct { a: &0, b: &0, c: &0 }; + | ^^^^^^^^^^^^^^^^^^^^^^^^^^ + | + = warning: this changes meaning in Rust 2024 + = note: for more information, see 123076 +help: desugar the match ergonomics + | +LL | let &Struct { a: &a, ref b, ref c } = &Struct { a: &0, b: &0, c: &0 }; + | + +++ + +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/migration_lint.rs:124:12 + | +LL | if let Struct { a: &Some(a), b: Some(&b), c: Some(c) } = + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + | + = warning: this changes meaning in Rust 2024 + = note: for more information, see 123076 +help: desugar the match ergonomics + | +LL | if let &Struct { a: &Some(a), b: &Some(&b), c: &Some(ref c) } = + | + + + +++ + +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/migration_lint.rs:137:9 + | +LL | (Some(mut x), migration_lint_macros::mixed_edition_pat!(y)) => { + | -^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + | | + | help: desugar the match ergonomics: `&` + +error: aborting due to 16 previous errors + diff --git a/tests/ui/pattern/rfc-3627-match-ergonomics-2024/min_match_ergonomics_fail.rs b/tests/ui/pattern/rfc-3627-match-ergonomics-2024/min_match_ergonomics_fail.rs new file mode 100644 index 00000000000..a822c90ab6e --- /dev/null +++ b/tests/ui/pattern/rfc-3627-match-ergonomics-2024/min_match_ergonomics_fail.rs @@ -0,0 +1,46 @@ +//@ check-fail +//@ edition: 2024 +//@ compile-flags: -Zunstable-options +#![deny(rust_2024_incompatible_pat)] + +fn main() {} + +#[derive(Copy, Clone)] +struct T; + +struct Foo { + f: &'static (u8,), +} + +macro_rules! test_pat_on_type { + ($($tt:tt)*) => { + const _: () = { + // Define a new function to ensure all cases are tested independently. + fn foo($($tt)*) {} + }; + }; +} + +test_pat_on_type![(&x,): &(T,)]; //~ ERROR mismatched types +test_pat_on_type![(&x,): &(&T,)]; //~ ERROR patterns are not allowed to reset the default binding mode +test_pat_on_type![(&x,): &(&mut T,)]; //~ ERROR mismatched types +test_pat_on_type![(&mut x,): &(&T,)]; //~ ERROR mismatched types +test_pat_on_type![(&mut x,): &(&mut T,)]; //~ ERROR patterns are not allowed to reset the default binding mode +test_pat_on_type![(&x,): &&mut &(T,)]; //~ ERROR mismatched types +test_pat_on_type![Foo { f: (&x,) }: Foo]; //~ ERROR mismatched types +test_pat_on_type![Foo { f: (&x,) }: &mut Foo]; //~ ERROR mismatched types +test_pat_on_type![Foo { f: &(x,) }: &Foo]; //~ ERROR patterns are not allowed to reset the default binding mode +test_pat_on_type![(mut x,): &(T,)]; //~ ERROR patterns are not allowed to reset the default binding mode +test_pat_on_type![(ref x,): &(T,)]; //~ ERROR patterns are not allowed to reset the default binding mode +test_pat_on_type![(ref mut x,): &mut (T,)]; //~ ERROR patterns are not allowed to reset the default binding mode + +fn get() -> X { + unimplemented!() +} + +// Make sure this works even when the underlying type is inferred. This test passes on rust stable. +fn infer() -> X { + match &get() { + (&x,) => x, //~ ERROR patterns are not allowed to reset the default binding mode + } +} diff --git a/tests/ui/pattern/rfc-3627-match-ergonomics-2024/min_match_ergonomics_fail.stderr b/tests/ui/pattern/rfc-3627-match-ergonomics-2024/min_match_ergonomics_fail.stderr new file mode 100644 index 00000000000..33e4f0021b7 --- /dev/null +++ b/tests/ui/pattern/rfc-3627-match-ergonomics-2024/min_match_ergonomics_fail.stderr @@ -0,0 +1,160 @@ +error[E0308]: mismatched types + --> $DIR/min_match_ergonomics_fail.rs:24:20 + | +LL | test_pat_on_type![(&x,): &(T,)]; + | ^^ ----- expected due to this + | | + | expected `T`, found `&_` + | + = note: expected struct `T` + found reference `&_` +help: consider removing `&` from the pattern + | +LL - test_pat_on_type![(&x,): &(T,)]; +LL + test_pat_on_type![(x,): &(T,)]; + | + +error[E0308]: mismatched types + --> $DIR/min_match_ergonomics_fail.rs:26:20 + | +LL | test_pat_on_type![(&x,): &(&mut T,)]; + | ^^ ---------- expected due to this + | | + | types differ in mutability + | + = note: expected mutable reference `&mut T` + found reference `&_` +help: consider removing `&` from the pattern + | +LL - test_pat_on_type![(&x,): &(&mut T,)]; +LL + test_pat_on_type![(x,): &(&mut T,)]; + | + +error[E0308]: mismatched types + --> $DIR/min_match_ergonomics_fail.rs:27:20 + | +LL | test_pat_on_type![(&mut x,): &(&T,)]; + | ^^^^^^ ------ expected due to this + | | + | types differ in mutability + | + = note: expected reference `&T` + found mutable reference `&mut _` +note: to declare a mutable binding use: `mut x` + --> $DIR/min_match_ergonomics_fail.rs:27:20 + | +LL | test_pat_on_type![(&mut x,): &(&T,)]; + | ^^^^^^ +help: consider removing `&mut` from the pattern + | +LL - test_pat_on_type![(&mut x,): &(&T,)]; +LL + test_pat_on_type![(x,): &(&T,)]; + | + +error[E0308]: mismatched types + --> $DIR/min_match_ergonomics_fail.rs:29:20 + | +LL | test_pat_on_type![(&x,): &&mut &(T,)]; + | ^^ ----------- expected due to this + | | + | expected `T`, found `&_` + | + = note: expected struct `T` + found reference `&_` +help: consider removing `&` from the pattern + | +LL - test_pat_on_type![(&x,): &&mut &(T,)]; +LL + test_pat_on_type![(x,): &&mut &(T,)]; + | + +error[E0308]: mismatched types + --> $DIR/min_match_ergonomics_fail.rs:30:29 + | +LL | test_pat_on_type![Foo { f: (&x,) }: Foo]; + | ^^ --- expected due to this + | | + | expected `u8`, found `&_` + | + = note: expected type `u8` + found reference `&_` +help: consider removing `&` from the pattern + | +LL - test_pat_on_type![Foo { f: (&x,) }: Foo]; +LL + test_pat_on_type![Foo { f: (x,) }: Foo]; + | + +error[E0308]: mismatched types + --> $DIR/min_match_ergonomics_fail.rs:31:29 + | +LL | test_pat_on_type![Foo { f: (&x,) }: &mut Foo]; + | ^^ -------- expected due to this + | | + | expected `u8`, found `&_` + | + = note: expected type `u8` + found reference `&_` +help: consider removing `&` from the pattern + | +LL - test_pat_on_type![Foo { f: (&x,) }: &mut Foo]; +LL + test_pat_on_type![Foo { f: (x,) }: &mut Foo]; + | + +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/min_match_ergonomics_fail.rs:25:19 + | +LL | test_pat_on_type![(&x,): &(&T,)]; + | -^^^^ + | | + | help: desugar the match ergonomics: `&` + +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/min_match_ergonomics_fail.rs:28:19 + | +LL | test_pat_on_type![(&mut x,): &(&mut T,)]; + | -^^^^^^^^ + | | + | help: desugar the match ergonomics: `&` + +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/min_match_ergonomics_fail.rs:32:19 + | +LL | test_pat_on_type![Foo { f: &(x,) }: &Foo]; + | -^^^^^^^^^^^^^^^ + | | + | help: desugar the match ergonomics: `&` + +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/min_match_ergonomics_fail.rs:33:19 + | +LL | test_pat_on_type![(mut x,): &(T,)]; + | -^^^^^^^ + | | + | help: desugar the match ergonomics: `&` + +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/min_match_ergonomics_fail.rs:34:19 + | +LL | test_pat_on_type![(ref x,): &(T,)]; + | -^^^^^^^ + | | + | help: desugar the match ergonomics: `&` + +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/min_match_ergonomics_fail.rs:35:19 + | +LL | test_pat_on_type![(ref mut x,): &mut (T,)]; + | -^^^^^^^^^^^ + | | + | help: desugar the match ergonomics: `&mut` + +error: patterns are not allowed to reset the default binding mode in edition 2024 + --> $DIR/min_match_ergonomics_fail.rs:44:9 + | +LL | (&x,) => x, + | -^^^^ + | | + | help: desugar the match ergonomics: `&` + +error: aborting due to 13 previous errors + +For more information about this error, try `rustc --explain E0308`. diff --git a/tests/ui/pattern/rfc-3627-match-ergonomics-2024/min_match_ergonomics_success.rs b/tests/ui/pattern/rfc-3627-match-ergonomics-2024/min_match_ergonomics_success.rs new file mode 100644 index 00000000000..0fb448afca9 --- /dev/null +++ b/tests/ui/pattern/rfc-3627-match-ergonomics-2024/min_match_ergonomics_success.rs @@ -0,0 +1,17 @@ +//@ check-pass +#![allow(incomplete_features)] + +fn main() {} + +// Tests type equality in a way that avoids coercing `&&T` to `&T`. +trait Eq {} +impl Eq for T {} +fn assert_type_eq>(_: T, _: U) {} + +#[derive(Copy, Clone)] +struct T; + +fn test() { + let (x,) = &(&T,); + assert_type_eq(x, &&T); +} diff --git a/tests/ui/traits/negative-bounds/opaque-type-unsatisfied-bound.rs b/tests/ui/traits/negative-bounds/opaque-type-unsatisfied-bound.rs index 35757f2339d..1260cca5106 100644 --- a/tests/ui/traits/negative-bounds/opaque-type-unsatisfied-bound.rs +++ b/tests/ui/traits/negative-bounds/opaque-type-unsatisfied-bound.rs @@ -13,9 +13,14 @@ fn main() { } fn weird0() -> impl Sized + !Sized {} -//~^ ERROR type mismatch resolving `impl !Sized + Sized == ()` +//~^ ERROR the trait bound `(): !Sized` is not satisfied +//~| ERROR the trait bound `(): !Sized` is not satisfied +//~| ERROR the trait bound `(): !Sized` is not satisfied fn weird1() -> impl !Sized + Sized {} -//~^ ERROR type mismatch resolving `impl !Sized + Sized == ()` +//~^ ERROR the trait bound `(): !Sized` is not satisfied +//~| ERROR the trait bound `(): !Sized` is not satisfied +//~| ERROR the trait bound `(): !Sized` is not satisfied fn weird2() -> impl !Sized {} -//~^ ERROR type mismatch resolving `impl !Sized == ()` -//~| ERROR the size for values of type `impl !Sized` cannot be known at compilation time +//~^ ERROR the trait bound `(): !Sized` is not satisfied +//~| ERROR the trait bound `(): !Sized` is not satisfied +//~| ERROR the trait bound `(): !Sized` is not satisfied diff --git a/tests/ui/traits/negative-bounds/opaque-type-unsatisfied-bound.stderr b/tests/ui/traits/negative-bounds/opaque-type-unsatisfied-bound.stderr index 3dd2b27b55b..4ec578a3b7b 100644 --- a/tests/ui/traits/negative-bounds/opaque-type-unsatisfied-bound.stderr +++ b/tests/ui/traits/negative-bounds/opaque-type-unsatisfied-bound.stderr @@ -1,29 +1,56 @@ -error[E0271]: type mismatch resolving `impl !Sized + Sized == ()` +error[E0277]: the trait bound `(): !Sized` is not satisfied --> $DIR/opaque-type-unsatisfied-bound.rs:15:16 | LL | fn weird0() -> impl Sized + !Sized {} - | ^^^^^^^^^^^^^^^^^^^ types differ + | ^^^^^^^^^^^^^^^^^^^ the trait bound `(): !Sized` is not satisfied -error[E0271]: type mismatch resolving `impl !Sized + Sized == ()` - --> $DIR/opaque-type-unsatisfied-bound.rs:17:16 +error[E0277]: the trait bound `(): !Sized` is not satisfied + --> $DIR/opaque-type-unsatisfied-bound.rs:15:36 + | +LL | fn weird0() -> impl Sized + !Sized {} + | ^^ the trait bound `(): !Sized` is not satisfied + +error[E0277]: the trait bound `(): !Sized` is not satisfied + --> $DIR/opaque-type-unsatisfied-bound.rs:15:1 + | +LL | fn weird0() -> impl Sized + !Sized {} + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait bound `(): !Sized` is not satisfied + +error[E0277]: the trait bound `(): !Sized` is not satisfied + --> $DIR/opaque-type-unsatisfied-bound.rs:19:16 | LL | fn weird1() -> impl !Sized + Sized {} - | ^^^^^^^^^^^^^^^^^^^ types differ + | ^^^^^^^^^^^^^^^^^^^ the trait bound `(): !Sized` is not satisfied -error[E0271]: type mismatch resolving `impl !Sized == ()` - --> $DIR/opaque-type-unsatisfied-bound.rs:19:16 +error[E0277]: the trait bound `(): !Sized` is not satisfied + --> $DIR/opaque-type-unsatisfied-bound.rs:19:36 + | +LL | fn weird1() -> impl !Sized + Sized {} + | ^^ the trait bound `(): !Sized` is not satisfied + +error[E0277]: the trait bound `(): !Sized` is not satisfied + --> $DIR/opaque-type-unsatisfied-bound.rs:19:1 + | +LL | fn weird1() -> impl !Sized + Sized {} + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait bound `(): !Sized` is not satisfied + +error[E0277]: the trait bound `(): !Sized` is not satisfied + --> $DIR/opaque-type-unsatisfied-bound.rs:23:16 | LL | fn weird2() -> impl !Sized {} - | ^^^^^^^^^^^ types differ + | ^^^^^^^^^^^ the trait bound `(): !Sized` is not satisfied -error[E0277]: the size for values of type `impl !Sized` cannot be known at compilation time - --> $DIR/opaque-type-unsatisfied-bound.rs:19:16 +error[E0277]: the trait bound `(): !Sized` is not satisfied + --> $DIR/opaque-type-unsatisfied-bound.rs:23:28 | LL | fn weird2() -> impl !Sized {} - | ^^^^^^^^^^^ doesn't have a size known at compile-time + | ^^ the trait bound `(): !Sized` is not satisfied + +error[E0277]: the trait bound `(): !Sized` is not satisfied + --> $DIR/opaque-type-unsatisfied-bound.rs:23:1 | - = help: the trait `Sized` is not implemented for `impl !Sized` - = note: the return type of a function must have a statically known size +LL | fn weird2() -> impl !Sized {} + | ^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait bound `(): !Sized` is not satisfied error[E0277]: the trait bound `impl !Trait: Trait` is not satisfied --> $DIR/opaque-type-unsatisfied-bound.rs:12:13 @@ -39,7 +66,6 @@ note: required by a bound in `consume` LL | fn consume(_: impl Trait) {} | ^^^^^ required by this bound in `consume` -error: aborting due to 5 previous errors +error: aborting due to 10 previous errors -Some errors have detailed explanations: E0271, E0277. -For more information about an error, try `rustc --explain E0271`. +For more information about this error, try `rustc --explain E0277`. diff --git a/tests/ui/traits/negative-bounds/opaque-type-unsatisfied-fn-bound.rs b/tests/ui/traits/negative-bounds/opaque-type-unsatisfied-fn-bound.rs index 9951826a846..c6826578658 100644 --- a/tests/ui/traits/negative-bounds/opaque-type-unsatisfied-fn-bound.rs +++ b/tests/ui/traits/negative-bounds/opaque-type-unsatisfied-fn-bound.rs @@ -3,6 +3,8 @@ #![feature(negative_bounds, unboxed_closures)] fn produce() -> impl !Fn<(u32,)> {} -//~^ ERROR type mismatch resolving `impl !Fn<(u32,)> == ()` +//~^ ERROR the trait bound `(): !Fn(u32)` is not satisfied +//~| ERROR the trait bound `(): !Fn(u32)` is not satisfied +//~| ERROR the trait bound `(): !Fn(u32)` is not satisfied fn main() {} diff --git a/tests/ui/traits/negative-bounds/opaque-type-unsatisfied-fn-bound.stderr b/tests/ui/traits/negative-bounds/opaque-type-unsatisfied-fn-bound.stderr index e1b84e0df7a..f81f0a23ac3 100644 --- a/tests/ui/traits/negative-bounds/opaque-type-unsatisfied-fn-bound.stderr +++ b/tests/ui/traits/negative-bounds/opaque-type-unsatisfied-fn-bound.stderr @@ -1,9 +1,21 @@ -error[E0271]: type mismatch resolving `impl !Fn<(u32,)> == ()` +error[E0277]: the trait bound `(): !Fn(u32)` is not satisfied --> $DIR/opaque-type-unsatisfied-fn-bound.rs:5:17 | LL | fn produce() -> impl !Fn<(u32,)> {} - | ^^^^^^^^^^^^^^^^ types differ + | ^^^^^^^^^^^^^^^^ the trait bound `(): !Fn(u32)` is not satisfied -error: aborting due to 1 previous error +error[E0277]: the trait bound `(): !Fn(u32)` is not satisfied + --> $DIR/opaque-type-unsatisfied-fn-bound.rs:5:34 + | +LL | fn produce() -> impl !Fn<(u32,)> {} + | ^^ the trait bound `(): !Fn(u32)` is not satisfied -For more information about this error, try `rustc --explain E0271`. +error[E0277]: the trait bound `(): !Fn(u32)` is not satisfied + --> $DIR/opaque-type-unsatisfied-fn-bound.rs:5:1 + | +LL | fn produce() -> impl !Fn<(u32,)> {} + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait bound `(): !Fn(u32)` is not satisfied + +error: aborting due to 3 previous errors + +For more information about this error, try `rustc --explain E0277`. diff --git a/tests/ui/traits/next-solver/issue-118950-root-region.rs b/tests/ui/traits/next-solver/issue-118950-root-region.rs index 9f6dea5d5bf..e1bd234a275 100644 --- a/tests/ui/traits/next-solver/issue-118950-root-region.rs +++ b/tests/ui/traits/next-solver/issue-118950-root-region.rs @@ -17,7 +17,7 @@ trait Overlap {} impl Overlap for T {} impl Overlap fn(Assoc<'a, T>)> for T where Missing: Overlap {} -//~^ ERROR conflicting implementations of trait `Overlap` for type `fn(_)` -//~| ERROR cannot find type `Missing` in this scope +//~^ ERROR cannot find type `Missing` in this scope +//~| ERROR the trait bound `for<'a> *const T: ToUnit<'a>` is not satisfied fn main() {} diff --git a/tests/ui/traits/next-solver/issue-118950-root-region.stderr b/tests/ui/traits/next-solver/issue-118950-root-region.stderr index 7c3e22fb401..f6545c6ebf9 100644 --- a/tests/ui/traits/next-solver/issue-118950-root-region.stderr +++ b/tests/ui/traits/next-solver/issue-118950-root-region.stderr @@ -26,21 +26,19 @@ LL | trait ToUnit<'a> { | ^^^^^^^^^^^^^^^^ WARN rustc_infer::infer::relate::generalize may incompletely handle alias type: AliasTy { args: ['^0.Named(DefId(0:15 ~ issue_118950_root_region[d54f]::{impl#1}::'a), "'a"), ?1t], def_id: DefId(0:8 ~ issue_118950_root_region[d54f]::Assoc), .. } - WARN rustc_infer::infer::relate::generalize may incompletely handle alias type: AliasTy { args: ['^0.Named(DefId(0:15 ~ issue_118950_root_region[d54f]::{impl#1}::'a), "'a"), ?1t], def_id: DefId(0:8 ~ issue_118950_root_region[d54f]::Assoc), .. } - WARN rustc_infer::infer::relate::generalize may incompletely handle alias type: AliasTy { args: ['^0.Named(DefId(0:15 ~ issue_118950_root_region[d54f]::{impl#1}::'a), "'a"), ?1t], def_id: DefId(0:8 ~ issue_118950_root_region[d54f]::Assoc), .. } - WARN rustc_infer::infer::relate::generalize may incompletely handle alias type: AliasTy { args: ['^0.Named(DefId(0:15 ~ issue_118950_root_region[d54f]::{impl#1}::'a), "'a"), ?1t], def_id: DefId(0:8 ~ issue_118950_root_region[d54f]::Assoc), .. } -error[E0119]: conflicting implementations of trait `Overlap` for type `fn(_)` - --> $DIR/issue-118950-root-region.rs:19:1 +error[E0277]: the trait bound `for<'a> *const T: ToUnit<'a>` is not satisfied + --> $DIR/issue-118950-root-region.rs:19:17 | -LL | impl Overlap for T {} - | ------------------------ first implementation here -LL | LL | impl Overlap fn(Assoc<'a, T>)> for T where Missing: Overlap {} - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation for `fn(_)` + | ^^^^^^^^^^^^^^^^^^^^^^^^ the trait `for<'a> ToUnit<'a>` is not implemented for `*const T` | - = note: this behavior recently changed as a result of a bug fix; see rust-lang/rust#56105 for details +help: this trait has no implementations, consider adding one + --> $DIR/issue-118950-root-region.rs:8:1 + | +LL | trait ToUnit<'a> { + | ^^^^^^^^^^^^^^^^ error: aborting due to 3 previous errors; 1 warning emitted -Some errors have detailed explanations: E0119, E0277, E0412. -For more information about an error, try `rustc --explain E0119`. +Some errors have detailed explanations: E0277, E0412. +For more information about an error, try `rustc --explain E0277`. diff --git a/tests/ui/traits/next-solver/normalize/normalize-region-obligations.rs b/tests/ui/traits/next-solver/normalize/normalize-region-obligations.rs index 7bf3274f9c6..c4c2e695a1d 100644 --- a/tests/ui/traits/next-solver/normalize/normalize-region-obligations.rs +++ b/tests/ui/traits/next-solver/normalize/normalize-region-obligations.rs @@ -15,7 +15,7 @@ trait Foo { impl Mirror for T { type Assoc = T; } trait MirrorRegion<'a> { type Assoc: ?Sized; } -impl<'a, T> MirrorRegion<'a> for T { type Assoc = T; } +impl<'a, T: ?Sized> MirrorRegion<'a> for T { type Assoc = T; } impl Foo for T { #[cfg(normalize_param_env)] diff --git a/tests/ui/typeck/issue-103899.rs b/tests/ui/typeck/issue-103899.rs index 38882e9dc54..81ab92a8994 100644 --- a/tests/ui/typeck/issue-103899.rs +++ b/tests/ui/typeck/issue-103899.rs @@ -1,11 +1,9 @@ //@ revisions: current next -//@[next] compile-flags: -Znext-solver -//@[next] check-pass //@ ignore-compare-mode-next-solver (explicit revisions) -//@[current] check-fail -//@[current] failure-status: 101 -//@[current] dont-check-compiler-stderr -//@[current] known-bug: #103899 +//@ check-fail +//@ failure-status: 101 +//@ dont-check-compiler-stderr +//@ known-bug: #103899 trait BaseWithAssoc { type Assoc;