@@ -661,40 +661,46 @@ impl Place {
661661 self . projection . iter ( ) . fold ( Ok ( start_ty) , |place_ty, elem| {
662662 let ty = place_ty?;
663663 match elem {
664- ProjectionElem :: Deref => {
665- let deref_ty = ty
666- . kind ( )
667- . builtin_deref ( true )
668- . ok_or_else ( || error ! ( "Cannot dereference type: {ty:?}" ) ) ?;
669- Ok ( deref_ty. ty )
670- }
664+ ProjectionElem :: Deref => Self :: deref_ty ( ty) ,
671665 ProjectionElem :: Field ( _idx, fty) => Ok ( * fty) ,
672- ProjectionElem :: Index ( _) | ProjectionElem :: ConstantIndex { .. } => ty
673- . kind ( )
674- . builtin_index ( )
675- . ok_or_else ( || error ! ( "Cannot index non-array type: {ty:?}" ) ) ,
666+ ProjectionElem :: Index ( _) | ProjectionElem :: ConstantIndex { .. } => {
667+ Self :: index_ty ( ty)
668+ }
676669 ProjectionElem :: Subslice { from, to, from_end } => {
677- let ty_kind = ty. kind ( ) ;
678- match ty_kind {
679- TyKind :: RigidTy ( RigidTy :: Slice ( ..) ) => Ok ( ty) ,
680- TyKind :: RigidTy ( RigidTy :: Array ( inner, _) ) if !from_end => {
681- Ty :: try_new_array (
682- inner,
683- to. checked_sub ( * from)
684- . ok_or_else ( || error ! ( "Subslice overflow: {from}..{to}" ) ) ?,
685- )
686- }
687- TyKind :: RigidTy ( RigidTy :: Array ( inner, size) ) => {
688- let size = size. eval_target_usize ( ) ?;
689- let len = size - from - to;
690- Ty :: try_new_array ( inner, len)
691- }
692- _ => Err ( Error ( format ! ( "Cannot subslice non-array type: `{ty_kind:?}`" ) ) ) ,
693- }
670+ Self :: subslice_ty ( ty, from, to, from_end)
694671 }
695672 ProjectionElem :: Downcast ( _) => Ok ( ty) ,
696673 ProjectionElem :: OpaqueCast ( ty) | ProjectionElem :: Subtype ( ty) => Ok ( * ty) ,
697674 }
698675 } )
699676 }
677+
678+ fn index_ty ( ty : Ty ) -> Result < Ty , Error > {
679+ ty. kind ( ) . builtin_index ( ) . ok_or_else ( || error ! ( "Cannot index non-array type: {ty:?}" ) )
680+ }
681+
682+ fn subslice_ty ( ty : Ty , from : & u64 , to : & u64 , from_end : & bool ) -> Result < Ty , Error > {
683+ let ty_kind = ty. kind ( ) ;
684+ match ty_kind {
685+ TyKind :: RigidTy ( RigidTy :: Slice ( ..) ) => Ok ( ty) ,
686+ TyKind :: RigidTy ( RigidTy :: Array ( inner, _) ) if !from_end => Ty :: try_new_array (
687+ inner,
688+ to. checked_sub ( * from) . ok_or_else ( || error ! ( "Subslice overflow: {from}..{to}" ) ) ?,
689+ ) ,
690+ TyKind :: RigidTy ( RigidTy :: Array ( inner, size) ) => {
691+ let size = size. eval_target_usize ( ) ?;
692+ let len = size - from - to;
693+ Ty :: try_new_array ( inner, len)
694+ }
695+ _ => Err ( Error ( format ! ( "Cannot subslice non-array type: `{ty_kind:?}`" ) ) ) ,
696+ }
697+ }
698+
699+ fn deref_ty ( ty : Ty ) -> Result < Ty , Error > {
700+ let deref_ty = ty
701+ . kind ( )
702+ . builtin_deref ( true )
703+ . ok_or_else ( || error ! ( "Cannot dereference type: {ty:?}" ) ) ?;
704+ Ok ( deref_ty. ty )
705+ }
700706}
0 commit comments