rfcs icon indicating copy to clipboard operation
rfcs copied to clipboard

Implement 48-bit integer types.

Open deeprobin opened this issue 5 years ago • 13 comments

I would be in favor of implementing u48 and i48. There are few CPUs that support 48-bit integers otherwise you could represent it as 16-bit and 32-bit numbers internally. But I guess this optimization is already done by LLVM.

Reasons why you should implement this:

  • Two new primitive types that are certainly good to use in libraries.
  • The library byteorder can already serialize these types but unfortunately they have to be represented as a 64-bit integer because this is not implemented yet

deeprobin avatar Apr 07 '20 10:04 deeprobin

48-bit integers is not even supported by Tier-1 Rust support. So I don't think that it is worth to have that 48-bit primitive integer type.

tesuji avatar Apr 07 '20 13:04 tesuji

Wouldn't this just be a storage format? I doubt any modern CPU would ever implement this directly, but using it for storage in cases where 32b is too small and 64b is too wasteful could make sense. But that could be easily implemented in library.

le-jzr avatar Apr 07 '20 14:04 le-jzr

Once const generics are done, we could have a generic uint<N> type that worked for any N, either as a crate or in libstd.

For now... apparently there's a crate that implements u1-u127 and i1-i127.

comex avatar Apr 09 '20 06:04 comex

ux's u48 is backed by a u64 (occupies 8 bytes), while what OP wants is likely a 6-byte type.

kennytm avatar Apr 10 '20 06:04 kennytm

I mean you could implement this type since LLVM supports it too. And it is not harmful to implement it, if you don't want to use it, you don't have to use it.

deeprobin avatar Apr 10 '20 15:04 deeprobin

Once const generics are done, we could have a generic uint<N> type that worked for any N, either as a crate or in libstd.

For now... apparently there's a crate that implements u1-u127 and i1-i127.

That's a good start. You can use uint<48> for example and create a type alias 'u48'.

deeprobin avatar Apr 10 '20 15:04 deeprobin

ux's u48 is backed by a u64 (occupies 8 bytes), while what OP wants is likely a 6-byte type.

Unless u48 would be less aligned than u32, it's going to be 8 bytes with padding regardless.

I mean you could implement this type since LLVM supports it too.

"can be written in LLVM IR" is not the same thing as "actually works". It took months of work to get the 128 bit integer types to a level of functionality on all of the relevant targets that they could actually be stabilized.

And it is not harmful to implement it, if you don't want to use it, you don't have to use it.

All features have a cost.

sfackler avatar Apr 10 '20 15:04 sfackler

"can be written in LLVM IR" is not the same thing as "actually works". It took months of work to get the 128-bit integer types to a level of functionality on all of the relevant targets that they could actually be stabilized.

Sure, of course, but time should not be the factor in rejecting the issue. And because 128-bit integers have been implemented, it may be easier, since a foundation stone has already been laid.

All features have a cost.

Certainly, the u48 in the build has its costs. But finally compiled it has more advantages than disadvantages.

deeprobin avatar Apr 10 '20 16:04 deeprobin

Unless u48 would be less aligned than u32, it's going to be 8 bytes with padding regardless.

Yes you could make it [u16; 3].

Additionally, being a u64 means it has 8-byte alignment while a (u32, u16) only needs 4-byte alignment (and [u16; 3] has 2-byte alignment).

There are many choices what a u48 should behave but no clear answer which one should be chosen, unlike the other power-of-2 primitive types.

kennytm avatar Apr 11 '20 13:04 kennytm

Once const generics are done, we could have a generic uint<N> type that worked for any N, either as a crate or in libstd.

Oh hey, I wrote an RFC for this too.

clarfonthey avatar May 12 '20 05:05 clarfonthey

Yes you could make it [u16; 3].

I just published the i48 crate, which represents the i48 type exactly like that, contributions welcome :)

Chubercik avatar Aug 03 '24 01:08 Chubercik

There's already an intx ­package that provides all 8N-bit integers (16, 24, 32, 40, 48, 56, 64, 72, 80, 88, 96, 104, 112, 120, 128) with minimal storage and alignment = 1 (they wrap [u8; N]).

kennytm avatar Aug 03 '24 20:08 kennytm

Thanks for the heads up, it's [u8; 6] now.

Chubercik avatar Aug 07 '24 23:08 Chubercik