auto merge of #5075 : luqmana/rust/derec, r=catamorphism

Now only `lib core/pipes.rs` has `#[allow(structural_records)]`. That can be removed after a snapshot.
This commit is contained in:
bors 2013-02-21 17:30:32 -08:00
commit f5cc0b9830
37 changed files with 131 additions and 196 deletions

View File

@ -21,7 +21,7 @@ pub enum mode {
mode_debug_info,
}
pub type config = {
pub struct config {
// The library paths required for running the compiler
compile_lib_path: ~str,
@ -68,4 +68,4 @@ pub type config = {
// Explain what's going on
verbose: bool
};
}

View File

@ -11,7 +11,6 @@
#[crate_type = "bin"];
#[no_core];
#[legacy_records];
#[allow(vecs_implicitly_copyable)];
#[allow(non_camel_case_types)];
@ -77,26 +76,28 @@ pub fn parse_config(args: ~[~str]) -> config {
Path(getopts::opt_str(m, nm))
}
return {compile_lib_path: getopts::opt_str(matches, ~"compile-lib-path"),
run_lib_path: getopts::opt_str(matches, ~"run-lib-path"),
rustc_path: opt_path(matches, ~"rustc-path"),
src_base: opt_path(matches, ~"src-base"),
build_base: opt_path(matches, ~"build-base"),
aux_base: opt_path(matches, ~"aux-base"),
stage_id: getopts::opt_str(matches, ~"stage-id"),
mode: str_mode(getopts::opt_str(matches, ~"mode")),
run_ignored: getopts::opt_present(matches, ~"ignored"),
filter:
config {
compile_lib_path: getopts::opt_str(matches, ~"compile-lib-path"),
run_lib_path: getopts::opt_str(matches, ~"run-lib-path"),
rustc_path: opt_path(matches, ~"rustc-path"),
src_base: opt_path(matches, ~"src-base"),
build_base: opt_path(matches, ~"build-base"),
aux_base: opt_path(matches, ~"aux-base"),
stage_id: getopts::opt_str(matches, ~"stage-id"),
mode: str_mode(getopts::opt_str(matches, ~"mode")),
run_ignored: getopts::opt_present(matches, ~"ignored"),
filter:
if vec::len(matches.free) > 0u {
option::Some(matches.free[0])
} else { option::None },
logfile: option::map(&getopts::opt_maybe_str(matches,
logfile: option::map(&getopts::opt_maybe_str(matches,
~"logfile"),
|s| Path(*s)),
runtool: getopts::opt_maybe_str(matches, ~"runtool"),
rustcflags: getopts::opt_maybe_str(matches, ~"rustcflags"),
jit: getopts::opt_present(matches, ~"jit"),
verbose: getopts::opt_present(matches, ~"verbose")};
|s| Path(*s)),
runtool: getopts::opt_maybe_str(matches, ~"runtool"),
rustcflags: getopts::opt_maybe_str(matches, ~"rustcflags"),
jit: getopts::opt_present(matches, ~"jit"),
verbose: getopts::opt_present(matches, ~"verbose")
}
}
pub fn log_config(config: config) {

View File

@ -1278,13 +1278,13 @@ fn test_simplification() {
let item_in = ast::ii_item(quote_item!(
fn new_int_alist<B:Copy>() -> alist<int, B> {
fn eq_int(&&a: int, &&b: int) -> bool { a == b }
return {eq_fn: eq_int, data: ~[]};
return alist {eq_fn: eq_int, data: ~[]};
}
).get());
let item_out = simplify_ast(item_in);
let item_exp = ast::ii_item(quote_item!(
fn new_int_alist<B:Copy>() -> alist<int, B> {
return {eq_fn: eq_int, data: ~[]};
return alist {eq_fn: eq_int, data: ~[]};
}
).get());
match (item_out, item_exp) {

View File

@ -706,23 +706,21 @@ fn check_item_deprecated_self(cx: ty::ctxt, item: @ast::item) {
}
fn check_item_structural_records(cx: ty::ctxt, it: @ast::item) {
if !cx.legacy_records {
let visit = item_stopping_visitor(
visit::mk_simple_visitor(@visit::SimpleVisitor {
visit_expr: |e: @ast::expr| {
match e.node {
ast::expr_rec(*) =>
cx.sess.span_lint(
structural_records, e.id, it.id,
e.span,
~"structural records are deprecated"),
_ => ()
}
},
.. *visit::default_simple_visitor()
}));
visit::visit_item(it, (), visit);
}
let visit = item_stopping_visitor(
visit::mk_simple_visitor(@visit::SimpleVisitor {
visit_expr: |e: @ast::expr| {
match e.node {
ast::expr_rec(*) =>
cx.sess.span_lint(
structural_records, e.id, it.id,
e.span,
~"structural records are deprecated"),
_ => ()
}
},
.. *visit::default_simple_visitor()
}));
visit::visit_item(it, (), visit);
}
fn check_item_ctypes(cx: ty::ctxt, it: @ast::item) {

View File

@ -233,7 +233,6 @@ struct ctxt_ {
mut next_id: uint,
vecs_implicitly_copyable: bool,
legacy_modes: bool,
legacy_records: bool,
cstore: @mut metadata::cstore::CStore,
sess: session::Session,
def_map: resolve::DefMap,
@ -789,16 +788,10 @@ pub fn mk_ctxt(s: session::Session,
crate: @ast::crate)
-> ctxt {
let mut legacy_modes = false;
let mut legacy_records = false;
for crate.node.attrs.each |attribute| {
match attribute.node.value.node {
ast::meta_word(w) if *w == ~"legacy_modes" => {
legacy_modes = true;
if legacy_records { break; }
}
ast::meta_word(w) if *w == ~"legacy_records" => {
legacy_records = true;
if legacy_modes { break; }
}
_ => {}
}
@ -814,7 +807,6 @@ pub fn mk_ctxt(s: session::Session,
mut next_id: 0u,
vecs_implicitly_copyable: vecs_implicitly_copyable,
legacy_modes: legacy_modes,
legacy_records: legacy_records,
cstore: s.cstore,
sess: s,
def_map: dm,

View File

@ -17,7 +17,6 @@
#[crate_type = "lib"];
#[legacy_records];
#[no_core];
#[allow(vecs_implicitly_copyable,

View File

@ -16,7 +16,6 @@
#[allow(non_implicitly_copyable_typarams)];
#[allow(owned_heap_memory)];
#[allow(path_statement)];
#[allow(structural_records)];
#[allow(unrecognized_lint)];
#[allow(unused_imports)];
#[allow(vecs_implicitly_copyable)];

View File

@ -20,8 +20,6 @@
#[allow(vecs_implicitly_copyable,
non_implicitly_copyable_typarams)];
#[legacy_records];
extern mod core(vers = "0.6");
extern mod std(vers = "0.6");
extern mod rustc(vers = "0.6");

View File

@ -1926,7 +1926,7 @@ pub impl Parser {
fields.push(self.parse_field(token::COLON));
}
self.expect(token::RBRACE);
//self.warn(~"REC");
self.warn(~"REC");
return expr_rec(fields, base);
}

View File

@ -10,8 +10,6 @@
// Compare bounded and unbounded protocol performance.
#[allow(structural_records)]; // Pipes
// Until a snapshot
// xfail-pretty
extern mod std;

View File

@ -8,10 +8,10 @@
// option. This file may not be copied, modified, or distributed
// except according to those terms.
type point = { x: int, y: int };
struct point {x: int, mut y: int }
fn a() {
let mut p = {x: 3, y: 4};
let mut p = point {x: 3, y: 4};
let _q = &p; //~ NOTE loan of mutable local variable granted here
// This assignment is illegal because the field x is not
@ -21,11 +21,11 @@ fn a() {
}
fn b() {
let mut p = {x: 3, mut y: 4};
let _q = &p;
let mut p = point {x: 3, mut y: 4};
// This assignment is legal because `y` is inherently mutable (and
// hence &_q.y is &mut int).
let _q = &p;
p.y = 5;
}
@ -33,9 +33,9 @@ fn c() {
// this is sort of the opposite. We take a loan to the interior of `p`
// and then try to overwrite `p` as a whole.
let mut p = {x: 3, mut y: 4};
let mut p = point {x: 3, mut y: 4};
let _q = &p.y; //~ NOTE loan of mutable local variable granted here
p = {x: 5, mut y: 7};//~ ERROR assigning to mutable local variable prohibited due to outstanding loan
p = point {x: 5, mut y: 7};//~ ERROR assigning to mutable local variable prohibited due to outstanding loan
copy p;
}
@ -43,7 +43,7 @@ fn d() {
// just for completeness's sake, the easy case, where we take the
// address of a subcomponent and then modify that subcomponent:
let mut p = {x: 3, mut y: 4};
let mut p = point {x: 3, mut y: 4};
let _q = &p.y; //~ NOTE loan of mutable field granted here
p.y = 5; //~ ERROR assigning to mutable field prohibited due to outstanding loan
copy p;

View File

@ -9,11 +9,23 @@
// except according to those terms.
fn main() {
let mut p = {a: 1,
w: {a: 1},
x: @{a: 1},
y: @const {a: 1},
z: @mut{a: 1}};
struct A {
a: int,
w: B,
x: @B,
y: @const B,
z: @mut B
}
struct B {
a: int
}
let mut p = A {
a: 1,
w: B {a: 1},
x: @B {a: 1},
y: @const B {a: 1},
z: @mut B {a: 1}
};
// even though `x` is not declared as a mutable field,
// `p` as a whole is mutable, so it can be modified.

View File

@ -12,8 +12,12 @@ fn each<T>(x: &[T], op: fn(elem: &T) -> bool) {
uint::range(0, x.len(), |i| op(&x[i]));
}
struct A {
mut a: int
}
fn main() {
let x = [{mut a: 0}];
let x = [A {mut a: 0}];
for each(x) |y| {
let z = &y.a; //~ ERROR illegal borrow unless pure
x[0].a = 10; //~ NOTE impure due to assigning to mutable field

View File

@ -13,7 +13,10 @@ fn each<T>(x: &[T], op: fn(elem: &T) -> bool) {
}
fn main() {
let x = ~[{mut a: 0}];
struct A {
mut a: int
}
let x = ~[A {mut a: 0}];
for each(x) |y| {
let z = &y.a; //~ ERROR illegal borrow unless pure
x[0].a = 10; //~ NOTE impure due to assigning to mutable field

View File

@ -8,7 +8,7 @@
// option. This file may not be copied, modified, or distributed
// except according to those terms.
type point = { x: int, y: int };
struct point { x: int, y: int }
trait methods {
fn impurem();
@ -27,7 +27,7 @@ impl methods for point {
}
fn a() {
let mut p = {x: 3, y: 4};
let mut p = point {x: 3, y: 4};
// Here: it's ok to call even though receiver is mutable, because we
// can loan it out.
@ -41,7 +41,7 @@ fn a() {
}
fn b() {
let mut p = {x: 3, y: 4};
let mut p = point {x: 3, y: 4};
// Here I create an outstanding loan and check that we get conflicts:
@ -56,7 +56,7 @@ fn b() {
fn c() {
// Loaning @mut as & is considered legal due to dynamic checks:
let q = @mut {x: 3, y: 4};
let q = @mut point {x: 3, y: 4};
q.purem();
q.impurem();
}

View File

@ -8,12 +8,16 @@
// option. This file may not be copied, modified, or distributed
// except according to those terms.
struct node_ {
mut a: ~cycle
}
enum cycle {
node({mut a: ~cycle}),
node(node_),
empty
}
fn main() {
let x = ~node({mut a: ~empty});
let x = ~node(node_ {mut a: ~empty});
// Create a cycle!
match *x { //~ NOTE loan of immutable local variable granted here
node(ref y) => {

View File

@ -16,12 +16,16 @@ fn local() {
}
fn local_rec() {
let mut v = {f: ~3};
struct F { f: ~int }
let mut v = F {f: ~3};
borrow(v.f);
}
fn local_recs() {
let mut v = {f: {g: {h: ~3}}};
struct F { f: G }
struct G { g: H }
struct H { h: ~int }
let mut v = F {f: G {g: H {h: ~3}}};
borrow(v.f.g.h);
}

View File

@ -8,10 +8,10 @@
// option. This file may not be copied, modified, or distributed
// except according to those terms.
type boxedFn = { theFn: fn () -> uint };
struct boxedFn { theFn: fn~() -> uint }
fn createClosure (closedUint: uint) -> boxedFn {
{ theFn: fn@ () -> uint { closedUint } } //~ ERROR mismatched types
boxedFn {theFn: fn@ () -> uint { closedUint }} //~ ERROR mismatched types
}
fn main () {

View File

@ -1,16 +0,0 @@
// Copyright 2012 The Rust Project Developers. See the COPYRIGHT
// file at the top-level directory of this distribution and at
// http://rust-lang.org/COPYRIGHT.
//
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
// option. This file may not be copied, modified, or distributed
// except according to those terms.
type cat = {cat_name: ~str, cat_name: int}; //~ ERROR Duplicate field name cat_name
fn main()
{
io::println(int::str({x: 1, x: 2}.x)); //~ ERROR Duplicate field name x
}

View File

@ -25,20 +25,23 @@ fn to_foo<T:Copy>(t: T) {
// the type of foo includes a region which will be resolved to
// the fn body itself.
let v = &3;
let x = {f:t} as foo;
struct F<T> { f: T }
let x = F {f:t} as foo;
assert x.foo(v) == 3;
}
fn to_foo_2<T:Copy>(t: T) -> foo {
// Not OK---T may contain borrowed ptrs and it is going to escape
// as part of the returned foo value
{f:t} as foo //~ ERROR value may contain borrowed pointers; use `&static` bound
struct F<T> { f: T }
F {f:t} as foo //~ ERROR value may contain borrowed pointers; use `&static` bound
}
fn to_foo_3<T:Copy + &static>(t: T) -> foo {
// OK---T may escape as part of the returned foo value, but it is
// owned and hence does not contain borrowed ptrs
{f:t} as foo
struct F<T> { f: T }
F {f:t} as foo
}
fn main() {

View File

@ -10,10 +10,10 @@
// except according to those terms.
type point = {x: int, y: int};
struct point {x: int, y: int}
fn main() {
let mut origin: point;
origin = {x: 10,.. origin}; //~ ERROR use of possibly uninitialized variable: `origin`
origin = point {x: 10,.. origin}; //~ ERROR use of possibly uninitialized variable: `origin`
copy origin;
}

View File

@ -1,20 +0,0 @@
// Copyright 2012 The Rust Project Developers. See the COPYRIGHT
// file at the top-level directory of this distribution and at
// http://rust-lang.org/COPYRIGHT.
//
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
// option. This file may not be copied, modified, or distributed
// except according to those terms.
fn main() {
fn f(&&v: {const field: int}) {
// This shouldn't be possible
v.field = 1 //~ ERROR assigning to const field
}
let v = {field: 0};
f(v);
}

View File

@ -41,8 +41,11 @@ fn r2(x:@mut int) -> r2 {
}
fn main() {
foo({f: 3});
foo({mut f: 3}); //~ ERROR does not fulfill `Const`
struct A<T> { f: T }
struct B<T> { mut f: T }
foo(A {f: 3});
foo(B {mut f: 3}); //~ ERROR does not fulfill `Const`
foo(~[1]);
foo(~[mut 1]); //~ ERROR does not fulfill `Const`
foo(~1);
@ -51,5 +54,5 @@ fn main() {
foo(@mut 1); //~ ERROR does not fulfill `Const`
foo(r(1)); // this is okay now.
foo(r2(@mut 1)); //~ ERROR does not fulfill `Const`
foo({f: {mut f: 1}}); //~ ERROR does not fulfill `Const`
foo(A {f: B {mut f: 1}}); //~ ERROR does not fulfill `Const`
}

View File

@ -51,11 +51,6 @@ fn obsolete_with() {
//~^ ERROR obsolete syntax: with
let c = S { foo: (), with a };
//~^ ERROR obsolete syntax: with
let a = { foo: (), bar: () };
let b = { foo: () with a };
//~^ ERROR obsolete syntax: with
let c = { foo: (), with a };
//~^ ERROR obsolete syntax: with
}
fn obsolete_moves() {

View File

@ -27,8 +27,9 @@ fn r(i: @mut int) -> r {
fn main() {
let i = @mut 0;
{
struct A { y: r }
// Can't do this copy
let x = ~~~{y: r(i)};
let x = ~~~A {y: r(i)};
let _z = copy x; //~ ERROR copying a value of non-copyable type
log(debug, x);
}

View File

@ -1,33 +0,0 @@
// Copyright 2012 The Rust Project Developers. See the COPYRIGHT
// file at the top-level directory of this distribution and at
// http://rust-lang.org/COPYRIGHT.
//
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
// option. This file may not be copied, modified, or distributed
// except according to those terms.
struct my_resource {
x: int,
}
impl Drop for my_resource {
fn finalize(&self) {
log(error, self.x);
}
}
fn my_resource(x: int) -> my_resource {
my_resource {
x: x
}
}
fn main() {
{
let a = {x: 0, y: my_resource(20)};
let b = {x: 2,.. copy a}; //~ ERROR copying a value of non-copyable type
log(error, (a, b));
}
}

View File

@ -8,14 +8,14 @@
// option. This file may not be copied, modified, or distributed
// except according to those terms.
type ctxt = { v: uint };
struct ctxt { v: uint }
trait get_ctxt {
// Here the `&` is bound in the method definition:
fn get_ctxt() -> &ctxt;
}
type has_ctxt = { c: &ctxt };
struct has_ctxt { c: &ctxt }
impl get_ctxt for has_ctxt {
@ -32,7 +32,7 @@ fn get_v(gc: get_ctxt) -> uint {
}
fn main() {
let ctxt = { v: 22u };
let hc = { c: &ctxt };
let ctxt = ctxt { v: 22u };
let hc = has_ctxt { c: &ctxt };
assert get_v(hc as get_ctxt) == 22u;
}

View File

@ -8,21 +8,21 @@
// option. This file may not be copied, modified, or distributed
// except according to those terms.
type ctxt = { v: uint };
struct ctxt { v: uint }
trait get_ctxt {
fn get_ctxt() -> &self/ctxt;
}
type has_ctxt = { c: &ctxt };
struct has_ctxt { c: &ctxt }
impl get_ctxt for has_ctxt {
fn get_ctxt() -> &self/ctxt { self.c }
}
fn make_gc() -> get_ctxt {
let ctxt = { v: 22u };
let hc = { c: &ctxt }; //~ ERROR illegal borrow
let ctxt = ctxt { v: 22u };
let hc = has_ctxt { c: &ctxt }; //~ ERROR illegal borrow
return hc as get_ctxt;
}

View File

@ -8,21 +8,22 @@
// option. This file may not be copied, modified, or distributed
// except according to those terms.
enum box_impl<T> = {
struct box<T> {
mut f: T
};
}
enum box_impl<T> = box<T>;
fn set_box_impl<T>(b: box_impl<@const T>, v: @const T) {
b.f = v;
}
fn main() {
let b = box_impl::<@int>({mut f: @3});
let b = box_impl::<@int>(box::<@int> {mut f: @3});
set_box_impl(b, @mut 5);
//~^ ERROR values differ in mutability
// No error when type of parameter actually IS @const int
let x: @const int = @3; // only way I could find to upcast
let b = box_impl::<@const int>({mut f: x});
let b = box_impl::<@const int>(box::<@const int>{mut f: x});
set_box_impl(b, @mut 5);
}

View File

@ -13,9 +13,11 @@ trait box_trait<T> {
fn set(t: T);
}
enum box_impl<T> = {
struct box<T> {
mut f: T
};
}
enum box_impl<T> = box<T>;
impl<T:Copy> box_trait<T> for box_impl<T> {
fn get() -> T { return self.f; }
@ -31,7 +33,7 @@ fn set_box_impl<T>(b: box_impl<@const T>, v: @const T) {
}
fn main() {
let b = box_impl::<@int>({mut f: @3});
let b = box_impl::<@int>(box::<@int> {mut f: @3});
set_box_trait(b as box_trait::<@int>, @mut 5);
//~^ ERROR values differ in mutability
set_box_impl(b, @mut 5);

View File

@ -14,8 +14,6 @@
// xfail-win32
#[legacy_records];
extern mod std;
use std::timer::sleep;
use std::uv;

View File

@ -10,8 +10,6 @@
// option. This file may not be copied, modified, or distributed
// except according to those terms.
#[legacy_records];
extern mod std;
use std::timer::sleep;
use std::uv;

View File

@ -17,21 +17,20 @@
// This was generated initially by the pipe compiler, but it's been
// modified in hopefully straightforward ways.
#[legacy_records];
mod pingpong {
use core::pipes::*;
use core::ptr;
pub type packets = {
pub struct Packets {
ping: Packet<ping>,
pong: Packet<pong>,
};
}
pub fn init() -> (client::ping, server::ping) {
let buffer = ~Buffer {
header: BufferHeader(),
data: {
data: Packets {
ping: mk_packet::<ping>(),
pong: mk_packet::<pong>()
}
@ -59,16 +58,16 @@ mod pingpong {
}
}
pub type ping = pipes::SendPacketBuffered<::pingpong::ping,
::pingpong::packets>;
::pingpong::Packets>;
pub type pong = pipes::RecvPacketBuffered<::pingpong::pong,
::pingpong::packets>;
::pingpong::Packets>;
}
pub mod server {
use core::pipes::*;
use core::ptr;
pub type ping = pipes::RecvPacketBuffered<::pingpong::ping,
::pingpong::packets>;
::pingpong::Packets>;
pub fn pong(+pipe: pong) -> ping {
{
let b = pipe.reuse_buffer();
@ -80,7 +79,7 @@ mod pingpong {
}
}
pub type pong = pipes::SendPacketBuffered<::pingpong::pong,
::pingpong::packets>;
::pingpong::Packets>;
}
}

View File

@ -12,8 +12,6 @@
// An example to make sure the protocol parsing syntax extension works.
#[legacy_records];
use core::option;
proto! pingpong (

View File

@ -15,8 +15,6 @@
// Code is easier to write in emacs, and it's good to be sure all the
// code samples compile (or not) as they should.
#[legacy_records];
use double_buffer::client::*;
use double_buffer::give_buffer;

View File

@ -13,8 +13,6 @@
// xfail-pretty
// xfail-win32
#[legacy_records];
extern mod std;
use std::timer::sleep;
use std::uv;

View File

@ -10,8 +10,6 @@
// option. This file may not be copied, modified, or distributed
// except according to those terms.
#[legacy_records];
extern mod std;
use std::timer::sleep;
use std::uv;