-
-
Notifications
You must be signed in to change notification settings - Fork 150
Closed
Description
Right now, making something compile-time generic over endianness is a huge pain:
extern crate byteorder;
use byteorder::{ByteOrder, LittleEndian};
use std::marker::PhantomData;
#[derive(Debug, Clone, Copy, PartialEq, Eq)]
struct EndianBuf<'a, Endian>(&'a [u8], PhantomData<Endian>) where Endian: ByteOrder;
impl<'a, Endian> EndianBuf<'a, Endian> where Endian: ByteOrder {
fn new(buf: &'a [u8]) -> EndianBuf<'a, Endian> {
EndianBuf(buf, PhantomData)
}
}
fn main() {
let buf = [1,2,3,4,5,6];
let a = EndianBuf::<LittleEndian>::new(&buf);
let b = EndianBuf::<LittleEndian>::new(&buf);
// Compiler error regarding this line!
assert_eq!(a, b);
}
If you do rustc -Z unstable-options --pretty expanded endian_buf.rs
, you will see this:
#[automatically_derived]
#[allow(unused_qualifications)]
impl <'a, Endian: ::std::clone::Clone> ::std::clone::Clone for EndianBuf<'a, Endian>
where Endian: ByteOrder
{
// ...snip...
}
The derived impls require that the type traits also implement the trait.
If ByteOrder
implied Eq
, Clone
, Copy
, etc... the problems would go away. Arguably, this is a bug in the #[derive(Foo)]
expansion code for not understanding PhantomData
, but adding this would work around that bug.
Since one can't even instantiate BigEndian
or LittleEndian
, all the impls could be unreachable!()
.
Would you be willing to accept a patch that does this?
Metadata
Metadata
Assignees
Labels
No labels