11use std:: fmt:: { self , Display } ;
22use std:: iter;
33
4+ use rustc_data_structures:: fx:: IndexEntry ;
45use rustc_errors:: Diagnostic ;
56use rustc_hir as hir;
67use rustc_hir:: def:: { DefKind , Res } ;
@@ -14,7 +15,7 @@ use crate::{universal_regions::DefiningTy, MirBorrowckCtxt};
1415
1516/// A name for a particular region used in emitting diagnostics. This name could be a generated
1617/// name like `'1`, a name used by the user like `'a`, or a name like `'static`.
17- #[ derive( Debug , Clone ) ]
18+ #[ derive( Debug , Clone , Copy ) ]
1819pub ( crate ) struct RegionName {
1920 /// The name of the region (interned).
2021 pub ( crate ) name : Symbol ,
@@ -25,7 +26,7 @@ pub(crate) struct RegionName {
2526/// Denotes the source of a region that is named by a `RegionName`. For example, a free region that
2627/// was named by the user would get `NamedLateParamRegion` and `'static` lifetime would get `Static`.
2728/// This helps to print the right kinds of diagnostics.
28- #[ derive( Debug , Clone ) ]
29+ #[ derive( Debug , Clone , Copy ) ]
2930pub ( crate ) enum RegionNameSource {
3031 /// A bound (not free) region that was instantiated at the def site (not an HRTB).
3132 NamedEarlyParamRegion ( Span ) ,
@@ -42,7 +43,7 @@ pub(crate) enum RegionNameSource {
4243 /// The region corresponding to the return type of a closure.
4344 AnonRegionFromOutput ( RegionNameHighlight , & ' static str ) ,
4445 /// The region from a type yielded by a coroutine.
45- AnonRegionFromYieldTy ( Span , String ) ,
46+ AnonRegionFromYieldTy ( Span , Symbol ) ,
4647 /// An anonymous region from an async fn.
4748 AnonRegionFromAsyncFn ( Span ) ,
4849 /// An anonymous region from an impl self type or trait
@@ -51,19 +52,19 @@ pub(crate) enum RegionNameSource {
5152
5253/// Describes what to highlight to explain to the user that we're giving an anonymous region a
5354/// synthesized name, and how to highlight it.
54- #[ derive( Debug , Clone ) ]
55+ #[ derive( Debug , Clone , Copy ) ]
5556pub ( crate ) enum RegionNameHighlight {
5657 /// The anonymous region corresponds to a reference that was found by traversing the type in the HIR.
5758 MatchedHirTy ( Span ) ,
5859 /// The anonymous region corresponds to a `'_` in the generics list of a struct/enum/union.
5960 MatchedAdtAndSegment ( Span ) ,
6061 /// The anonymous region corresponds to a region where the type annotation is completely missing
6162 /// from the code, e.g. in a closure arguments `|x| { ... }`, where `x` is a reference.
62- CannotMatchHirTy ( Span , String ) ,
63+ CannotMatchHirTy ( Span , Symbol ) ,
6364 /// The anonymous region corresponds to a region where the type annotation is completely missing
6465 /// from the code, and *even if* we print out the full name of the type, the region name won't
6566 /// be included. This currently occurs for opaque types like `impl Future`.
66- Occluded ( Span , String ) ,
67+ Occluded ( Span , Symbol ) ,
6768}
6869
6970impl RegionName {
@@ -247,25 +248,28 @@ impl<'tcx> MirBorrowckCtxt<'_, 'tcx> {
247248
248249 assert ! ( self . regioncx. universal_regions( ) . is_universal_region( fr) ) ;
249250
250- if let Some ( value) = self . region_names . try_borrow_mut ( ) . unwrap ( ) . get ( & fr) {
251- return Some ( value. clone ( ) ) ;
252- }
251+ match self . region_names . borrow_mut ( ) . entry ( fr) {
252+ IndexEntry :: Occupied ( precomputed_name) => Some ( * precomputed_name. get ( ) ) ,
253+ IndexEntry :: Vacant ( slot) => {
254+ let new_name = self
255+ . give_name_from_error_region ( fr)
256+ . or_else ( || self . give_name_if_anonymous_region_appears_in_arguments ( fr) )
257+ . or_else ( || self . give_name_if_anonymous_region_appears_in_upvars ( fr) )
258+ . or_else ( || self . give_name_if_anonymous_region_appears_in_output ( fr) )
259+ . or_else ( || self . give_name_if_anonymous_region_appears_in_yield_ty ( fr) )
260+ . or_else ( || self . give_name_if_anonymous_region_appears_in_impl_signature ( fr) )
261+ . or_else ( || {
262+ self . give_name_if_anonymous_region_appears_in_arg_position_impl_trait ( fr)
263+ } ) ;
264+
265+ if let Some ( new_name) = new_name {
266+ slot. insert ( new_name) ;
267+ }
268+ debug ! ( "give_region_a_name: gave name {:?}" , new_name) ;
253269
254- let value = self
255- . give_name_from_error_region ( fr)
256- . or_else ( || self . give_name_if_anonymous_region_appears_in_arguments ( fr) )
257- . or_else ( || self . give_name_if_anonymous_region_appears_in_upvars ( fr) )
258- . or_else ( || self . give_name_if_anonymous_region_appears_in_output ( fr) )
259- . or_else ( || self . give_name_if_anonymous_region_appears_in_yield_ty ( fr) )
260- . or_else ( || self . give_name_if_anonymous_region_appears_in_impl_signature ( fr) )
261- . or_else ( || self . give_name_if_anonymous_region_appears_in_arg_position_impl_trait ( fr) ) ;
262-
263- if let Some ( value) = & value {
264- self . region_names . try_borrow_mut ( ) . unwrap ( ) . insert ( fr, value. clone ( ) ) ;
270+ new_name
271+ }
265272 }
266-
267- debug ! ( "give_region_a_name: gave name {:?}" , value) ;
268- value
269273 }
270274
271275 /// Checks for the case where `fr` maps to something that the
@@ -457,9 +461,9 @@ impl<'tcx> MirBorrowckCtxt<'_, 'tcx> {
457461 ) ;
458462 if type_name. contains ( & format ! ( "'{counter}" ) ) {
459463 // Only add a label if we can confirm that a region was labelled.
460- RegionNameHighlight :: CannotMatchHirTy ( span, type_name)
464+ RegionNameHighlight :: CannotMatchHirTy ( span, Symbol :: intern ( & type_name) )
461465 } else {
462- RegionNameHighlight :: Occluded ( span, type_name)
466+ RegionNameHighlight :: Occluded ( span, Symbol :: intern ( & type_name) )
463467 }
464468 }
465469
@@ -888,7 +892,7 @@ impl<'tcx> MirBorrowckCtxt<'_, 'tcx> {
888892
889893 Some ( RegionName {
890894 name : self . synthesize_region_name ( ) ,
891- source : RegionNameSource :: AnonRegionFromYieldTy ( yield_span, type_name) ,
895+ source : RegionNameSource :: AnonRegionFromYieldTy ( yield_span, Symbol :: intern ( & type_name) ) ,
892896 } )
893897 }
894898
@@ -980,7 +984,7 @@ impl<'tcx> MirBorrowckCtxt<'_, 'tcx> {
980984 Some ( RegionName {
981985 name : region_name,
982986 source : RegionNameSource :: AnonRegionFromArgument (
983- RegionNameHighlight :: CannotMatchHirTy ( arg_span, arg_name?. to_string ( ) ) ,
987+ RegionNameHighlight :: CannotMatchHirTy ( arg_span, arg_name?) ,
984988 ) ,
985989 } )
986990 } else {
0 commit comments