Help make this code compile

pub trait Fixed_Serde_Inner {
    const mem_size: usize;

    fn write_to_mem<W: Write>(&self, writer: &mut [u8; Self::mem_size])
        -> Result<(), My_Serde_Err>;

    fn read_from_mem<R: Read>(reader: &[u8; Self::mem_size]) -> Result<Self, My_Serde_Err>
    where
        Self: Sized;
}

Here is the intuition: any type that implements Fixed_Serde_Inner has the following property: there exists some fixed constant Self::mem_size which determines the space required to serialize the type.

Now, not all types can implement Fixed_Serde_Inner. For example, Vec<u8> can not while [u8; 4] and [u8; 8] can.

Question: how can I make the above code compile ?

The unstable #![feature(generic_const_exprs)] seems to work. It is marked as incomplete feature though.

If you're on nightly, you can use #![feature(generic_const_exprs)]. Follow this thread for updates on this feature.

Another solution suggested on the same thread is to use a const generic. Something like:

pub trait Fixed_Serde_Inner<const mem_size: usize> {
    fn write_to_mem<W: Write>(&self, writer: &mut [u8; mem_size])
        -> Result<(), My_Serde_Err>;

    fn read_from_mem<R: Read>(reader: &[u8; mem_size]) -> Result<Self, My_Serde_Err>
    where
        Self: Sized;
}

This can be implemented on a type using:

impl Fixed_Serde_Inner<4> for [u8; 4] {
    // use `4` here instead of `mem_size`.
    fn write_to_mem<W: Write>(&self, writer: &mut [u8; 4]) -> Result<(), My_Serde_Err> {
        ..
    }

    // use `4` here instead of `mem_size`.
    fn read_from_mem<R: Read>(reader:: &[u8; 4]) -> Result<Self, My_Serde_Err>
    where
        Self: Sized,
    {
        ..
    }
}

Notice that you need to repeat the constant many times in one impl if you're using this.