@@ -1625,54 +1625,38 @@ impl<T> OwnedVector<T> for ~[T] {
1625
1625
}
1626
1626
1627
1627
fn shift_opt ( & mut self ) -> Option < T > {
1628
- unsafe {
1629
- let ln = match self . len ( ) {
1630
- 0 => return None ,
1631
- 1 => return self . pop_opt ( ) ,
1632
- 2 => {
1633
- let last = self . pop ( ) ;
1634
- let first = self . pop_opt ( ) ;
1635
- self . push ( last) ;
1636
- return first;
1637
- }
1638
- x => x
1639
- } ;
1640
-
1641
- let next_ln = self . len ( ) - 1 ;
1642
-
1643
- // Save the last element. We're going to overwrite its position
1644
- let work_elt = self . pop ( ) ;
1645
- // We still should have room to work where what last element was
1646
- assert ! ( self . capacity( ) >= ln) ;
1647
- // Pretend like we have the original length so we can use
1648
- // the vector copy_memory to overwrite the hole we just made
1649
- self . set_len ( ln) ;
1650
-
1651
- // Memcopy the head element (the one we want) to the location we just
1652
- // popped. For the moment it unsafely exists at both the head and last
1653
- // positions
1654
- {
1655
- let first_slice = self . slice ( 0 , 1 ) ;
1656
- let last_slice = self . slice ( next_ln, ln) ;
1657
- raw:: copy_memory ( cast:: transmute ( last_slice) , first_slice) ;
1628
+ match self . len ( ) {
1629
+ 0 => None ,
1630
+ 1 => self . pop_opt ( ) ,
1631
+ 2 => {
1632
+ let last = self . pop ( ) ;
1633
+ let first = self . pop_opt ( ) ;
1634
+ self . push ( last) ;
1635
+ first
1658
1636
}
1637
+ len => {
1638
+ unsafe {
1639
+ let next_len = len - 1 ;
1659
1640
1660
- // Memcopy everything to the left one element
1661
- {
1662
- let init_slice = self . slice ( 0 , next_ln) ;
1663
- let tail_slice = self . slice ( 1 , ln) ;
1664
- raw:: copy_memory ( cast:: transmute ( init_slice) ,
1665
- tail_slice) ;
1666
- }
1641
+ let ptr = self . as_ptr ( ) ;
1642
+
1643
+ // copy out the head element, for the moment it exists
1644
+ // unsafely on the stack and as the first element of the
1645
+ // vector.
1646
+ let head = ptr:: read_ptr ( ptr) ;
1667
1647
1668
- // Set the new length. Now the vector is back to normal
1669
- self . set_len ( next_ln) ;
1648
+ // Memcpy everything to the left one element (leaving the
1649
+ // last element unsafely in two consecutive memory
1650
+ // locations)
1651
+ ptr:: copy_memory ( self . as_mut_ptr ( ) , ptr. offset ( 1 ) , next_len) ;
1670
1652
1671
- // Swap out the element we want from the end
1672
- let vp = self . as_mut_ptr ( ) ;
1673
- let vp = ptr :: mut_offset ( vp , ( next_ln - 1 ) as int ) ;
1653
+ // set the new length, which means the second instance of
1654
+ // the last element is forgotten.
1655
+ self . set_len ( next_len ) ;
1674
1656
1675
- Some ( ptr:: replace_ptr ( vp, work_elt) )
1657
+ Some ( head)
1658
+ }
1659
+ }
1676
1660
}
1677
1661
}
1678
1662
@@ -2073,6 +2057,19 @@ pub trait MutableVector<'a, T> {
2073
2057
/// Unsafely sets the element in index to the value
2074
2058
unsafe fn unsafe_set ( self , index : uint , val : T ) ;
2075
2059
2060
+ /**
2061
+ * Unchecked vector index assignment. Does not drop the
2062
+ * old value and hence is only suitable when the vector
2063
+ * is newly allocated.
2064
+ */
2065
+ unsafe fn init_elem ( self , i : uint , val : T ) ;
2066
+
2067
+ /// Copies data from `src` to `self`.
2068
+ ///
2069
+ /// `self` and `src` must not overlap. Fails if `self` is
2070
+ /// shorter than `src`.
2071
+ unsafe fn copy_memory ( self , src : & [ T ] ) ;
2072
+
2076
2073
/// Similar to `as_imm_buf` but passing a `*mut T`
2077
2074
fn as_mut_buf < U > ( self , f : |* mut T , uint| -> U ) -> U ;
2078
2075
}
@@ -2201,6 +2198,21 @@ impl<'a,T> MutableVector<'a, T> for &'a mut [T] {
2201
2198
* self . unsafe_mut_ref ( index) = val;
2202
2199
}
2203
2200
2201
+ #[ inline]
2202
+ unsafe fn init_elem ( self , i : uint , val : T ) {
2203
+ intrinsics:: move_val_init ( & mut ( * self . as_mut_ptr ( ) . offset ( i as int ) ) , val) ;
2204
+ }
2205
+
2206
+ #[ inline]
2207
+ unsafe fn copy_memory ( self , src : & [ T ] ) {
2208
+ self . as_mut_buf ( |p_dst, len_dst| {
2209
+ src. as_imm_buf ( |p_src, len_src| {
2210
+ assert ! ( len_dst >= len_src)
2211
+ ptr:: copy_nonoverlapping_memory ( p_dst, p_src, len_src)
2212
+ } )
2213
+ } )
2214
+ }
2215
+
2204
2216
#[ inline]
2205
2217
fn as_mut_buf < U > ( self , f : |* mut T , uint| -> U ) -> U {
2206
2218
let Slice { data, len } = self . repr ( ) ;
@@ -2241,10 +2253,8 @@ pub unsafe fn from_buf<T>(ptr: *T, elts: uint) -> ~[T] {
2241
2253
/// Unsafe operations
2242
2254
pub mod raw {
2243
2255
use cast;
2244
- use option:: Some ;
2245
2256
use ptr;
2246
- use unstable:: intrinsics;
2247
- use vec:: { with_capacity, ImmutableVector , MutableVector } ;
2257
+ use vec:: { with_capacity, MutableVector } ;
2248
2258
use unstable:: raw:: Slice ;
2249
2259
2250
2260
/**
@@ -2277,20 +2287,6 @@ pub mod raw {
2277
2287
} ) )
2278
2288
}
2279
2289
2280
- /**
2281
- * Unchecked vector index assignment. Does not drop the
2282
- * old value and hence is only suitable when the vector
2283
- * is newly allocated.
2284
- */
2285
- #[ inline]
2286
- pub unsafe fn init_elem < T > ( v : & mut [ T ] , i : uint , val : T ) {
2287
- let mut alloc = Some ( val) ;
2288
- v. as_mut_buf ( |p, _len| {
2289
- intrinsics:: move_val_init ( & mut ( * ptr:: mut_offset ( p, i as int ) ) ,
2290
- alloc. take_unwrap ( ) ) ;
2291
- } )
2292
- }
2293
-
2294
2290
/**
2295
2291
* Constructs a vector from an unsafe pointer to a buffer
2296
2292
*
@@ -2308,21 +2304,6 @@ pub mod raw {
2308
2304
dst
2309
2305
}
2310
2306
2311
- /**
2312
- * Copies data from one vector to another.
2313
- *
2314
- * Copies `src` to `dst`. The source and destination may overlap.
2315
- */
2316
- #[ inline]
2317
- pub unsafe fn copy_memory < T > ( dst : & mut [ T ] , src : & [ T ] ) {
2318
- dst. as_mut_buf ( |p_dst, len_dst| {
2319
- src. as_imm_buf ( |p_src, len_src| {
2320
- assert ! ( len_dst >= len_src)
2321
- ptr:: copy_memory ( p_dst, p_src, len_src)
2322
- } )
2323
- } )
2324
- }
2325
-
2326
2307
/**
2327
2308
* Returns a pointer to first element in slice and adjusts
2328
2309
* slice so it no longer contains that element. Fails if
@@ -2351,7 +2332,7 @@ pub mod raw {
2351
2332
2352
2333
/// Operations on `[u8]`.
2353
2334
pub mod bytes {
2354
- use vec:: raw ;
2335
+ use vec:: MutableVector ;
2355
2336
use ptr;
2356
2337
2357
2338
/// A trait for operations on mutable `[u8]`s.
@@ -2369,17 +2350,14 @@ pub mod bytes {
2369
2350
}
2370
2351
}
2371
2352
2372
- /**
2373
- * Copies data from one vector to another.
2374
- *
2375
- * Copies `src` to `dst`. The source and destination may
2376
- * overlap. Fails if the length of `dst` is less than the length
2377
- * of `src`.
2378
- */
2353
+ /// Copies data from `src` to `dst`
2354
+ ///
2355
+ /// `src` and `dst` must not overlap. Fails if the length of `dst`
2356
+ /// is less than the length of `src`.
2379
2357
#[ inline]
2380
2358
pub fn copy_memory ( dst : & mut [ u8 ] , src : & [ u8 ] ) {
2381
- // Bound checks are done at vec::raw:: copy_memory.
2382
- unsafe { raw :: copy_memory ( dst , src) }
2359
+ // Bound checks are done at . copy_memory.
2360
+ unsafe { dst . copy_memory ( src) }
2383
2361
}
2384
2362
2385
2363
/**
@@ -3601,7 +3579,7 @@ mod tests {
3601
3579
unsafe {
3602
3580
let mut a = [ 1 , 2 , 3 , 4 ] ;
3603
3581
let b = [ 1 , 2 , 3 , 4 , 5 ] ;
3604
- raw :: copy_memory ( a , b) ;
3582
+ a . copy_memory ( b) ;
3605
3583
}
3606
3584
}
3607
3585
0 commit comments