@@ -1740,20 +1740,18 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> {
17401740
17411741 self . check_if_full_path_is_moved ( location, desired_action, place_span, flow_state) ;
17421742
1743- if let [ base_proj @ .. , ProjectionElem :: Subslice { from, to, from_end : false } ] =
1744- place_span. 0 . projection
1743+ if let Some ( ( place_base , ProjectionElem :: Subslice { from, to, from_end : false } ) ) =
1744+ place_span. 0 . last_projection ( )
17451745 {
1746- let place_ty =
1747- Place :: ty_from ( place_span. 0 . local , base_proj, self . body ( ) , self . infcx . tcx ) ;
1746+ let place_ty = PlaceRef :: ty ( & place_base, self . body ( ) , self . infcx . tcx ) ;
17481747 if let ty:: Array ( ..) = place_ty. ty . kind ( ) {
1749- let array_place = PlaceRef { local : place_span. 0 . local , projection : base_proj } ;
17501748 self . check_if_subslice_element_is_moved (
17511749 location,
17521750 desired_action,
1753- ( array_place , place_span. 1 ) ,
1751+ ( place_base , place_span. 1 ) ,
17541752 maybe_uninits,
1755- * from,
1756- * to,
1753+ from,
1754+ to,
17571755 ) ;
17581756 return ;
17591757 }
@@ -1825,10 +1823,7 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> {
18251823 debug ! ( "check_if_assigned_path_is_moved place: {:?}" , place) ;
18261824
18271825 // None case => assigning to `x` does not require `x` be initialized.
1828- let mut cursor = & * place. projection . as_ref ( ) ;
1829- while let [ proj_base @ .., elem] = cursor {
1830- cursor = proj_base;
1831-
1826+ for ( place_base, elem) in place. iter_projections ( ) . rev ( ) {
18321827 match elem {
18331828 ProjectionElem :: Index ( _/*operand*/ ) |
18341829 ProjectionElem :: ConstantIndex { .. } |
@@ -1843,10 +1838,7 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> {
18431838 ProjectionElem :: Deref => {
18441839 self . check_if_full_path_is_moved (
18451840 location, InitializationRequiringAction :: Use ,
1846- ( PlaceRef {
1847- local : place. local ,
1848- projection : proj_base,
1849- } , span) , flow_state) ;
1841+ ( place_base, span) , flow_state) ;
18501842 // (base initialized; no need to
18511843 // recur further)
18521844 break ;
@@ -1862,15 +1854,12 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> {
18621854 // assigning to `P.f` requires `P` itself
18631855 // be already initialized
18641856 let tcx = self . infcx . tcx ;
1865- let base_ty = Place :: ty_from ( place . local , proj_base , self . body ( ) , tcx) . ty ;
1857+ let base_ty = PlaceRef :: ty ( & place_base , self . body ( ) , tcx) . ty ;
18661858 match base_ty. kind ( ) {
18671859 ty:: Adt ( def, _) if def. has_dtor ( tcx) => {
18681860 self . check_if_path_or_subpath_is_moved (
18691861 location, InitializationRequiringAction :: Assignment ,
1870- ( PlaceRef {
1871- local : place. local ,
1872- projection : proj_base,
1873- } , span) , flow_state) ;
1862+ ( place_base, span) , flow_state) ;
18741863
18751864 // (base initialized; no need to
18761865 // recur further)
@@ -1880,10 +1869,7 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> {
18801869 // Once `let s; s.x = V; read(s.x);`,
18811870 // is allowed, remove this match arm.
18821871 ty:: Adt ( ..) | ty:: Tuple ( ..) => {
1883- check_parent_of_field ( self , location, PlaceRef {
1884- local : place. local ,
1885- projection : proj_base,
1886- } , span, flow_state) ;
1872+ check_parent_of_field ( self , location, place_base, span, flow_state) ;
18871873
18881874 // rust-lang/rust#21232, #54499, #54986: during period where we reject
18891875 // partial initialization, do not complain about unnecessary `mut` on
@@ -1965,9 +1951,7 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> {
19651951 // no move out from an earlier location) then this is an attempt at initialization
19661952 // of the union - we should error in that case.
19671953 let tcx = this. infcx . tcx ;
1968- if let ty:: Adt ( def, _) =
1969- Place :: ty_from ( base. local , base. projection , this. body ( ) , tcx) . ty . kind ( )
1970- {
1954+ if let ty:: Adt ( def, _) = PlaceRef :: ty ( & base, this. body ( ) , tcx) . ty . kind ( ) {
19711955 if def. is_union ( ) {
19721956 if this. move_data . path_map [ mpi] . iter ( ) . any ( |moi| {
19731957 this. move_data . moves [ * moi] . source . is_predecessor_of ( location, this. body )
@@ -2162,9 +2146,9 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> {
21622146 place : PlaceRef < ' tcx > ,
21632147 is_local_mutation_allowed : LocalMutationIsAllowed ,
21642148 ) -> Result < RootPlace < ' tcx > , PlaceRef < ' tcx > > {
2165- match place {
2166- PlaceRef { local , projection : [ ] } => {
2167- let local = & self . body . local_decls [ local] ;
2149+ match place. last_projection ( ) {
2150+ None => {
2151+ let local = & self . body . local_decls [ place . local ] ;
21682152 match local. mutability {
21692153 Mutability :: Not => match is_local_mutation_allowed {
21702154 LocalMutationIsAllowed :: Yes => Ok ( RootPlace {
@@ -2186,11 +2170,10 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> {
21862170 } ) ,
21872171 }
21882172 }
2189- PlaceRef { local : _ , projection : [ proj_base @ .. , elem] } => {
2173+ Some ( ( place_base , elem) ) => {
21902174 match elem {
21912175 ProjectionElem :: Deref => {
2192- let base_ty =
2193- Place :: ty_from ( place. local , proj_base, self . body ( ) , self . infcx . tcx ) . ty ;
2176+ let base_ty = PlaceRef :: ty ( & place_base, self . body ( ) , self . infcx . tcx ) . ty ;
21942177
21952178 // Check the kind of deref to decide
21962179 match base_ty. kind ( ) {
@@ -2208,10 +2191,7 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> {
22082191 _ => LocalMutationIsAllowed :: Yes ,
22092192 } ;
22102193
2211- self . is_mutable (
2212- PlaceRef { local : place. local , projection : proj_base } ,
2213- mode,
2214- )
2194+ self . is_mutable ( place_base, mode)
22152195 }
22162196 }
22172197 }
@@ -2229,10 +2209,9 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> {
22292209 }
22302210 }
22312211 // `Box<T>` owns its content, so mutable if its location is mutable
2232- _ if base_ty. is_box ( ) => self . is_mutable (
2233- PlaceRef { local : place. local , projection : proj_base } ,
2234- is_local_mutation_allowed,
2235- ) ,
2212+ _ if base_ty. is_box ( ) => {
2213+ self . is_mutable ( place_base, is_local_mutation_allowed)
2214+ }
22362215 // Deref should only be for reference, pointers or boxes
22372216 _ => bug ! ( "Deref of unexpected type: {:?}" , base_ty) ,
22382217 }
@@ -2286,10 +2265,8 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> {
22862265 // });
22872266 // }
22882267 // ```
2289- let _ = self . is_mutable (
2290- PlaceRef { local : place. local , projection : proj_base } ,
2291- is_local_mutation_allowed,
2292- ) ?;
2268+ let _ =
2269+ self . is_mutable ( place_base, is_local_mutation_allowed) ?;
22932270 Ok ( RootPlace {
22942271 place_local : place. local ,
22952272 place_projection : place. projection ,
@@ -2298,10 +2275,7 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> {
22982275 }
22992276 }
23002277 } else {
2301- self . is_mutable (
2302- PlaceRef { local : place. local , projection : proj_base } ,
2303- is_local_mutation_allowed,
2304- )
2278+ self . is_mutable ( place_base, is_local_mutation_allowed)
23052279 }
23062280 }
23072281 }
0 commit comments