@@ -564,6 +564,11 @@ fn find_opaque_ty_constraints_for_tait(tcx: TyCtxt<'_>, def_id: LocalDefId) -> T
564564 /// checked against it (we also carry the span of that first
565565 /// type).
566566 found : Option < ty:: OpaqueHiddenType < ' tcx > > ,
567+
568+ /// In the presence of dead code, typeck may figure out a hidden type
569+ /// while borrowck will now. We collect these cases here and check at
570+ /// the end that we actually found a type that matches (modulo regions).
571+ typeck_types : Vec < ty:: OpaqueHiddenType < ' tcx > > ,
567572 }
568573
569574 impl ConstraintLocator < ' _ > {
@@ -590,18 +595,23 @@ fn find_opaque_ty_constraints_for_tait(tcx: TyCtxt<'_>, def_id: LocalDefId) -> T
590595 self . found = Some ( ty:: OpaqueHiddenType { span : DUMMY_SP , ty : self . tcx . ty_error ( ) } ) ;
591596 return ;
592597 }
593- if ! tables. concrete_opaque_types . contains_key ( & self . def_id ) {
598+ let Some ( & typeck_hidden_ty ) = tables. concrete_opaque_types . get ( & self . def_id ) else {
594599 debug ! ( "no constraints in typeck results" ) ;
595600 return ;
601+ } ;
602+ if self . typeck_types . iter ( ) . all ( |prev| prev. ty != typeck_hidden_ty. ty ) {
603+ self . typeck_types . push ( typeck_hidden_ty) ;
596604 }
605+
597606 // Use borrowck to get the type with unerased regions.
598607 let concrete_opaque_types = & self . tcx . mir_borrowck ( item_def_id) . concrete_opaque_types ;
599608 debug ! ( ?concrete_opaque_types) ;
600609 if let Some ( & concrete_type) = concrete_opaque_types. get ( & self . def_id ) {
601610 debug ! ( ?concrete_type, "found constraint" ) ;
602- if let Some ( prev) = self . found {
603- if concrete_type. ty != prev. ty && !( concrete_type, prev) . references_error ( ) {
611+ if let Some ( prev) = & mut self . found {
612+ if concrete_type. ty != prev. ty && !( concrete_type, prev. ty ) . references_error ( ) {
604613 prev. report_mismatch ( & concrete_type, self . tcx ) ;
614+ prev. ty = self . tcx . ty_error ( ) ;
605615 }
606616 } else {
607617 self . found = Some ( concrete_type) ;
@@ -648,7 +658,7 @@ fn find_opaque_ty_constraints_for_tait(tcx: TyCtxt<'_>, def_id: LocalDefId) -> T
648658
649659 let hir_id = tcx. hir ( ) . local_def_id_to_hir_id ( def_id) ;
650660 let scope = tcx. hir ( ) . get_defining_scope ( hir_id) ;
651- let mut locator = ConstraintLocator { def_id : def_id, tcx, found : None } ;
661+ let mut locator = ConstraintLocator { def_id : def_id, tcx, found : None , typeck_types : vec ! [ ] } ;
652662
653663 debug ! ( ?scope) ;
654664
@@ -678,16 +688,26 @@ fn find_opaque_ty_constraints_for_tait(tcx: TyCtxt<'_>, def_id: LocalDefId) -> T
678688 }
679689 }
680690
681- match locator. found {
682- Some ( hidden) => hidden. ty ,
683- None => {
684- tcx. sess . emit_err ( UnconstrainedOpaqueType {
685- span : tcx. def_span ( def_id) ,
686- name : tcx. item_name ( tcx. local_parent ( def_id) . to_def_id ( ) ) ,
687- } ) ;
688- tcx. ty_error ( )
691+ let Some ( hidden) = locator. found else {
692+ tcx. sess . emit_err ( UnconstrainedOpaqueType {
693+ span : tcx. def_span ( def_id) ,
694+ name : tcx. item_name ( tcx. local_parent ( def_id) . to_def_id ( ) ) ,
695+ } ) ;
696+ return tcx. ty_error ( ) ;
697+ } ;
698+
699+ // Only check against typeck if we didn't already error
700+ if !hidden. ty . references_error ( ) {
701+ for concrete_type in locator. typeck_types {
702+ if tcx. erase_regions ( concrete_type. ty ) != tcx. erase_regions ( hidden. ty )
703+ && !( concrete_type, hidden) . references_error ( )
704+ {
705+ hidden. report_mismatch ( & concrete_type, tcx) ;
706+ }
689707 }
690708 }
709+
710+ hidden. ty
691711}
692712
693713fn find_opaque_ty_constraints_for_rpit (
@@ -788,7 +808,7 @@ fn find_opaque_ty_constraints_for_rpit(
788808 // the `concrete_opaque_types` table.
789809 tcx. ty_error ( )
790810 } else {
791- table. concrete_opaque_types . get ( & def_id) . copied ( ) . unwrap_or_else ( || {
811+ table. concrete_opaque_types . get ( & def_id) . map ( |ty| ty . ty ) . unwrap_or_else ( || {
792812 // We failed to resolve the opaque type or it
793813 // resolves to itself. We interpret this as the
794814 // no values of the hidden type ever being constructed,
0 commit comments