diff options
Diffstat (limited to 'src/libstd/ebml.rs')
| -rw-r--r-- | src/libstd/ebml.rs | 818 |
1 files changed, 754 insertions, 64 deletions
diff --git a/src/libstd/ebml.rs b/src/libstd/ebml.rs index 2598e96a141..41c5a0f7690 100644 --- a/src/libstd/ebml.rs +++ b/src/libstd/ebml.rs @@ -36,13 +36,27 @@ pub struct TaggedDoc { } pub enum EbmlEncoderTag { - EsUint, EsU64, EsU32, EsU16, EsU8, - EsInt, EsI64, EsI32, EsI16, EsI8, - EsBool, - EsStr, - EsF64, EsF32, EsFloat, - EsEnum, EsEnumVid, EsEnumBody, - EsVec, EsVecLen, EsVecElt, + EsUint, // 0 + EsU64, // 1 + EsU32, // 2 + EsU16, // 3 + EsU8, // 4 + EsInt, // 5 + EsI64, // 6 + EsI32, // 7 + EsI16, // 8 + EsI8, // 9 + EsBool, // 10 + EsStr, // 11 + EsF64, // 12 + EsF32, // 13 + EsFloat, // 14 + EsEnum, // 15 + EsEnumVid, // 16 + EsEnumBody, // 17 + EsVec, // 18 + EsVecLen, // 19 + EsVecElt, // 20 EsOpaque, @@ -249,17 +263,27 @@ pub mod reader { pub fn doc_as_i32(d: Doc) -> i32 { doc_as_u32(d) as i32 } pub fn doc_as_i64(d: Doc) -> i64 { doc_as_u64(d) as i64 } - + #[cfg(stage0)] pub struct Decoder { priv mut parent: Doc, priv mut pos: uint, } + #[cfg(not(stage0))] + pub struct Decoder { + priv parent: Doc, + priv pos: uint, + } + pub fn Decoder(d: Doc) -> Decoder { - Decoder { parent: d, pos: d.start } + Decoder { + parent: d, + pos: d.start + } } priv impl Decoder { + #[cfg(stage0)] fn _check_label(&self, lbl: &str) { if self.pos < self.parent.end { let TaggedDoc { tag: r_tag, doc: r_doc } = @@ -269,13 +293,33 @@ pub mod reader { self.pos = r_doc.end; let str = doc_as_str(r_doc); if lbl != str { - fail!(fmt!("Expected label %s but found %s", lbl, - str)); + fail!(fmt!("Expected label %s but found %s", + lbl, + str)); + } + } + } + } + + #[cfg(not(stage0))] + fn _check_label(&mut self, lbl: &str) { + if self.pos < self.parent.end { + let TaggedDoc { tag: r_tag, doc: r_doc } = + doc_at(self.parent.data, self.pos); + + if r_tag == (EsLabel as uint) { + self.pos = r_doc.end; + let str = doc_as_str(r_doc); + if lbl != str { + fail!(fmt!("Expected label %s but found %s", + lbl, + str)); } } } } + #[cfg(stage0)] fn next_doc(&self, exp_tag: EbmlEncoderTag) -> Doc { debug!(". next_doc(exp_tag=%?)", exp_tag); if self.pos >= self.parent.end { @@ -298,6 +342,30 @@ pub mod reader { r_doc } + #[cfg(not(stage0))] + fn next_doc(&mut self, exp_tag: EbmlEncoderTag) -> Doc { + debug!(". next_doc(exp_tag=%?)", exp_tag); + if self.pos >= self.parent.end { + fail!(~"no more documents in current node!"); + } + let TaggedDoc { tag: r_tag, doc: r_doc } = + doc_at(self.parent.data, self.pos); + debug!("self.parent=%?-%? self.pos=%? r_tag=%? r_doc=%?-%?", + copy self.parent.start, copy self.parent.end, + copy self.pos, r_tag, r_doc.start, r_doc.end); + if r_tag != (exp_tag as uint) { + fail!(fmt!("expected EBML doc with tag %? but found tag %?", + exp_tag, r_tag)); + } + if r_doc.end > self.parent.end { + fail!(fmt!("invalid EBML, child extends to 0x%x, \ + parent to 0x%x", r_doc.end, self.parent.end)); + } + self.pos = r_doc.end; + r_doc + } + + #[cfg(stage0)] fn push_doc<T>(&self, d: Doc, f: &fn() -> T) -> T { let old_parent = self.parent; let old_pos = self.pos; @@ -309,21 +377,58 @@ pub mod reader { r } + #[cfg(not(stage0))] + fn push_doc<T>(&mut self, d: Doc, f: &fn() -> T) -> T { + let old_parent = self.parent; + let old_pos = self.pos; + self.parent = d; + self.pos = d.start; + let r = f(); + self.parent = old_parent; + self.pos = old_pos; + r + } + + #[cfg(stage0)] fn _next_uint(&self, exp_tag: EbmlEncoderTag) -> uint { let r = doc_as_u32(self.next_doc(exp_tag)); debug!("_next_uint exp_tag=%? result=%?", exp_tag, r); r as uint } + + #[cfg(not(stage0))] + fn _next_uint(&mut self, exp_tag: EbmlEncoderTag) -> uint { + let r = doc_as_u32(self.next_doc(exp_tag)); + debug!("_next_uint exp_tag=%? result=%?", exp_tag, r); + r as uint + } } pub impl Decoder { + #[cfg(stage0)] fn read_opaque<R>(&self, op: &fn(Doc) -> R) -> R { do self.push_doc(self.next_doc(EsOpaque)) { op(copy self.parent) } } + + #[cfg(not(stage0))] + fn read_opaque<R>(&mut self, op: &fn(&mut Decoder, Doc) -> R) -> R { + let doc = self.next_doc(EsOpaque); + + let (old_parent, old_pos) = (self.parent, self.pos); + self.parent = doc; + self.pos = doc.start; + + let result = op(self, doc); + + self.parent = old_parent; + self.pos = old_pos; + result + } } + #[cfg(stage0)] impl serialize::Decoder for Decoder { fn read_nil(&self) -> () { () } @@ -339,10 +444,18 @@ pub mod reader { v as uint } - fn read_i64(&self) -> i64 { doc_as_u64(self.next_doc(EsI64)) as i64 } - fn read_i32(&self) -> i32 { doc_as_u32(self.next_doc(EsI32)) as i32 } - fn read_i16(&self) -> i16 { doc_as_u16(self.next_doc(EsI16)) as i16 } - fn read_i8 (&self) -> i8 { doc_as_u8 (self.next_doc(EsI8 )) as i8 } + fn read_i64(&self) -> i64 { + doc_as_u64(self.next_doc(EsI64)) as i64 + } + fn read_i32(&self) -> i32 { + doc_as_u32(self.next_doc(EsI32)) as i32 + } + fn read_i16(&self) -> i16 { + doc_as_u16(self.next_doc(EsI16)) as i16 + } + fn read_i8 (&self) -> i8 { + doc_as_u8(self.next_doc(EsI8 )) as i8 + } fn read_int(&self) -> int { let v = doc_as_u64(self.next_doc(EsInt)) as i64; if v > (int::max_value as i64) || v < (int::min_value as i64) { @@ -351,8 +464,9 @@ pub mod reader { v as int } - fn read_bool(&self) -> bool { doc_as_u8(self.next_doc(EsBool)) - as bool } + fn read_bool(&self) -> bool { + doc_as_u8(self.next_doc(EsBool)) as bool + } fn read_f64(&self) -> f64 { fail!(~"read_f64()"); } fn read_f32(&self) -> f32 { fail!(~"read_f32()"); } @@ -367,7 +481,10 @@ pub mod reader { self.push_doc(self.next_doc(EsEnum), f) } - fn read_enum_variant<T>(&self, _names: &[&str], f: &fn(uint) -> T) -> T { + fn read_enum_variant<T>(&self, + _: &[&str], + f: &fn(uint) -> T) + -> T { debug!("read_enum_variant()"); let idx = self._next_uint(EsEnumVid); debug!(" idx=%u", idx); @@ -376,12 +493,17 @@ pub mod reader { } } - fn read_enum_variant_arg<T>(&self, idx: uint, f: &fn() -> T) -> T { + fn read_enum_variant_arg<T>(&self, + idx: uint, + f: &fn() -> T) -> T { debug!("read_enum_variant_arg(idx=%u)", idx); f() } - fn read_enum_struct_variant<T>(&self, _names: &[&str], f: &fn(uint) -> T) -> T { + fn read_enum_struct_variant<T>(&self, + _: &[&str], + f: &fn(uint) -> T) + -> T { debug!("read_enum_struct_variant()"); let idx = self._next_uint(EsEnumVid); debug!(" idx=%u", idx); @@ -390,32 +512,34 @@ pub mod reader { } } - fn read_enum_struct_variant_field<T>(&self, name: &str, idx: uint, f: &fn() -> T) -> T { + fn read_enum_struct_variant_field<T>(&self, + name: &str, + idx: uint, + f: &fn() -> T) + -> T { debug!("read_enum_struct_variant_arg(name=%?, idx=%u)", name, idx); f() } - fn read_struct<T>(&self, name: &str, _len: uint, f: &fn() -> T) -> T { + fn read_struct<T>(&self, + name: &str, + _: uint, + f: &fn() -> T) + -> T { debug!("read_struct(name=%s)", name); f() } - #[cfg(stage0)] - fn read_field<T>(&self, name: &str, idx: uint, f: &fn() -> T) -> T { + fn read_field<T>(&self, + name: &str, + idx: uint, + f: &fn() -> T) + -> T { debug!("read_field(name=%?, idx=%u)", name, idx); self._check_label(name); f() } - #[cfg(stage1)] - #[cfg(stage2)] - #[cfg(stage3)] - fn read_struct_field<T>(&self, name: &str, idx: uint, f: &fn() -> T) -> T { - debug!("read_struct_field(name=%?, idx=%u)", name, idx); - self._check_label(name); - f() - } - fn read_tuple<T>(&self, f: &fn(uint) -> T) -> T { debug!("read_tuple()"); self.read_seq(f) @@ -426,12 +550,18 @@ pub mod reader { self.read_seq_elt(idx, f) } - fn read_tuple_struct<T>(&self, name: &str, f: &fn(uint) -> T) -> T { + fn read_tuple_struct<T>(&self, + name: &str, + f: &fn(uint) -> T) + -> T { debug!("read_tuple_struct(name=%?)", name); self.read_tuple(f) } - fn read_tuple_struct_arg<T>(&self, idx: uint, f: &fn() -> T) -> T { + fn read_tuple_struct_arg<T>(&self, + idx: uint, + f: &fn() -> T) + -> T { debug!("read_tuple_struct_arg(idx=%u)", idx); self.read_tuple_arg(idx, f) } @@ -478,6 +608,245 @@ pub mod reader { fail!(~"read_map_elt_val is unimplemented"); } } + + #[cfg(not(stage0))] + impl serialize::Decoder for Decoder { + fn read_nil(&mut self) -> () { () } + + fn read_u64(&mut self) -> u64 { doc_as_u64(self.next_doc(EsU64)) } + fn read_u32(&mut self) -> u32 { doc_as_u32(self.next_doc(EsU32)) } + fn read_u16(&mut self) -> u16 { doc_as_u16(self.next_doc(EsU16)) } + fn read_u8 (&mut self) -> u8 { doc_as_u8 (self.next_doc(EsU8 )) } + fn read_uint(&mut self) -> uint { + let v = doc_as_u64(self.next_doc(EsUint)); + if v > (::core::uint::max_value as u64) { + fail!(fmt!("uint %? too large for this architecture", v)); + } + v as uint + } + + fn read_i64(&mut self) -> i64 { + doc_as_u64(self.next_doc(EsI64)) as i64 + } + fn read_i32(&mut self) -> i32 { + doc_as_u32(self.next_doc(EsI32)) as i32 + } + fn read_i16(&mut self) -> i16 { + doc_as_u16(self.next_doc(EsI16)) as i16 + } + fn read_i8 (&mut self) -> i8 { + doc_as_u8(self.next_doc(EsI8 )) as i8 + } + fn read_int(&mut self) -> int { + let v = doc_as_u64(self.next_doc(EsInt)) as i64; + if v > (int::max_value as i64) || v < (int::min_value as i64) { + fail!(fmt!("int %? out of range for this architecture", v)); + } + v as int + } + + fn read_bool(&mut self) -> bool { + doc_as_u8(self.next_doc(EsBool)) as bool + } + + fn read_f64(&mut self) -> f64 { fail!(~"read_f64()"); } + fn read_f32(&mut self) -> f32 { fail!(~"read_f32()"); } + fn read_float(&mut self) -> float { fail!(~"read_float()"); } + fn read_char(&mut self) -> char { fail!(~"read_char()"); } + fn read_str(&mut self) -> ~str { doc_as_str(self.next_doc(EsStr)) } + + // Compound types: + fn read_enum<T>(&mut self, + name: &str, + f: &fn(&mut Decoder) -> T) + -> T { + debug!("read_enum(%s)", name); + self._check_label(name); + + let doc = self.next_doc(EsEnum); + + let (old_parent, old_pos) = (self.parent, self.pos); + self.parent = doc; + self.pos = self.parent.start; + + let result = f(self); + + self.parent = old_parent; + self.pos = old_pos; + result + } + + fn read_enum_variant<T>(&mut self, + _: &[&str], + f: &fn(&mut Decoder, uint) -> T) + -> T { + debug!("read_enum_variant()"); + let idx = self._next_uint(EsEnumVid); + debug!(" idx=%u", idx); + + let doc = self.next_doc(EsEnumBody); + + let (old_parent, old_pos) = (self.parent, self.pos); + self.parent = doc; + self.pos = self.parent.start; + + let result = f(self, idx); + + self.parent = old_parent; + self.pos = old_pos; + result + } + + fn read_enum_variant_arg<T>(&mut self, + idx: uint, + f: &fn(&mut Decoder) -> T) -> T { + debug!("read_enum_variant_arg(idx=%u)", idx); + f(self) + } + + fn read_enum_struct_variant<T>(&mut self, + _: &[&str], + f: &fn(&mut Decoder, uint) -> T) + -> T { + debug!("read_enum_struct_variant()"); + let idx = self._next_uint(EsEnumVid); + debug!(" idx=%u", idx); + + let doc = self.next_doc(EsEnumBody); + + let (old_parent, old_pos) = (self.parent, self.pos); + self.parent = doc; + self.pos = self.parent.start; + + let result = f(self, idx); + + self.parent = old_parent; + self.pos = old_pos; + result + } + + fn read_enum_struct_variant_field<T>(&mut self, + name: &str, + idx: uint, + f: &fn(&mut Decoder) -> T) + -> T { + debug!("read_enum_struct_variant_arg(name=%?, idx=%u)", name, idx); + f(self) + } + + fn read_struct<T>(&mut self, + name: &str, + _: uint, + f: &fn(&mut Decoder) -> T) + -> T { + debug!("read_struct(name=%s)", name); + f(self) + } + + fn read_struct_field<T>(&mut self, + name: &str, + idx: uint, + f: &fn(&mut Decoder) -> T) + -> T { + debug!("read_struct_field(name=%?, idx=%u)", name, idx); + self._check_label(name); + f(self) + } + + fn read_tuple<T>(&mut self, f: &fn(&mut Decoder, uint) -> T) -> T { + debug!("read_tuple()"); + self.read_seq(f) + } + + fn read_tuple_arg<T>(&mut self, idx: uint, f: &fn(&mut Decoder) -> T) + -> T { + debug!("read_tuple_arg(idx=%u)", idx); + self.read_seq_elt(idx, f) + } + + fn read_tuple_struct<T>(&mut self, + name: &str, + f: &fn(&mut Decoder, uint) -> T) + -> T { + debug!("read_tuple_struct(name=%?)", name); + self.read_tuple(f) + } + + fn read_tuple_struct_arg<T>(&mut self, + idx: uint, + f: &fn(&mut Decoder) -> T) + -> T { + debug!("read_tuple_struct_arg(idx=%u)", idx); + self.read_tuple_arg(idx, f) + } + + fn read_option<T>(&mut self, f: &fn(&mut Decoder, bool) -> T) -> T { + debug!("read_option()"); + do self.read_enum("Option") |this| { + do this.read_enum_variant(["None", "Some"]) |this, idx| { + match idx { + 0 => f(this, false), + 1 => f(this, true), + _ => fail!(), + } + } + } + } + + fn read_seq<T>(&mut self, f: &fn(&mut Decoder, uint) -> T) -> T { + debug!("read_seq()"); + let doc = self.next_doc(EsVec); + + let (old_parent, old_pos) = (self.parent, self.pos); + self.parent = doc; + self.pos = self.parent.start; + + let len = self._next_uint(EsVecLen); + debug!(" len=%u", len); + let result = f(self, len); + + self.parent = old_parent; + self.pos = old_pos; + result + } + + fn read_seq_elt<T>(&mut self, idx: uint, f: &fn(&mut Decoder) -> T) + -> T { + debug!("read_seq_elt(idx=%u)", idx); + let doc = self.next_doc(EsVecElt); + + let (old_parent, old_pos) = (self.parent, self.pos); + self.parent = doc; + self.pos = self.parent.start; + + let result = f(self); + + self.parent = old_parent; + self.pos = old_pos; + result + } + + fn read_map<T>(&mut self, _: &fn(&mut Decoder, uint) -> T) -> T { + debug!("read_map()"); + fail!(~"read_map is unimplemented"); + } + + fn read_map_elt_key<T>(&mut self, + idx: uint, + _: &fn(&mut Decoder) -> T) + -> T { + debug!("read_map_elt_key(idx=%u)", idx); + fail!(~"read_map_elt_val is unimplemented"); + } + + fn read_map_elt_val<T>(&mut self, + idx: uint, + _: &fn(&mut Decoder) -> T) + -> T { + debug!("read_map_elt_val(idx=%u)", idx); + fail!(~"read_map_elt_val is unimplemented"); + } + } } pub mod writer { @@ -522,6 +891,7 @@ pub mod writer { } // FIXME (#2741): Provide a function to write the standard ebml header. + #[cfg(stage0)] pub impl Encoder { fn start_tag(&self, tag_id: uint) { debug!("Start tag %u", tag_id); @@ -617,13 +987,111 @@ pub mod writer { } } + // FIXME (#2741): Provide a function to write the standard ebml header. + #[cfg(not(stage0))] + pub impl Encoder { + fn start_tag(&mut self, tag_id: uint) { + debug!("Start tag %u", tag_id); + + // Write the enum ID: + write_vuint(self.writer, tag_id); + + // Write a placeholder four-byte size. + self.size_positions.push(self.writer.tell()); + let zeroes: &[u8] = &[0u8, 0u8, 0u8, 0u8]; + self.writer.write(zeroes); + } + + fn end_tag(&mut self) { + let last_size_pos = self.size_positions.pop(); + let cur_pos = self.writer.tell(); + self.writer.seek(last_size_pos as int, io::SeekSet); + let size = (cur_pos - last_size_pos - 4u); + write_sized_vuint(self.writer, size, 4u); + self.writer.seek(cur_pos as int, io::SeekSet); + + debug!("End tag (size = %u)", size); + } + + fn wr_tag(&mut self, tag_id: uint, blk: &fn()) { + self.start_tag(tag_id); + blk(); + self.end_tag(); + } + + fn wr_tagged_bytes(&mut self, tag_id: uint, b: &[u8]) { + write_vuint(self.writer, tag_id); + write_vuint(self.writer, vec::len(b)); + self.writer.write(b); + } + + fn wr_tagged_u64(&mut self, tag_id: uint, v: u64) { + do io::u64_to_be_bytes(v, 8u) |v| { + self.wr_tagged_bytes(tag_id, v); + } + } + + fn wr_tagged_u32(&mut self, tag_id: uint, v: u32) { + do io::u64_to_be_bytes(v as u64, 4u) |v| { + self.wr_tagged_bytes(tag_id, v); + } + } + + fn wr_tagged_u16(&mut self, tag_id: uint, v: u16) { + do io::u64_to_be_bytes(v as u64, 2u) |v| { + self.wr_tagged_bytes(tag_id, v); + } + } + + fn wr_tagged_u8(&mut self, tag_id: uint, v: u8) { + self.wr_tagged_bytes(tag_id, &[v]); + } + + fn wr_tagged_i64(&mut self, tag_id: uint, v: i64) { + do io::u64_to_be_bytes(v as u64, 8u) |v| { + self.wr_tagged_bytes(tag_id, v); + } + } + + fn wr_tagged_i32(&mut self, tag_id: uint, v: i32) { + do io::u64_to_be_bytes(v as u64, 4u) |v| { + self.wr_tagged_bytes(tag_id, v); + } + } + + fn wr_tagged_i16(&mut self, tag_id: uint, v: i16) { + do io::u64_to_be_bytes(v as u64, 2u) |v| { + self.wr_tagged_bytes(tag_id, v); + } + } + + fn wr_tagged_i8(&mut self, tag_id: uint, v: i8) { + self.wr_tagged_bytes(tag_id, &[v as u8]); + } + + fn wr_tagged_str(&mut self, tag_id: uint, v: &str) { + str::byte_slice(v, |b| self.wr_tagged_bytes(tag_id, b)); + } + + fn wr_bytes(&mut self, b: &[u8]) { + debug!("Write %u bytes", vec::len(b)); + self.writer.write(b); + } + + fn wr_str(&mut self, s: &str) { + debug!("Write str: %?", s); + self.writer.write(str::to_bytes(s)); + } + } + // FIXME (#2743): optionally perform "relaxations" on end_tag to more // efficiently encode sizes; this is a fixed point iteration // Set to true to generate more debugging in EBML code. // Totally lame approach. - static debug: bool = false; + static debug: bool = true; + #[cfg(stage0)] priv impl Encoder { // used internally to emit things like the vector length and so on fn _emit_tagged_uint(&self, t: EbmlEncoderTag, v: uint) { @@ -642,6 +1110,26 @@ pub mod writer { } } + #[cfg(not(stage0))] + priv impl Encoder { + // used internally to emit things like the vector length and so on + fn _emit_tagged_uint(&mut self, t: EbmlEncoderTag, v: uint) { + assert!(v <= 0xFFFF_FFFF_u); + self.wr_tagged_u32(t as uint, v as u32); + } + + fn _emit_label(&mut self, label: &str) { + // There are various strings that we have access to, such as + // the name of a record field, which do not actually appear in + // the encoded EBML (normally). This is just for + // efficiency. When debugging, though, we can emit such + // labels and then they will be checked by decoder to + // try and check failures more quickly. + if debug { self.wr_tagged_str(EsLabel as uint, label) } + } + } + + #[cfg(stage0)] pub impl Encoder { fn emit_opaque(&self, f: &fn()) { do self.wr_tag(EsOpaque as uint) { @@ -650,24 +1138,50 @@ pub mod writer { } } + #[cfg(not(stage0))] + pub impl Encoder { + fn emit_opaque(&mut self, f: &fn(&mut Encoder)) { + self.start_tag(EsOpaque as uint); + f(self); + self.end_tag(); + } + } + + #[cfg(stage0)] impl ::serialize::Encoder for Encoder { fn emit_nil(&self) {} fn emit_uint(&self, v: uint) { self.wr_tagged_u64(EsUint as uint, v as u64); } - fn emit_u64(&self, v: u64) { self.wr_tagged_u64(EsU64 as uint, v); } - fn emit_u32(&self, v: u32) { self.wr_tagged_u32(EsU32 as uint, v); } - fn emit_u16(&self, v: u16) { self.wr_tagged_u16(EsU16 as uint, v); } - fn emit_u8(&self, v: u8) { self.wr_tagged_u8 (EsU8 as uint, v); } + fn emit_u64(&self, v: u64) { + self.wr_tagged_u64(EsU64 as uint, v); + } + fn emit_u32(&self, v: u32) { + self.wr_tagged_u32(EsU32 as uint, v); + } + fn emit_u16(&self, v: u16) { + self.wr_tagged_u16(EsU16 as uint, v); + } + fn emit_u8(&self, v: u8) { + self.wr_tagged_u8(EsU8 as uint, v); + } fn emit_int(&self, v: int) { self.wr_tagged_i64(EsInt as uint, v as i64); } - fn emit_i64(&self, v: i64) { self.wr_tagged_i64(EsI64 as uint, v); } - fn emit_i32(&self, v: i32) { self.wr_tagged_i32(EsI32 as uint, v); } - fn emit_i16(&self, v: i16) { self.wr_tagged_i16(EsI16 as uint, v); } - fn emit_i8(&self, v: i8) { self.wr_tagged_i8 (EsI8 as uint, v); } + fn emit_i64(&self, v: i64) { + self.wr_tagged_i64(EsI64 as uint, v); + } + fn emit_i32(&self, v: i32) { + self.wr_tagged_i32(EsI32 as uint, v); + } + fn emit_i16(&self, v: i16) { + self.wr_tagged_i16(EsI16 as uint, v); + } + fn emit_i8(&self, v: i8) { + self.wr_tagged_i8(EsI8 as uint, v); + } fn emit_bool(&self, v: bool) { self.wr_tagged_u8(EsBool as uint, v as u8) @@ -697,41 +1211,56 @@ pub mod writer { self.wr_tag(EsEnum as uint, f) } - fn emit_enum_variant(&self, _v_name: &str, v_id: uint, _cnt: uint, + fn emit_enum_variant(&self, + _: &str, + v_id: uint, + _: uint, f: &fn()) { self._emit_tagged_uint(EsEnumVid, v_id); self.wr_tag(EsEnumBody as uint, f) } - fn emit_enum_variant_arg(&self, _idx: uint, f: &fn()) { f() } + fn emit_enum_variant_arg(&self, _: uint, f: &fn()) { + f() + } - fn emit_enum_struct_variant(&self, v_name: &str, v_id: uint, cnt: uint, f: &fn()) { + fn emit_enum_struct_variant(&self, + v_name: &str, + v_id: uint, + cnt: uint, + f: &fn()) { self.emit_enum_variant(v_name, v_id, cnt, f) } - fn emit_enum_struct_variant_field(&self, _f_name: &str, idx: uint, f: &fn()) { + fn emit_enum_struct_variant_field(&self, + _: &str, + idx: uint, + f: &fn()) { self.emit_enum_variant_arg(idx, f) } - fn emit_struct(&self, _name: &str, _len: uint, f: &fn()) { f() } - #[cfg(stage0)] - fn emit_field(&self, name: &str, _idx: uint, f: &fn()) { - self._emit_label(name); + fn emit_struct(&self, _: &str, _len: uint, f: &fn()) { f() } - #[cfg(stage1)] - #[cfg(stage2)] - #[cfg(stage3)] - fn emit_struct_field(&self, name: &str, _idx: uint, f: &fn()) { + + fn emit_field(&self, name: &str, _idx: uint, f: &fn()) { self._emit_label(name); f() } - fn emit_tuple(&self, len: uint, f: &fn()) { self.emit_seq(len, f) } - fn emit_tuple_arg(&self, idx: uint, f: &fn()) { self.emit_seq_elt(idx, f) } + fn emit_tuple(&self, len: uint, f: &fn()) { + self.emit_seq(len, f) + } + fn emit_tuple_arg(&self, idx: uint, f: &fn()) { + self.emit_seq_elt(idx, f) + } - fn emit_tuple_struct(&self, _name: &str, len: uint, f: &fn()) { self.emit_seq(len, f) } - fn emit_tuple_struct_arg(&self, idx: uint, f: &fn()) { self.emit_seq_elt(idx, f) } + fn emit_tuple_struct(&self, _name: &str, len: uint, f: &fn()) { + self.emit_seq(len, f) + } + fn emit_tuple_struct_arg(&self, idx: uint, f: &fn()) { + self.emit_seq_elt(idx, f) + } fn emit_option(&self, f: &fn()) { self.emit_enum("Option", f); @@ -766,6 +1295,167 @@ pub mod writer { fail!(~"emit_map_elt_val is unimplemented"); } } + + #[cfg(not(stage0))] + impl ::serialize::Encoder for Encoder { + fn emit_nil(&mut self) {} + + fn emit_uint(&mut self, v: uint) { + self.wr_tagged_u64(EsUint as uint, v as u64); + } + fn emit_u64(&mut self, v: u64) { + self.wr_tagged_u64(EsU64 as uint, v); + } + fn emit_u32(&mut self, v: u32) { + self.wr_tagged_u32(EsU32 as uint, v); + } + fn emit_u16(&mut self, v: u16) { + self.wr_tagged_u16(EsU16 as uint, v); + } + fn emit_u8(&mut self, v: u8) { + self.wr_tagged_u8(EsU8 as uint, v); + } + + fn emit_int(&mut self, v: int) { + self.wr_tagged_i64(EsInt as uint, v as i64); + } + fn emit_i64(&mut self, v: i64) { + self.wr_tagged_i64(EsI64 as uint, v); + } + fn emit_i32(&mut self, v: i32) { + self.wr_tagged_i32(EsI32 as uint, v); + } + fn emit_i16(&mut self, v: i16) { + self.wr_tagged_i16(EsI16 as uint, v); + } + fn emit_i8(&mut self, v: i8) { + self.wr_tagged_i8(EsI8 as uint, v); + } + + fn emit_bool(&mut self, v: bool) { + self.wr_tagged_u8(EsBool as uint, v as u8) + } + + // FIXME (#2742): implement these + fn emit_f64(&mut self, _v: f64) { + fail!(~"Unimplemented: serializing an f64"); + } + fn emit_f32(&mut self, _v: f32) { + fail!(~"Unimplemented: serializing an f32"); + } + fn emit_float(&mut self, _v: float) { + fail!(~"Unimplemented: serializing a float"); + } + + fn emit_char(&mut self, _v: char) { + fail!(~"Unimplemented: serializing a char"); + } + + fn emit_str(&mut self, v: &str) { + self.wr_tagged_str(EsStr as uint, v) + } + + fn emit_enum(&mut self, name: &str, f: &fn(&mut Encoder)) { + self._emit_label(name); + self.start_tag(EsEnum as uint); + f(self); + self.end_tag(); + } + + fn emit_enum_variant(&mut self, + _: &str, + v_id: uint, + _: uint, + f: &fn(&mut Encoder)) { + self._emit_tagged_uint(EsEnumVid, v_id); + self.start_tag(EsEnumBody as uint); + f(self); + self.end_tag(); + } + + fn emit_enum_variant_arg(&mut self, _: uint, f: &fn(&mut Encoder)) { + f(self) + } + + fn emit_enum_struct_variant(&mut self, + v_name: &str, + v_id: uint, + cnt: uint, + f: &fn(&mut Encoder)) { + self.emit_enum_variant(v_name, v_id, cnt, f) + } + + fn emit_enum_struct_variant_field(&mut self, + _: &str, + idx: uint, + f: &fn(&mut Encoder)) { + self.emit_enum_variant_arg(idx, f) + } + + fn emit_struct(&mut self, _: &str, _len: uint, f: &fn(&mut Encoder)) { + f(self) + } + + fn emit_struct_field(&mut self, + name: &str, + _: uint, + f: &fn(&mut Encoder)) { + self._emit_label(name); + f(self) + } + + fn emit_tuple(&mut self, len: uint, f: &fn(&mut Encoder)) { + self.emit_seq(len, f) + } + fn emit_tuple_arg(&mut self, idx: uint, f: &fn(&mut Encoder)) { + self.emit_seq_elt(idx, f) + } + + fn emit_tuple_struct(&mut self, + _: &str, + len: uint, + f: &fn(&mut Encoder)) { + self.emit_seq(len, f) + } + fn emit_tuple_struct_arg(&mut self, idx: uint, f: &fn(&mut Encoder)) { + self.emit_seq_elt(idx, f) + } + + fn emit_option(&mut self, f: &fn(&mut Encoder)) { + self.emit_enum("Option", f); + } + fn emit_option_none(&mut self) { + self.emit_enum_variant("None", 0, 0, |_| ()) + } + fn emit_option_some(&mut self, f: &fn(&mut Encoder)) { + self.emit_enum_variant("Some", 1, 1, f) + } + + fn emit_seq(&mut self, len: uint, f: &fn(&mut Encoder)) { + self.start_tag(EsVec as uint); + self._emit_tagged_uint(EsVecLen, len); + f(self); + self.end_tag(); + } + + fn emit_seq_elt(&mut self, _idx: uint, f: &fn(&mut Encoder)) { + self.start_tag(EsVecElt as uint); + f(self); + self.end_tag(); + } + + fn emit_map(&mut self, _len: uint, _f: &fn(&mut Encoder)) { + fail!(~"emit_map is unimplemented"); + } + + fn emit_map_elt_key(&mut self, _idx: uint, _f: &fn(&mut Encoder)) { + fail!(~"emit_map_elt_key is unimplemented"); + } + + fn emit_map_elt_val(&mut self, _idx: uint, _f: &fn(&mut Encoder)) { + fail!(~"emit_map_elt_val is unimplemented"); + } + } } // ___________________________________________________________________________ @@ -786,12 +1476,12 @@ mod tests { fn test_v(v: Option<int>) { debug!("v == %?", v); let bytes = do io::with_bytes_writer |wr| { - let ebml_w = writer::Encoder(wr); - v.encode(&ebml_w) + let mut ebml_w = writer::Encoder(wr); + v.encode(&mut ebml_w) }; let ebml_doc = reader::Doc(@bytes); - let deser = reader::Decoder(ebml_doc); - let v1 = serialize::Decodable::decode(&deser); + let mut deser = reader::Decoder(ebml_doc); + let v1 = serialize::Decodable::decode(&mut deser); debug!("v1 == %?", v1); assert!(v == v1); } |
