@@ -1621,54 +1621,38 @@ impl<T> OwnedVector<T> for ~[T] {
16211621 }
16221622
16231623 fn shift_opt ( & mut self ) -> Option < T > {
1624- unsafe {
1625- let ln = match self . len ( ) {
1626- 0 => return None ,
1627- 1 => return self . pop_opt ( ) ,
1628- 2 => {
1629- let last = self . pop ( ) ;
1630- let first = self . pop_opt ( ) ;
1631- self . push ( last) ;
1632- return first;
1633- }
1634- x => x
1635- } ;
1636-
1637- let next_ln = self . len ( ) - 1 ;
1638-
1639- // Save the last element. We're going to overwrite its position
1640- let work_elt = self . pop ( ) ;
1641- // We still should have room to work where what last element was
1642- assert ! ( self . capacity( ) >= ln) ;
1643- // Pretend like we have the original length so we can use
1644- // the vector copy_memory to overwrite the hole we just made
1645- self . set_len ( ln) ;
1646-
1647- // Memcopy the head element (the one we want) to the location we just
1648- // popped. For the moment it unsafely exists at both the head and last
1649- // positions
1650- {
1651- let first_slice = self . slice ( 0 , 1 ) ;
1652- let last_slice = self . slice ( next_ln, ln) ;
1653- raw:: copy_memory ( cast:: transmute ( last_slice) , first_slice) ;
1624+ match self . len ( ) {
1625+ 0 => None ,
1626+ 1 => self . pop_opt ( ) ,
1627+ 2 => {
1628+ let last = self . pop ( ) ;
1629+ let first = self . pop_opt ( ) ;
1630+ self . push ( last) ;
1631+ first
16541632 }
1633+ len => {
1634+ unsafe {
1635+ let next_len = len - 1 ;
16551636
1656- // Memcopy everything to the left one element
1657- {
1658- let init_slice = self . slice ( 0 , next_ln) ;
1659- let tail_slice = self . slice ( 1 , ln) ;
1660- raw:: copy_memory ( cast:: transmute ( init_slice) ,
1661- tail_slice) ;
1662- }
1637+ let ptr = self . as_ptr ( ) ;
1638+
1639+ // copy out the head element, for the moment it exists
1640+ // unsafely on the stack and as the first element of the
1641+ // vector.
1642+ let head = ptr:: read_ptr ( ptr) ;
16631643
1664- // Set the new length. Now the vector is back to normal
1665- self . set_len ( next_ln) ;
1644+ // Memcpy everything to the left one element (leaving the
1645+ // last element unsafely in two consecutive memory
1646+ // locations)
1647+ ptr:: copy_memory ( self . as_mut_ptr ( ) , ptr. offset ( 1 ) , next_len) ;
16661648
1667- // Swap out the element we want from the end
1668- let vp = self . as_mut_ptr ( ) ;
1669- let vp = ptr :: mut_offset ( vp , ( next_ln - 1 ) as int ) ;
1649+ // set the new length, which means the second instance of
1650+ // the last element is forgotten.
1651+ self . set_len ( next_len ) ;
16701652
1671- Some ( ptr:: replace_ptr ( vp, work_elt) )
1653+ Some ( head)
1654+ }
1655+ }
16721656 }
16731657 }
16741658
0 commit comments