about summary refs log tree commit diff
diff options
context:
space:
mode:
-rw-r--r--src/rustc/metadata/common.rs4
-rw-r--r--src/rustc/metadata/cstore.rs4
-rw-r--r--src/rustc/metadata/decoder.rs25
-rw-r--r--src/rustc/metadata/encoder.rs50
4 files changed, 57 insertions, 26 deletions
diff --git a/src/rustc/metadata/common.rs b/src/rustc/metadata/common.rs
index 4d534efea35..b74d1149d76 100644
--- a/src/rustc/metadata/common.rs
+++ b/src/rustc/metadata/common.rs
@@ -64,6 +64,10 @@ const tag_crate_hash: uint = 0x28u;
 
 const tag_parent_item: uint = 0x29u;
 
+const tag_crate_dep_name: uint = 0x2au;
+const tag_crate_dep_hash: uint = 0x2bu;
+const tag_crate_dep_vers: uint = 0x2cu;
+
 const tag_mod_impl: uint = 0x30u;
 
 const tag_item_method: uint = 0x31u;
diff --git a/src/rustc/metadata/cstore.rs b/src/rustc/metadata/cstore.rs
index fd7f82a7bc7..370d09e0017 100644
--- a/src/rustc/metadata/cstore.rs
+++ b/src/rustc/metadata/cstore.rs
@@ -88,9 +88,7 @@ fn get_crate_hash(cstore: cstore, cnum: ast::crate_num) -> str {
 
 fn get_crate_vers(cstore: cstore, cnum: ast::crate_num) -> str {
     let cdata = get_crate_data(cstore, cnum);
-    let attrs = decoder::get_crate_attributes(cdata.data);
-    ret option::get(attr::meta_item_value_from_list(
-        attr::find_linkage_metas(attrs), "vers"));
+    ret decoder::get_crate_vers(cdata.data);
 }
 
 fn set_crate_data(cstore: cstore, cnum: ast::crate_num,
diff --git a/src/rustc/metadata/decoder.rs b/src/rustc/metadata/decoder.rs
index c40e8d8f609..015f9d27258 100644
--- a/src/rustc/metadata/decoder.rs
+++ b/src/rustc/metadata/decoder.rs
@@ -33,6 +33,7 @@ export list_crate_metadata;
 export crate_dep;
 export get_crate_deps;
 export get_crate_hash;
+export get_crate_vers;
 export get_impls_for_mod;
 export get_iface_methods;
 export get_crate_module_paths;
@@ -579,16 +580,22 @@ fn get_crate_attributes(data: @[u8]) -> [ast::attribute] {
     ret get_attributes(ebml::doc(data));
 }
 
-type crate_dep = {cnum: ast::crate_num, ident: str};
+type crate_dep = {cnum: ast::crate_num, name: ast::ident,
+                  vers: str, hash: str};
 
 fn get_crate_deps(data: @[u8]) -> [crate_dep] {
     let mut deps: [crate_dep] = [];
     let cratedoc = ebml::doc(data);
     let depsdoc = ebml::get_doc(cratedoc, tag_crate_deps);
     let mut crate_num = 1;
+    fn docstr(doc: ebml::doc, tag_: uint) -> str {
+        str::from_bytes(ebml::doc_data(ebml::get_doc(doc, tag_)))
+    }
     ebml::tagged_docs(depsdoc, tag_crate_dep) {|depdoc|
-        let depname = str::from_bytes(ebml::doc_data(depdoc));
-        deps += [{cnum: crate_num, ident: depname}];
+        deps += [{cnum: crate_num,
+                  name: docstr(depdoc, tag_crate_dep_name),
+                  vers: docstr(depdoc, tag_crate_dep_vers),
+                  hash: docstr(depdoc, tag_crate_dep_hash)}];
         crate_num += 1;
     };
     ret deps;
@@ -598,7 +605,8 @@ fn list_crate_deps(data: @[u8], out: io::writer) {
     out.write_str("=External Dependencies=\n");
 
     for get_crate_deps(data).each {|dep|
-        out.write_str(#fmt["%d %s\n", dep.cnum, dep.ident]);
+        out.write_str(#fmt["%d %s-%s-%s\n",
+                           dep.cnum, dep.name, dep.hash, dep.vers]);
     }
 
     out.write_str("\n");
@@ -610,6 +618,15 @@ fn get_crate_hash(data: @[u8]) -> str {
     ret str::from_bytes(ebml::doc_data(hashdoc));
 }
 
+fn get_crate_vers(data: @[u8]) -> str {
+    let attrs = decoder::get_crate_attributes(data);
+    ret alt attr::meta_item_value_from_list(
+        attr::find_linkage_metas(attrs), "vers") {
+      some(ver) { ver }
+      none { "0.0" }
+    };
+}
+
 fn list_crate_items(bytes: @[u8], md: ebml::doc, out: io::writer) {
     out.write_str("=Items=\n");
     let items = ebml::get_doc(md, tag_items);
diff --git a/src/rustc/metadata/encoder.rs b/src/rustc/metadata/encoder.rs
index 5a8f26c6d8d..197f8be6f02 100644
--- a/src/rustc/metadata/encoder.rs
+++ b/src/rustc/metadata/encoder.rs
@@ -907,47 +907,59 @@ fn synthesize_crate_attrs(ecx: @encode_ctxt, crate: @crate) -> [attribute] {
 
 fn encode_crate_deps(ebml_w: ebml::writer, cstore: cstore::cstore) {
 
-    fn get_ordered_names(cstore: cstore::cstore) -> [str] {
+    fn get_ordered_deps(cstore: cstore::cstore) -> [decoder::crate_dep] {
         type hashkv = @{key: crate_num, val: cstore::crate_metadata};
-        type numname = {crate: crate_num, ident: str};
+        type numdep = decoder::crate_dep;
 
-        // Pull the cnums and names out of cstore
-        let mut pairs: [mut numname] = [mut];
+        // Pull the cnums and name,vers,hash out of cstore
+        let mut deps: [mut numdep] = [mut];
         cstore::iter_crate_data(cstore) {|key, val|
-            pairs += [mut {crate: key, ident: val.name}];
+            let dep = {cnum: key, name: val.name,
+                       vers: decoder::get_crate_vers(val.data),
+                       hash:  decoder::get_crate_hash(val.data)};
+            deps += [mut dep];
         };
 
         // Sort by cnum
-        fn lteq(kv1: numname, kv2: numname) -> bool { kv1.crate <= kv2.crate }
-        std::sort::quick_sort(lteq, pairs);
+        fn lteq(kv1: numdep, kv2: numdep) -> bool { kv1.cnum <= kv2.cnum }
+        std::sort::quick_sort(lteq, deps);
 
         // Sanity-check the crate numbers
         let mut expected_cnum = 1;
-        for pairs.each {|n|
-            assert (n.crate == expected_cnum);
+        for deps.each {|n|
+            assert (n.cnum == expected_cnum);
             expected_cnum += 1;
         }
 
-        // Return just the names
-        fn name(kv: numname) -> str { kv.ident }
         // mut -> immutable hack for vec::map
-        let immpairs = vec::slice(pairs, 0u, vec::len(pairs));
-        ret vec::map(immpairs, name);
+        ret vec::slice(deps, 0u, vec::len(deps));
     }
 
-    // We're just going to write a list of crate names, with the assumption
-    // that they are numbered 1 to n.
+    // We're just going to write a list of crate 'name-hash-version's, with
+    // the assumption that they are numbered 1 to n.
     // FIXME: This is not nearly enough to support correct versioning
     // but is enough to get transitive crate dependencies working.
     ebml_w.start_tag(tag_crate_deps);
-    for get_ordered_names(cstore).each {|cname|
-        ebml_w.start_tag(tag_crate_dep);
-        ebml_w.writer.write(str::bytes(cname));
-        ebml_w.end_tag();
+    for get_ordered_deps(cstore).each {|dep|
+        encode_crate_dep(ebml_w, dep);
     }
     ebml_w.end_tag();
 }
 
+fn encode_crate_dep(ebml_w: ebml::writer, dep: decoder::crate_dep) {
+    ebml_w.start_tag(tag_crate_dep);
+    ebml_w.start_tag(tag_crate_dep_name);
+    ebml_w.writer.write(str::bytes(dep.name));
+    ebml_w.end_tag();
+    ebml_w.start_tag(tag_crate_dep_vers);
+    ebml_w.writer.write(str::bytes(dep.vers));
+    ebml_w.end_tag();
+    ebml_w.start_tag(tag_crate_dep_hash);
+    ebml_w.writer.write(str::bytes(dep.hash));
+    ebml_w.end_tag();
+    ebml_w.end_tag();
+}
+
 fn encode_hash(ebml_w: ebml::writer, hash: str) {
     ebml_w.start_tag(tag_crate_hash);
     ebml_w.writer.write(str::bytes(hash));