@@ -34,36 +34,41 @@ where
3434#[ cfg_attr( not( feature = "panic_immediate_abort" ) ,  inline( never) ,  cold) ]  
3535#[ cfg_attr( feature = "panic_immediate_abort" ,  inline) ]  
3636#[ track_caller]  
37- const  fn  slice_start_index_len_fail ( index :  usize ,  len :  usize )  -> ! { 
38-     const_panic ! ( 
39-         "slice start index is out of range for slice" , 
40-         "range start index {index} out of range for slice of length {len}" , 
41-         index:  usize , 
42-         len:  usize , 
43-     ) 
44- } 
45- 
46- #[ cfg_attr( not( feature = "panic_immediate_abort" ) ,  inline( never) ,  cold) ]  
47- #[ cfg_attr( feature = "panic_immediate_abort" ,  inline) ]  
48- #[ track_caller]  
49- const  fn  slice_end_index_len_fail ( index :  usize ,  len :  usize )  -> ! { 
37+ const  fn  slice_index_fail ( start :  usize ,  end :  usize ,  len :  usize )  -> ! { 
38+     if  start > len { 
39+         const_panic ! ( 
40+             "slice start index is out of range for slice" , 
41+             "range start index {start} out of range for slice of length {len}" , 
42+             start:  usize , 
43+             len:  usize , 
44+         ) 
45+     } 
46+ 
47+     if  end > len { 
48+         const_panic ! ( 
49+             "slice end index is out of range for slice" , 
50+             "range end index {end} out of range for slice of length {len}" , 
51+             end:  usize , 
52+             len:  usize , 
53+         ) 
54+     } 
55+ 
56+     if  start > end { 
57+         const_panic ! ( 
58+             "slice index start is larger than end" , 
59+             "slice index starts at {start} but ends at {end}" , 
60+             start:  usize , 
61+             end:  usize , 
62+         ) 
63+     } 
64+ 
65+     // Only reachable if the range was a `RangeInclusive` or a 
66+     // `RangeToInclusive`, with `end == len`. 
5067    const_panic ! ( 
5168        "slice end index is out of range for slice" , 
52-         "range end index {index} out of range for slice of length {len}" , 
53-         index:  usize , 
54-         len:  usize , 
55-     ) 
56- } 
57- 
58- #[ cfg_attr( not( feature = "panic_immediate_abort" ) ,  inline( never) ,  cold) ]  
59- #[ cfg_attr( feature = "panic_immediate_abort" ,  inline) ]  
60- #[ track_caller]  
61- const  fn  slice_index_order_fail ( index :  usize ,  end :  usize )  -> ! { 
62-     const_panic ! ( 
63-         "slice index start is larger than end" , 
64-         "slice index starts at {index} but ends at {end}" , 
65-         index:  usize , 
69+         "range end index {end} out of range for slice of length {len}" , 
6670        end:  usize , 
71+         len:  usize , 
6772    ) 
6873} 
6974
@@ -327,7 +332,7 @@ unsafe impl<T> const SliceIndex<[T]> for ops::IndexRange {
327332            // SAFETY: `self` is checked to be valid and in bounds above. 
328333            unsafe  {  & * get_offset_len_noubcheck ( slice,  self . start ( ) ,  self . len ( ) )  } 
329334        }  else  { 
330-             slice_end_index_len_fail ( self . end ( ) ,  slice. len ( ) ) 
335+             slice_index_fail ( self . start ( ) ,   self . end ( ) ,  slice. len ( ) ) 
331336        } 
332337    } 
333338
@@ -337,7 +342,7 @@ unsafe impl<T> const SliceIndex<[T]> for ops::IndexRange {
337342            // SAFETY: `self` is checked to be valid and in bounds above. 
338343            unsafe  {  & mut  * get_offset_len_mut_noubcheck ( slice,  self . start ( ) ,  self . len ( ) )  } 
339344        }  else  { 
340-             slice_end_index_len_fail ( self . end ( ) ,  slice. len ( ) ) 
345+             slice_index_fail ( self . start ( ) ,   self . end ( ) ,  slice. len ( ) ) 
341346        } 
342347    } 
343348} 
@@ -422,26 +427,27 @@ unsafe impl<T> const SliceIndex<[T]> for ops::Range<usize> {
422427    #[ inline( always) ]  
423428    fn  index ( self ,  slice :  & [ T ] )  -> & [ T ]  { 
424429        // Using checked_sub is a safe way to get `SubUnchecked` in MIR 
425-         let  Some ( new_len)  = usize:: checked_sub ( self . end ,  self . start )  else  { 
426-             slice_index_order_fail ( self . start ,  self . end ) 
427-         } ; 
428-         if  self . end  > slice. len ( )  { 
429-             slice_end_index_len_fail ( self . end ,  slice. len ( ) ) ; 
430+         if  let  Some ( new_len)  = usize:: checked_sub ( self . end ,  self . start ) 
431+             && self . end  <= slice. len ( ) 
432+         { 
433+             // SAFETY: `self` is checked to be valid and in bounds above. 
434+             unsafe  {  & * get_offset_len_noubcheck ( slice,  self . start ,  new_len)  } 
435+         }  else  { 
436+             slice_index_fail ( self . start ,  self . end ,  slice. len ( ) ) 
430437        } 
431-         // SAFETY: `self` is checked to be valid and in bounds above. 
432-         unsafe  {  & * get_offset_len_noubcheck ( slice,  self . start ,  new_len)  } 
433438    } 
434439
435440    #[ inline]  
436441    fn  index_mut ( self ,  slice :  & mut  [ T ] )  -> & mut  [ T ]  { 
437-         let  Some ( new_len)  = usize:: checked_sub ( self . end ,  self . start )  else  { 
438-             slice_index_order_fail ( self . start ,  self . end ) 
439-         } ; 
440-         if  self . end  > slice. len ( )  { 
441-             slice_end_index_len_fail ( self . end ,  slice. len ( ) ) ; 
442+         // Using checked_sub is a safe way to get `SubUnchecked` in MIR 
443+         if  let  Some ( new_len)  = usize:: checked_sub ( self . end ,  self . start ) 
444+             && self . end  <= slice. len ( ) 
445+         { 
446+             // SAFETY: `self` is checked to be valid and in bounds above. 
447+             unsafe  {  & mut  * get_offset_len_mut_noubcheck ( slice,  self . start ,  new_len)  } 
448+         }  else  { 
449+             slice_index_fail ( self . start ,  self . end ,  slice. len ( ) ) 
442450        } 
443-         // SAFETY: `self` is checked to be valid and in bounds above. 
444-         unsafe  {  & mut  * get_offset_len_mut_noubcheck ( slice,  self . start ,  new_len)  } 
445451    } 
446452} 
447453
@@ -553,7 +559,7 @@ unsafe impl<T> const SliceIndex<[T]> for ops::RangeFrom<usize> {
553559    #[ inline]  
554560    fn  index ( self ,  slice :  & [ T ] )  -> & [ T ]  { 
555561        if  self . start  > slice. len ( )  { 
556-             slice_start_index_len_fail ( self . start ,  slice. len ( ) ) ; 
562+             slice_index_fail ( self . start ,  slice. len ( ) ,  slice . len ( ) ) 
557563        } 
558564        // SAFETY: `self` is checked to be valid and in bounds above. 
559565        unsafe  {  & * self . get_unchecked ( slice)  } 
@@ -562,7 +568,7 @@ unsafe impl<T> const SliceIndex<[T]> for ops::RangeFrom<usize> {
562568    #[ inline]  
563569    fn  index_mut ( self ,  slice :  & mut  [ T ] )  -> & mut  [ T ]  { 
564570        if  self . start  > slice. len ( )  { 
565-             slice_start_index_len_fail ( self . start ,  slice. len ( ) ) ; 
571+             slice_index_fail ( self . start ,  slice. len ( ) ,  slice . len ( ) ) 
566572        } 
567573        // SAFETY: `self` is checked to be valid and in bounds above. 
568574        unsafe  {  & mut  * self . get_unchecked_mut ( slice)  } 
@@ -678,15 +684,15 @@ unsafe impl<T> const SliceIndex<[T]> for ops::RangeInclusive<usize> {
678684    #[ inline]  
679685    fn  index ( self ,  slice :  & [ T ] )  -> & [ T ]  { 
680686        if  * self . end ( )  >= slice. len ( )  { 
681-             slice_end_index_len_fail ( * self . end ( ) ,  slice. len ( ) ) ; 
687+             slice_index_fail ( self . start ,   self . end ,  slice. len ( ) ) 
682688        } 
683689        self . into_slice_range ( ) . index ( slice) 
684690    } 
685691
686692    #[ inline]  
687693    fn  index_mut ( self ,  slice :  & mut  [ T ] )  -> & mut  [ T ]  { 
688694        if  * self . end ( )  >= slice. len ( )  { 
689-             slice_end_index_len_fail ( * self . end ( ) ,  slice. len ( ) ) ; 
695+             slice_index_fail ( self . start ,   self . end ,  slice. len ( ) ) 
690696        } 
691697        self . into_slice_range ( ) . index_mut ( slice) 
692698    } 
@@ -840,22 +846,22 @@ where
840846    let  len = bounds. end ; 
841847
842848    let  end = match  range. end_bound ( )  { 
843-         ops:: Bound :: Included ( & end)  if  end >= len => slice_end_index_len_fail ( end,  len) , 
849+         ops:: Bound :: Included ( & end)  if  end >= len => slice_index_fail ( 0 ,   end,  len) , 
844850        // Cannot overflow because `end < len` implies `end < usize::MAX`. 
845851        ops:: Bound :: Included ( & end)  => end + 1 , 
846852
847-         ops:: Bound :: Excluded ( & end)  if  end > len => slice_end_index_len_fail ( end,  len) , 
853+         ops:: Bound :: Excluded ( & end)  if  end > len => slice_index_fail ( 0 ,   end,  len) , 
848854        ops:: Bound :: Excluded ( & end)  => end, 
849855
850856        ops:: Bound :: Unbounded  => len, 
851857    } ; 
852858
853859    let  start = match  range. start_bound ( )  { 
854-         ops:: Bound :: Excluded ( & start)  if  start >= end => slice_index_order_fail ( start,  end) , 
860+         ops:: Bound :: Excluded ( & start)  if  start >= end => slice_index_fail ( start,  end,  len ) , 
855861        // Cannot overflow because `start < end` implies `start < usize::MAX`. 
856862        ops:: Bound :: Excluded ( & start)  => start + 1 , 
857863
858-         ops:: Bound :: Included ( & start)  if  start > end => slice_index_order_fail ( start,  end) , 
864+         ops:: Bound :: Included ( & start)  if  start > end => slice_index_fail ( start,  end,  len ) , 
859865        ops:: Bound :: Included ( & start)  => start, 
860866
861867        ops:: Bound :: Unbounded  => 0 , 
@@ -985,22 +991,22 @@ pub(crate) fn into_slice_range(
985991    ( start,  end) :  ( ops:: Bound < usize > ,  ops:: Bound < usize > ) , 
986992)  -> ops:: Range < usize >  { 
987993    let  end = match  end { 
988-         ops:: Bound :: Included ( end)  if  end >= len => slice_end_index_len_fail ( end,  len) , 
994+         ops:: Bound :: Included ( end)  if  end >= len => slice_index_fail ( 0 ,   end,  len) , 
989995        // Cannot overflow because `end < len` implies `end < usize::MAX`. 
990996        ops:: Bound :: Included ( end)  => end + 1 , 
991997
992-         ops:: Bound :: Excluded ( end)  if  end > len => slice_end_index_len_fail ( end,  len) , 
998+         ops:: Bound :: Excluded ( end)  if  end > len => slice_index_fail ( 0 ,   end,  len) , 
993999        ops:: Bound :: Excluded ( end)  => end, 
9941000
9951001        ops:: Bound :: Unbounded  => len, 
9961002    } ; 
9971003
9981004    let  start = match  start { 
999-         ops:: Bound :: Excluded ( start)  if  start >= end => slice_index_order_fail ( start,  end) , 
1005+         ops:: Bound :: Excluded ( start)  if  start >= end => slice_index_fail ( start,  end,  len ) , 
10001006        // Cannot overflow because `start < end` implies `start < usize::MAX`. 
10011007        ops:: Bound :: Excluded ( start)  => start + 1 , 
10021008
1003-         ops:: Bound :: Included ( start)  if  start > end => slice_index_order_fail ( start,  end) , 
1009+         ops:: Bound :: Included ( start)  if  start > end => slice_index_fail ( start,  end,  len ) , 
10041010        ops:: Bound :: Included ( start)  => start, 
10051011
10061012        ops:: Bound :: Unbounded  => 0 , 
0 commit comments