Bug 1295666 - Build byteorder as a separate crate. r?kinetik draft
authorRalph Giles <giles@mozilla.com>
Tue, 16 Aug 2016 11:06:46 -0700
changeset 401236 1875a45487fded4d1058cbddbc459728ffd9c492
parent 401235 deaa9ec30dcf8a30a51642beb5fc058beb2cdb10
child 528442 093c9957d65f57dc1477a2a7a2df5d12f684b54c
push id26409
push userbmo:giles@thaumas.net
push dateTue, 16 Aug 2016 18:11:01 +0000
reviewerskinetik
bugs1295666
milestone51.0a1
Bug 1295666 - Build byteorder as a separate crate. r?kinetik Run the updated import script to split the in-tree byteorder code into a separate directory and build it as a dependent crate. MozReview-Commit-ID: EI5X4icOdmM
media/libstagefright/binding/byteorder/Cargo.toml
media/libstagefright/binding/byteorder/src/lib.rs
media/libstagefright/binding/byteorder/src/new.rs
media/libstagefright/binding/mp4parse/Cargo.toml
media/libstagefright/binding/mp4parse/src/byteorder/mod.rs
media/libstagefright/binding/mp4parse/src/byteorder/new.rs
media/libstagefright/binding/mp4parse/src/lib.rs
toolkit/library/rust/Cargo.lock
new file mode 100644
--- /dev/null
+++ b/media/libstagefright/binding/byteorder/Cargo.toml
@@ -0,0 +1,25 @@
+[package]
+name = "byteorder"
+version = "0.5.3"  #:version
+authors = ["Andrew Gallant <jamslam@gmail.com>"]
+description = "Library for reading/writing numbers in big-endian and little-endian."
+documentation = "http://burntsushi.net/rustdoc/byteorder/"
+homepage = "https://github.com/BurntSushi/byteorder"
+repository = "https://github.com/BurntSushi/byteorder"
+readme = "README.md"
+keywords = ["byte", "endian", "big-endian", "little-endian", "binary"]
+license = "Unlicense/MIT"
+
+[lib]
+name = "byteorder"
+
+[dev-dependencies]
+quickcheck = "0.2"
+rand = "0.3"
+
+[features]
+default = ["std"]
+std = []
+
+[profile.bench]
+opt-level = 3
new file mode 100644
--- /dev/null
+++ b/media/libstagefright/binding/byteorder/src/lib.rs
@@ -0,0 +1,802 @@
+/*!
+This crate provides convenience methods for encoding and decoding numbers
+in either big-endian or little-endian order.
+
+The organization of the crate is pretty simple. A trait, `ByteOrder`, specifies
+byte conversion methods for each type of number in Rust (sans numbers that have
+a platform dependent size like `usize` and `isize`). Two types, `BigEndian`
+and `LittleEndian` implement these methods. Finally, `ReadBytesExt` and
+`WriteBytesExt` provide convenience methods available to all types that
+implement `Read` and `Write`.
+
+# Examples
+
+Read unsigned 16 bit big-endian integers from a `Read` type:
+
+```rust
+use std::io::Cursor;
+use byteorder::{BigEndian, ReadBytesExt};
+
+let mut rdr = Cursor::new(vec![2, 5, 3, 0]);
+// Note that we use type parameters to indicate which kind of byte order
+// we want!
+assert_eq!(517, rdr.read_u16::<BigEndian>().unwrap());
+assert_eq!(768, rdr.read_u16::<BigEndian>().unwrap());
+```
+
+Write unsigned 16 bit little-endian integers to a `Write` type:
+
+```rust
+use byteorder::{LittleEndian, WriteBytesExt};
+
+let mut wtr = vec![];
+wtr.write_u16::<LittleEndian>(517).unwrap();
+wtr.write_u16::<LittleEndian>(768).unwrap();
+assert_eq!(wtr, vec![5, 2, 0, 3]);
+```
+*/
+
+#![crate_name = "byteorder"]
+#![doc(html_root_url = "http://burntsushi.net/rustdoc/byteorder")]
+
+#![cfg_attr(not(feature = "std"), no_std)]
+
+#![deny(missing_docs)]
+
+#[cfg(feature = "std")]
+extern crate core;
+
+use core::mem::transmute;
+use core::ptr::copy_nonoverlapping;
+
+#[cfg(feature = "std")]
+pub use new::{ReadBytesExt, WriteBytesExt};
+
+#[cfg(feature = "std")]
+mod new;
+
+#[inline]
+fn extend_sign(val: u64, nbytes: usize) -> i64 {
+    let shift = (8 - nbytes) * 8;
+    (val << shift) as i64 >> shift
+}
+
+#[inline]
+fn unextend_sign(val: i64, nbytes: usize) -> u64 {
+    let shift = (8 - nbytes) * 8;
+    (val << shift) as u64 >> shift
+}
+
+#[inline]
+fn pack_size(n: u64) -> usize {
+    if n < 1 << 8 {
+        1
+    } else if n < 1 << 16 {
+        2
+    } else if n < 1 << 24 {
+        3
+    } else if n < 1 << 32 {
+        4
+    } else if n < 1 << 40 {
+        5
+    } else if n < 1 << 48 {
+        6
+    } else if n < 1 << 56 {
+        7
+    } else {
+        8
+    }
+}
+
+/// ByteOrder describes types that can serialize integers as bytes.
+///
+/// Note that `Self` does not appear anywhere in this trait's definition!
+/// Therefore, in order to use it, you'll need to use syntax like
+/// `T::read_u16(&[0, 1])` where `T` implements `ByteOrder`.
+///
+/// This crate provides two types that implement `ByteOrder`: `BigEndian`
+/// and `LittleEndian`.
+///
+/// # Examples
+///
+/// Write and read `u32` numbers in little endian order:
+///
+/// ```rust
+/// use byteorder::{ByteOrder, LittleEndian};
+///
+/// let mut buf = [0; 4];
+/// LittleEndian::write_u32(&mut buf, 1_000_000);
+/// assert_eq!(1_000_000, LittleEndian::read_u32(&buf));
+/// ```
+///
+/// Write and read `i16` numbers in big endian order:
+///
+/// ```rust
+/// use byteorder::{ByteOrder, BigEndian};
+///
+/// let mut buf = [0; 2];
+/// BigEndian::write_i16(&mut buf, -50_000);
+/// assert_eq!(-50_000, BigEndian::read_i16(&buf));
+/// ```
+pub trait ByteOrder {
+    /// Reads an unsigned 16 bit integer from `buf`.
+    ///
+    /// Panics when `buf.len() < 2`.
+    fn read_u16(buf: &[u8]) -> u16;
+
+    /// Reads an unsigned 32 bit integer from `buf`.
+    ///
+    /// Panics when `buf.len() < 4`.
+    fn read_u32(buf: &[u8]) -> u32;
+
+    /// Reads an unsigned 64 bit integer from `buf`.
+    ///
+    /// Panics when `buf.len() < 8`.
+    fn read_u64(buf: &[u8]) -> u64;
+
+    /// Reads an unsigned n-bytes integer from `buf`.
+    ///
+    /// Panics when `nbytes < 1` or `nbytes > 8` or
+    /// `buf.len() < nbytes`
+    fn read_uint(buf: &[u8], nbytes: usize) -> u64;
+
+    /// Writes an unsigned 16 bit integer `n` to `buf`.
+    ///
+    /// Panics when `buf.len() < 2`.
+    fn write_u16(buf: &mut [u8], n: u16);
+
+    /// Writes an unsigned 32 bit integer `n` to `buf`.
+    ///
+    /// Panics when `buf.len() < 4`.
+    fn write_u32(buf: &mut [u8], n: u32);
+
+    /// Writes an unsigned 64 bit integer `n` to `buf`.
+    ///
+    /// Panics when `buf.len() < 8`.
+    fn write_u64(buf: &mut [u8], n: u64);
+
+    /// Writes an unsigned integer `n` to `buf` using only `nbytes`.
+    ///
+    /// If `n` is not representable in `nbytes`, or if `nbytes` is `> 8`, then
+    /// this method panics.
+    fn write_uint(buf: &mut [u8], n: u64, nbytes: usize);
+
+    /// Reads a signed 16 bit integer from `buf`.
+    ///
+    /// Panics when `buf.len() < 2`.
+    #[inline]
+    fn read_i16(buf: &[u8]) -> i16 {
+        Self::read_u16(buf) as i16
+    }
+
+    /// Reads a signed 32 bit integer from `buf`.
+    ///
+    /// Panics when `buf.len() < 4`.
+    #[inline]
+    fn read_i32(buf: &[u8]) -> i32 {
+        Self::read_u32(buf) as i32
+    }
+
+    /// Reads a signed 64 bit integer from `buf`.
+    ///
+    /// Panics when `buf.len() < 8`.
+    #[inline]
+    fn read_i64(buf: &[u8]) -> i64 {
+        Self::read_u64(buf) as i64
+    }
+
+    /// Reads a signed n-bytes integer from `buf`.
+    ///
+    /// Panics when `nbytes < 1` or `nbytes > 8` or
+    /// `buf.len() < nbytes`
+    #[inline]
+    fn read_int(buf: &[u8], nbytes: usize) -> i64 {
+        extend_sign(Self::read_uint(buf, nbytes), nbytes)
+    }
+
+    /// Reads a IEEE754 single-precision (4 bytes) floating point number.
+    ///
+    /// Panics when `buf.len() < 4`.
+    #[inline]
+    fn read_f32(buf: &[u8]) -> f32 {
+        unsafe { transmute(Self::read_u32(buf)) }
+    }
+
+    /// Reads a IEEE754 double-precision (8 bytes) floating point number.
+    ///
+    /// Panics when `buf.len() < 8`.
+    #[inline]
+    fn read_f64(buf: &[u8]) -> f64 {
+        unsafe { transmute(Self::read_u64(buf)) }
+    }
+
+    /// Writes a signed 16 bit integer `n` to `buf`.
+    ///
+    /// Panics when `buf.len() < 2`.
+    #[inline]
+    fn write_i16(buf: &mut [u8], n: i16) {
+        Self::write_u16(buf, n as u16)
+    }
+
+    /// Writes a signed 32 bit integer `n` to `buf`.
+    ///
+    /// Panics when `buf.len() < 4`.
+    #[inline]
+    fn write_i32(buf: &mut [u8], n: i32) {
+        Self::write_u32(buf, n as u32)
+    }
+
+    /// Writes a signed 64 bit integer `n` to `buf`.
+    ///
+    /// Panics when `buf.len() < 8`.
+    #[inline]
+    fn write_i64(buf: &mut [u8], n: i64) {
+        Self::write_u64(buf, n as u64)
+    }
+
+    /// Writes a signed integer `n` to `buf` using only `nbytes`.
+    ///
+    /// If `n` is not representable in `nbytes`, or if `nbytes` is `> 8`, then
+    /// this method panics.
+    #[inline]
+    fn write_int(buf: &mut [u8], n: i64, nbytes: usize) {
+        Self::write_uint(buf, unextend_sign(n, nbytes), nbytes)
+    }
+
+    /// Writes a IEEE754 single-precision (4 bytes) floating point number.
+    ///
+    /// Panics when `buf.len() < 4`.
+    #[inline]
+    fn write_f32(buf: &mut [u8], n: f32) {
+        Self::write_u32(buf, unsafe { transmute(n) })
+    }
+
+    /// Writes a IEEE754 double-precision (8 bytes) floating point number.
+    ///
+    /// Panics when `buf.len() < 8`.
+    #[inline]
+    fn write_f64(buf: &mut [u8], n: f64) {
+        Self::write_u64(buf, unsafe { transmute(n) })
+    }
+}
+
+/// Defines big-endian serialization.
+///
+/// Note that this type has no value constructor. It is used purely at the
+/// type level.
+#[allow(missing_copy_implementations)] pub enum BigEndian {}
+
+/// Defines little-endian serialization.
+///
+/// Note that this type has no value constructor. It is used purely at the
+/// type level.
+#[allow(missing_copy_implementations)] pub enum LittleEndian {}
+
+/// Defines network byte order serialization.
+///
+/// Network byte order is defined by [RFC 1700][1] to be big-endian, and is
+/// referred to in several protocol specifications.  This type is an alias of
+/// BigEndian.
+///
+/// [1]: https://tools.ietf.org/html/rfc1700
+///
+/// Note that this type has no value constructor. It is used purely at the
+/// type level.
+pub type NetworkEndian = BigEndian;
+
+/// Defines system native-endian serialization.
+///
+/// Note that this type has no value constructor. It is used purely at the
+/// type level.
+#[cfg(target_endian = "little")]
+pub type NativeEndian = LittleEndian;
+
+/// Defines system native-endian serialization.
+///
+/// Note that this type has no value constructor. It is used purely at the
+/// type level.
+#[cfg(target_endian = "big")]
+pub type NativeEndian = BigEndian;
+
+macro_rules! read_num_bytes {
+    ($ty:ty, $size:expr, $src:expr, $which:ident) => ({
+        assert!($size == ::core::mem::size_of::<$ty>());
+        assert!($size <= $src.len());
+        let mut data: $ty = 0;
+        unsafe {
+            copy_nonoverlapping(
+                $src.as_ptr(),
+                &mut data as *mut $ty as *mut u8,
+                $size);
+        }
+        data.$which()
+    });
+}
+
+macro_rules! write_num_bytes {
+    ($ty:ty, $size:expr, $n:expr, $dst:expr, $which:ident) => ({
+        assert!($size <= $dst.len());
+        unsafe {
+            // N.B. https://github.com/rust-lang/rust/issues/22776
+            let bytes = transmute::<_, [u8; $size]>($n.$which());
+            copy_nonoverlapping((&bytes).as_ptr(), $dst.as_mut_ptr(), $size);
+        }
+    });
+}
+
+impl ByteOrder for BigEndian {
+    #[inline]
+    fn read_u16(buf: &[u8]) -> u16 {
+        read_num_bytes!(u16, 2, buf, to_be)
+    }
+
+    #[inline]
+    fn read_u32(buf: &[u8]) -> u32 {
+        read_num_bytes!(u32, 4, buf, to_be)
+    }
+
+    #[inline]
+    fn read_u64(buf: &[u8]) -> u64 {
+        read_num_bytes!(u64, 8, buf, to_be)
+    }
+
+    #[inline]
+    fn read_uint(buf: &[u8], nbytes: usize) -> u64 {
+        assert!(1 <= nbytes && nbytes <= 8 && nbytes <= buf.len());
+        let mut out = [0u8; 8];
+        let ptr_out = out.as_mut_ptr();
+        unsafe {
+            copy_nonoverlapping(
+                buf.as_ptr(), ptr_out.offset((8 - nbytes) as isize), nbytes);
+            (*(ptr_out as *const u64)).to_be()
+        }
+    }
+
+    #[inline]
+    fn write_u16(buf: &mut [u8], n: u16) {
+        write_num_bytes!(u16, 2, n, buf, to_be);
+    }
+
+    #[inline]
+    fn write_u32(buf: &mut [u8], n: u32) {
+        write_num_bytes!(u32, 4, n, buf, to_be);
+    }
+
+    #[inline]
+    fn write_u64(buf: &mut [u8], n: u64) {
+        write_num_bytes!(u64, 8, n, buf, to_be);
+    }
+
+    #[inline]
+    fn write_uint(buf: &mut [u8], n: u64, nbytes: usize) {
+        assert!(pack_size(n) <= nbytes && nbytes <= 8);
+        assert!(nbytes <= buf.len());
+        unsafe {
+            let bytes: [u8; 8] = transmute(n.to_be());
+            copy_nonoverlapping(
+                bytes.as_ptr().offset((8 - nbytes) as isize),
+                buf.as_mut_ptr(),
+                nbytes);
+        }
+    }
+}
+
+impl ByteOrder for LittleEndian {
+    #[inline]
+    fn read_u16(buf: &[u8]) -> u16 {
+        read_num_bytes!(u16, 2, buf, to_le)
+    }
+
+    #[inline]
+    fn read_u32(buf: &[u8]) -> u32 {
+        read_num_bytes!(u32, 4, buf, to_le)
+    }
+
+    #[inline]
+    fn read_u64(buf: &[u8]) -> u64 {
+        read_num_bytes!(u64, 8, buf, to_le)
+    }
+
+    #[inline]
+    fn read_uint(buf: &[u8], nbytes: usize) -> u64 {
+        assert!(1 <= nbytes && nbytes <= 8 && nbytes <= buf.len());
+        let mut out = [0u8; 8];
+        let ptr_out = out.as_mut_ptr();
+        unsafe {
+            copy_nonoverlapping(buf.as_ptr(), ptr_out, nbytes);
+            (*(ptr_out as *const u64)).to_le()
+        }
+    }
+
+    #[inline]
+    fn write_u16(buf: &mut [u8], n: u16) {
+        write_num_bytes!(u16, 2, n, buf, to_le);
+    }
+
+    #[inline]
+    fn write_u32(buf: &mut [u8], n: u32) {
+        write_num_bytes!(u32, 4, n, buf, to_le);
+    }
+
+    #[inline]
+    fn write_u64(buf: &mut [u8], n: u64) {
+        write_num_bytes!(u64, 8, n, buf, to_le);
+    }
+
+    #[inline]
+    fn write_uint(buf: &mut [u8], n: u64, nbytes: usize) {
+        assert!(pack_size(n as u64) <= nbytes && nbytes <= 8);
+        assert!(nbytes <= buf.len());
+        unsafe {
+            let bytes: [u8; 8] = transmute(n.to_le());
+            copy_nonoverlapping(bytes.as_ptr(), buf.as_mut_ptr(), nbytes);
+        }
+    }
+}
+
+#[cfg(test)]
+mod test {
+    extern crate quickcheck;
+    extern crate rand;
+
+    use test::rand::thread_rng;
+    use test::quickcheck::{QuickCheck, StdGen, Testable};
+
+    const U64_MAX: u64 = ::std::u64::MAX;
+    const I64_MAX: u64 = ::std::i64::MAX as u64;
+
+    fn qc_sized<A: Testable>(f: A, size: u64) {
+        QuickCheck::new()
+            .gen(StdGen::new(thread_rng(), size as usize))
+            .tests(1_00)
+            .max_tests(10_000)
+            .quickcheck(f);
+    }
+
+    macro_rules! qc_byte_order {
+        ($name:ident, $ty_int:ident, $max:expr,
+         $bytes:expr, $read:ident, $write:ident) => (
+            mod $name {
+                use {BigEndian, ByteOrder, NativeEndian, LittleEndian};
+                use super::qc_sized;
+
+                #[test]
+                fn big_endian() {
+                    let max = ($max - 1) >> (8 * (8 - $bytes));
+                    fn prop(n: $ty_int) -> bool {
+                        let mut buf = [0; 8];
+                        BigEndian::$write(&mut buf, n, $bytes);
+                        n == BigEndian::$read(&mut buf[..$bytes], $bytes)
+                    }
+                    qc_sized(prop as fn($ty_int) -> bool, max);
+                }
+
+                #[test]
+                fn little_endian() {
+                    let max = ($max - 1) >> (8 * (8 - $bytes));
+                    fn prop(n: $ty_int) -> bool {
+                        let mut buf = [0; 8];
+                        LittleEndian::$write(&mut buf, n, $bytes);
+                        n == LittleEndian::$read(&mut buf[..$bytes], $bytes)
+                    }
+                    qc_sized(prop as fn($ty_int) -> bool, max);
+                }
+
+                #[test]
+                fn native_endian() {
+                    let max = ($max - 1) >> (8 * (8 - $bytes));
+                    fn prop(n: $ty_int) -> bool {
+                        let mut buf = [0; 8];
+                        NativeEndian::$write(&mut buf, n, $bytes);
+                        n == NativeEndian::$read(&mut buf[..$bytes], $bytes)
+                    }
+                    qc_sized(prop as fn($ty_int) -> bool, max);
+                }
+            }
+        );
+        ($name:ident, $ty_int:ident, $max:expr,
+         $read:ident, $write:ident) => (
+            mod $name {
+                use std::mem::size_of;
+                use {BigEndian, ByteOrder, NativeEndian, LittleEndian};
+                use super::qc_sized;
+
+                #[test]
+                fn big_endian() {
+                    fn prop(n: $ty_int) -> bool {
+                        let bytes = size_of::<$ty_int>();
+                        let mut buf = [0; 8];
+                        BigEndian::$write(&mut buf[8 - bytes..], n);
+                        n == BigEndian::$read(&mut buf[8 - bytes..])
+                    }
+                    qc_sized(prop as fn($ty_int) -> bool, $max - 1);
+                }
+
+                #[test]
+                fn little_endian() {
+                    fn prop(n: $ty_int) -> bool {
+                        let bytes = size_of::<$ty_int>();
+                        let mut buf = [0; 8];
+                        LittleEndian::$write(&mut buf[..bytes], n);
+                        n == LittleEndian::$read(&mut buf[..bytes])
+                    }
+                    qc_sized(prop as fn($ty_int) -> bool, $max - 1);
+                }
+
+                #[test]
+                fn native_endian() {
+                    fn prop(n: $ty_int) -> bool {
+                        let bytes = size_of::<$ty_int>();
+                        let mut buf = [0; 8];
+                        NativeEndian::$write(&mut buf[..bytes], n);
+                        n == NativeEndian::$read(&mut buf[..bytes])
+                    }
+                    qc_sized(prop as fn($ty_int) -> bool, $max - 1);
+                }
+            }
+        );
+    }
+
+    qc_byte_order!(prop_u16, u16, ::std::u16::MAX as u64, read_u16, write_u16);
+    qc_byte_order!(prop_i16, i16, ::std::i16::MAX as u64, read_i16, write_i16);
+    qc_byte_order!(prop_u32, u32, ::std::u32::MAX as u64, read_u32, write_u32);
+    qc_byte_order!(prop_i32, i32, ::std::i32::MAX as u64, read_i32, write_i32);
+    qc_byte_order!(prop_u64, u64, ::std::u64::MAX as u64, read_u64, write_u64);
+    qc_byte_order!(prop_i64, i64, ::std::i64::MAX as u64, read_i64, write_i64);
+    qc_byte_order!(prop_f32, f32, ::std::u64::MAX as u64, read_f32, write_f32);
+    qc_byte_order!(prop_f64, f64, ::std::i64::MAX as u64, read_f64, write_f64);
+
+    qc_byte_order!(prop_uint_1, u64, super::U64_MAX, 1, read_uint, write_uint);
+    qc_byte_order!(prop_uint_2, u64, super::U64_MAX, 2, read_uint, write_uint);
+    qc_byte_order!(prop_uint_3, u64, super::U64_MAX, 3, read_uint, write_uint);
+    qc_byte_order!(prop_uint_4, u64, super::U64_MAX, 4, read_uint, write_uint);
+    qc_byte_order!(prop_uint_5, u64, super::U64_MAX, 5, read_uint, write_uint);
+    qc_byte_order!(prop_uint_6, u64, super::U64_MAX, 6, read_uint, write_uint);
+    qc_byte_order!(prop_uint_7, u64, super::U64_MAX, 7, read_uint, write_uint);
+    qc_byte_order!(prop_uint_8, u64, super::U64_MAX, 8, read_uint, write_uint);
+
+    qc_byte_order!(prop_int_1, i64, super::I64_MAX, 1, read_int, write_int);
+    qc_byte_order!(prop_int_2, i64, super::I64_MAX, 2, read_int, write_int);
+    qc_byte_order!(prop_int_3, i64, super::I64_MAX, 3, read_int, write_int);
+    qc_byte_order!(prop_int_4, i64, super::I64_MAX, 4, read_int, write_int);
+    qc_byte_order!(prop_int_5, i64, super::I64_MAX, 5, read_int, write_int);
+    qc_byte_order!(prop_int_6, i64, super::I64_MAX, 6, read_int, write_int);
+    qc_byte_order!(prop_int_7, i64, super::I64_MAX, 7, read_int, write_int);
+    qc_byte_order!(prop_int_8, i64, super::I64_MAX, 8, read_int, write_int);
+
+    macro_rules! qc_bytes_ext {
+        ($name:ident, $ty_int:ident, $max:expr,
+         $bytes:expr, $read:ident, $write:ident) => (
+            mod $name {
+                use std::io::Cursor;
+                use {
+                    ReadBytesExt, WriteBytesExt,
+                    BigEndian, NativeEndian, LittleEndian,
+                };
+                use super::qc_sized;
+
+                #[test]
+                fn big_endian() {
+                    let max = ($max - 1) >> (8 * (8 - $bytes));
+                    fn prop(n: $ty_int) -> bool {
+                        let mut wtr = vec![];
+                        wtr.$write::<BigEndian>(n).unwrap();
+                        let mut rdr = Vec::new();
+                        rdr.extend(wtr[8 - $bytes..].iter().map(|&x|x));
+                        let mut rdr = Cursor::new(rdr);
+                        n == rdr.$read::<BigEndian>($bytes).unwrap()
+                    }
+                    qc_sized(prop as fn($ty_int) -> bool, max);
+                }
+
+                #[test]
+                fn little_endian() {
+                    let max = ($max - 1) >> (8 * (8 - $bytes));
+                    fn prop(n: $ty_int) -> bool {
+                        let mut wtr = vec![];
+                        wtr.$write::<LittleEndian>(n).unwrap();
+                        let mut rdr = Cursor::new(wtr);
+                        n == rdr.$read::<LittleEndian>($bytes).unwrap()
+                    }
+                    qc_sized(prop as fn($ty_int) -> bool, max);
+                }
+
+                #[test]
+                fn native_endian() {
+                    let max = ($max - 1) >> (8 * (8 - $bytes));
+                    fn prop(n: $ty_int) -> bool {
+                        let mut wtr = vec![];
+                        wtr.$write::<NativeEndian>(n).unwrap();
+                        let mut rdr = Cursor::new(wtr);
+                        n == rdr.$read::<NativeEndian>($bytes).unwrap()
+                    }
+                    qc_sized(prop as fn($ty_int) -> bool, max);
+                }
+            }
+        );
+        ($name:ident, $ty_int:ident, $max:expr, $read:ident, $write:ident) => (
+            mod $name {
+                use std::io::Cursor;
+                use {
+                    ReadBytesExt, WriteBytesExt,
+                    BigEndian, NativeEndian, LittleEndian,
+                };
+                use super::qc_sized;
+
+                #[test]
+                fn big_endian() {
+                    fn prop(n: $ty_int) -> bool {
+                        let mut wtr = vec![];
+                        wtr.$write::<BigEndian>(n).unwrap();
+                        let mut rdr = Cursor::new(wtr);
+                        n == rdr.$read::<BigEndian>().unwrap()
+                    }
+                    qc_sized(prop as fn($ty_int) -> bool, $max - 1);
+                }
+
+                #[test]
+                fn little_endian() {
+                    fn prop(n: $ty_int) -> bool {
+                        let mut wtr = vec![];
+                        wtr.$write::<LittleEndian>(n).unwrap();
+                        let mut rdr = Cursor::new(wtr);
+                        n == rdr.$read::<LittleEndian>().unwrap()
+                    }
+                    qc_sized(prop as fn($ty_int) -> bool, $max - 1);
+                }
+
+                #[test]
+                fn native_endian() {
+                    fn prop(n: $ty_int) -> bool {
+                        let mut wtr = vec![];
+                        wtr.$write::<NativeEndian>(n).unwrap();
+                        let mut rdr = Cursor::new(wtr);
+                        n == rdr.$read::<NativeEndian>().unwrap()
+                    }
+                    qc_sized(prop as fn($ty_int) -> bool, $max - 1);
+                }
+            }
+        );
+    }
+
+    qc_bytes_ext!(prop_ext_u16, u16, ::std::u16::MAX as u64, read_u16, write_u16);
+    qc_bytes_ext!(prop_ext_i16, i16, ::std::i16::MAX as u64, read_i16, write_i16);
+    qc_bytes_ext!(prop_ext_u32, u32, ::std::u32::MAX as u64, read_u32, write_u32);
+    qc_bytes_ext!(prop_ext_i32, i32, ::std::i32::MAX as u64, read_i32, write_i32);
+    qc_bytes_ext!(prop_ext_u64, u64, ::std::u64::MAX as u64, read_u64, write_u64);
+    qc_bytes_ext!(prop_ext_i64, i64, ::std::i64::MAX as u64, read_i64, write_i64);
+    qc_bytes_ext!(prop_ext_f32, f32, ::std::u64::MAX as u64, read_f32, write_f32);
+    qc_bytes_ext!(prop_ext_f64, f64, ::std::i64::MAX as u64, read_f64, write_f64);
+
+    qc_bytes_ext!(prop_ext_uint_1, u64, super::U64_MAX, 1, read_uint, write_u64);
+    qc_bytes_ext!(prop_ext_uint_2, u64, super::U64_MAX, 2, read_uint, write_u64);
+    qc_bytes_ext!(prop_ext_uint_3, u64, super::U64_MAX, 3, read_uint, write_u64);
+    qc_bytes_ext!(prop_ext_uint_4, u64, super::U64_MAX, 4, read_uint, write_u64);
+    qc_bytes_ext!(prop_ext_uint_5, u64, super::U64_MAX, 5, read_uint, write_u64);
+    qc_bytes_ext!(prop_ext_uint_6, u64, super::U64_MAX, 6, read_uint, write_u64);
+    qc_bytes_ext!(prop_ext_uint_7, u64, super::U64_MAX, 7, read_uint, write_u64);
+    qc_bytes_ext!(prop_ext_uint_8, u64, super::U64_MAX, 8, read_uint, write_u64);
+
+    qc_bytes_ext!(prop_ext_int_1, i64, super::I64_MAX, 1, read_int, write_i64);
+    qc_bytes_ext!(prop_ext_int_2, i64, super::I64_MAX, 2, read_int, write_i64);
+    qc_bytes_ext!(prop_ext_int_3, i64, super::I64_MAX, 3, read_int, write_i64);
+    qc_bytes_ext!(prop_ext_int_4, i64, super::I64_MAX, 4, read_int, write_i64);
+    qc_bytes_ext!(prop_ext_int_5, i64, super::I64_MAX, 5, read_int, write_i64);
+    qc_bytes_ext!(prop_ext_int_6, i64, super::I64_MAX, 6, read_int, write_i64);
+    qc_bytes_ext!(prop_ext_int_7, i64, super::I64_MAX, 7, read_int, write_i64);
+    qc_bytes_ext!(prop_ext_int_8, i64, super::I64_MAX, 8, read_int, write_i64);
+
+    // Test that all of the byte conversion functions panic when given a
+    // buffer that is too small.
+    //
+    // These tests are critical to ensure safety, otherwise we might end up
+    // with a buffer overflow.
+    macro_rules! too_small {
+        ($name:ident, $maximally_small:expr, $zero:expr,
+         $read:ident, $write:ident) => (
+            mod $name {
+                use {BigEndian, ByteOrder, NativeEndian, LittleEndian};
+
+                #[test]
+                #[should_panic]
+                fn read_big_endian() {
+                    let buf = [0; $maximally_small];
+                    BigEndian::$read(&buf);
+                }
+
+                #[test]
+                #[should_panic]
+                fn read_little_endian() {
+                    let buf = [0; $maximally_small];
+                    LittleEndian::$read(&buf);
+                }
+
+                #[test]
+                #[should_panic]
+                fn read_native_endian() {
+                    let buf = [0; $maximally_small];
+                    NativeEndian::$read(&buf);
+                }
+
+                #[test]
+                #[should_panic]
+                fn write_big_endian() {
+                    let mut buf = [0; $maximally_small];
+                    BigEndian::$write(&mut buf, $zero);
+                }
+
+                #[test]
+                #[should_panic]
+                fn write_little_endian() {
+                    let mut buf = [0; $maximally_small];
+                    LittleEndian::$write(&mut buf, $zero);
+                }
+
+                #[test]
+                #[should_panic]
+                fn write_native_endian() {
+                    let mut buf = [0; $maximally_small];
+                    NativeEndian::$write(&mut buf, $zero);
+                }
+            }
+        );
+        ($name:ident, $maximally_small:expr, $read:ident) => (
+            mod $name {
+                use {BigEndian, ByteOrder, NativeEndian, LittleEndian};
+
+                #[test]
+                #[should_panic]
+                fn read_big_endian() {
+                    let buf = [0; $maximally_small];
+                    BigEndian::$read(&buf, $maximally_small + 1);
+                }
+
+                #[test]
+                #[should_panic]
+                fn read_little_endian() {
+                    let buf = [0; $maximally_small];
+                    LittleEndian::$read(&buf, $maximally_small + 1);
+                }
+
+                #[test]
+                #[should_panic]
+                fn read_native_endian() {
+                    let buf = [0; $maximally_small];
+                    NativeEndian::$read(&buf, $maximally_small + 1);
+                }
+            }
+        );
+    }
+
+    too_small!(small_u16, 1, 0, read_u16, write_u16);
+    too_small!(small_i16, 1, 0, read_i16, write_i16);
+    too_small!(small_u32, 3, 0, read_u32, write_u32);
+    too_small!(small_i32, 3, 0, read_i32, write_i32);
+    too_small!(small_u64, 7, 0, read_u64, write_u64);
+    too_small!(small_i64, 7, 0, read_i64, write_i64);
+    too_small!(small_f32, 3, 0.0, read_f32, write_f32);
+    too_small!(small_f64, 7, 0.0, read_f64, write_f64);
+
+    too_small!(small_uint_1, 1, read_uint);
+    too_small!(small_uint_2, 2, read_uint);
+    too_small!(small_uint_3, 3, read_uint);
+    too_small!(small_uint_4, 4, read_uint);
+    too_small!(small_uint_5, 5, read_uint);
+    too_small!(small_uint_6, 6, read_uint);
+    too_small!(small_uint_7, 7, read_uint);
+
+    too_small!(small_int_1, 1, read_int);
+    too_small!(small_int_2, 2, read_int);
+    too_small!(small_int_3, 3, read_int);
+    too_small!(small_int_4, 4, read_int);
+    too_small!(small_int_5, 5, read_int);
+    too_small!(small_int_6, 6, read_int);
+    too_small!(small_int_7, 7, read_int);
+
+    #[test]
+    fn uint_bigger_buffer() {
+        use {ByteOrder, LittleEndian};
+        let n = LittleEndian::read_uint(&[1, 2, 3, 4, 5, 6, 7, 8], 5);
+        assert_eq!(n, 0x0504030201);
+    }
+}
new file mode 100644
--- /dev/null
+++ b/media/libstagefright/binding/byteorder/src/new.rs
@@ -0,0 +1,269 @@
+use std::io::{self, Result};
+
+use ByteOrder;
+
+/// Extends `Read` with methods for reading numbers. (For `std::io`.)
+///
+/// Most of the methods defined here have an unconstrained type parameter that
+/// must be explicitly instantiated. Typically, it is instantiated with either
+/// the `BigEndian` or `LittleEndian` types defined in this crate.
+///
+/// # Examples
+///
+/// Read unsigned 16 bit big-endian integers from a `Read`:
+///
+/// ```rust
+/// use std::io::Cursor;
+/// use byteorder::{BigEndian, ReadBytesExt};
+///
+/// let mut rdr = Cursor::new(vec![2, 5, 3, 0]);
+/// assert_eq!(517, rdr.read_u16::<BigEndian>().unwrap());
+/// assert_eq!(768, rdr.read_u16::<BigEndian>().unwrap());
+/// ```
+pub trait ReadBytesExt: io::Read {
+    /// Reads an unsigned 8 bit integer from the underlying reader.
+    ///
+    /// Note that since this reads a single byte, no byte order conversions
+    /// are used. It is included for completeness.
+    #[inline]
+    fn read_u8(&mut self) -> Result<u8> {
+        let mut buf = [0; 1];
+        try!(self.read_exact(&mut buf));
+        Ok(buf[0])
+    }
+
+    /// Reads a signed 8 bit integer from the underlying reader.
+    ///
+    /// Note that since this reads a single byte, no byte order conversions
+    /// are used. It is included for completeness.
+    #[inline]
+    fn read_i8(&mut self) -> Result<i8> {
+        let mut buf = [0; 1];
+        try!(self.read_exact(&mut buf));
+        Ok(buf[0] as i8)
+    }
+
+    /// Reads an unsigned 16 bit integer from the underlying reader.
+    #[inline]
+    fn read_u16<T: ByteOrder>(&mut self) -> Result<u16> {
+        let mut buf = [0; 2];
+        try!(self.read_exact(&mut buf));
+        Ok(T::read_u16(&buf))
+    }
+
+    /// Reads a signed 16 bit integer from the underlying reader.
+    #[inline]
+    fn read_i16<T: ByteOrder>(&mut self) -> Result<i16> {
+        let mut buf = [0; 2];
+        try!(self.read_exact(&mut buf));
+        Ok(T::read_i16(&buf))
+    }
+
+    /// Reads an unsigned 32 bit integer from the underlying reader.
+    #[inline]
+    fn read_u32<T: ByteOrder>(&mut self) -> Result<u32> {
+        let mut buf = [0; 4];
+        try!(self.read_exact(&mut buf));
+        Ok(T::read_u32(&buf))
+    }
+
+    /// Reads a signed 32 bit integer from the underlying reader.
+    #[inline]
+    fn read_i32<T: ByteOrder>(&mut self) -> Result<i32> {
+        let mut buf = [0; 4];
+        try!(self.read_exact(&mut buf));
+        Ok(T::read_i32(&buf))
+    }
+
+    /// Reads an unsigned 64 bit integer from the underlying reader.
+    #[inline]
+    fn read_u64<T: ByteOrder>(&mut self) -> Result<u64> {
+        let mut buf = [0; 8];
+        try!(self.read_exact(&mut buf));
+        Ok(T::read_u64(&buf))
+    }
+
+    /// Reads a signed 64 bit integer from the underlying reader.
+    #[inline]
+    fn read_i64<T: ByteOrder>(&mut self) -> Result<i64> {
+        let mut buf = [0; 8];
+        try!(self.read_exact(&mut buf));
+        Ok(T::read_i64(&buf))
+    }
+
+    /// Reads an unsigned n-bytes integer from the underlying reader.
+    #[inline]
+    fn read_uint<T: ByteOrder>(&mut self, nbytes: usize) -> Result<u64> {
+        let mut buf = [0; 8];
+        try!(self.read_exact(&mut buf[..nbytes]));
+        Ok(T::read_uint(&buf[..nbytes], nbytes))
+    }
+
+    /// Reads a signed n-bytes integer from the underlying reader.
+    #[inline]
+    fn read_int<T: ByteOrder>(&mut self, nbytes: usize) -> Result<i64> {
+        let mut buf = [0; 8];
+        try!(self.read_exact(&mut buf[..nbytes]));
+        Ok(T::read_int(&buf[..nbytes], nbytes))
+    }
+
+    /// Reads a IEEE754 single-precision (4 bytes) floating point number from
+    /// the underlying reader.
+    #[inline]
+    fn read_f32<T: ByteOrder>(&mut self) -> Result<f32> {
+        let mut buf = [0; 4];
+        try!(self.read_exact(&mut buf));
+        Ok(T::read_f32(&buf))
+    }
+
+    /// Reads a IEEE754 double-precision (8 bytes) floating point number from
+    /// the underlying reader.
+    #[inline]
+    fn read_f64<T: ByteOrder>(&mut self) -> Result<f64> {
+        let mut buf = [0; 8];
+        try!(self.read_exact(&mut buf));
+        Ok(T::read_f64(&buf))
+    }
+}
+
+/// All types that implement `Read` get methods defined in `ReadBytesExt`
+/// for free.
+impl<R: io::Read + ?Sized> ReadBytesExt for R {}
+
+/// Extends `Write` with methods for writing numbers. (For `std::io`.)
+///
+/// Most of the methods defined here have an unconstrained type parameter that
+/// must be explicitly instantiated. Typically, it is instantiated with either
+/// the `BigEndian` or `LittleEndian` types defined in this crate.
+///
+/// # Examples
+///
+/// Write unsigned 16 bit big-endian integers to a `Write`:
+///
+/// ```rust
+/// use byteorder::{BigEndian, WriteBytesExt};
+///
+/// let mut wtr = vec![];
+/// wtr.write_u16::<BigEndian>(517).unwrap();
+/// wtr.write_u16::<BigEndian>(768).unwrap();
+/// assert_eq!(wtr, vec![2, 5, 3, 0]);
+/// ```
+pub trait WriteBytesExt: io::Write {
+    /// Writes an unsigned 8 bit integer to the underlying writer.
+    ///
+    /// Note that since this writes a single byte, no byte order conversions
+    /// are used. It is included for completeness.
+    #[inline]
+    fn write_u8(&mut self, n: u8) -> Result<()> {
+        self.write_all(&[n])
+    }
+
+    /// Writes a signed 8 bit integer to the underlying writer.
+    ///
+    /// Note that since this writes a single byte, no byte order conversions
+    /// are used. It is included for completeness.
+    #[inline]
+    fn write_i8(&mut self, n: i8) -> Result<()> {
+        self.write_all(&[n as u8])
+    }
+
+    /// Writes an unsigned 16 bit integer to the underlying writer.
+    #[inline]
+    fn write_u16<T: ByteOrder>(&mut self, n: u16) -> Result<()> {
+        let mut buf = [0; 2];
+        T::write_u16(&mut buf, n);
+        self.write_all(&buf)
+    }
+
+    /// Writes a signed 16 bit integer to the underlying writer.
+    #[inline]
+    fn write_i16<T: ByteOrder>(&mut self, n: i16) -> Result<()> {
+        let mut buf = [0; 2];
+        T::write_i16(&mut buf, n);
+        self.write_all(&buf)
+    }
+
+    /// Writes an unsigned 32 bit integer to the underlying writer.
+    #[inline]
+    fn write_u32<T: ByteOrder>(&mut self, n: u32) -> Result<()> {
+        let mut buf = [0; 4];
+        T::write_u32(&mut buf, n);
+        self.write_all(&buf)
+    }
+
+    /// Writes a signed 32 bit integer to the underlying writer.
+    #[inline]
+    fn write_i32<T: ByteOrder>(&mut self, n: i32) -> Result<()> {
+        let mut buf = [0; 4];
+        T::write_i32(&mut buf, n);
+        self.write_all(&buf)
+    }
+
+    /// Writes an unsigned 64 bit integer to the underlying writer.
+    #[inline]
+    fn write_u64<T: ByteOrder>(&mut self, n: u64) -> Result<()> {
+        let mut buf = [0; 8];
+        T::write_u64(&mut buf, n);
+        self.write_all(&buf)
+    }
+
+    /// Writes a signed 64 bit integer to the underlying writer.
+    #[inline]
+    fn write_i64<T: ByteOrder>(&mut self, n: i64) -> Result<()> {
+        let mut buf = [0; 8];
+        T::write_i64(&mut buf, n);
+        self.write_all(&buf)
+    }
+
+    /// Writes an unsigned n-bytes integer to the underlying writer.
+    ///
+    /// If the given integer is not representable in the given number of bytes,
+    /// this method panics. If `nbytes > 8`, this method panics.
+    #[inline]
+    fn write_uint<T: ByteOrder>(
+        &mut self,
+        n: u64,
+        nbytes: usize,
+    ) -> Result<()> {
+        let mut buf = [0; 8];
+        T::write_uint(&mut buf, n, nbytes);
+        self.write_all(&buf[0..nbytes])
+    }
+
+    /// Writes a signed n-bytes integer to the underlying writer.
+    ///
+    /// If the given integer is not representable in the given number of bytes,
+    /// this method panics. If `nbytes > 8`, this method panics.
+    #[inline]
+    fn write_int<T: ByteOrder>(
+        &mut self,
+        n: i64,
+        nbytes: usize,
+    ) -> Result<()> {
+        let mut buf = [0; 8];
+        T::write_int(&mut buf, n, nbytes);
+        self.write_all(&buf[0..nbytes])
+    }
+
+    /// Writes a IEEE754 single-precision (4 bytes) floating point number to
+    /// the underlying writer.
+    #[inline]
+    fn write_f32<T: ByteOrder>(&mut self, n: f32) -> Result<()> {
+        let mut buf = [0; 4];
+        T::write_f32(&mut buf, n);
+        self.write_all(&buf)
+    }
+
+    /// Writes a IEEE754 double-precision (8 bytes) floating point number to
+    /// the underlying writer.
+    #[inline]
+    fn write_f64<T: ByteOrder>(&mut self, n: f64) -> Result<()> {
+        let mut buf = [0; 8];
+        T::write_f64(&mut buf, n);
+        self.write_all(&buf)
+    }
+}
+
+/// All types that implement `Write` get methods defined in `WriteBytesExt`
+/// for free.
+impl<W: io::Write + ?Sized> WriteBytesExt for W {}
--- a/media/libstagefright/binding/mp4parse/Cargo.toml
+++ b/media/libstagefright/binding/mp4parse/Cargo.toml
@@ -15,8 +15,11 @@ repository = "https://github.com/mozilla
 # by default! Avoid bloating the package with test files.
 exclude = [
   "*.mp4",
 ]
 
 # Somewhat heavy-handed, but we want at least -Z force-overflow-checks=on.
 [profile.release]
 debug-assertions = true
+
+[dependencies]
+byteorder = { path = "../byteorder" }
deleted file mode 100644
--- a/media/libstagefright/binding/mp4parse/src/byteorder/mod.rs
+++ /dev/null
@@ -1,795 +0,0 @@
-/*!
-This crate provides convenience methods for encoding and decoding numbers
-in either big-endian or little-endian order.
-
-The organization of the crate is pretty simple. A trait, `ByteOrder`, specifies
-byte conversion methods for each type of number in Rust (sans numbers that have
-a platform dependent size like `usize` and `isize`). Two types, `BigEndian`
-and `LittleEndian` implement these methods. Finally, `ReadBytesExt` and
-`WriteBytesExt` provide convenience methods available to all types that
-implement `Read` and `Write`.
-
-# Examples
-
-Read unsigned 16 bit big-endian integers from a `Read` type:
-
-```rust
-use std::io::Cursor;
-use byteorder::{BigEndian, ReadBytesExt};
-
-let mut rdr = Cursor::new(vec![2, 5, 3, 0]);
-// Note that we use type parameters to indicate which kind of byte order
-// we want!
-assert_eq!(517, rdr.read_u16::<BigEndian>().unwrap());
-assert_eq!(768, rdr.read_u16::<BigEndian>().unwrap());
-```
-
-Write unsigned 16 bit little-endian integers to a `Write` type:
-
-```rust
-use byteorder::{LittleEndian, WriteBytesExt};
-
-let mut wtr = vec![];
-wtr.write_u16::<LittleEndian>(517).unwrap();
-wtr.write_u16::<LittleEndian>(768).unwrap();
-assert_eq!(wtr, vec![5, 2, 0, 3]);
-```
-*/
-
-#![doc(html_root_url = "http://burntsushi.net/rustdoc/byteorder")]
-
-#![deny(missing_docs)]
-
-use std::mem::transmute;
-use std::ptr::copy_nonoverlapping;
-
-pub use byteorder::new::{ReadBytesExt, WriteBytesExt};
-
-// Re-export new so gecko can build us as a mod instead of a crate.
-pub mod new;
-
-#[inline]
-fn extend_sign(val: u64, nbytes: usize) -> i64 {
-    let shift = (8 - nbytes) * 8;
-    (val << shift) as i64 >> shift
-}
-
-#[inline]
-fn unextend_sign(val: i64, nbytes: usize) -> u64 {
-    let shift = (8 - nbytes) * 8;
-    (val << shift) as u64 >> shift
-}
-
-#[inline]
-fn pack_size(n: u64) -> usize {
-    if n < 1 << 8 {
-        1
-    } else if n < 1 << 16 {
-        2
-    } else if n < 1 << 24 {
-        3
-    } else if n < 1 << 32 {
-        4
-    } else if n < 1 << 40 {
-        5
-    } else if n < 1 << 48 {
-        6
-    } else if n < 1 << 56 {
-        7
-    } else {
-        8
-    }
-}
-
-/// ByteOrder describes types that can serialize integers as bytes.
-///
-/// Note that `Self` does not appear anywhere in this trait's definition!
-/// Therefore, in order to use it, you'll need to use syntax like
-/// `T::read_u16(&[0, 1])` where `T` implements `ByteOrder`.
-///
-/// This crate provides two types that implement `ByteOrder`: `BigEndian`
-/// and `LittleEndian`.
-///
-/// # Examples
-///
-/// Write and read `u32` numbers in little endian order:
-///
-/// ```rust
-/// use byteorder::{ByteOrder, LittleEndian};
-///
-/// let mut buf = [0; 4];
-/// LittleEndian::write_u32(&mut buf, 1_000_000);
-/// assert_eq!(1_000_000, LittleEndian::read_u32(&buf));
-/// ```
-///
-/// Write and read `i16` numbers in big endian order:
-///
-/// ```rust
-/// use byteorder::{ByteOrder, BigEndian};
-///
-/// let mut buf = [0; 2];
-/// BigEndian::write_i16(&mut buf, -50_000);
-/// assert_eq!(-50_000, BigEndian::read_i16(&buf));
-/// ```
-pub trait ByteOrder {
-    /// Reads an unsigned 16 bit integer from `buf`.
-    ///
-    /// Panics when `buf.len() < 2`.
-    fn read_u16(buf: &[u8]) -> u16;
-
-    /// Reads an unsigned 32 bit integer from `buf`.
-    ///
-    /// Panics when `buf.len() < 4`.
-    fn read_u32(buf: &[u8]) -> u32;
-
-    /// Reads an unsigned 64 bit integer from `buf`.
-    ///
-    /// Panics when `buf.len() < 8`.
-    fn read_u64(buf: &[u8]) -> u64;
-
-    /// Reads an unsigned n-bytes integer from `buf`.
-    ///
-    /// Panics when `nbytes < 1` or `nbytes > 8` or
-    /// `buf.len() < nbytes`
-    fn read_uint(buf: &[u8], nbytes: usize) -> u64;
-
-    /// Writes an unsigned 16 bit integer `n` to `buf`.
-    ///
-    /// Panics when `buf.len() < 2`.
-    fn write_u16(buf: &mut [u8], n: u16);
-
-    /// Writes an unsigned 32 bit integer `n` to `buf`.
-    ///
-    /// Panics when `buf.len() < 4`.
-    fn write_u32(buf: &mut [u8], n: u32);
-
-    /// Writes an unsigned 64 bit integer `n` to `buf`.
-    ///
-    /// Panics when `buf.len() < 8`.
-    fn write_u64(buf: &mut [u8], n: u64);
-
-    /// Writes an unsigned integer `n` to `buf` using only `nbytes`.
-    ///
-    /// If `n` is not representable in `nbytes`, or if `nbytes` is `> 8`, then
-    /// this method panics.
-    fn write_uint(buf: &mut [u8], n: u64, nbytes: usize);
-
-    /// Reads a signed 16 bit integer from `buf`.
-    ///
-    /// Panics when `buf.len() < 2`.
-    #[inline]
-    fn read_i16(buf: &[u8]) -> i16 {
-        Self::read_u16(buf) as i16
-    }
-
-    /// Reads a signed 32 bit integer from `buf`.
-    ///
-    /// Panics when `buf.len() < 4`.
-    #[inline]
-    fn read_i32(buf: &[u8]) -> i32 {
-        Self::read_u32(buf) as i32
-    }
-
-    /// Reads a signed 64 bit integer from `buf`.
-    ///
-    /// Panics when `buf.len() < 8`.
-    #[inline]
-    fn read_i64(buf: &[u8]) -> i64 {
-        Self::read_u64(buf) as i64
-    }
-
-    /// Reads a signed n-bytes integer from `buf`.
-    ///
-    /// Panics when `nbytes < 1` or `nbytes > 8` or
-    /// `buf.len() < nbytes`
-    #[inline]
-    fn read_int(buf: &[u8], nbytes: usize) -> i64 {
-        extend_sign(Self::read_uint(buf, nbytes), nbytes)
-    }
-
-    /// Reads a IEEE754 single-precision (4 bytes) floating point number.
-    ///
-    /// Panics when `buf.len() < 4`.
-    #[inline]
-    fn read_f32(buf: &[u8]) -> f32 {
-        unsafe { transmute(Self::read_u32(buf)) }
-    }
-
-    /// Reads a IEEE754 double-precision (8 bytes) floating point number.
-    ///
-    /// Panics when `buf.len() < 8`.
-    #[inline]
-    fn read_f64(buf: &[u8]) -> f64 {
-        unsafe { transmute(Self::read_u64(buf)) }
-    }
-
-    /// Writes a signed 16 bit integer `n` to `buf`.
-    ///
-    /// Panics when `buf.len() < 2`.
-    #[inline]
-    fn write_i16(buf: &mut [u8], n: i16) {
-        Self::write_u16(buf, n as u16)
-    }
-
-    /// Writes a signed 32 bit integer `n` to `buf`.
-    ///
-    /// Panics when `buf.len() < 4`.
-    #[inline]
-    fn write_i32(buf: &mut [u8], n: i32) {
-        Self::write_u32(buf, n as u32)
-    }
-
-    /// Writes a signed 64 bit integer `n` to `buf`.
-    ///
-    /// Panics when `buf.len() < 8`.
-    #[inline]
-    fn write_i64(buf: &mut [u8], n: i64) {
-        Self::write_u64(buf, n as u64)
-    }
-
-    /// Writes a signed integer `n` to `buf` using only `nbytes`.
-    ///
-    /// If `n` is not representable in `nbytes`, or if `nbytes` is `> 8`, then
-    /// this method panics.
-    #[inline]
-    fn write_int(buf: &mut [u8], n: i64, nbytes: usize) {
-        Self::write_uint(buf, unextend_sign(n, nbytes), nbytes)
-    }
-
-    /// Writes a IEEE754 single-precision (4 bytes) floating point number.
-    ///
-    /// Panics when `buf.len() < 4`.
-    #[inline]
-    fn write_f32(buf: &mut [u8], n: f32) {
-        Self::write_u32(buf, unsafe { transmute(n) })
-    }
-
-    /// Writes a IEEE754 double-precision (8 bytes) floating point number.
-    ///
-    /// Panics when `buf.len() < 8`.
-    #[inline]
-    fn write_f64(buf: &mut [u8], n: f64) {
-        Self::write_u64(buf, unsafe { transmute(n) })
-    }
-}
-
-/// Defines big-endian serialization.
-///
-/// Note that this type has no value constructor. It is used purely at the
-/// type level.
-#[allow(missing_copy_implementations)] pub enum BigEndian {}
-
-/// Defines little-endian serialization.
-///
-/// Note that this type has no value constructor. It is used purely at the
-/// type level.
-#[allow(missing_copy_implementations)] pub enum LittleEndian {}
-
-/// Defines network byte order serialization.
-///
-/// Network byte order is defined by [RFC 1700][1] to be big-endian, and is
-/// referred to in several protocol specifications.  This type is an alias of
-/// BigEndian.
-///
-/// [1]: https://tools.ietf.org/html/rfc1700
-///
-/// Note that this type has no value constructor. It is used purely at the
-/// type level.
-pub type NetworkEndian = BigEndian;
-
-/// Defines system native-endian serialization.
-///
-/// Note that this type has no value constructor. It is used purely at the
-/// type level.
-#[cfg(target_endian = "little")]
-pub type NativeEndian = LittleEndian;
-
-/// Defines system native-endian serialization.
-///
-/// Note that this type has no value constructor. It is used purely at the
-/// type level.
-#[cfg(target_endian = "big")]
-pub type NativeEndian = BigEndian;
-
-macro_rules! read_num_bytes {
-    ($ty:ty, $size:expr, $src:expr, $which:ident) => ({
-        assert!($size == ::std::mem::size_of::<$ty>());
-        assert!($size <= $src.len());
-        let mut data: $ty = 0;
-        unsafe {
-            copy_nonoverlapping(
-                $src.as_ptr(),
-                &mut data as *mut $ty as *mut u8,
-                $size);
-        }
-        data.$which()
-    });
-}
-
-macro_rules! write_num_bytes {
-    ($ty:ty, $size:expr, $n:expr, $dst:expr, $which:ident) => ({
-        assert!($size <= $dst.len());
-        unsafe {
-            // N.B. https://github.com/rust-lang/rust/issues/22776
-            let bytes = transmute::<_, [u8; $size]>($n.$which());
-            copy_nonoverlapping((&bytes).as_ptr(), $dst.as_mut_ptr(), $size);
-        }
-    });
-}
-
-impl ByteOrder for BigEndian {
-    #[inline]
-    fn read_u16(buf: &[u8]) -> u16 {
-        read_num_bytes!(u16, 2, buf, to_be)
-    }
-
-    #[inline]
-    fn read_u32(buf: &[u8]) -> u32 {
-        read_num_bytes!(u32, 4, buf, to_be)
-    }
-
-    #[inline]
-    fn read_u64(buf: &[u8]) -> u64 {
-        read_num_bytes!(u64, 8, buf, to_be)
-    }
-
-    #[inline]
-    fn read_uint(buf: &[u8], nbytes: usize) -> u64 {
-        assert!(1 <= nbytes && nbytes <= 8 && nbytes <= buf.len());
-        let mut out = [0u8; 8];
-        let ptr_out = out.as_mut_ptr();
-        unsafe {
-            copy_nonoverlapping(
-                buf.as_ptr(), ptr_out.offset((8 - nbytes) as isize), nbytes);
-            (*(ptr_out as *const u64)).to_be()
-        }
-    }
-
-    #[inline]
-    fn write_u16(buf: &mut [u8], n: u16) {
-        write_num_bytes!(u16, 2, n, buf, to_be);
-    }
-
-    #[inline]
-    fn write_u32(buf: &mut [u8], n: u32) {
-        write_num_bytes!(u32, 4, n, buf, to_be);
-    }
-
-    #[inline]
-    fn write_u64(buf: &mut [u8], n: u64) {
-        write_num_bytes!(u64, 8, n, buf, to_be);
-    }
-
-    #[inline]
-    fn write_uint(buf: &mut [u8], n: u64, nbytes: usize) {
-        assert!(pack_size(n) <= nbytes && nbytes <= 8);
-        assert!(nbytes <= buf.len());
-        unsafe {
-            let bytes: [u8; 8] = transmute(n.to_be());
-            copy_nonoverlapping(
-                bytes.as_ptr().offset((8 - nbytes) as isize),
-                buf.as_mut_ptr(),
-                nbytes);
-        }
-    }
-}
-
-impl ByteOrder for LittleEndian {
-    #[inline]
-    fn read_u16(buf: &[u8]) -> u16 {
-        read_num_bytes!(u16, 2, buf, to_le)
-    }
-
-    #[inline]
-    fn read_u32(buf: &[u8]) -> u32 {
-        read_num_bytes!(u32, 4, buf, to_le)
-    }
-
-    #[inline]
-    fn read_u64(buf: &[u8]) -> u64 {
-        read_num_bytes!(u64, 8, buf, to_le)
-    }
-
-    #[inline]
-    fn read_uint(buf: &[u8], nbytes: usize) -> u64 {
-        assert!(1 <= nbytes && nbytes <= 8 && nbytes <= buf.len());
-        let mut out = [0u8; 8];
-        let ptr_out = out.as_mut_ptr();
-        unsafe {
-            copy_nonoverlapping(buf.as_ptr(), ptr_out, nbytes);
-            (*(ptr_out as *const u64)).to_le()
-        }
-    }
-
-    #[inline]
-    fn write_u16(buf: &mut [u8], n: u16) {
-        write_num_bytes!(u16, 2, n, buf, to_le);
-    }
-
-    #[inline]
-    fn write_u32(buf: &mut [u8], n: u32) {
-        write_num_bytes!(u32, 4, n, buf, to_le);
-    }
-
-    #[inline]
-    fn write_u64(buf: &mut [u8], n: u64) {
-        write_num_bytes!(u64, 8, n, buf, to_le);
-    }
-
-    #[inline]
-    fn write_uint(buf: &mut [u8], n: u64, nbytes: usize) {
-        assert!(pack_size(n as u64) <= nbytes && nbytes <= 8);
-        assert!(nbytes <= buf.len());
-        unsafe {
-            let bytes: [u8; 8] = transmute(n.to_le());
-            copy_nonoverlapping(bytes.as_ptr(), buf.as_mut_ptr(), nbytes);
-        }
-    }
-}
-
-#[cfg(test)]
-mod test {
-    extern crate quickcheck;
-    extern crate rand;
-
-    use test::rand::thread_rng;
-    use test::quickcheck::{QuickCheck, StdGen, Testable};
-
-    const U64_MAX: u64 = ::std::u64::MAX;
-    const I64_MAX: u64 = ::std::i64::MAX as u64;
-
-    fn qc_sized<A: Testable>(f: A, size: u64) {
-        QuickCheck::new()
-            .gen(StdGen::new(thread_rng(), size as usize))
-            .tests(1_00)
-            .max_tests(10_000)
-            .quickcheck(f);
-    }
-
-    macro_rules! qc_byte_order {
-        ($name:ident, $ty_int:ident, $max:expr,
-         $bytes:expr, $read:ident, $write:ident) => (
-            mod $name {
-                use {BigEndian, ByteOrder, NativeEndian, LittleEndian};
-                use super::qc_sized;
-
-                #[test]
-                fn big_endian() {
-                    let max = ($max - 1) >> (8 * (8 - $bytes));
-                    fn prop(n: $ty_int) -> bool {
-                        let mut buf = [0; 8];
-                        BigEndian::$write(&mut buf, n, $bytes);
-                        n == BigEndian::$read(&mut buf[..$bytes], $bytes)
-                    }
-                    qc_sized(prop as fn($ty_int) -> bool, max);
-                }
-
-                #[test]
-                fn little_endian() {
-                    let max = ($max - 1) >> (8 * (8 - $bytes));
-                    fn prop(n: $ty_int) -> bool {
-                        let mut buf = [0; 8];
-                        LittleEndian::$write(&mut buf, n, $bytes);
-                        n == LittleEndian::$read(&mut buf[..$bytes], $bytes)
-                    }
-                    qc_sized(prop as fn($ty_int) -> bool, max);
-                }
-
-                #[test]
-                fn native_endian() {
-                    let max = ($max - 1) >> (8 * (8 - $bytes));
-                    fn prop(n: $ty_int) -> bool {
-                        let mut buf = [0; 8];
-                        NativeEndian::$write(&mut buf, n, $bytes);
-                        n == NativeEndian::$read(&mut buf[..$bytes], $bytes)
-                    }
-                    qc_sized(prop as fn($ty_int) -> bool, max);
-                }
-            }
-        );
-        ($name:ident, $ty_int:ident, $max:expr,
-         $read:ident, $write:ident) => (
-            mod $name {
-                use std::mem::size_of;
-                use {BigEndian, ByteOrder, NativeEndian, LittleEndian};
-                use super::qc_sized;
-
-                #[test]
-                fn big_endian() {
-                    fn prop(n: $ty_int) -> bool {
-                        let bytes = size_of::<$ty_int>();
-                        let mut buf = [0; 8];
-                        BigEndian::$write(&mut buf[8 - bytes..], n);
-                        n == BigEndian::$read(&mut buf[8 - bytes..])
-                    }
-                    qc_sized(prop as fn($ty_int) -> bool, $max - 1);
-                }
-
-                #[test]
-                fn little_endian() {
-                    fn prop(n: $ty_int) -> bool {
-                        let bytes = size_of::<$ty_int>();
-                        let mut buf = [0; 8];
-                        LittleEndian::$write(&mut buf[..bytes], n);
-                        n == LittleEndian::$read(&mut buf[..bytes])
-                    }
-                    qc_sized(prop as fn($ty_int) -> bool, $max - 1);
-                }
-
-                #[test]
-                fn native_endian() {
-                    fn prop(n: $ty_int) -> bool {
-                        let bytes = size_of::<$ty_int>();
-                        let mut buf = [0; 8];
-                        NativeEndian::$write(&mut buf[..bytes], n);
-                        n == NativeEndian::$read(&mut buf[..bytes])
-                    }
-                    qc_sized(prop as fn($ty_int) -> bool, $max - 1);
-                }
-            }
-        );
-    }
-
-    qc_byte_order!(prop_u16, u16, ::std::u16::MAX as u64, read_u16, write_u16);
-    qc_byte_order!(prop_i16, i16, ::std::i16::MAX as u64, read_i16, write_i16);
-    qc_byte_order!(prop_u32, u32, ::std::u32::MAX as u64, read_u32, write_u32);
-    qc_byte_order!(prop_i32, i32, ::std::i32::MAX as u64, read_i32, write_i32);
-    qc_byte_order!(prop_u64, u64, ::std::u64::MAX as u64, read_u64, write_u64);
-    qc_byte_order!(prop_i64, i64, ::std::i64::MAX as u64, read_i64, write_i64);
-    qc_byte_order!(prop_f32, f32, ::std::u64::MAX as u64, read_f32, write_f32);
-    qc_byte_order!(prop_f64, f64, ::std::i64::MAX as u64, read_f64, write_f64);
-
-    qc_byte_order!(prop_uint_1, u64, super::U64_MAX, 1, read_uint, write_uint);
-    qc_byte_order!(prop_uint_2, u64, super::U64_MAX, 2, read_uint, write_uint);
-    qc_byte_order!(prop_uint_3, u64, super::U64_MAX, 3, read_uint, write_uint);
-    qc_byte_order!(prop_uint_4, u64, super::U64_MAX, 4, read_uint, write_uint);
-    qc_byte_order!(prop_uint_5, u64, super::U64_MAX, 5, read_uint, write_uint);
-    qc_byte_order!(prop_uint_6, u64, super::U64_MAX, 6, read_uint, write_uint);
-    qc_byte_order!(prop_uint_7, u64, super::U64_MAX, 7, read_uint, write_uint);
-    qc_byte_order!(prop_uint_8, u64, super::U64_MAX, 8, read_uint, write_uint);
-
-    qc_byte_order!(prop_int_1, i64, super::I64_MAX, 1, read_int, write_int);
-    qc_byte_order!(prop_int_2, i64, super::I64_MAX, 2, read_int, write_int);
-    qc_byte_order!(prop_int_3, i64, super::I64_MAX, 3, read_int, write_int);
-    qc_byte_order!(prop_int_4, i64, super::I64_MAX, 4, read_int, write_int);
-    qc_byte_order!(prop_int_5, i64, super::I64_MAX, 5, read_int, write_int);
-    qc_byte_order!(prop_int_6, i64, super::I64_MAX, 6, read_int, write_int);
-    qc_byte_order!(prop_int_7, i64, super::I64_MAX, 7, read_int, write_int);
-    qc_byte_order!(prop_int_8, i64, super::I64_MAX, 8, read_int, write_int);
-
-    macro_rules! qc_bytes_ext {
-        ($name:ident, $ty_int:ident, $max:expr,
-         $bytes:expr, $read:ident, $write:ident) => (
-            mod $name {
-                use std::io::Cursor;
-                use {
-                    ReadBytesExt, WriteBytesExt,
-                    BigEndian, NativeEndian, LittleEndian,
-                };
-                use super::qc_sized;
-
-                #[test]
-                fn big_endian() {
-                    let max = ($max - 1) >> (8 * (8 - $bytes));
-                    fn prop(n: $ty_int) -> bool {
-                        let mut wtr = vec![];
-                        wtr.$write::<BigEndian>(n).unwrap();
-                        let mut rdr = Vec::new();
-                        rdr.extend(wtr[8 - $bytes..].iter().map(|&x|x));
-                        let mut rdr = Cursor::new(rdr);
-                        n == rdr.$read::<BigEndian>($bytes).unwrap()
-                    }
-                    qc_sized(prop as fn($ty_int) -> bool, max);
-                }
-
-                #[test]
-                fn little_endian() {
-                    let max = ($max - 1) >> (8 * (8 - $bytes));
-                    fn prop(n: $ty_int) -> bool {
-                        let mut wtr = vec![];
-                        wtr.$write::<LittleEndian>(n).unwrap();
-                        let mut rdr = Cursor::new(wtr);
-                        n == rdr.$read::<LittleEndian>($bytes).unwrap()
-                    }
-                    qc_sized(prop as fn($ty_int) -> bool, max);
-                }
-
-                #[test]
-                fn native_endian() {
-                    let max = ($max - 1) >> (8 * (8 - $bytes));
-                    fn prop(n: $ty_int) -> bool {
-                        let mut wtr = vec![];
-                        wtr.$write::<NativeEndian>(n).unwrap();
-                        let mut rdr = Cursor::new(wtr);
-                        n == rdr.$read::<NativeEndian>($bytes).unwrap()
-                    }
-                    qc_sized(prop as fn($ty_int) -> bool, max);
-                }
-            }
-        );
-        ($name:ident, $ty_int:ident, $max:expr, $read:ident, $write:ident) => (
-            mod $name {
-                use std::io::Cursor;
-                use {
-                    ReadBytesExt, WriteBytesExt,
-                    BigEndian, NativeEndian, LittleEndian,
-                };
-                use super::qc_sized;
-
-                #[test]
-                fn big_endian() {
-                    fn prop(n: $ty_int) -> bool {
-                        let mut wtr = vec![];
-                        wtr.$write::<BigEndian>(n).unwrap();
-                        let mut rdr = Cursor::new(wtr);
-                        n == rdr.$read::<BigEndian>().unwrap()
-                    }
-                    qc_sized(prop as fn($ty_int) -> bool, $max - 1);
-                }
-
-                #[test]
-                fn little_endian() {
-                    fn prop(n: $ty_int) -> bool {
-                        let mut wtr = vec![];
-                        wtr.$write::<LittleEndian>(n).unwrap();
-                        let mut rdr = Cursor::new(wtr);
-                        n == rdr.$read::<LittleEndian>().unwrap()
-                    }
-                    qc_sized(prop as fn($ty_int) -> bool, $max - 1);
-                }
-
-                #[test]
-                fn native_endian() {
-                    fn prop(n: $ty_int) -> bool {
-                        let mut wtr = vec![];
-                        wtr.$write::<NativeEndian>(n).unwrap();
-                        let mut rdr = Cursor::new(wtr);
-                        n == rdr.$read::<NativeEndian>().unwrap()
-                    }
-                    qc_sized(prop as fn($ty_int) -> bool, $max - 1);
-                }
-            }
-        );
-    }
-
-    qc_bytes_ext!(prop_ext_u16, u16, ::std::u16::MAX as u64, read_u16, write_u16);
-    qc_bytes_ext!(prop_ext_i16, i16, ::std::i16::MAX as u64, read_i16, write_i16);
-    qc_bytes_ext!(prop_ext_u32, u32, ::std::u32::MAX as u64, read_u32, write_u32);
-    qc_bytes_ext!(prop_ext_i32, i32, ::std::i32::MAX as u64, read_i32, write_i32);
-    qc_bytes_ext!(prop_ext_u64, u64, ::std::u64::MAX as u64, read_u64, write_u64);
-    qc_bytes_ext!(prop_ext_i64, i64, ::std::i64::MAX as u64, read_i64, write_i64);
-    qc_bytes_ext!(prop_ext_f32, f32, ::std::u64::MAX as u64, read_f32, write_f32);
-    qc_bytes_ext!(prop_ext_f64, f64, ::std::i64::MAX as u64, read_f64, write_f64);
-
-    qc_bytes_ext!(prop_ext_uint_1, u64, super::U64_MAX, 1, read_uint, write_u64);
-    qc_bytes_ext!(prop_ext_uint_2, u64, super::U64_MAX, 2, read_uint, write_u64);
-    qc_bytes_ext!(prop_ext_uint_3, u64, super::U64_MAX, 3, read_uint, write_u64);
-    qc_bytes_ext!(prop_ext_uint_4, u64, super::U64_MAX, 4, read_uint, write_u64);
-    qc_bytes_ext!(prop_ext_uint_5, u64, super::U64_MAX, 5, read_uint, write_u64);
-    qc_bytes_ext!(prop_ext_uint_6, u64, super::U64_MAX, 6, read_uint, write_u64);
-    qc_bytes_ext!(prop_ext_uint_7, u64, super::U64_MAX, 7, read_uint, write_u64);
-    qc_bytes_ext!(prop_ext_uint_8, u64, super::U64_MAX, 8, read_uint, write_u64);
-
-    qc_bytes_ext!(prop_ext_int_1, i64, super::I64_MAX, 1, read_int, write_i64);
-    qc_bytes_ext!(prop_ext_int_2, i64, super::I64_MAX, 2, read_int, write_i64);
-    qc_bytes_ext!(prop_ext_int_3, i64, super::I64_MAX, 3, read_int, write_i64);
-    qc_bytes_ext!(prop_ext_int_4, i64, super::I64_MAX, 4, read_int, write_i64);
-    qc_bytes_ext!(prop_ext_int_5, i64, super::I64_MAX, 5, read_int, write_i64);
-    qc_bytes_ext!(prop_ext_int_6, i64, super::I64_MAX, 6, read_int, write_i64);
-    qc_bytes_ext!(prop_ext_int_7, i64, super::I64_MAX, 7, read_int, write_i64);
-    qc_bytes_ext!(prop_ext_int_8, i64, super::I64_MAX, 8, read_int, write_i64);
-
-    // Test that all of the byte conversion functions panic when given a
-    // buffer that is too small.
-    //
-    // These tests are critical to ensure safety, otherwise we might end up
-    // with a buffer overflow.
-    macro_rules! too_small {
-        ($name:ident, $maximally_small:expr, $zero:expr,
-         $read:ident, $write:ident) => (
-            mod $name {
-                use {BigEndian, ByteOrder, NativeEndian, LittleEndian};
-
-                #[test]
-                #[should_panic]
-                fn read_big_endian() {
-                    let buf = [0; $maximally_small];
-                    BigEndian::$read(&buf);
-                }
-
-                #[test]
-                #[should_panic]
-                fn read_little_endian() {
-                    let buf = [0; $maximally_small];
-                    LittleEndian::$read(&buf);
-                }
-
-                #[test]
-                #[should_panic]
-                fn read_native_endian() {
-                    let buf = [0; $maximally_small];
-                    NativeEndian::$read(&buf);
-                }
-
-                #[test]
-                #[should_panic]
-                fn write_big_endian() {
-                    let mut buf = [0; $maximally_small];
-                    BigEndian::$write(&mut buf, $zero);
-                }
-
-                #[test]
-                #[should_panic]
-                fn write_little_endian() {
-                    let mut buf = [0; $maximally_small];
-                    LittleEndian::$write(&mut buf, $zero);
-                }
-
-                #[test]
-                #[should_panic]
-                fn write_native_endian() {
-                    let mut buf = [0; $maximally_small];
-                    NativeEndian::$write(&mut buf, $zero);
-                }
-            }
-        );
-        ($name:ident, $maximally_small:expr, $read:ident) => (
-            mod $name {
-                use {BigEndian, ByteOrder, NativeEndian, LittleEndian};
-
-                #[test]
-                #[should_panic]
-                fn read_big_endian() {
-                    let buf = [0; $maximally_small];
-                    BigEndian::$read(&buf, $maximally_small + 1);
-                }
-
-                #[test]
-                #[should_panic]
-                fn read_little_endian() {
-                    let buf = [0; $maximally_small];
-                    LittleEndian::$read(&buf, $maximally_small + 1);
-                }
-
-                #[test]
-                #[should_panic]
-                fn read_native_endian() {
-                    let buf = [0; $maximally_small];
-                    NativeEndian::$read(&buf, $maximally_small + 1);
-                }
-            }
-        );
-    }
-
-    too_small!(small_u16, 1, 0, read_u16, write_u16);
-    too_small!(small_i16, 1, 0, read_i16, write_i16);
-    too_small!(small_u32, 3, 0, read_u32, write_u32);
-    too_small!(small_i32, 3, 0, read_i32, write_i32);
-    too_small!(small_u64, 7, 0, read_u64, write_u64);
-    too_small!(small_i64, 7, 0, read_i64, write_i64);
-    too_small!(small_f32, 3, 0.0, read_f32, write_f32);
-    too_small!(small_f64, 7, 0.0, read_f64, write_f64);
-
-    too_small!(small_uint_1, 1, read_uint);
-    too_small!(small_uint_2, 2, read_uint);
-    too_small!(small_uint_3, 3, read_uint);
-    too_small!(small_uint_4, 4, read_uint);
-    too_small!(small_uint_5, 5, read_uint);
-    too_small!(small_uint_6, 6, read_uint);
-    too_small!(small_uint_7, 7, read_uint);
-
-    too_small!(small_int_1, 1, read_int);
-    too_small!(small_int_2, 2, read_int);
-    too_small!(small_int_3, 3, read_int);
-    too_small!(small_int_4, 4, read_int);
-    too_small!(small_int_5, 5, read_int);
-    too_small!(small_int_6, 6, read_int);
-    too_small!(small_int_7, 7, read_int);
-
-    #[test]
-    fn uint_bigger_buffer() {
-        use {ByteOrder, LittleEndian};
-        let n = LittleEndian::read_uint(&[1, 2, 3, 4, 5, 6, 7, 8], 5);
-        assert_eq!(n, 0x0504030201);
-    }
-}
deleted file mode 100644
--- a/media/libstagefright/binding/mp4parse/src/byteorder/new.rs
+++ /dev/null
@@ -1,269 +0,0 @@
-use std::io::{self, Result};
-
-use byteorder::ByteOrder;
-
-/// Extends `Read` with methods for reading numbers. (For `std::io`.)
-///
-/// Most of the methods defined here have an unconstrained type parameter that
-/// must be explicitly instantiated. Typically, it is instantiated with either
-/// the `BigEndian` or `LittleEndian` types defined in this crate.
-///
-/// # Examples
-///
-/// Read unsigned 16 bit big-endian integers from a `Read`:
-///
-/// ```rust
-/// use std::io::Cursor;
-/// use byteorder::{BigEndian, ReadBytesExt};
-///
-/// let mut rdr = Cursor::new(vec![2, 5, 3, 0]);
-/// assert_eq!(517, rdr.read_u16::<BigEndian>().unwrap());
-/// assert_eq!(768, rdr.read_u16::<BigEndian>().unwrap());
-/// ```
-pub trait ReadBytesExt: io::Read {
-    /// Reads an unsigned 8 bit integer from the underlying reader.
-    ///
-    /// Note that since this reads a single byte, no byte order conversions
-    /// are used. It is included for completeness.
-    #[inline]
-    fn read_u8(&mut self) -> Result<u8> {
-        let mut buf = [0; 1];
-        try!(self.read_exact(&mut buf));
-        Ok(buf[0])
-    }
-
-    /// Reads a signed 8 bit integer from the underlying reader.
-    ///
-    /// Note that since this reads a single byte, no byte order conversions
-    /// are used. It is included for completeness.
-    #[inline]
-    fn read_i8(&mut self) -> Result<i8> {
-        let mut buf = [0; 1];
-        try!(self.read_exact(&mut buf));
-        Ok(buf[0] as i8)
-    }
-
-    /// Reads an unsigned 16 bit integer from the underlying reader.
-    #[inline]
-    fn read_u16<T: ByteOrder>(&mut self) -> Result<u16> {
-        let mut buf = [0; 2];
-        try!(self.read_exact(&mut buf));
-        Ok(T::read_u16(&buf))
-    }
-
-    /// Reads a signed 16 bit integer from the underlying reader.
-    #[inline]
-    fn read_i16<T: ByteOrder>(&mut self) -> Result<i16> {
-        let mut buf = [0; 2];
-        try!(self.read_exact(&mut buf));
-        Ok(T::read_i16(&buf))
-    }
-
-    /// Reads an unsigned 32 bit integer from the underlying reader.
-    #[inline]
-    fn read_u32<T: ByteOrder>(&mut self) -> Result<u32> {
-        let mut buf = [0; 4];
-        try!(self.read_exact(&mut buf));
-        Ok(T::read_u32(&buf))
-    }
-
-    /// Reads a signed 32 bit integer from the underlying reader.
-    #[inline]
-    fn read_i32<T: ByteOrder>(&mut self) -> Result<i32> {
-        let mut buf = [0; 4];
-        try!(self.read_exact(&mut buf));
-        Ok(T::read_i32(&buf))
-    }
-
-    /// Reads an unsigned 64 bit integer from the underlying reader.
-    #[inline]
-    fn read_u64<T: ByteOrder>(&mut self) -> Result<u64> {
-        let mut buf = [0; 8];
-        try!(self.read_exact(&mut buf));
-        Ok(T::read_u64(&buf))
-    }
-
-    /// Reads a signed 64 bit integer from the underlying reader.
-    #[inline]
-    fn read_i64<T: ByteOrder>(&mut self) -> Result<i64> {
-        let mut buf = [0; 8];
-        try!(self.read_exact(&mut buf));
-        Ok(T::read_i64(&buf))
-    }
-
-    /// Reads an unsigned n-bytes integer from the underlying reader.
-    #[inline]
-    fn read_uint<T: ByteOrder>(&mut self, nbytes: usize) -> Result<u64> {
-        let mut buf = [0; 8];
-        try!(self.read_exact(&mut buf[..nbytes]));
-        Ok(T::read_uint(&buf[..nbytes], nbytes))
-    }
-
-    /// Reads a signed n-bytes integer from the underlying reader.
-    #[inline]
-    fn read_int<T: ByteOrder>(&mut self, nbytes: usize) -> Result<i64> {
-        let mut buf = [0; 8];
-        try!(self.read_exact(&mut buf[..nbytes]));
-        Ok(T::read_int(&buf[..nbytes], nbytes))
-    }
-
-    /// Reads a IEEE754 single-precision (4 bytes) floating point number from
-    /// the underlying reader.
-    #[inline]
-    fn read_f32<T: ByteOrder>(&mut self) -> Result<f32> {
-        let mut buf = [0; 4];
-        try!(self.read_exact(&mut buf));
-        Ok(T::read_f32(&buf))
-    }
-
-    /// Reads a IEEE754 double-precision (8 bytes) floating point number from
-    /// the underlying reader.
-    #[inline]
-    fn read_f64<T: ByteOrder>(&mut self) -> Result<f64> {
-        let mut buf = [0; 8];
-        try!(self.read_exact(&mut buf));
-        Ok(T::read_f64(&buf))
-    }
-}
-
-/// All types that implement `Read` get methods defined in `ReadBytesExt`
-/// for free.
-impl<R: io::Read + ?Sized> ReadBytesExt for R {}
-
-/// Extends `Write` with methods for writing numbers. (For `std::io`.)
-///
-/// Most of the methods defined here have an unconstrained type parameter that
-/// must be explicitly instantiated. Typically, it is instantiated with either
-/// the `BigEndian` or `LittleEndian` types defined in this crate.
-///
-/// # Examples
-///
-/// Write unsigned 16 bit big-endian integers to a `Write`:
-///
-/// ```rust
-/// use byteorder::{BigEndian, WriteBytesExt};
-///
-/// let mut wtr = vec![];
-/// wtr.write_u16::<BigEndian>(517).unwrap();
-/// wtr.write_u16::<BigEndian>(768).unwrap();
-/// assert_eq!(wtr, vec![2, 5, 3, 0]);
-/// ```
-pub trait WriteBytesExt: io::Write {
-    /// Writes an unsigned 8 bit integer to the underlying writer.
-    ///
-    /// Note that since this writes a single byte, no byte order conversions
-    /// are used. It is included for completeness.
-    #[inline]
-    fn write_u8(&mut self, n: u8) -> Result<()> {
-        self.write_all(&[n])
-    }
-
-    /// Writes a signed 8 bit integer to the underlying writer.
-    ///
-    /// Note that since this writes a single byte, no byte order conversions
-    /// are used. It is included for completeness.
-    #[inline]
-    fn write_i8(&mut self, n: i8) -> Result<()> {
-        self.write_all(&[n as u8])
-    }
-
-    /// Writes an unsigned 16 bit integer to the underlying writer.
-    #[inline]
-    fn write_u16<T: ByteOrder>(&mut self, n: u16) -> Result<()> {
-        let mut buf = [0; 2];
-        T::write_u16(&mut buf, n);
-        self.write_all(&buf)
-    }
-
-    /// Writes a signed 16 bit integer to the underlying writer.
-    #[inline]
-    fn write_i16<T: ByteOrder>(&mut self, n: i16) -> Result<()> {
-        let mut buf = [0; 2];
-        T::write_i16(&mut buf, n);
-        self.write_all(&buf)
-    }
-
-    /// Writes an unsigned 32 bit integer to the underlying writer.
-    #[inline]
-    fn write_u32<T: ByteOrder>(&mut self, n: u32) -> Result<()> {
-        let mut buf = [0; 4];
-        T::write_u32(&mut buf, n);
-        self.write_all(&buf)
-    }
-
-    /// Writes a signed 32 bit integer to the underlying writer.
-    #[inline]
-    fn write_i32<T: ByteOrder>(&mut self, n: i32) -> Result<()> {
-        let mut buf = [0; 4];
-        T::write_i32(&mut buf, n);
-        self.write_all(&buf)
-    }
-
-    /// Writes an unsigned 64 bit integer to the underlying writer.
-    #[inline]
-    fn write_u64<T: ByteOrder>(&mut self, n: u64) -> Result<()> {
-        let mut buf = [0; 8];
-        T::write_u64(&mut buf, n);
-        self.write_all(&buf)
-    }
-
-    /// Writes a signed 64 bit integer to the underlying writer.
-    #[inline]
-    fn write_i64<T: ByteOrder>(&mut self, n: i64) -> Result<()> {
-        let mut buf = [0; 8];
-        T::write_i64(&mut buf, n);
-        self.write_all(&buf)
-    }
-
-    /// Writes an unsigned n-bytes integer to the underlying writer.
-    ///
-    /// If the given integer is not representable in the given number of bytes,
-    /// this method panics. If `nbytes > 8`, this method panics.
-    #[inline]
-    fn write_uint<T: ByteOrder>(
-        &mut self,
-        n: u64,
-        nbytes: usize,
-    ) -> Result<()> {
-        let mut buf = [0; 8];
-        T::write_uint(&mut buf, n, nbytes);
-        self.write_all(&buf[0..nbytes])
-    }
-
-    /// Writes a signed n-bytes integer to the underlying writer.
-    ///
-    /// If the given integer is not representable in the given number of bytes,
-    /// this method panics. If `nbytes > 8`, this method panics.
-    #[inline]
-    fn write_int<T: ByteOrder>(
-        &mut self,
-        n: i64,
-        nbytes: usize,
-    ) -> Result<()> {
-        let mut buf = [0; 8];
-        T::write_int(&mut buf, n, nbytes);
-        self.write_all(&buf[0..nbytes])
-    }
-
-    /// Writes a IEEE754 single-precision (4 bytes) floating point number to
-    /// the underlying writer.
-    #[inline]
-    fn write_f32<T: ByteOrder>(&mut self, n: f32) -> Result<()> {
-        let mut buf = [0; 4];
-        T::write_f32(&mut buf, n);
-        self.write_all(&buf)
-    }
-
-    /// Writes a IEEE754 double-precision (8 bytes) floating point number to
-    /// the underlying writer.
-    #[inline]
-    fn write_f64<T: ByteOrder>(&mut self, n: f64) -> Result<()> {
-        let mut buf = [0; 8];
-        T::write_f64(&mut buf, n);
-        self.write_all(&buf)
-    }
-}
-
-/// All types that implement `Write` get methods defined in `WriteBytesExt`
-/// for free.
-impl<W: io::Write + ?Sized> WriteBytesExt for W {}
--- a/media/libstagefright/binding/mp4parse/src/lib.rs
+++ b/media/libstagefright/binding/mp4parse/src/lib.rs
@@ -3,17 +3,17 @@
 // This Source Code Form is subject to the terms of the Mozilla Public
 // License, v. 2.0. If a copy of the MPL was not distributed with this
 // file, You can obtain one at https://mozilla.org/MPL/2.0/.
 #![cfg_attr(feature = "fuzz", feature(plugin))]
 #![cfg_attr(feature = "fuzz", plugin(afl_plugin))]
 #[cfg(feature = "fuzz")]
 extern crate afl;
 
-mod byteorder; // 'extern crate' upstream.
+extern crate byteorder;
 use byteorder::ReadBytesExt;
 use std::io::{Read, Take};
 use std::cmp;
 
 // Expose C api wrapper.
 pub mod capi;
 pub use capi::*;
 
--- a/toolkit/library/rust/Cargo.lock
+++ b/toolkit/library/rust/Cargo.lock
@@ -1,11 +1,18 @@
 [root]
 name = "gkrust"
 version = "0.1.0"
 dependencies = [
  "mp4parse 0.4.0",
 ]
 
 [[package]]
+name = "byteorder"
+version = "0.5.3"
+
+[[package]]
 name = "mp4parse"
 version = "0.4.0"
+dependencies = [
+ "byteorder 0.5.3",
+]