@@ -42,7 +42,7 @@ use rustc_attr_parsing::InlineAttr;
42
42
use rustc_errors:: codes:: * ;
43
43
use rustc_errors:: { Applicability , Diag , struct_span_code_err} ;
44
44
use rustc_hir:: def_id:: { DefId , LocalDefId } ;
45
- use rustc_hir:: { self as hir, LangItem } ;
45
+ use rustc_hir:: { self as hir} ;
46
46
use rustc_hir_analysis:: hir_ty_lowering:: HirTyLowerer ;
47
47
use rustc_infer:: infer:: relate:: RelateResult ;
48
48
use rustc_infer:: infer:: { Coercion , DefineOpaqueTypes , InferOk , InferResult } ;
@@ -55,7 +55,7 @@ use rustc_middle::ty::adjustment::{
55
55
Adjust , Adjustment , AllowTwoPhase , AutoBorrow , AutoBorrowMutability , PointerCoercion ,
56
56
} ;
57
57
use rustc_middle:: ty:: error:: TypeError ;
58
- use rustc_middle:: ty:: { self , AliasTy , GenericArgsRef , Ty , TyCtxt , TypeVisitableExt } ;
58
+ use rustc_middle:: ty:: { self , GenericArgsRef , Ty , TyCtxt , TypeVisitableExt } ;
59
59
use rustc_span:: { BytePos , DUMMY_SP , DesugaringKind , Span } ;
60
60
use rustc_trait_selection:: infer:: InferCtxtExt as _;
61
61
use rustc_trait_selection:: traits:: query:: evaluate_obligation:: InferCtxtExt ;
@@ -599,57 +599,6 @@ impl<'f, 'tcx> Coerce<'f, 'tcx> {
599
599
ty:: TraitRef :: new ( self . tcx , coerce_unsized_did, [ coerce_source, coerce_target] ) ,
600
600
) ;
601
601
602
- // If the root `Source: CoerceUnsized<Target>` obligation can't possibly hold,
603
- // we don't have to assume that this is unsizing coercion (it will always lead to an error)
604
- //
605
- // However, we don't want to bail early all the time, since the unholdable obligations
606
- // may be interesting for diagnostics (such as trying to coerce `&T` to `&dyn Id<This = U>`),
607
- // so we only bail if there (likely) is another way to convert the types.
608
- if !self . infcx . predicate_may_hold ( & root_obligation) {
609
- if let Some ( dyn_metadata_adt_def_id) = self . tcx . lang_items ( ) . get ( LangItem :: DynMetadata )
610
- && let Some ( metadata_type_def_id) = self . tcx . lang_items ( ) . get ( LangItem :: Metadata )
611
- {
612
- self . probe ( |_| {
613
- let ocx = ObligationCtxt :: new ( & self . infcx ) ;
614
-
615
- // returns `true` if `<ty as Pointee>::Metadata` is `DynMetadata<_>`
616
- let has_dyn_trait_metadata = |ty| {
617
- let metadata_ty: Result < _ , _ > = ocx. structurally_normalize_ty (
618
- & ObligationCause :: dummy ( ) ,
619
- self . fcx . param_env ,
620
- Ty :: new_alias (
621
- self . tcx ,
622
- ty:: AliasTyKind :: Projection ,
623
- AliasTy :: new ( self . tcx , metadata_type_def_id, [ ty] ) ,
624
- ) ,
625
- ) ;
626
-
627
- metadata_ty. is_ok_and ( |metadata_ty| {
628
- metadata_ty
629
- . ty_adt_def ( )
630
- . is_some_and ( |d| d. did ( ) == dyn_metadata_adt_def_id)
631
- } )
632
- } ;
633
-
634
- // If both types are raw pointers to a (wrapper over a) trait object,
635
- // this might be a cast like `*const W<dyn Trait> -> *const dyn Trait`.
636
- // So it's better to bail and try that. (even if the cast is not possible, for
637
- // example due to vtables not matching, cast diagnostic will likely still be better)
638
- //
639
- // N.B. use `target`, not `coerce_target` (the latter is a var)
640
- if let & ty:: RawPtr ( source_pointee, _) = coerce_source. kind ( )
641
- && let & ty:: RawPtr ( target_pointee, _) = target. kind ( )
642
- && has_dyn_trait_metadata ( source_pointee)
643
- && has_dyn_trait_metadata ( target_pointee)
644
- {
645
- return Err ( TypeError :: Mismatch ) ;
646
- }
647
-
648
- Ok ( ( ) )
649
- } ) ?;
650
- }
651
- }
652
-
653
602
// Use a FIFO queue for this custom fulfillment procedure.
654
603
//
655
604
// A Vec (or SmallVec) is not a natural choice for a queue. However,
@@ -725,16 +674,12 @@ impl<'f, 'tcx> Coerce<'f, 'tcx> {
725
674
}
726
675
727
676
// Dyn-compatibility violations or miscellaneous.
728
- Err ( err) => {
729
- let guar = self . err_ctxt ( ) . report_selection_error (
730
- obligation. clone ( ) ,
731
- & obligation,
732
- & err,
733
- ) ;
734
- self . fcx . set_tainted_by_errors ( guar) ;
735
- // Treat this like an obligation and follow through
736
- // with the unsizing - the lack of a coercion should
737
- // be silent, as it causes a type mismatch later.
677
+ Err ( _) => {
678
+ // Previously we reported an error here; instead of doing that,
679
+ // we just register the failing obligation which will be reported
680
+ // in the outer selection loop. This prevents reporting errors
681
+ // in places like `may_coerce` calls.
682
+ coercion. obligations . push ( obligation) ;
738
683
}
739
684
740
685
Ok ( Some ( impl_source) ) => queue. extend ( impl_source. nested_obligations ( ) ) ,
0 commit comments