libcore: Remove more mutable fields from comm

This commit is contained in:
Patrick Walton 2013-05-03 17:37:08 -07:00
parent 8919f32f83
commit d12d25534b
4 changed files with 114 additions and 73 deletions

View File

@ -234,8 +234,9 @@ impl<T: Owned> Selectable for Port<T> {
} }
/// Treat many ports as one. /// Treat many ports as one.
#[unsafe_mut_field(ports)]
pub struct PortSet<T> { pub struct PortSet<T> {
mut ports: ~[Port<T>], ports: ~[Port<T>],
} }
pub impl<T: Owned> PortSet<T> { pub impl<T: Owned> PortSet<T> {
@ -246,7 +247,10 @@ pub impl<T: Owned> PortSet<T> {
} }
fn add(&self, port: Port<T>) { fn add(&self, port: Port<T>) {
self.ports.push(port) unsafe {
let self_ports = transmute_mut(&self.ports);
self_ports.push(port)
}
} }
fn chan(&self) -> Chan<T> { fn chan(&self) -> Chan<T> {
@ -258,25 +262,28 @@ pub impl<T: Owned> PortSet<T> {
impl<T:Owned> GenericPort<T> for PortSet<T> { impl<T:Owned> GenericPort<T> for PortSet<T> {
fn try_recv(&self) -> Option<T> { fn try_recv(&self) -> Option<T> {
let mut result = None; unsafe {
// we have to swap the ports array so we aren't borrowing let mut self_ports = transmute_mut(&self.ports);
// aliasable mutable memory. let mut result = None;
let mut ports = ~[]; // we have to swap the ports array so we aren't borrowing
ports <-> self.ports; // aliasable mutable memory.
while result.is_none() && ports.len() > 0 { let mut ports = ~[];
let i = wait_many(ports); ports <-> *self_ports;
match ports[i].try_recv() { while result.is_none() && ports.len() > 0 {
Some(m) => { let i = wait_many(ports);
result = Some(m); match ports[i].try_recv() {
} Some(m) => {
None => { result = Some(m);
// Remove this port. }
let _ = ports.swap_remove(i); None => {
// Remove this port.
let _ = ports.swap_remove(i);
}
} }
} }
ports <-> *self_ports;
result
} }
ports <-> self.ports;
result
} }
fn recv(&self) -> T { fn recv(&self) -> T {
self.try_recv().expect("port_set: endpoints closed") self.try_recv().expect("port_set: endpoints closed")
@ -288,10 +295,9 @@ impl<T: Owned> Peekable<T> for PortSet<T> {
// It'd be nice to use self.port.each, but that version isn't // It'd be nice to use self.port.each, but that version isn't
// pure. // pure.
for uint::range(0, vec::uniq_len(&const self.ports)) |i| { for uint::range(0, vec::uniq_len(&const self.ports)) |i| {
// XXX: Botch pending demuting. let port: &Port<T> = &self.ports[i];
unsafe { if port.peek() {
let port: &Port<T> = cast::transmute(&mut self.ports[i]); return true;
if port.peek() { return true }
} }
} }
false false

View File

@ -983,36 +983,50 @@ pub fn file_reader(path: &Path) -> Result<@Reader, ~str> {
// Byte readers // Byte readers
pub struct BytesReader<'self> { pub struct BytesReader<'self> {
bytes: &'self [u8], bytes: &'self [u8],
mut pos: uint pos: @mut uint
} }
impl<'self> Reader for BytesReader<'self> { impl<'self> Reader for BytesReader<'self> {
fn read(&self, bytes: &mut [u8], len: uint) -> uint { fn read(&self, bytes: &mut [u8], len: uint) -> uint {
let count = uint::min(len, self.bytes.len() - self.pos); let count = uint::min(len, self.bytes.len() - *self.pos);
let view = vec::slice(self.bytes, self.pos, self.bytes.len()); let view = vec::slice(self.bytes, *self.pos, self.bytes.len());
vec::bytes::copy_memory(bytes, view, count); vec::bytes::copy_memory(bytes, view, count);
self.pos += count; *self.pos += count;
count count
} }
fn read_byte(&self) -> int { fn read_byte(&self) -> int {
if self.pos == self.bytes.len() { return -1; } if *self.pos == self.bytes.len() {
let b = self.bytes[self.pos]; return -1;
self.pos += 1u; }
return b as int;
let b = self.bytes[*self.pos];
*self.pos += 1u;
b as int
} }
fn eof(&self) -> bool { self.pos == self.bytes.len() }
fn eof(&self) -> bool {
*self.pos == self.bytes.len()
}
fn seek(&self, offset: int, whence: SeekStyle) { fn seek(&self, offset: int, whence: SeekStyle) {
let pos = self.pos; let pos = *self.pos;
self.pos = seek_in_buf(offset, pos, self.bytes.len(), whence); *self.pos = seek_in_buf(offset, pos, self.bytes.len(), whence);
}
fn tell(&self) -> uint {
*self.pos
} }
fn tell(&self) -> uint { self.pos }
} }
pub fn with_bytes_reader<t>(bytes: &[u8], f: &fn(@Reader) -> t) -> t { pub fn with_bytes_reader<T>(bytes: &[u8], f: &fn(@Reader) -> T) -> T {
f(@BytesReader { bytes: bytes, pos: 0u } as @Reader) f(@BytesReader {
bytes: bytes,
pos: @mut 0
} as @Reader)
} }
pub fn with_str_reader<T>(s: &str, f: &fn(@Reader) -> T) -> T { pub fn with_str_reader<T>(s: &str, f: &fn(@Reader) -> T) -> T {
@ -1498,49 +1512,67 @@ pub fn buffered_file_writer(path: &Path) -> Result<@Writer, ~str> {
pub fn stdout() -> @Writer { fd_writer(libc::STDOUT_FILENO as c_int, false) } pub fn stdout() -> @Writer { fd_writer(libc::STDOUT_FILENO as c_int, false) }
pub fn stderr() -> @Writer { fd_writer(libc::STDERR_FILENO as c_int, false) } pub fn stderr() -> @Writer { fd_writer(libc::STDERR_FILENO as c_int, false) }
pub fn print(s: &str) { stdout().write_str(s); } pub fn print(s: &str) {
pub fn println(s: &str) { stdout().write_line(s); } stdout().write_str(s);
}
pub fn println(s: &str) {
stdout().write_line(s);
}
pub struct BytesWriter { pub struct BytesWriter {
mut bytes: ~[u8], bytes: @mut ~[u8],
mut pos: uint, pos: @mut uint,
} }
impl Writer for BytesWriter { impl Writer for BytesWriter {
fn write(&self, v: &[u8]) { fn write(&self, v: &[u8]) {
let v_len = v.len(); let v_len = v.len();
let bytes_len = vec::uniq_len(&const self.bytes); let bytes_len = vec::uniq_len(&const *self.bytes);
let count = uint::max(bytes_len, self.pos + v_len); let count = uint::max(bytes_len, *self.pos + v_len);
vec::reserve(&mut self.bytes, count); vec::reserve(&mut *self.bytes, count);
unsafe { unsafe {
vec::raw::set_len(&mut self.bytes, count); vec::raw::set_len(&mut *self.bytes, count);
let view = vec::mut_slice(self.bytes, self.pos, count); let view = vec::mut_slice(*self.bytes, *self.pos, count);
vec::bytes::copy_memory(view, v, v_len); vec::bytes::copy_memory(view, v, v_len);
} }
self.pos += v_len; *self.pos += v_len;
} }
fn seek(&self, offset: int, whence: SeekStyle) { fn seek(&self, offset: int, whence: SeekStyle) {
let pos = self.pos; let pos = *self.pos;
let len = vec::uniq_len(&const self.bytes); let len = vec::uniq_len(&const *self.bytes);
self.pos = seek_in_buf(offset, pos, len, whence); *self.pos = seek_in_buf(offset, pos, len, whence);
}
fn tell(&self) -> uint {
*self.pos
}
fn flush(&self) -> int {
0
}
fn get_type(&self) -> WriterType {
File
} }
fn tell(&self) -> uint { self.pos }
fn flush(&self) -> int { 0 }
fn get_type(&self) -> WriterType { File }
} }
pub fn BytesWriter() -> BytesWriter { pub fn BytesWriter() -> BytesWriter {
BytesWriter { bytes: ~[], mut pos: 0u } BytesWriter {
bytes: @mut ~[],
pos: @mut 0
}
} }
pub fn with_bytes_writer(f: &fn(@Writer)) -> ~[u8] { pub fn with_bytes_writer(f: &fn(@Writer)) -> ~[u8] {
let wr = @BytesWriter(); let wr = @BytesWriter();
f(wr as @Writer); f(wr as @Writer);
let @BytesWriter{bytes, _} = wr; let @BytesWriter { bytes, _ } = wr;
return bytes; copy *bytes
} }
pub fn with_str_writer(f: &fn(@Writer)) -> ~str { pub fn with_str_writer(f: &fn(@Writer)) -> ~str {
@ -1550,7 +1582,9 @@ pub fn with_str_writer(f: &fn(@Writer)) -> ~str {
v.push(0); v.push(0);
assert!(str::is_utf8(v)); assert!(str::is_utf8(v));
unsafe { ::cast::transmute(v) } unsafe {
::cast::transmute(v)
}
} }
// Utility functions // Utility functions

View File

@ -1372,41 +1372,40 @@ pub fn encode_metadata(parms: EncodeParams, crate: &crate) -> ~[u8] {
encode_hash(&mut ebml_w, ecx.link_meta.extras_hash); encode_hash(&mut ebml_w, ecx.link_meta.extras_hash);
let mut i = wr.pos; let mut i = *wr.pos;
let crate_attrs = synthesize_crate_attrs(ecx, crate); let crate_attrs = synthesize_crate_attrs(ecx, crate);
encode_attributes(&mut ebml_w, crate_attrs); encode_attributes(&mut ebml_w, crate_attrs);
ecx.stats.attr_bytes = wr.pos - i; ecx.stats.attr_bytes = *wr.pos - i;
i = wr.pos; i = *wr.pos;
encode_crate_deps(ecx, &mut ebml_w, ecx.cstore); encode_crate_deps(ecx, &mut ebml_w, ecx.cstore);
ecx.stats.dep_bytes = wr.pos - i; ecx.stats.dep_bytes = *wr.pos - i;
// Encode the language items. // Encode the language items.
i = wr.pos; i = *wr.pos;
encode_lang_items(ecx, &mut ebml_w); encode_lang_items(ecx, &mut ebml_w);
ecx.stats.lang_item_bytes = wr.pos - i; ecx.stats.lang_item_bytes = *wr.pos - i;
// Encode the link args. // Encode the link args.
i = wr.pos; i = *wr.pos;
encode_link_args(ecx, &mut ebml_w); encode_link_args(ecx, &mut ebml_w);
ecx.stats.link_args_bytes = wr.pos - i; ecx.stats.link_args_bytes = *wr.pos - i;
// Encode and index the items. // Encode and index the items.
ebml_w.start_tag(tag_items); ebml_w.start_tag(tag_items);
i = wr.pos; i = *wr.pos;
let items_index = encode_info_for_items(ecx, &mut ebml_w, crate); let items_index = encode_info_for_items(ecx, &mut ebml_w, crate);
ecx.stats.item_bytes = wr.pos - i; ecx.stats.item_bytes = *wr.pos - i;
i = wr.pos; i = *wr.pos;
let items_buckets = create_index(items_index); let items_buckets = create_index(items_index);
encode_index(&mut ebml_w, items_buckets, write_int); encode_index(&mut ebml_w, items_buckets, write_int);
ecx.stats.index_bytes = wr.pos - i; ecx.stats.index_bytes = *wr.pos - i;
ebml_w.end_tag(); ebml_w.end_tag();
ecx.stats.total_bytes = wr.pos; ecx.stats.total_bytes = *wr.pos;
if (tcx.sess.meta_stats()) { if (tcx.sess.meta_stats()) {
do wr.bytes.each |e| { do wr.bytes.each |e| {
if *e == 0 { if *e == 0 {
ecx.stats.zero_bytes += 1; ecx.stats.zero_bytes += 1;
@ -1438,9 +1437,11 @@ pub fn encode_metadata(parms: EncodeParams, crate: &crate) -> ~[u8] {
// //
// vec::from_slice(metadata_encoding_version) + // vec::from_slice(metadata_encoding_version) +
let writer_bytes: &mut ~[u8] = wr.bytes;
(do str::as_bytes(&~"rust\x00\x00\x00\x01") |bytes| { (do str::as_bytes(&~"rust\x00\x00\x00\x01") |bytes| {
vec::slice(*bytes, 0, 8).to_vec() vec::slice(*bytes, 0, 8).to_vec()
}) + flate::deflate_bytes(wr.bytes) }) + flate::deflate_bytes(*writer_bytes)
} }
// Get the encoded string for a type // Get the encoded string for a type

View File

@ -29,13 +29,13 @@ pub impl BufReader {
// I can't get the borrowing to work correctly // I can't get the borrowing to work correctly
let bytes_reader = BytesReader { let bytes_reader = BytesReader {
bytes: ::core::util::id::<&[u8]>(self.buf), bytes: ::core::util::id::<&[u8]>(self.buf),
pos: *self.pos pos: @mut *self.pos
}; };
let res = f(&bytes_reader); let res = f(&bytes_reader);
// FIXME #4429: This isn't correct if f fails // FIXME #4429: This isn't correct if f fails
*self.pos = bytes_reader.pos; *self.pos = *bytes_reader.pos;
return res; return res;
} }