Skip to content

Are (non-free) generic constants guaranteed to be evaluated? #409

Closed
@joshlf

Description

@joshlf

Thanks to this suggestion by @gootorov, we're considering doing something like the following in zerocopy:

pub trait MaybeTransmutableInto<T: FromBytes>: Sized + AsBytes {
    const REF_TRANSMUTABLE_INTO: () = assert!(
        mem::size_of::<Self>() == mem::size_of::<T>()
            && mem::align_of::<Self>() >= mem::align_of::<T>()
    );

    fn transmute_ref_into(&self) -> &T {
        let _: () = <Self as MaybeTransmutableInto<T>>::REF_TRANSMUTABLE_INTO;
        unsafe { mem::transmute(self) }
    }
}

The nightly reference guarantees that "free constants are always evaluated at compile time." However, that's not quite what we have here - we evaluate the constant REF_TRANSMUTABLE_INTO but assign it to a runtime variable (let _: () = ...). If we replaced let _ with const _, that would be a free constant, but it would never compile (even when we wanted it to) because a constant in a function body isn't allowed to reference types which are generic in that context.

What I want to know is: Is this constant guaranteed to be evaluated so long as transmute_ref_into is used?

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions