about summary refs log tree commit diff
path: root/src/libcore
diff options
context:
space:
mode:
authorNiko Matsakis <niko@alum.mit.edu>2012-09-26 17:33:34 -0700
committerNiko Matsakis <niko@alum.mit.edu>2012-09-26 18:02:07 -0700
commit67a8e7128aea292445b763b47b04bc5f4fd43cb2 (patch)
tree9ddde322dbc8fd5af39e903419cae508d9df05f6 /src/libcore
parentcd79e1d1b20a2c289dd15bc2766f97c789d975aa (diff)
downloadrust-67a8e7128aea292445b763b47b04bc5f4fd43cb2.tar.gz
rust-67a8e7128aea292445b763b47b04bc5f4fd43cb2.zip
Demode vec::push (and convert to method)
Diffstat (limited to 'src/libcore')
-rw-r--r--src/libcore/core.rs2
-rw-r--r--src/libcore/dvec.rs8
-rw-r--r--src/libcore/either.rs28
-rw-r--r--src/libcore/extfmt.rs4
-rw-r--r--src/libcore/flate.rs4
-rw-r--r--src/libcore/float.rs2
-rw-r--r--src/libcore/io.rs18
-rw-r--r--src/libcore/os.rs2
-rw-r--r--src/libcore/path.rs10
-rw-r--r--src/libcore/pipes.rs2
-rw-r--r--src/libcore/private.rs2
-rw-r--r--src/libcore/rand.rs2
-rw-r--r--src/libcore/result.rs4
-rw-r--r--src/libcore/run.rs12
-rw-r--r--src/libcore/send_map.rs15
-rw-r--r--src/libcore/str.rs23
-rw-r--r--src/libcore/vec.rs189
17 files changed, 178 insertions, 149 deletions
diff --git a/src/libcore/core.rs b/src/libcore/core.rs
index 8806131c9fb..dae77d66f25 100644
--- a/src/libcore/core.rs
+++ b/src/libcore/core.rs
@@ -17,6 +17,7 @@ use tuple::{TupleOps, ExtendedTupleOps};
 use str::{StrSlice, UniqueStr};
 use vec::{ConstVector, CopyableVector, ImmutableVector};
 use vec::{ImmutableEqVector, ImmutableCopyableVector};
+use vec::{MutableVector, MutableCopyableVector};
 use iter::{BaseIter, ExtendedIter, EqIter, CopyableIter};
 use iter::{CopyableOrderedIter, Times, TimesIx};
 use num::Num;
@@ -33,6 +34,7 @@ export Num, Times, TimesIx;
 export StrSlice, UniqueStr;
 export ConstVector, CopyableVector, ImmutableVector;
 export ImmutableEqVector, ImmutableCopyableVector, IterTraitExtensions;
+export MutableVector, MutableCopyableVector;
 export BaseIter, CopyableIter, CopyableOrderedIter, ExtendedIter, EqIter;
 export TupleOps, ExtendedTupleOps;
 export Ptr;
diff --git a/src/libcore/dvec.rs b/src/libcore/dvec.rs
index 9d3d2e97f9a..eb221926fc1 100644
--- a/src/libcore/dvec.rs
+++ b/src/libcore/dvec.rs
@@ -172,7 +172,7 @@ impl<A> DVec<A> {
             if data_ptr.is_null() { fail ~"Recursive use of dvec"; }
             log(error, ~"a");
             self.data <- ~[move t];
-            vec::push_all_move(self.data, move data);
+            self.data.push_all_move(move data);
             log(error, ~"b");
         }
     }
@@ -180,7 +180,7 @@ impl<A> DVec<A> {
     /// Append a single item to the end of the list
     fn push(+t: A) {
         self.check_not_borrowed();
-        vec::push(self.data, move t);
+        self.data.push(move t);
     }
 
     /// Remove and return the first element
@@ -240,7 +240,7 @@ impl<A: Copy> DVec<A> {
             vec::reserve(&mut v, new_len);
             let mut i = from_idx;
             while i < to_idx {
-                vec::push(v, ts[i]);
+                v.push(ts[i]);
                 i += 1u;
             }
             move v
@@ -266,7 +266,7 @@ impl<A: Copy> DVec<A> {
             }
            };
 
-        for ts.each |t| { vec::push(v, *t) };
+        for ts.each |t| { v.push(*t) };
            v
         }
     }
diff --git a/src/libcore/either.rs b/src/libcore/either.rs
index 55e22f7cfe9..d93074e4a40 100644
--- a/src/libcore/either.rs
+++ b/src/libcore/either.rs
@@ -32,27 +32,27 @@ fn either<T, U, V>(f_left: fn((&T)) -> V,
 fn lefts<T: Copy, U>(eithers: &[Either<T, U>]) -> ~[T] {
     //! Extracts from a vector of either all the left values
 
-    let mut result: ~[T] = ~[];
-    for vec::each(eithers) |elt| {
-        match *elt {
-          Left(l) => vec::push(result, l),
-          _ => { /* fallthrough */ }
+    do vec::build_sized(eithers.len()) |push| {
+        for vec::each(eithers) |elt| {
+            match *elt {
+                Left(ref l) => { push(*l); }
+                _ => { /* fallthrough */ }
+            }
         }
     }
-    move result
 }
 
 fn rights<T, U: Copy>(eithers: &[Either<T, U>]) -> ~[U] {
     //! Extracts from a vector of either all the right values
 
-    let mut result: ~[U] = ~[];
-    for vec::each(eithers) |elt| {
-        match *elt {
-          Right(r) => vec::push(result, r),
-          _ => { /* fallthrough */ }
+    do vec::build_sized(eithers.len()) |push| {
+        for vec::each(eithers) |elt| {
+            match *elt {
+                Right(ref r) => { push(*r); }
+                _ => { /* fallthrough */ }
+            }
         }
     }
-    move result
 }
 
 fn partition<T: Copy, U: Copy>(eithers: &[Either<T, U>])
@@ -68,8 +68,8 @@ fn partition<T: Copy, U: Copy>(eithers: &[Either<T, U>])
     let mut rights: ~[U] = ~[];
     for vec::each(eithers) |elt| {
         match *elt {
-          Left(l) => vec::push(lefts, l),
-          Right(r) => vec::push(rights, r)
+          Left(l) => lefts.push(l),
+          Right(r) => rights.push(r)
         }
     }
     return {lefts: move lefts, rights: move rights};
diff --git a/src/libcore/extfmt.rs b/src/libcore/extfmt.rs
index 9a992143a11..fda3f50ca29 100644
--- a/src/libcore/extfmt.rs
+++ b/src/libcore/extfmt.rs
@@ -90,7 +90,7 @@ mod ct {
         fn flush_buf(+buf: ~str, &pieces: ~[Piece]) -> ~str {
             if str::len(buf) > 0 {
                 let piece = PieceString(move buf);
-                vec::push(pieces, move piece);
+                pieces.push(move piece);
             }
             return ~"";
         }
@@ -110,7 +110,7 @@ mod ct {
                 } else {
                     buf = flush_buf(move buf, pieces);
                     let rs = parse_conversion(s, i, lim, error);
-                    vec::push(pieces, copy rs.piece);
+                    pieces.push(copy rs.piece);
                     i = rs.next;
                 }
             } else { buf += curr; i += size; }
diff --git a/src/libcore/flate.rs b/src/libcore/flate.rs
index b75894e0c1b..6b4c93949e5 100644
--- a/src/libcore/flate.rs
+++ b/src/libcore/flate.rs
@@ -71,12 +71,12 @@ fn test_flate_round_trip() {
     let r = rand::Rng();
     let mut words = ~[];
     for 20.times {
-        vec::push(words, r.gen_bytes(r.gen_uint_range(1, 10)));
+        words.push(r.gen_bytes(r.gen_uint_range(1, 10)));
     }
     for 20.times {
         let mut in = ~[];
         for 2000.times {
-            vec::push_all(in, r.choose(words));
+            in.push_all(r.choose(words));
         }
         debug!("de/inflate of %u bytes of random word-sequences",
                in.len());
diff --git a/src/libcore/float.rs b/src/libcore/float.rs
index eaa51814056..cf8a10b9c7b 100644
--- a/src/libcore/float.rs
+++ b/src/libcore/float.rs
@@ -143,7 +143,7 @@ fn to_str_common(num: float, digits: uint, exact: bool) -> ~str {
         // store the next digit
         frac *= 10.0;
         let digit = frac as uint;
-        vec::push(fractionalParts, digit);
+        fractionalParts.push(digit);
 
         // calculate the next frac
         frac -= digit as float;
diff --git a/src/libcore/io.rs b/src/libcore/io.rs
index 97039800fb6..385df30e824 100644
--- a/src/libcore/io.rs
+++ b/src/libcore/io.rs
@@ -76,7 +76,7 @@ impl<T: Reader> T : ReaderUtil {
         loop {
             let ch = self.read_byte();
             if ch == -1 || ch == 10 { break; }
-            vec::push(buf, ch as u8);
+            buf.push(ch as u8);
         }
         str::from_bytes(buf)
     }
@@ -94,7 +94,7 @@ impl<T: Reader> T : ReaderUtil {
                 i += 1;
                 assert (w > 0);
                 if w == 1 {
-                    vec::push(*chars, b0 as char);
+                    chars.push(b0 as char);
                     loop;
                 }
                 // can't satisfy this char with the existing data
@@ -113,7 +113,7 @@ impl<T: Reader> T : ReaderUtil {
                 // See str::char_at
                 val += ((b0 << ((w + 1) as u8)) as uint)
                     << (w - 1) * 6 - w - 1u;
-                vec::push(*chars, val as char);
+                chars.push(val as char);
             }
             return (i, 0);
         }
@@ -128,7 +128,7 @@ impl<T: Reader> T : ReaderUtil {
                 // we're split in a unicode char?
                 break;
             }
-            vec::push_all(buf, data);
+            buf.push_all(data);
             let (offset, nbreq) = chars_from_bytes::<T>(&buf, &mut chars);
             let ncreq = n - chars.len();
             // again we either know we need a certain number of bytes
@@ -155,7 +155,7 @@ impl<T: Reader> T : ReaderUtil {
         let mut buf: ~[u8] = ~[];
         loop {
             let ch = self.read_byte();
-            if ch < 1 { break; } else { vec::push(buf, ch as u8); }
+            if ch < 1 { break; } else { buf.push(ch as u8); }
         }
         str::from_bytes(buf)
     }
@@ -190,7 +190,7 @@ impl<T: Reader> T : ReaderUtil {
 
     fn read_whole_stream() -> ~[u8] {
         let mut buf: ~[u8] = ~[];
-        while !self.eof() { vec::push_all(buf, self.read_bytes(2048u)); }
+        while !self.eof() { buf.push_all(self.read_bytes(2048u)); }
         move buf
     }
 
@@ -503,7 +503,7 @@ fn u64_to_le_bytes<T>(n: u64, size: uint, f: fn(v: &[u8]) -> T) -> T {
 
         let mut bytes: ~[u8] = ~[], i = size, n = n;
         while i > 0u {
-            vec::push(bytes, (n & 255_u64) as u8);
+            bytes.push((n & 255_u64) as u8);
             n >>= 8_u64;
             i -= 1u;
         }
@@ -535,7 +535,7 @@ fn u64_to_be_bytes<T>(n: u64, size: uint, f: fn(v: &[u8]) -> T) -> T {
         let mut i = size;
         while i > 0u {
             let shift = ((i - 1u) * 8u) as u64;
-            vec::push(bytes, (n >> shift) as u8);
+            bytes.push((n >> shift) as u8);
             i -= 1u;
         }
         f(bytes)
@@ -737,7 +737,7 @@ fn with_str_writer(f: fn(Writer)) -> ~str {
     let mut v = with_bytes_writer(f);
 
     // Make sure the vector has a trailing null and is proper utf8.
-    vec::push(v, 0);
+    v.push(0);
     assert str::is_utf8(v);
 
     unsafe { move ::cast::transmute(v) }
diff --git a/src/libcore/os.rs b/src/libcore/os.rs
index b4c284cbd82..0a2f00e3f2b 100644
--- a/src/libcore/os.rs
+++ b/src/libcore/os.rs
@@ -219,7 +219,7 @@ mod global_env {
             for vec::each(rustrt::rust_env_pairs()) |p| {
                 let vs = str::splitn_char(*p, '=', 1u);
                 assert vec::len(vs) == 2u;
-                vec::push(pairs, (copy vs[0], copy vs[1]));
+                pairs.push((copy vs[0], copy vs[1]));
             }
             move pairs
         }
diff --git a/src/libcore/path.rs b/src/libcore/path.rs
index ab847702d68..505ecff2bcf 100644
--- a/src/libcore/path.rs
+++ b/src/libcore/path.rs
@@ -206,7 +206,7 @@ impl PosixPath : GenericPath {
             let mut ss = str::split_nonempty(
                 *e,
                 |c| windows::is_sep(c as u8));
-            unsafe { vec::push_all_move(v, move ss); }
+            unsafe { v.push_all_move(move ss); }
         }
         PosixPath { components: move v, ..self }
     }
@@ -214,7 +214,7 @@ impl PosixPath : GenericPath {
     pure fn push(s: &str) -> PosixPath {
         let mut v = copy self.components;
         let mut ss = str::split_nonempty(s, |c| windows::is_sep(c as u8));
-        unsafe { vec::push_all_move(v, move ss); }
+        unsafe { v.push_all_move(move ss); }
         PosixPath { components: move v, ..self }
     }
 
@@ -400,7 +400,7 @@ impl WindowsPath : GenericPath {
             let mut ss = str::split_nonempty(
                 *e,
                 |c| windows::is_sep(c as u8));
-            unsafe { vec::push_all_move(v, move ss); }
+            unsafe { v.push_all_move(move ss); }
         }
         return WindowsPath { components: move v, ..self }
     }
@@ -408,7 +408,7 @@ impl WindowsPath : GenericPath {
     pure fn push(s: &str) -> WindowsPath {
         let mut v = copy self.components;
         let mut ss = str::split_nonempty(s, |c| windows::is_sep(c as u8));
-        unsafe { vec::push_all_move(v, move ss); }
+        unsafe { v.push_all_move(move ss); }
         return WindowsPath { components: move v, ..self }
     }
 
@@ -440,7 +440,7 @@ pure fn normalize(components: &[~str]) -> ~[~str] {
                     vec::pop(cs);
                     loop;
                 }
-                vec::push(cs, copy *c);
+                cs.push(copy *c);
             }
         }
     }
diff --git a/src/libcore/pipes.rs b/src/libcore/pipes.rs
index bbabceafe8e..c4a7fa1437a 100644
--- a/src/libcore/pipes.rs
+++ b/src/libcore/pipes.rs
@@ -1059,7 +1059,7 @@ pub fn PortSet<T: Send>() -> PortSet<T>{
 impl<T: Send> PortSet<T> : Recv<T> {
 
     fn add(+port: pipes::Port<T>) {
-        vec::push(self.ports, move port)
+        self.ports.push(move port)
     }
 
     fn chan() -> Chan<T> {
diff --git a/src/libcore/private.rs b/src/libcore/private.rs
index 4021ad5e88f..7eba81803b3 100644
--- a/src/libcore/private.rs
+++ b/src/libcore/private.rs
@@ -564,7 +564,7 @@ pub mod tests {
 
         for uint::range(0u, num_tasks) |_i| {
             let total = total.clone();
-            vec::push(futures, future::spawn(|| {
+            futures.push(future::spawn(|| {
                 for uint::range(0u, count) |_i| {
                     do total.with |count| {
                         **count += 1u;
diff --git a/src/libcore/rand.rs b/src/libcore/rand.rs
index 02aa8530072..d68bd97ae5d 100644
--- a/src/libcore/rand.rs
+++ b/src/libcore/rand.rs
@@ -215,7 +215,7 @@ impl Rng {
         let mut r = ~[];
         for v.each |item| {
             for uint::range(0u, item.weight) |_i| {
-                vec::push(r, item.item);
+                r.push(item.item);
             }
         }
         move r
diff --git a/src/libcore/result.rs b/src/libcore/result.rs
index 7644175f93c..3968b0264d9 100644
--- a/src/libcore/result.rs
+++ b/src/libcore/result.rs
@@ -280,7 +280,7 @@ fn map_vec<T,U:Copy,V:Copy>(
     let mut vs: ~[V] = vec::with_capacity(vec::len(ts));
     for vec::each(ts) |t| {
         match op(t) {
-          Ok(v) => vec::push(vs, v),
+          Ok(v) => vs.push(v),
           Err(u) => return Err(u)
         }
     }
@@ -317,7 +317,7 @@ fn map_vec2<S,T,U:Copy,V:Copy>(ss: &[S], ts: &[T],
     let mut i = 0u;
     while i < n {
         match op(&ss[i],&ts[i]) {
-          Ok(v) => vec::push(vs, v),
+          Ok(v) => vs.push(v),
           Err(u) => return Err(u)
         }
         i += 1u;
diff --git a/src/libcore/run.rs b/src/libcore/run.rs
index e3e8491e15a..abeff1bd1d6 100644
--- a/src/libcore/run.rs
+++ b/src/libcore/run.rs
@@ -82,10 +82,10 @@ fn with_argv<T>(prog: &str, args: &[~str],
     let mut tmps = ~[];
     for vec::each(args) |arg| {
         let t = @copy *arg;
-        vec::push(tmps, t);
-        vec::push_all(argptrs, str::as_c_str(*t, |b| ~[b]));
+        tmps.push(t);
+        argptrs.push_all(str::as_c_str(*t, |b| ~[b]));
     }
-    vec::push(argptrs, ptr::null());
+    argptrs.push(ptr::null());
     vec::as_imm_buf(argptrs, |buf, _len| cb(buf))
 }
 
@@ -102,10 +102,10 @@ fn with_envp<T>(env: &Option<~[(~str,~str)]>,
         for vec::each(es) |e| {
             let (k,v) = copy *e;
             let t = @(fmt!("%s=%s", k, v));
-            vec::push(tmps, t);
-            vec::push_all(ptrs, str::as_c_str(*t, |b| ~[b]));
+            tmps.push(t);
+            ptrs.push_all(str::as_c_str(*t, |b| ~[b]));
         }
-        vec::push(ptrs, ptr::null());
+        ptrs.push(ptr::null());
         vec::as_imm_buf(ptrs, |p, _len|
             unsafe { cb(::cast::reinterpret_cast(&p)) }
         )
diff --git a/src/libcore/send_map.rs b/src/libcore/send_map.rs
index ac9a012c373..7ed962b4a90 100644
--- a/src/libcore/send_map.rs
+++ b/src/libcore/send_map.rs
@@ -283,18 +283,9 @@ pub mod linear {
                 FoundEntry(idx) => {
                     match self.buckets[idx] {
                         Some(ref bkt) => {
-                            let ptr = unsafe {
-                                // FIXME(#3148)--region inference
-                                // fails to capture needed deps.
-                                // Here, the bucket value is known to
-                                // live as long as self, because self
-                                // is immutable.  But the region
-                                // inference stupidly infers a
-                                // lifetime for `ref bkt` that is
-                                // shorter than it needs to be.
-                                cast::copy_lifetime(self, &bkt.value)
-                            };
-                            Some(ptr)
+                            // FIXME(#3148)---should be inferred
+                            let bkt: &self/Bucket<K,V> = bkt;
+                            Some(&bkt.value)
                         }
                         None => {
                             fail ~"LinearMap::find: internal logic error"
diff --git a/src/libcore/str.rs b/src/libcore/str.rs
index 13fb2260045..0993d1df63f 100644
--- a/src/libcore/str.rs
+++ b/src/libcore/str.rs
@@ -468,7 +468,7 @@ pure fn chars(s: &str) -> ~[char] {
     let len = len(s);
     while i < len {
         let {ch, next} = char_range_at(s, i);
-        unsafe { vec::push(buf, ch); }
+        unsafe { buf.push(ch); }
         i = next;
     }
     move buf
@@ -537,8 +537,7 @@ pure fn split_char_inner(s: &str, sep: char, count: uint, allow_empty: bool)
         while i < l && done < count {
             if s[i] == b {
                 if allow_empty || start < i unsafe {
-                    vec::push(result,
-                              unsafe { raw::slice_bytes(s, start, i) });
+                    result.push(unsafe { raw::slice_bytes(s, start, i) });
                 }
                 start = i + 1u;
                 done += 1u;
@@ -546,7 +545,7 @@ pure fn split_char_inner(s: &str, sep: char, count: uint, allow_empty: bool)
             i += 1u;
         }
         if allow_empty || start < l {
-            unsafe { vec::push(result, raw::slice_bytes(s, start, l) ) };
+            unsafe { result.push(raw::slice_bytes(s, start, l) ) };
         }
         move result
     } else {
@@ -581,7 +580,7 @@ pure fn split_inner(s: &str, sepfn: fn(cc: char) -> bool, count: uint,
         let {ch, next} = char_range_at(s, i);
         if sepfn(ch) {
             if allow_empty || start < i unsafe {
-                vec::push(result, unsafe { raw::slice_bytes(s, start, i)});
+                result.push(unsafe { raw::slice_bytes(s, start, i)});
             }
             start = next;
             done += 1u;
@@ -589,7 +588,7 @@ pure fn split_inner(s: &str, sepfn: fn(cc: char) -> bool, count: uint,
         i = next;
     }
     if allow_empty || start < l unsafe {
-        vec::push(result, unsafe { raw::slice_bytes(s, start, l) });
+        result.push(unsafe { raw::slice_bytes(s, start, l) });
     }
     move result
 }
@@ -643,7 +642,7 @@ pure fn iter_between_matches(s: &a/str, sep: &b/str, f: fn(uint, uint)) {
 pure fn split_str(s: &a/str, sep: &b/str) -> ~[~str] {
     let mut result = ~[];
     do iter_between_matches(s, sep) |from, to| {
-        unsafe { vec::push(result, raw::slice_bytes(s, from, to)); }
+        unsafe { result.push(raw::slice_bytes(s, from, to)); }
     }
     move result
 }
@@ -652,7 +651,7 @@ pure fn split_str_nonempty(s: &a/str, sep: &b/str) -> ~[~str] {
     let mut result = ~[];
     do iter_between_matches(s, sep) |from, to| {
         if to > from {
-            unsafe { vec::push(result, raw::slice_bytes(s, from, to)); }
+            unsafe { result.push(raw::slice_bytes(s, from, to)); }
         }
     }
     move result
@@ -1535,14 +1534,14 @@ pure fn to_utf16(s: &str) -> ~[u16] {
         if (ch & 0xFFFF_u32) == ch unsafe {
             // The BMP falls through (assuming non-surrogate, as it should)
             assert ch <= 0xD7FF_u32 || ch >= 0xE000_u32;
-            vec::push(u, ch as u16)
+            u.push(ch as u16)
         } else unsafe {
             // Supplementary planes break into surrogates.
             assert ch >= 0x1_0000_u32 && ch <= 0x10_FFFF_u32;
             ch -= 0x1_0000_u32;
             let w1 = 0xD800_u16 | ((ch >> 10) as u16);
             let w2 = 0xDC00_u16 | ((ch as u16) & 0x3FF_u16);
-            vec::push_all(u, ~[w1, w2])
+            u.push_all(~[w1, w2])
         }
     }
     move u
@@ -2010,7 +2009,7 @@ mod raw {
             ptr::memcpy(vbuf, buf as *u8, len)
         });
         vec::raw::set_len(v, len);
-        vec::push(v, 0u8);
+        v.push(0u8);
 
         assert is_utf8(v);
         return ::cast::transmute(move v);
@@ -2067,7 +2066,7 @@ mod raw {
                     ptr::memcpy(vbuf, src, end - begin);
                 }
                 vec::raw::set_len(v, end - begin);
-                vec::push(v, 0u8);
+                v.push(0u8);
                 ::cast::transmute(move v)
             }
         }
diff --git a/src/libcore/vec.rs b/src/libcore/vec.rs
index 7c5f242e8ba..50011dbacec 100644
--- a/src/libcore/vec.rs
+++ b/src/libcore/vec.rs
@@ -92,6 +92,8 @@ export CopyableVector;
 export ImmutableVector;
 export ImmutableEqVector;
 export ImmutableCopyableVector;
+export MutableVector;
+export MutableCopyableVector;
 export IterTraitExtensions;
 export vec_concat;
 export traits;
@@ -238,7 +240,7 @@ pure fn with_capacity<T>(capacity: uint) -> ~[T] {
 pure fn build_sized<A>(size: uint,
                        builder: fn(push: pure fn(+v: A))) -> ~[A] {
     let mut vec = with_capacity(size);
-    builder(|+x| unsafe { push(vec, move x) });
+    builder(|+x| unsafe { vec.push(move x) });
     move vec
 }
 
@@ -330,7 +332,7 @@ pure fn slice<T: Copy>(v: &[const T], start: uint, end: uint) -> ~[T] {
     assert (end <= len(v));
     let mut result = ~[];
     unsafe {
-        for uint::range(start, end) |i| { vec::push(result, v[i]) }
+        for uint::range(start, end) |i| { result.push(v[i]) }
     }
     move result
 }
@@ -383,14 +385,14 @@ fn split<T: Copy>(v: &[T], f: fn(T) -> bool) -> ~[~[T]] {
     let mut result = ~[];
     while start < ln {
         match position_between(v, start, ln, f) {
-          None => break,
-          Some(i) => {
-            push(result, slice(v, start, i));
-            start = i + 1u;
-          }
+            None => break,
+            Some(i) => {
+                result.push(slice(v, start, i));
+                start = i + 1u;
+            }
         }
     }
-    push(result, slice(v, start, ln));
+    result.push(slice(v, start, ln));
     move result
 }
 
@@ -407,16 +409,16 @@ fn splitn<T: Copy>(v: &[T], n: uint, f: fn(T) -> bool) -> ~[~[T]] {
     let mut result = ~[];
     while start < ln && count > 0u {
         match position_between(v, start, ln, f) {
-          None => break,
-          Some(i) => {
-            push(result, slice(v, start, i));
-            // Make sure to skip the separator.
-            start = i + 1u;
-            count -= 1u;
-          }
+            None => break,
+            Some(i) => {
+                result.push(slice(v, start, i));
+                // Make sure to skip the separator.
+                start = i + 1u;
+                count -= 1u;
+            }
         }
     }
-    push(result, slice(v, start, ln));
+    result.push(slice(v, start, ln));
     move result
 }
 
@@ -432,14 +434,14 @@ fn rsplit<T: Copy>(v: &[T], f: fn(T) -> bool) -> ~[~[T]] {
     let mut result = ~[];
     while end > 0u {
         match rposition_between(v, 0u, end, f) {
-          None => break,
-          Some(i) => {
-            push(result, slice(v, i + 1u, end));
-            end = i;
-          }
+            None => break,
+            Some(i) => {
+                result.push(slice(v, i + 1u, end));
+                end = i;
+            }
         }
     }
-    push(result, slice(v, 0u, end));
+    result.push(slice(v, 0u, end));
     reverse(result);
     return move result;
 }
@@ -457,16 +459,16 @@ fn rsplitn<T: Copy>(v: &[T], n: uint, f: fn(T) -> bool) -> ~[~[T]] {
     let mut result = ~[];
     while end > 0u && count > 0u {
         match rposition_between(v, 0u, end, f) {
-          None => break,
-          Some(i) => {
-            push(result, slice(v, i + 1u, end));
-            // Make sure to skip the separator.
-            end = i;
-            count -= 1u;
-          }
+            None => break,
+            Some(i) => {
+                result.push(slice(v, i + 1u, end));
+                // Make sure to skip the separator.
+                end = i;
+                count -= 1u;
+            }
         }
     }
-    push(result, slice(v, 0u, end));
+    result.push(slice(v, 0u, end));
     reverse(result);
     move result
 }
@@ -489,7 +491,7 @@ fn shift<T>(&v: ~[T]) -> T {
 
             for uint::range(1, ln) |i| {
                 let r <- *ptr::offset(vv, i);
-                push(v, move r);
+                v.push(move r);
             }
         }
         raw::set_len(vv, 0);
@@ -503,7 +505,7 @@ fn unshift<T>(&v: ~[T], +x: T) {
     let mut vv = ~[move x];
     v <-> vv;
     while len(vv) > 0 {
-        push(v, shift(vv));
+        v.push(shift(vv));
     }
 }
 
@@ -568,9 +570,9 @@ fn swap_remove<T>(&v: ~[const T], index: uint) -> T {
 
 /// Append an element to a vector
 #[inline(always)]
-fn push<T>(&v: ~[T], +initval: T) {
+fn push<T>(v: &mut ~[T], +initval: T) {
     unsafe {
-        let repr: **raw::VecRepr = ::cast::reinterpret_cast(&addr_of(v));
+        let repr: **raw::VecRepr = ::cast::transmute(copy v);
         let fill = (**repr).unboxed.fill;
         if (**repr).unboxed.alloc > fill {
             push_fast(v, move initval);
@@ -583,8 +585,8 @@ fn push<T>(&v: ~[T], +initval: T) {
 
 // This doesn't bother to make sure we have space.
 #[inline(always)] // really pretty please
-unsafe fn push_fast<T>(&v: ~[T], +initval: T) {
-    let repr: **raw::VecRepr = ::cast::reinterpret_cast(&addr_of(v));
+unsafe fn push_fast<T>(+v: &mut ~[T], +initval: T) {
+    let repr: **raw::VecRepr = ::cast::transmute(v);
     let fill = (**repr).unboxed.fill;
     (**repr).unboxed.fill += sys::size_of::<T>();
     let p = ptr::addr_of((**repr).unboxed.data);
@@ -593,14 +595,14 @@ unsafe fn push_fast<T>(&v: ~[T], +initval: T) {
 }
 
 #[inline(never)]
-fn push_slow<T>(&v: ~[T], +initval: T) {
-    reserve_at_least(&mut v, v.len() + 1u);
+fn push_slow<T>(+v: &mut ~[T], +initval: T) {
+    reserve_at_least(v, v.len() + 1u);
     unsafe { push_fast(v, move initval) }
 }
 
 #[inline(always)]
-fn push_all<T: Copy>(&v: ~[T], rhs: &[const T]) {
-    reserve(&mut v, v.len() + rhs.len());
+fn push_all<T: Copy>(+v: &mut ~[T], rhs: &[const T]) {
+    reserve(v, v.len() + rhs.len());
 
     for uint::range(0u, rhs.len()) |i| {
         push(v, unsafe { raw::get(rhs, i) })
@@ -608,8 +610,8 @@ fn push_all<T: Copy>(&v: ~[T], rhs: &[const T]) {
 }
 
 #[inline(always)]
-fn push_all_move<T>(&v: ~[T], -rhs: ~[const T]) {
-    reserve(&mut v, v.len() + rhs.len());
+fn push_all_move<T>(v: &mut ~[T], -rhs: ~[const T]) {
+    reserve(v, v.len() + rhs.len());
     unsafe {
         do as_imm_buf(rhs) |p, len| {
             for uint::range(0, len) |i| {
@@ -675,7 +677,7 @@ fn dedup<T: Eq>(&v: ~[const T]) unsafe {
 pure fn append<T: Copy>(+lhs: ~[T], rhs: &[const T]) -> ~[T] {
     let mut v <- lhs;
     unsafe {
-        push_all(v, rhs);
+        v.push_all(rhs);
     }
     move v
 }
@@ -683,7 +685,7 @@ pure fn append<T: Copy>(+lhs: ~[T], rhs: &[const T]) -> ~[T] {
 #[inline(always)]
 pure fn append_one<T>(+lhs: ~[T], +x: T) -> ~[T] {
     let mut v <- lhs;
-    unsafe { push(v, move x); }
+    unsafe { v.push(move x); }
     move v
 }
 
@@ -705,7 +707,10 @@ fn grow<T: Copy>(&v: ~[T], n: uint, initval: T) {
     reserve_at_least(&mut v, len(v) + n);
     let mut i: uint = 0u;
 
-    while i < n { push(v, initval); i += 1u; }
+    while i < n {
+        v.push(initval);
+        i += 1u;
+    }
 }
 
 /**
@@ -724,7 +729,10 @@ fn grow<T: Copy>(&v: ~[T], n: uint, initval: T) {
 fn grow_fn<T>(&v: ~[T], n: uint, op: iter::InitOp<T>) {
     reserve_at_least(&mut v, len(v) + n);
     let mut i: uint = 0u;
-    while i < n { push(v, op(i)); i += 1u; }
+    while i < n {
+        v.push(op(i));
+        i += 1u;
+    }
 }
 
 /**
@@ -745,14 +753,18 @@ fn grow_set<T: Copy>(&v: ~[T], index: uint, initval: T, val: T) {
 /// Apply a function to each element of a vector and return the results
 pure fn map<T, U>(v: &[T], f: fn(v: &T) -> U) -> ~[U] {
     let mut result = with_capacity(len(v));
-    for each(v) |elem| { unsafe { push(result, f(elem)); } }
+    for each(v) |elem| {
+        unsafe {
+            result.push(f(elem));
+        }
+    }
     move result
 }
 
 fn map_consume<T, U>(+v: ~[T], f: fn(+v: T) -> U) -> ~[U] {
     let mut result = ~[];
     do consume(move v) |_i, x| {
-        vec::push(result, f(move x));
+        result.push(f(move x));
     }
     move result
 }
@@ -772,7 +784,7 @@ pure fn mapi<T, U>(v: &[T], f: fn(uint, v: &T) -> U) -> ~[U] {
  */
 pure fn flat_map<T, U>(v: &[T], f: fn(T) -> ~[U]) -> ~[U] {
     let mut result = ~[];
-    for each(v) |elem| { unsafe{ push_all_move(result, f(*elem)); } }
+    for each(v) |elem| { unsafe{ result.push_all_move(f(*elem)); } }
     move result
 }
 
@@ -784,7 +796,7 @@ pure fn map2<T: Copy, U: Copy, V>(v0: &[T], v1: &[U],
     let mut u: ~[V] = ~[];
     let mut i = 0u;
     while i < v0_len {
-        unsafe { push(u, f(copy v0[i], copy v1[i])) };
+        unsafe { u.push(f(copy v0[i], copy v1[i])) };
         i += 1u;
     }
     move u
@@ -802,7 +814,7 @@ pure fn filter_map<T, U: Copy>(v: &[T], f: fn(T) -> Option<U>)
     for each(v) |elem| {
         match f(*elem) {
           None => {/* no-op */ }
-          Some(result_elem) => unsafe { push(result, result_elem); }
+          Some(result_elem) => unsafe { result.push(result_elem); }
         }
     }
     move result
@@ -818,7 +830,7 @@ pure fn filter_map<T, U: Copy>(v: &[T], f: fn(T) -> Option<U>)
 pure fn filter<T: Copy>(v: &[T], f: fn(T) -> bool) -> ~[T] {
     let mut result = ~[];
     for each(v) |elem| {
-        if f(*elem) { unsafe { push(result, *elem); } }
+        if f(*elem) { unsafe { result.push(*elem); } }
     }
     move result
 }
@@ -830,7 +842,7 @@ pure fn filter<T: Copy>(v: &[T], f: fn(T) -> bool) -> ~[T] {
  */
 pure fn concat<T: Copy>(v: &[~[T]]) -> ~[T] {
     let mut r = ~[];
-    for each(v) |inner| { unsafe { push_all(r, *inner); } }
+    for each(v) |inner| { unsafe { r.push_all(*inner); } }
     move r
 }
 
@@ -839,8 +851,8 @@ pure fn connect<T: Copy>(v: &[~[T]], sep: T) -> ~[T] {
     let mut r: ~[T] = ~[];
     let mut first = true;
     for each(v) |inner| {
-        if first { first = false; } else { unsafe { push(r, sep); } }
-        unsafe { push_all(r, *inner) };
+        if first { first = false; } else { unsafe { r.push(sep); } }
+        unsafe { r.push_all(*inner) };
     }
     move r
 }
@@ -1059,15 +1071,15 @@ pure fn rposition_between<T>(v: &[T], start: uint, end: uint,
  * Convert a vector of pairs into a pair of vectors, by reference. As unzip().
  */
 pure fn unzip_slice<T: Copy, U: Copy>(v: &[(T, U)]) -> (~[T], ~[U]) {
-    let mut as_ = ~[], bs = ~[];
+    let mut ts = ~[], us = ~[];
     for each(v) |p| {
-        let (a, b) = *p;
+        let (t, u) = *p;
         unsafe {
-            vec::push(as_, a);
-            vec::push(bs, b);
+            ts.push(t);
+            us.push(u);
         }
     }
-    return (move as_, move bs);
+    return (move ts, move us);
 }
 
 /**
@@ -1082,9 +1094,9 @@ pure fn unzip<T,U>(+v: ~[(T, U)]) -> (~[T], ~[U]) {
     let mut ts = ~[], us = ~[];
     unsafe {
         do consume(move v) |_i, p| {
-            let (a,b) = move p;
-            push(ts, move a);
-            push(us, move b);
+            let (t, u) = move p;
+            ts.push(move t);
+            us.push(move u);
         }
     }
     (move ts, move us)
@@ -1099,7 +1111,7 @@ pure fn zip_slice<T: Copy, U: Copy>(v: &[const T], u: &[const U])
     let sz = len(v);
     let mut i = 0u;
     assert sz == len(u);
-    while i < sz unsafe { vec::push(zipped, (v[i], u[i])); i += 1u; }
+    while i < sz unsafe { zipped.push((v[i], u[i])); i += 1u; }
     move zipped
 }
 
@@ -1114,7 +1126,7 @@ pure fn zip<T, U>(+v: ~[const T], +u: ~[const U]) -> ~[(T, U)] {
     assert i == len(u);
     let mut w = with_capacity(i);
     while i > 0 {
-        unsafe { push(w, (pop(v),pop(u))); }
+        unsafe { w.push((pop(v),pop(u))); }
         i -= 1;
     }
     unsafe { reverse(w); }
@@ -1147,8 +1159,8 @@ pure fn reversed<T: Copy>(v: &[const T]) -> ~[T] {
     let mut i = len::<T>(v);
     if i == 0 { return (move rs); } else { i -= 1; }
     unsafe {
-        while i != 0 { vec::push(rs, v[i]); i -= 1; }
-        vec::push(rs, v[0]);
+        while i != 0 { rs.push(v[i]); i -= 1; }
+        rs.push(v[0]);
     }
     move rs
 }
@@ -1283,7 +1295,7 @@ pure fn permute<T: Copy>(v: &[const T], put: fn(~[T])) {
             let elt = v[i];
             let mut rest = slice(v, 0u, i);
             unsafe {
-                push_all(rest, const_view(v, i+1u, ln));
+                rest.push_all(const_view(v, i+1u, ln));
                 permute(rest, |permutation| {
                     put(append(~[elt], permutation))
                 })
@@ -1299,7 +1311,7 @@ pure fn windowed<TT: Copy>(nn: uint, xx: &[TT]) -> ~[~[TT]] {
     for vec::eachi (xx) |ii, _x| {
         let len = vec::len(xx);
         if ii+nn <= len unsafe {
-            vec::push(ww, vec::slice(xx, ii, ii+nn));
+            ww.push(vec::slice(xx, ii, ii+nn));
         }
     }
     move ww
@@ -1551,7 +1563,7 @@ impl<T> &[T]: ImmutableVector<T> {
         let mut r = ~[];
         let mut i = 0;
         while i < self.len() {
-            push(r, f(&self[i]));
+            r.push(f(&self[i]));
             i += 1;
         }
         move r
@@ -1637,6 +1649,31 @@ impl<T: Copy> &[T]: ImmutableCopyableVector<T> {
     pure fn rfind(f: fn(T) -> bool) -> Option<T> { rfind(self, f) }
 }
 
+trait MutableVector<T> {
+    fn push(&mut self, +t: T);
+    fn push_all_move(&mut self, -rhs: ~[const T]);
+}
+
+trait MutableCopyableVector<T: Copy> {
+    fn push_all(&mut self, rhs: &[const T]);
+}
+
+impl<T> ~[T]: MutableVector<T> {
+    fn push(&mut self, +t: T) {
+        push(self, move t);
+    }
+
+    fn push_all_move(&mut self, -rhs: ~[const T]) {
+        push_all_move(self, move rhs);
+    }
+}
+
+impl<T: Copy> ~[T]: MutableCopyableVector<T> {
+    fn push_all(&mut self, rhs: &[const T]) {
+        push_all(self, rhs);
+    }
+}
+
 /// Unsafe operations
 mod raw {
     #[legacy_exports];
@@ -2109,12 +2146,12 @@ mod tests {
     fn test_push() {
         // Test on-stack push().
         let mut v = ~[];
-        push(v, 1);
+        v.push(1);
         assert (len(v) == 1u);
         assert (v[0] == 1);
 
         // Test on-heap push().
-        push(v, 2);
+        v.push(2);
         assert (len(v) == 2u);
         assert (v[0] == 1);
         assert (v[1] == 2);
@@ -2380,19 +2417,19 @@ mod tests {
         let mut results: ~[~[int]];
 
         results = ~[];
-        permute(~[], |v| vec::push(results, copy v));
+        permute(~[], |v| results.push(copy v));
         assert results == ~[~[]];
 
         results = ~[];
-        permute(~[7], |v| push(results, copy v));
+        permute(~[7], |v| results.push(copy v));
         assert results == ~[~[7]];
 
         results = ~[];
-        permute(~[1,1], |v| push(results, copy v));
+        permute(~[1,1], |v| results.push(copy v));
         assert results == ~[~[1,1],~[1,1]];
 
         results = ~[];
-        permute(~[5,2,0], |v| push(results, copy v));
+        permute(~[5,2,0], |v| results.push(copy v));
         assert results ==
             ~[~[5,2,0],~[5,0,2],~[2,5,0],~[2,0,5],~[0,5,2],~[0,2,5]];
     }