-
Notifications
You must be signed in to change notification settings - Fork 13.4k
Reduce integer Display
implementation size
#133247
New issue
Have a question about this project? # for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “#”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? # to your account
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -199,32 +199,12 @@ static DEC_DIGITS_LUT: &[u8; 200] = b"0001020304050607080910111213141516171819\ | |
8081828384858687888990919293949596979899"; | ||
|
||
macro_rules! impl_Display { | ||
($($t:ident $(as $positive:ident)? named $name:ident,)* ; as $u:ident via $conv_fn:ident named $gen_name:ident) => { | ||
($($signed:ident, $unsigned:ident,)* ; as $u:ident via $conv_fn:ident named $gen_name:ident) => { | ||
|
||
$( | ||
#[stable(feature = "rust1", since = "1.0.0")] | ||
impl fmt::Display for $t { | ||
impl fmt::Display for $unsigned { | ||
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { | ||
// If it's a signed integer. | ||
$( | ||
let is_nonnegative = *self >= 0; | ||
|
||
#[cfg(not(feature = "optimize_for_size"))] | ||
{ | ||
if !is_nonnegative { | ||
// convert the negative num to positive by summing 1 to its 2s complement | ||
return (!self as $positive).wrapping_add(1)._fmt(false, f); | ||
} | ||
} | ||
#[cfg(feature = "optimize_for_size")] | ||
{ | ||
if !is_nonnegative { | ||
// convert the negative num to positive by summing 1 to its 2s complement | ||
return $gen_name((!self.$conv_fn()).wrapping_add(1), false, f); | ||
} | ||
} | ||
)? | ||
// If it's a positive integer. | ||
#[cfg(not(feature = "optimize_for_size"))] | ||
{ | ||
self._fmt(true, f) | ||
|
@@ -236,10 +216,24 @@ macro_rules! impl_Display { | |
} | ||
} | ||
|
||
#[stable(feature = "rust1", since = "1.0.0")] | ||
impl fmt::Display for $signed { | ||
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { | ||
#[cfg(not(feature = "optimize_for_size"))] | ||
{ | ||
return self.unsigned_abs()._fmt(*self >= 0, f); | ||
} | ||
#[cfg(feature = "optimize_for_size")] | ||
{ | ||
return $gen_name(self.unsigned_abs().$conv_fn(), *self >= 0, f); | ||
} | ||
} | ||
} | ||
|
||
#[cfg(not(feature = "optimize_for_size"))] | ||
impl $t { | ||
fn _fmt(mut self: $t, is_nonnegative: bool, f: &mut fmt::Formatter<'_>) -> fmt::Result { | ||
const SIZE: usize = $t::MAX.ilog(10) as usize + 1; | ||
impl $unsigned { | ||
fn _fmt(mut self, is_nonnegative: bool, f: &mut fmt::Formatter<'_>) -> fmt::Result { | ||
const SIZE: usize = $unsigned::MAX.ilog(10) as usize + 1; | ||
let mut buf = [MaybeUninit::<u8>::uninit(); SIZE]; | ||
let mut curr = SIZE; | ||
let buf_ptr = MaybeUninit::slice_as_mut_ptr(&mut buf); | ||
|
@@ -258,7 +252,7 @@ macro_rules! impl_Display { | |
#[allow(unused_comparisons)] | ||
// This block will be removed for smaller types at compile time and in the worst | ||
// case, it will prevent to have the `10000` literal to overflow for `i8` and `u8`. | ||
if core::mem::size_of::<$t>() >= 2 { | ||
if core::mem::size_of::<$unsigned>() >= 2 { | ||
// eagerly decode 4 characters at a time | ||
while self >= 10000 { | ||
let rem = (self % 10000) as usize; | ||
|
@@ -312,8 +306,8 @@ macro_rules! impl_Display { | |
|
||
#[cfg(feature = "optimize_for_size")] | ||
fn $gen_name(mut n: $u, is_nonnegative: bool, f: &mut fmt::Formatter<'_>) -> fmt::Result { | ||
// 2^128 is about 3*10^38, so 39 gives an extra byte of space | ||
let mut buf = [MaybeUninit::<u8>::uninit(); 39]; | ||
const SIZE: usize = $u::MAX.ilog(10) as usize + 1; | ||
let mut buf = [MaybeUninit::<u8>::uninit(); SIZE]; | ||
Comment on lines
307
to
+310
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. ? What is the effect of this change on binary size? Or is There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. On smaller targets, the maximum size might be of There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I see, hopefully so. |
||
let mut curr = buf.len(); | ||
let buf_ptr = MaybeUninit::slice_as_mut_ptr(&mut buf); | ||
|
||
|
@@ -523,16 +517,11 @@ impl_Debug! { | |
mod imp { | ||
use super::*; | ||
impl_Display!( | ||
i8 as u8 named fmt_i8, | ||
u8 named fmt_u8, | ||
i16 as u16 named fmt_i16, | ||
u16 named fmt_u16, | ||
i32 as u32 named fmt_i32, | ||
u32 named fmt_u32, | ||
i64 as u64 named fmt_i64, | ||
u64 named fmt_u64, | ||
isize as usize named fmt_isize, | ||
usize named fmt_usize, | ||
i8, u8, | ||
i16, u16, | ||
i32, u32, | ||
i64, u64, | ||
isize, usize, | ||
; as u64 via to_u64 named fmt_u64 | ||
); | ||
impl_Exp!( | ||
|
@@ -545,18 +534,13 @@ mod imp { | |
mod imp { | ||
use super::*; | ||
impl_Display!( | ||
i8 as u8 named fmt_i8, | ||
u8 named fmt_u8, | ||
i16 as u16 named fmt_i16, | ||
u16 named fmt_u16, | ||
i32 as u32 named fmt_i32, | ||
u32 named fmt_u32, | ||
isize as usize named fmt_isize, | ||
usize named fmt_usize, | ||
i8, u8, | ||
i16, u16, | ||
i32, u32, | ||
isize, usize, | ||
; as u32 via to_u32 named fmt_u32); | ||
impl_Display!( | ||
i64 as u64 named fmt_i64, | ||
u64 named fmt_u64, | ||
i64, u64, | ||
; as u64 via to_u64 named fmt_u64); | ||
|
||
impl_Exp!(i8, u8, i16, u16, i32, u32, isize, usize as u32 via to_u32 named exp_u32); | ||
|
Uh oh!
There was an error while loading. Please reload this page.