about summary refs log tree commit diff
path: root/src/libsyntax
diff options
context:
space:
mode:
authorPatrick Walton <pcwalton@mimiga.net>2012-10-24 14:36:00 -0700
committerPatrick Walton <pcwalton@mimiga.net>2012-10-25 11:49:26 -0700
commit599b4208fb64b18aaddf9add5d8ce2319c7e7cfe (patch)
tree3b54245720a1450d324e0ae41756c5e35fe10bd0 /src/libsyntax
parentce23a9992542f0c82e0f32c427b572caae790754 (diff)
downloadrust-599b4208fb64b18aaddf9add5d8ce2319c7e7cfe.tar.gz
rust-599b4208fb64b18aaddf9add5d8ce2319c7e7cfe.zip
rustc: Translate tuple struct constructors
Diffstat (limited to 'src/libsyntax')
-rw-r--r--src/libsyntax/ast.rs2
-rw-r--r--src/libsyntax/ast_map.rs17
-rw-r--r--src/libsyntax/ast_util.rs6
-rw-r--r--src/libsyntax/fold.rs4
-rw-r--r--src/libsyntax/parse/parser.rs9
-rw-r--r--src/libsyntax/parse/token.rs1
6 files changed, 34 insertions, 5 deletions
diff --git a/src/libsyntax/ast.rs b/src/libsyntax/ast.rs
index e25fb470bb9..60f22f1b844 100644
--- a/src/libsyntax/ast.rs
+++ b/src/libsyntax/ast.rs
@@ -1480,7 +1480,7 @@ type struct_def = {
     dtor: Option<class_dtor>,
     /* ID of the constructor. This is only used for tuple- or enum-like
      * structs. */
-    ctor_id: node_id
+    ctor_id: Option<node_id>
 };
 
 /*
diff --git a/src/libsyntax/ast_map.rs b/src/libsyntax/ast_map.rs
index bcda838b248..e63de5aefeb 100644
--- a/src/libsyntax/ast_map.rs
+++ b/src/libsyntax/ast_map.rs
@@ -74,6 +74,7 @@ enum ast_node {
     // Destructor for a class
     node_dtor(~[ty_param], @class_dtor, def_id, @path),
     node_block(blk),
+    node_struct_ctor(@struct_def, @item, @path)
 }
 
 type map = std::map::HashMap<node_id, ast_node>;
@@ -284,6 +285,19 @@ fn map_struct_def(struct_def: @ast::struct_def, parent_node: ast_node,
     for vec::each(struct_def.methods) |m| {
         map_method(d_id, p, *m, cx);
     }
+    // If this is a tuple-like struct, register the constructor.
+    match struct_def.ctor_id {
+        None => {}
+        Some(ctor_id) => {
+            match parent_node {
+                node_item(item, _) => {
+                    cx.map.insert(ctor_id,
+                                  node_struct_ctor(struct_def, item, p));
+                }
+                _ => fail ~"struct def parent wasn't an item"
+            }
+        }
+    }
 }
 
 fn map_view_item(vi: @view_item, cx: ctx, _v: vt) {
@@ -375,6 +389,9 @@ fn node_id_to_str(map: map, id: node_id, itr: @ident_interner) -> ~str {
       Some(node_block(_)) => {
         fmt!("block")
       }
+      Some(node_struct_ctor(*)) => {
+        fmt!("struct_ctor")
+      }
     }
 }
 // Local Variables:
diff --git a/src/libsyntax/ast_util.rs b/src/libsyntax/ast_util.rs
index 6fd84c3317f..ea49cce5047 100644
--- a/src/libsyntax/ast_util.rs
+++ b/src/libsyntax/ast_util.rs
@@ -589,6 +589,12 @@ fn view_path_id(p: @view_path) -> node_id {
     }
 }
 
+/// Returns true if the given struct def is tuple-like; i.e. that its fields
+/// are unnamed.
+fn struct_def_is_tuple_like(struct_def: @ast::struct_def) -> bool {
+    struct_def.ctor_id.is_some()
+}
+
 // Local Variables:
 // mode: rust
 // fill-column: 78;
diff --git a/src/libsyntax/fold.rs b/src/libsyntax/fold.rs
index d1b97549225..e2b6e6daa2f 100644
--- a/src/libsyntax/fold.rs
+++ b/src/libsyntax/fold.rs
@@ -281,7 +281,7 @@ fn fold_struct_def(struct_def: @ast::struct_def, fld: ast_fold)
         fields: vec::map(struct_def.fields, |f| fold_struct_field(*f, fld)),
         methods: vec::map(struct_def.methods, |m| fld.fold_method(*m)),
         dtor: dtor,
-        ctor_id: fld.new_id(struct_def.ctor_id)
+        ctor_id: option::map(&struct_def.ctor_id, |cid| fld.new_id(*cid))
     };
 }
 
@@ -565,7 +565,7 @@ fn noop_fold_variant(v: variant_, fld: ast_fold) -> variant_ {
                 methods: vec::map(struct_def.methods,
                                   |m| fld.fold_method(*m)),
                 dtor: dtor,
-                ctor_id: fld.new_id(struct_def.ctor_id)
+                ctor_id: option::map(&struct_def.ctor_id, |c| fld.new_id(*c))
             })
         }
 
diff --git a/src/libsyntax/parse/parser.rs b/src/libsyntax/parse/parser.rs
index 1af516424de..23ddf61606d 100644
--- a/src/libsyntax/parse/parser.rs
+++ b/src/libsyntax/parse/parser.rs
@@ -2659,9 +2659,11 @@ impl Parser {
         let mut fields: ~[@struct_field];
         let mut methods: ~[@method] = ~[];
         let mut the_dtor: Option<(blk, ~[attribute], codemap::span)> = None;
+        let is_tuple_like;
 
         if self.eat(token::LBRACE) {
             // It's a record-like struct.
+            is_tuple_like = false;
             fields = ~[];
             while self.token != token::RBRACE {
                 match self.parse_class_item() {
@@ -2694,6 +2696,7 @@ impl Parser {
             self.bump();
         } else if self.token == token::LPAREN {
             // It's a tuple-like struct.
+            is_tuple_like = true;
             fields = do self.parse_unspanned_seq(token::LPAREN, token::RPAREN,
                                                  seq_sep_trailing_allowed
                                                     (token::COMMA)) |p| {
@@ -2708,6 +2711,7 @@ impl Parser {
             self.expect(token::SEMI);
         } else if self.eat(token::SEMI) {
             // It's a unit-like struct.
+            is_tuple_like = true;
             fields = ~[];
         } else {
             self.fatal(fmt!("expected `{`, `(`, or `;` after struct name \
@@ -2723,13 +2727,14 @@ impl Parser {
                     body: d_body},
              span: d_s}};
         let _ = self.get_id();  // XXX: Workaround for crazy bug.
+        let new_id = self.get_id();
         (class_name,
          item_class(@{
              traits: traits,
              fields: move fields,
              methods: move methods,
              dtor: actual_dtor,
-             ctor_id: self.get_id()
+             ctor_id: if is_tuple_like { Some(new_id) } else { None }
          }, ty_params),
          None)
     }
@@ -3076,7 +3081,7 @@ impl Parser {
             fields: move fields,
             methods: move methods,
             dtor: actual_dtor,
-            ctor_id: self.get_id()
+            ctor_id: Some(self.get_id())
         };
     }
 
diff --git a/src/libsyntax/parse/token.rs b/src/libsyntax/parse/token.rs
index 5151fd1bac8..53c1ce1c7f5 100644
--- a/src/libsyntax/parse/token.rs
+++ b/src/libsyntax/parse/token.rs
@@ -311,6 +311,7 @@ mod special_idents {
     const static : ident = ident { repr: 31u };
     const intrinsic : ident = ident { repr: 32u };
     const clownshoes_foreign_mod: ident = ident { repr: 33 };
+    const unnamed_field: ident = ident { repr: 34 };
 }
 
 struct ident_interner {