librustc: Implement explicit self for Add and Index; add a hack in the borrow checker to support this. r=nmatsakis
This commit is contained in:
parent
56ece46f7d
commit
d1ebdbeb6c
@ -145,12 +145,22 @@ pub pure fn from_elem<T: Copy>(n_elts: uint, t: T) -> @[T] {
|
||||
|
||||
#[cfg(notest)]
|
||||
pub mod traits {
|
||||
#[cfg(stage0)]
|
||||
pub impl<T: Copy> @[T] : Add<&[const T],@[T]> {
|
||||
#[inline(always)]
|
||||
pure fn add(rhs: & &self/[const T]) -> @[T] {
|
||||
append(self, (*rhs))
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(stage1)]
|
||||
#[cfg(stage2)]
|
||||
pub impl<T: Copy> @[T] : Add<&[const T],@[T]> {
|
||||
#[inline(always)]
|
||||
pure fn add(&self, rhs: & &self/[const T]) -> @[T] {
|
||||
append(*self, (*rhs))
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
|
@ -358,10 +358,19 @@ impl<A: Copy> DVec<A> {
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(stage0)]
|
||||
impl<A:Copy> DVec<A>: Index<uint,A> {
|
||||
#[inline(always)]
|
||||
pure fn index(idx: uint) -> A {
|
||||
self.get_elt(idx)
|
||||
}
|
||||
}
|
||||
#[cfg(stage1)]
|
||||
#[cfg(stage2)]
|
||||
impl<A:Copy> DVec<A>: Index<uint,A> {
|
||||
#[inline(always)]
|
||||
pure fn index(&self, idx: uint) -> A {
|
||||
self.get_elt(idx)
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -18,11 +18,19 @@ pub trait Drop {
|
||||
fn finalize(&self); // XXX: Rename to "drop"? --pcwalton
|
||||
}
|
||||
|
||||
#[cfg(stage0)]
|
||||
#[lang="add"]
|
||||
pub trait Add<RHS,Result> {
|
||||
pure fn add(rhs: &RHS) -> Result;
|
||||
}
|
||||
|
||||
#[cfg(stage1)]
|
||||
#[cfg(stage2)]
|
||||
#[lang="add"]
|
||||
pub trait Add<RHS,Result> {
|
||||
pure fn add(&self, rhs: &RHS) -> Result;
|
||||
}
|
||||
|
||||
#[lang="sub"]
|
||||
pub trait Sub<RHS,Result> {
|
||||
pure fn sub(&self, rhs: &RHS) -> Result;
|
||||
@ -73,8 +81,16 @@ pub trait Shr<RHS,Result> {
|
||||
pure fn shr(&self, rhs: &RHS) -> Result;
|
||||
}
|
||||
|
||||
#[cfg(stage0)]
|
||||
#[lang="index"]
|
||||
pub trait Index<Index,Result> {
|
||||
pure fn index(index: Index) -> Result;
|
||||
}
|
||||
|
||||
#[cfg(stage1)]
|
||||
#[cfg(stage2)]
|
||||
#[lang="index"]
|
||||
pub trait Index<Index,Result> {
|
||||
pure fn index(&self, index: Index) -> Result;
|
||||
}
|
||||
|
||||
|
@ -2107,12 +2107,21 @@ impl ~str: Trimmable {
|
||||
|
||||
#[cfg(notest)]
|
||||
pub mod traits {
|
||||
#[cfg(stage0)]
|
||||
impl ~str : Add<&str,~str> {
|
||||
#[inline(always)]
|
||||
pure fn add(rhs: & &self/str) -> ~str {
|
||||
append(copy self, (*rhs))
|
||||
}
|
||||
}
|
||||
#[cfg(stage1)]
|
||||
#[cfg(stage2)]
|
||||
impl ~str : Add<&str,~str> {
|
||||
#[inline(always)]
|
||||
pure fn add(&self, rhs: & &self/str) -> ~str {
|
||||
append(copy *self, (*rhs))
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
|
@ -1438,18 +1438,37 @@ impl<T: Ord> @[T] : Ord {
|
||||
}
|
||||
|
||||
#[cfg(notest)]
|
||||
impl<T: Copy> ~[T] : Add<&[const T],~[T]> {
|
||||
#[inline(always)]
|
||||
pure fn add(rhs: & &self/[const T]) -> ~[T] {
|
||||
append(copy self, (*rhs))
|
||||
pub mod traits {
|
||||
#[cfg(stage0)]
|
||||
impl<T: Copy> ~[T] : Add<&[const T],~[T]> {
|
||||
#[inline(always)]
|
||||
pure fn add(rhs: & &self/[const T]) -> ~[T] {
|
||||
append(copy self, (*rhs))
|
||||
}
|
||||
}
|
||||
#[cfg(stage1)]
|
||||
#[cfg(stage2)]
|
||||
impl<T: Copy> ~[T] : Add<&[const T],~[T]> {
|
||||
#[inline(always)]
|
||||
pure fn add(&self, rhs: & &self/[const T]) -> ~[T] {
|
||||
append(copy *self, (*rhs))
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(notest)]
|
||||
impl<T: Copy> ~[mut T] : Add<&[const T],~[mut T]> {
|
||||
#[inline(always)]
|
||||
pure fn add(rhs: & &self/[const T]) -> ~[mut T] {
|
||||
append_mut(copy self, (*rhs))
|
||||
#[cfg(stage0)]
|
||||
impl<T: Copy> ~[mut T] : Add<&[const T],~[mut T]> {
|
||||
#[inline(always)]
|
||||
pure fn add(rhs: & &self/[const T]) -> ~[mut T] {
|
||||
append_mut(copy self, (*rhs))
|
||||
}
|
||||
}
|
||||
#[cfg(stage1)]
|
||||
#[cfg(stage2)]
|
||||
impl<T: Copy> ~[mut T] : Add<&[const T],~[mut T]> {
|
||||
#[inline(always)]
|
||||
pure fn add(&self, rhs: & &self/[const T]) -> ~[mut T] {
|
||||
append_mut(copy *self, (*rhs))
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -20,6 +20,8 @@ use mem_categorization::{mem_categorization_ctxt, opt_deref_kind};
|
||||
use preserve::{preserve_condition, pc_ok, pc_if_pure};
|
||||
use ty::{ty_region};
|
||||
|
||||
use core::send_map::linear::LinearMap;
|
||||
|
||||
export gather_loans;
|
||||
|
||||
/// Context used while gathering loans:
|
||||
@ -53,14 +55,16 @@ export gather_loans;
|
||||
enum gather_loan_ctxt = @{bccx: borrowck_ctxt,
|
||||
req_maps: req_maps,
|
||||
mut item_ub: ast::node_id,
|
||||
mut root_ub: ast::node_id};
|
||||
mut root_ub: ast::node_id,
|
||||
mut ignore_adjustments: LinearMap<ast::node_id,()>};
|
||||
|
||||
fn gather_loans(bccx: borrowck_ctxt, crate: @ast::crate) -> req_maps {
|
||||
let glcx = gather_loan_ctxt(@{bccx: bccx,
|
||||
req_maps: {req_loan_map: HashMap(),
|
||||
pure_map: HashMap()},
|
||||
mut item_ub: 0,
|
||||
mut root_ub: 0});
|
||||
mut root_ub: 0,
|
||||
mut ignore_adjustments: LinearMap()});
|
||||
let v = visit::mk_vt(@{visit_expr: req_loans_in_expr,
|
||||
visit_fn: req_loans_in_fn,
|
||||
.. *visit::default_visitor()});
|
||||
@ -104,8 +108,10 @@ fn req_loans_in_expr(ex: @ast::expr,
|
||||
ex.id, pprust::expr_to_str(ex, tcx.sess.intr()));
|
||||
|
||||
// If this expression is borrowed, have to ensure it remains valid:
|
||||
for tcx.adjustments.find(ex.id).each |adjustments| {
|
||||
self.guarantee_adjustments(ex, *adjustments);
|
||||
if !self.ignore_adjustments.contains_key(&ex.id) {
|
||||
for tcx.adjustments.find(ex.id).each |adjustments| {
|
||||
self.guarantee_adjustments(ex, *adjustments);
|
||||
}
|
||||
}
|
||||
|
||||
// Special checks for various kinds of expressions:
|
||||
@ -179,7 +185,8 @@ fn req_loans_in_expr(ex: @ast::expr,
|
||||
|
||||
ast::expr_index(rcvr, _) |
|
||||
ast::expr_binary(_, rcvr, _) |
|
||||
ast::expr_unary(_, rcvr)
|
||||
ast::expr_unary(_, rcvr) |
|
||||
ast::expr_assign_op(_, rcvr, _)
|
||||
if self.bccx.method_map.contains_key(ex.id) => {
|
||||
// Receivers in method calls are always passed by ref.
|
||||
//
|
||||
@ -193,6 +200,11 @@ fn req_loans_in_expr(ex: @ast::expr,
|
||||
let scope_r = ty::re_scope(ex.id);
|
||||
let rcvr_cmt = self.bccx.cat_expr(rcvr);
|
||||
self.guarantee_valid(rcvr_cmt, m_imm, scope_r);
|
||||
|
||||
// FIXME (#3387): Total hack: Ignore adjustments for the left-hand
|
||||
// side. Their regions will be inferred to be too large.
|
||||
self.ignore_adjustments.insert(rcvr.id, ());
|
||||
|
||||
visit::visit_expr(ex, self, vt);
|
||||
}
|
||||
|
||||
|
@ -565,11 +565,19 @@ pure fn land(w0: uint, w1: uint) -> uint { return w0 & w1; }
|
||||
|
||||
pure fn right(_w0: uint, w1: uint) -> uint { return w1; }
|
||||
|
||||
#[cfg(stage0)]
|
||||
impl Bitv: ops::Index<uint,bool> {
|
||||
pure fn index(i: uint) -> bool {
|
||||
self.get(i)
|
||||
}
|
||||
}
|
||||
#[cfg(stage1)]
|
||||
#[cfg(stage2)]
|
||||
impl Bitv: ops::Index<uint,bool> {
|
||||
pure fn index(&self, i: uint) -> bool {
|
||||
self.get(i)
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
mod tests {
|
||||
|
@ -57,6 +57,7 @@ pub mod Reader {
|
||||
|
||||
// ebml reading
|
||||
|
||||
#[cfg(stage0)]
|
||||
impl Doc: ops::Index<uint,Doc> {
|
||||
pure fn index(tag: uint) -> Doc {
|
||||
unsafe {
|
||||
@ -64,6 +65,15 @@ pub mod Reader {
|
||||
}
|
||||
}
|
||||
}
|
||||
#[cfg(stage1)]
|
||||
#[cfg(stage2)]
|
||||
impl Doc: ops::Index<uint,Doc> {
|
||||
pure fn index(&self, tag: uint) -> Doc {
|
||||
unsafe {
|
||||
get_doc(*self, tag)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fn vuint_at(data: &[u8], start: uint) -> {val: uint, next: uint} {
|
||||
let a = data[start];
|
||||
|
@ -429,6 +429,7 @@ pub mod chained {
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(stage0)]
|
||||
impl<K:Eq IterBytes Hash Copy, V: Copy> T<K, V>: ops::Index<K, V> {
|
||||
pure fn index(k: K) -> V {
|
||||
unsafe {
|
||||
@ -436,6 +437,15 @@ pub mod chained {
|
||||
}
|
||||
}
|
||||
}
|
||||
#[cfg(stage1)]
|
||||
#[cfg(stage2)]
|
||||
impl<K:Eq IterBytes Hash Copy, V: Copy> T<K, V>: ops::Index<K, V> {
|
||||
pure fn index(&self, k: K) -> V {
|
||||
unsafe {
|
||||
self.get(k)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fn chains<K,V>(nchains: uint) -> ~[mut Option<@Entry<K,V>>] {
|
||||
vec::to_mut(vec::from_elem(nchains, None))
|
||||
|
@ -150,6 +150,7 @@ impl<V: Copy> SmallIntMap<V>: map::Map<uint, V> {
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(stage0)]
|
||||
impl<V: Copy> SmallIntMap<V>: ops::Index<uint, V> {
|
||||
pure fn index(key: uint) -> V {
|
||||
unsafe {
|
||||
@ -157,6 +158,15 @@ impl<V: Copy> SmallIntMap<V>: ops::Index<uint, V> {
|
||||
}
|
||||
}
|
||||
}
|
||||
#[cfg(stage1)]
|
||||
#[cfg(stage2)]
|
||||
impl<V: Copy> SmallIntMap<V>: ops::Index<uint, V> {
|
||||
pure fn index(&self, key: uint) -> V {
|
||||
unsafe {
|
||||
get(*self, key)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// Cast the given smallintmap to a map::map
|
||||
pub fn as_map<V: Copy>(s: SmallIntMap<V>) -> map::Map<uint, V> {
|
||||
|
Loading…
x
Reference in New Issue
Block a user