1 //===-- Decimal Float Converter for printf ----------------------*- C++ -*-===//
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
7 //===----------------------------------------------------------------------===//
9 #ifndef LLVM_LIBC_SRC_STDIO_PRINTF_CORE_FLOAT_DEC_CONVERTER_H
10 #define LLVM_LIBC_SRC_STDIO_PRINTF_CORE_FLOAT_DEC_CONVERTER_H
12 #include "src/__support/CPP/string_view.h"
13 #include "src/__support/FPUtil/FEnvImpl.h"
14 #include "src/__support/FPUtil/FPBits.h"
15 #include "src/__support/FPUtil/FloatProperties.h"
16 #include "src/__support/FPUtil/rounding_mode.h"
17 #include "src/__support/UInt.h"
18 #include "src/__support/UInt128.h"
19 #include "src/__support/common.h"
20 #include "src/__support/float_to_string.h"
21 #include "src/__support/integer_to_string.h"
22 #include "src/__support/libc_assert.h"
23 #include "src/stdio/printf_core/converter_utils.h"
24 #include "src/stdio/printf_core/core_structs.h"
25 #include "src/stdio/printf_core/float_inf_nan_converter.h"
26 #include "src/stdio/printf_core/writer.h"
31 namespace LIBC_NAMESPACE
{
32 namespace printf_core
{
34 using MantissaInt
= fputil::FPBits
<long double>::UIntType
;
35 using DecimalString
= IntegerToString
<intmax_t>;
36 using ExponentString
=
37 IntegerToString
<intmax_t, radix::Dec::WithWidth
<2>::WithSign
>;
39 // Returns true if value is divisible by 2^p.
41 LIBC_INLINE
constexpr cpp::enable_if_t
<cpp::is_integral_v
<T
>, bool>
42 multiple_of_power_of_2(T value
, uint32_t p
) {
43 return (value
& ((T(1) << p
) - 1)) == 0;
46 constexpr size_t BLOCK_SIZE
= 9;
47 constexpr uint32_t MAX_BLOCK
= 999999999;
49 // constexpr size_t BLOCK_SIZE = 18;
50 // constexpr uint32_t MAX_BLOCK = 999999999999999999;
51 constexpr char DECIMAL_POINT
= '.';
53 // This is used to represent which direction the number should be rounded.
54 enum class RoundDirection
{ Up
, Down
, Even
};
56 LIBC_INLINE RoundDirection
get_round_direction(int last_digit
, bool truncated
,
58 switch (fputil::quick_get_round()) {
60 // Round to nearest, if it's exactly halfway then round to even.
61 if (last_digit
!= 5) {
62 return last_digit
> 5 ? RoundDirection::Up
: RoundDirection::Down
;
64 return !truncated
? RoundDirection::Even
: RoundDirection::Up
;
67 if (is_negative
&& (truncated
|| last_digit
> 0)) {
68 return RoundDirection::Up
;
70 return RoundDirection::Down
;
73 if (!is_negative
&& (truncated
|| last_digit
> 0)) {
74 return RoundDirection::Up
;
76 return RoundDirection::Down
;
78 return is_negative
? RoundDirection::Down
: RoundDirection::Up
;
80 return RoundDirection::Down
;
82 return RoundDirection::Down
;
87 LIBC_INLINE
constexpr cpp::enable_if_t
<cpp::is_integral_v
<T
>, bool>
88 zero_after_digits(int32_t base_2_exp
, int32_t digits_after_point
, T mantissa
,
89 const int32_t mant_width
) {
90 const int32_t required_twos
= -base_2_exp
- digits_after_point
- 1;
91 // Add 8 to mant width since this is a loose bound.
92 const bool has_trailing_zeros
=
94 (required_twos
< (mant_width
+ 8) &&
95 multiple_of_power_of_2(mantissa
, static_cast<uint32_t>(required_twos
)));
96 return has_trailing_zeros
;
100 bool left_justified
= false;
101 bool leading_zeroes
= false;
103 size_t min_width
= 0;
107 PaddingWriter(const FormatSection
&to_conv
, char init_sign_char
)
108 : left_justified((to_conv
.flags
& FormatFlags::LEFT_JUSTIFIED
) > 0),
109 leading_zeroes((to_conv
.flags
& FormatFlags::LEADING_ZEROES
) > 0),
110 sign_char(init_sign_char
),
111 min_width(to_conv
.min_width
> 0 ? to_conv
.min_width
: 0) {}
113 int write_left_padding(Writer
*writer
, size_t total_digits
) {
114 // The pattern is (spaces) (sign) (zeroes), but only one of spaces and
115 // zeroes can be written, and only if the padding amount is positive.
117 static_cast<int>(min_width
- total_digits
- (sign_char
> 0 ? 1 : 0));
118 if (left_justified
|| padding_amount
< 0) {
120 RET_IF_RESULT_NEGATIVE(writer
->write(sign_char
));
124 if (!leading_zeroes
) {
125 RET_IF_RESULT_NEGATIVE(writer
->write(' ', padding_amount
));
128 RET_IF_RESULT_NEGATIVE(writer
->write(sign_char
));
130 if (leading_zeroes
) {
131 RET_IF_RESULT_NEGATIVE(writer
->write('0', padding_amount
));
136 int write_right_padding(Writer
*writer
, size_t total_digits
) {
137 // If and only if the conversion is left justified, there may be trailing
140 static_cast<int>(min_width
- total_digits
- (sign_char
> 0 ? 1 : 0));
141 if (left_justified
&& padding_amount
> 0) {
142 RET_IF_RESULT_NEGATIVE(writer
->write(' ', padding_amount
));
149 We only need to round a given segment if all of the segments below it are
150 the max (or this is the last segment). This means that we don't have to
151 write those initially, we can just keep the most recent non-maximal
152 segment and a counter of the number of maximal segments. When we reach a
153 non-maximal segment, we write the stored segment as well as as many 9s as
154 are necessary. Alternately, if we reach the end and have to round up, then
155 we round the stored segment, and write zeroes following it. If this
156 crosses the decimal point, then we have to shift it one space to the
158 This FloatWriter class does the buffering and counting, and writes to the
159 output when necessary.
162 char block_buffer
[BLOCK_SIZE
]; // The buffer that holds a block.
163 size_t buffered_digits
= 0; // The number of digits held in the buffer.
164 bool has_written
= false; // True once any digits have been output.
165 size_t max_block_count
= 0; // The # of blocks of all 9s currently buffered.
166 size_t total_digits
= 0; // The number of digits that will be output.
167 size_t digits_before_decimal
= 0; // The # of digits to write before the '.'
168 size_t total_digits_written
= 0; // The # of digits that have been output.
169 bool has_decimal_point
; // True if the number has a decimal point.
170 Writer
*writer
; // Writes to the final output.
171 PaddingWriter padding_writer
; // Handles prefixes/padding, uses total_digits.
173 int flush_buffer(bool round_up_max_blocks
= false) {
174 const char MAX_BLOCK_DIGIT
= (round_up_max_blocks
? '0' : '9');
176 // Write the most recent buffered block, and mark has_written
179 RET_IF_RESULT_NEGATIVE(
180 padding_writer
.write_left_padding(writer
, total_digits
));
183 // if the decimal point is the next character, or is in the range covered
184 // by the buffered block, write the appropriate digits and the decimal
186 if (total_digits_written
< digits_before_decimal
&&
187 total_digits_written
+ buffered_digits
>= digits_before_decimal
&&
189 size_t digits_to_write
= digits_before_decimal
- total_digits_written
;
190 if (digits_to_write
> 0) {
191 // Write the digits before the decimal point.
192 RET_IF_RESULT_NEGATIVE(writer
->write({block_buffer
, digits_to_write
}));
194 RET_IF_RESULT_NEGATIVE(writer
->write(DECIMAL_POINT
));
195 if (buffered_digits
- digits_to_write
> 0) {
196 // Write the digits after the decimal point.
197 RET_IF_RESULT_NEGATIVE(
198 writer
->write({block_buffer
+ digits_to_write
,
199 (buffered_digits
- digits_to_write
)}));
201 // add 1 for the decimal point
202 total_digits_written
+= buffered_digits
+ 1;
203 // Mark the buffer as empty.
207 // Clear the buffered digits.
208 if (buffered_digits
> 0) {
209 RET_IF_RESULT_NEGATIVE(writer
->write({block_buffer
, buffered_digits
}));
210 total_digits_written
+= buffered_digits
;
214 // if the decimal point is the next character, or is in the range covered
215 // by the max blocks, write the appropriate digits and the decimal point.
216 if (total_digits_written
< digits_before_decimal
&&
217 total_digits_written
+ BLOCK_SIZE
* max_block_count
>=
218 digits_before_decimal
&&
220 size_t digits_to_write
= digits_before_decimal
- total_digits_written
;
221 if (digits_to_write
> 0) {
222 RET_IF_RESULT_NEGATIVE(writer
->write(MAX_BLOCK_DIGIT
, digits_to_write
));
224 RET_IF_RESULT_NEGATIVE(writer
->write(DECIMAL_POINT
));
225 if ((BLOCK_SIZE
* max_block_count
) - digits_to_write
> 0) {
226 RET_IF_RESULT_NEGATIVE(writer
->write(
227 MAX_BLOCK_DIGIT
, (BLOCK_SIZE
* max_block_count
) - digits_to_write
));
229 // add 1 for the decimal point
230 total_digits_written
+= BLOCK_SIZE
* max_block_count
+ 1;
231 // clear the buffer of max blocks
235 // Clear the buffer of max blocks
236 if (max_block_count
> 0) {
237 RET_IF_RESULT_NEGATIVE(
238 writer
->write(MAX_BLOCK_DIGIT
, max_block_count
* BLOCK_SIZE
));
239 total_digits_written
+= max_block_count
* BLOCK_SIZE
;
245 // -exponent will never overflow because all long double types we support
246 // have at most 15 bits of mantissa and the C standard defines an int as
247 // being at least 16 bits.
248 static_assert(fputil::FloatProperties
<long double>::EXPONENT_WIDTH
<
252 FloatWriter(Writer
*init_writer
, bool init_has_decimal_point
,
253 const PaddingWriter
&init_padding_writer
)
254 : has_decimal_point(init_has_decimal_point
), writer(init_writer
),
255 padding_writer(init_padding_writer
) {}
257 void init(size_t init_total_digits
, size_t init_digits_before_decimal
) {
258 total_digits
= init_total_digits
;
259 digits_before_decimal
= init_digits_before_decimal
;
262 void write_first_block(BlockInt block
, bool exp_format
= false) {
263 const DecimalString
buf(block
);
264 const cpp::string_view int_to_str
= buf
.view();
265 size_t digits_buffered
= int_to_str
.size();
266 // Block Buffer is guaranteed to not overflow since block cannot have more
267 // than BLOCK_SIZE digits.
268 // TODO: Replace with memcpy
269 for (size_t count
= 0; count
< digits_buffered
; ++count
) {
270 block_buffer
[count
] = int_to_str
[count
];
272 buffered_digits
= digits_buffered
;
274 // In the exponent format (%e) we know how many digits will be written even
275 // before calculating any blocks, whereas the decimal format (%f) has to
276 // write all of the blocks that would come before the decimal place.
278 total_digits
+= digits_buffered
;
279 digits_before_decimal
+= digits_buffered
;
283 int write_middle_block(BlockInt block
) {
284 if (block
== MAX_BLOCK
) { // Buffer max blocks in case of rounding
286 } else { // If a non-max block has been found
287 RET_IF_RESULT_NEGATIVE(flush_buffer());
289 // Now buffer the current block. We add 1 + MAX_BLOCK to force the
290 // leading zeroes, and drop the leading one. This is probably inefficient,
291 // but it works. See https://xkcd.com/2021/
292 const DecimalString
buf(block
+ (MAX_BLOCK
+ 1));
293 const cpp::string_view int_to_str
= buf
.view();
294 // TODO: Replace with memcpy
295 for (size_t count
= 0; count
< BLOCK_SIZE
; ++count
) {
296 block_buffer
[count
] = int_to_str
[count
+ 1];
299 buffered_digits
= BLOCK_SIZE
;
304 int write_last_block(BlockInt block
, size_t block_digits
,
305 RoundDirection round
, int exponent
= 0,
306 char exp_char
= '\0') {
307 bool has_exp
= (exp_char
!= '\0');
309 char end_buff
[BLOCK_SIZE
];
312 const DecimalString
buf(block
+ (MAX_BLOCK
+ 1));
313 const cpp::string_view int_to_str
= buf
.view();
315 // copy the last block_digits characters into the start of end_buff.
316 // TODO: Replace with memcpy
317 for (size_t count
= 0; count
< block_digits
; ++count
) {
318 end_buff
[count
] = int_to_str
[count
+ 1 + (BLOCK_SIZE
- block_digits
)];
322 char low_digit
= '0';
323 if (block_digits
> 0) {
324 low_digit
= end_buff
[block_digits
- 1];
325 } else if (max_block_count
> 0) {
327 } else if (buffered_digits
> 0) {
328 low_digit
= block_buffer
[buffered_digits
- 1];
331 bool round_up_max_blocks
= false;
334 if (round
== RoundDirection::Up
||
335 (round
== RoundDirection::Even
&& low_digit
% 2 != 0)) {
336 bool has_carry
= true;
337 round_up_max_blocks
= true; // if we're rounding up, we might need to
338 // round up the max blocks that are buffered.
340 // handle the low block that we're adding
341 for (int count
= static_cast<int>(block_digits
) - 1;
342 count
>= 0 && has_carry
; --count
) {
343 if (end_buff
[count
] == '9') {
344 end_buff
[count
] = '0';
346 end_buff
[count
] += 1;
348 round_up_max_blocks
= false; // If the low block isn't all nines, then
349 // the max blocks aren't rounded up.
352 // handle the high block that's buffered
353 for (int count
= static_cast<int>(buffered_digits
) - 1;
354 count
>= 0 && has_carry
; --count
) {
355 if (block_buffer
[count
] == '9') {
356 block_buffer
[count
] = '0';
358 block_buffer
[count
] += 1;
363 // has_carry should only be true here if every previous digit is 9, which
364 // implies that the number has never been written.
365 if (has_carry
/* && !has_written */) {
366 if (has_exp
) { // This is in %e style
367 // Since this is exponential notation, we don't write any more digits
368 // but we do increment the exponent.
371 const ExponentString
buf(exponent
);
372 const cpp::string_view int_to_str
= buf
.view();
374 // TODO: also change this to calculate the width of the number more
376 size_t exponent_width
= int_to_str
.size();
377 size_t number_digits
=
378 buffered_digits
+ (max_block_count
* BLOCK_SIZE
) + block_digits
;
380 // Here we have to recalculate the total number of digits since the
381 // exponent's width may have changed. We're only adding 1 to exponent
382 // width since exp_str appends the sign.
384 (has_decimal_point
? 1 : 0) + number_digits
+ 1 + exponent_width
;
386 // Normally write_left_padding is called by flush_buffer but since
387 // we're rounding up all of the digits, the ones in the buffer are
388 // wrong and can't be flushed.
389 RET_IF_RESULT_NEGATIVE(
390 padding_writer
.write_left_padding(writer
, total_digits
));
391 // Now we know we need to print a leading 1, the decimal point, and
392 // then zeroes after it.
393 RET_IF_RESULT_NEGATIVE(writer
->write('1'));
394 // digits_before_decimal - 1 to account for the leading '1'
395 if (has_decimal_point
) {
396 RET_IF_RESULT_NEGATIVE(writer
->write(DECIMAL_POINT
));
397 // This is just the length of the number, not including the decimal
398 // point, or exponent.
400 if (number_digits
> 1) {
401 RET_IF_RESULT_NEGATIVE(writer
->write('0', number_digits
- 1));
404 RET_IF_RESULT_NEGATIVE(writer
->write(exp_char
));
405 RET_IF_RESULT_NEGATIVE(writer
->write(int_to_str
));
407 total_digits_written
= total_digits
;
409 } else { // This is in %f style
411 ++digits_before_decimal
;
412 // Normally write_left_padding is called by flush_buffer but since
413 // we're rounding up all of the digits, the ones in the buffer are
414 // wrong and can't be flushed.
415 RET_IF_RESULT_NEGATIVE(
416 padding_writer
.write_left_padding(writer
, total_digits
));
417 // Now we know we need to print a leading 1, zeroes up to the decimal
418 // point, the decimal point, and then finally digits after it.
419 RET_IF_RESULT_NEGATIVE(writer
->write('1'));
420 // digits_before_decimal - 1 to account for the leading '1'
421 RET_IF_RESULT_NEGATIVE(writer
->write('0', digits_before_decimal
- 1));
422 if (has_decimal_point
) {
423 RET_IF_RESULT_NEGATIVE(writer
->write(DECIMAL_POINT
));
424 // add one to digits_before_decimal to account for the decimal point
426 if (total_digits
> digits_before_decimal
+ 1) {
427 RET_IF_RESULT_NEGATIVE(writer
->write(
428 '0', total_digits
- (digits_before_decimal
+ 1)));
431 total_digits_written
= total_digits
;
436 // Either we intend to round down, or the rounding up is complete. Flush the
439 RET_IF_RESULT_NEGATIVE(flush_buffer(round_up_max_blocks
));
441 // And then write the final block. It's written via the buffer so that if
442 // this is also the first block, the decimal point will be placed correctly.
444 // TODO: Replace with memcpy
445 for (size_t count
= 0; count
< block_digits
; ++count
) {
446 block_buffer
[count
] = end_buff
[count
];
448 buffered_digits
= block_digits
;
449 RET_IF_RESULT_NEGATIVE(flush_buffer());
452 RET_IF_RESULT_NEGATIVE(writer
->write(exp_char
));
453 const ExponentString
buf(exponent
);
454 RET_IF_RESULT_NEGATIVE(writer
->write(buf
.view()));
456 total_digits_written
= total_digits
;
461 int write_zeroes(uint32_t num_zeroes
) {
462 RET_IF_RESULT_NEGATIVE(flush_buffer());
463 RET_IF_RESULT_NEGATIVE(writer
->write('0', num_zeroes
));
468 return padding_writer
.write_right_padding(writer
, total_digits
);
472 // This implementation is based on the Ryu Printf algorithm by Ulf Adams:
473 // Ulf Adams. 2019. Ryū revisited: printf floating point conversion.
474 // Proc. ACM Program. Lang. 3, OOPSLA, Article 169 (October 2019), 23 pages.
475 // https://doi.org/10.1145/3360595
476 template <typename T
, cpp::enable_if_t
<cpp::is_floating_point_v
<T
>, int> = 0>
477 LIBC_INLINE
int convert_float_decimal_typed(Writer
*writer
,
478 const FormatSection
&to_conv
,
479 fputil::FPBits
<T
> float_bits
) {
480 // signed because later we use -MANT_WIDTH
481 constexpr int32_t MANT_WIDTH
= fputil::MantissaWidth
<T
>::VALUE
;
482 bool is_negative
= float_bits
.get_sign();
483 int exponent
= float_bits
.get_explicit_exponent();
489 else if ((to_conv
.flags
& FormatFlags::FORCE_SIGN
) == FormatFlags::FORCE_SIGN
)
490 sign_char
= '+'; // FORCE_SIGN has precedence over SPACE_PREFIX
491 else if ((to_conv
.flags
& FormatFlags::SPACE_PREFIX
) ==
492 FormatFlags::SPACE_PREFIX
)
495 // If to_conv doesn't specify a precision, the precision defaults to 6.
496 const unsigned int precision
= to_conv
.precision
< 0 ? 6 : to_conv
.precision
;
497 bool has_decimal_point
=
498 (precision
> 0) || ((to_conv
.flags
& FormatFlags::ALTERNATE_FORM
) != 0);
500 // nonzero is false until a nonzero digit is found. It is used to determine if
501 // leading zeroes should be printed, since before the first digit they are
503 bool nonzero
= false;
505 PaddingWriter
padding_writer(to_conv
, sign_char
);
506 FloatWriter
float_writer(writer
, has_decimal_point
, padding_writer
);
507 FloatToString
<T
> float_converter(static_cast<T
>(float_bits
));
509 const size_t positive_blocks
= float_converter
.get_positive_blocks();
511 if (positive_blocks
>= 0) {
512 // This loop iterates through the number a block at a time until it finds a
513 // block that is not zero or it hits the decimal point. This is because all
514 // zero blocks before the first nonzero digit or the decimal point are
515 // ignored (no leading zeroes, at least at this stage).
516 int32_t i
= static_cast<int32_t>(positive_blocks
) - 1;
517 for (; i
>= 0; --i
) {
518 BlockInt digits
= float_converter
.get_positive_block(i
);
520 RET_IF_RESULT_NEGATIVE(float_writer
.write_middle_block(digits
));
521 } else if (digits
!= 0) {
522 size_t blocks_before_decimal
= i
;
523 float_writer
.init((blocks_before_decimal
* BLOCK_SIZE
) +
524 (has_decimal_point
? 1 : 0) + precision
,
525 blocks_before_decimal
* BLOCK_SIZE
);
526 float_writer
.write_first_block(digits
);
533 // if we haven't yet found a valid digit, buffer a zero.
535 float_writer
.init((has_decimal_point
? 1 : 0) + precision
, 0);
536 float_writer
.write_first_block(0);
539 if (exponent
< MANT_WIDTH
) {
540 const uint32_t blocks
= (precision
/ BLOCK_SIZE
) + 1;
542 // if all the blocks we should write are zero
543 if (blocks
<= float_converter
.zero_blocks_after_point()) {
544 i
= blocks
; // just write zeroes up to precision
545 RET_IF_RESULT_NEGATIVE(float_writer
.write_zeroes(precision
));
546 } else if (i
< float_converter
.zero_blocks_after_point()) {
547 // else if there are some blocks that are zeroes
548 i
= static_cast<uint32_t>(float_converter
.zero_blocks_after_point());
549 // write those blocks as zeroes.
550 RET_IF_RESULT_NEGATIVE(float_writer
.write_zeroes(9 * i
));
552 // for each unwritten block
553 for (; i
< blocks
; ++i
) {
554 if (float_converter
.is_lowest_block(i
)) {
555 const uint32_t fill
= precision
- 9 * i
;
556 RET_IF_RESULT_NEGATIVE(float_writer
.write_zeroes(fill
));
559 BlockInt digits
= float_converter
.get_negative_block(i
);
560 if (i
< blocks
- 1) {
561 RET_IF_RESULT_NEGATIVE(float_writer
.write_middle_block(digits
));
564 const uint32_t maximum
= precision
- BLOCK_SIZE
* i
;
565 uint32_t last_digit
= 0;
566 for (uint32_t k
= 0; k
< BLOCK_SIZE
- maximum
; ++k
) {
567 last_digit
= digits
% 10;
570 RoundDirection round
;
571 const bool truncated
=
572 !zero_after_digits(exponent
- MANT_WIDTH
, precision
,
573 float_bits
.get_explicit_mantissa(), MANT_WIDTH
);
574 round
= get_round_direction(last_digit
, truncated
, is_negative
);
576 RET_IF_RESULT_NEGATIVE(
577 float_writer
.write_last_block(digits
, maximum
, round
));
582 RET_IF_RESULT_NEGATIVE(float_writer
.write_zeroes(precision
));
584 RET_IF_RESULT_NEGATIVE(float_writer
.right_pad());
588 template <typename T
, cpp::enable_if_t
<cpp::is_floating_point_v
<T
>, int> = 0>
589 LIBC_INLINE
int convert_float_dec_exp_typed(Writer
*writer
,
590 const FormatSection
&to_conv
,
591 fputil::FPBits
<T
> float_bits
) {
592 // signed because later we use -MANT_WIDTH
593 constexpr int32_t MANT_WIDTH
= fputil::MantissaWidth
<T
>::VALUE
;
594 bool is_negative
= float_bits
.get_sign();
595 int exponent
= float_bits
.get_explicit_exponent();
596 MantissaInt mantissa
= float_bits
.get_explicit_mantissa();
598 const char a
= (to_conv
.conv_name
& 32) | 'A';
604 else if ((to_conv
.flags
& FormatFlags::FORCE_SIGN
) == FormatFlags::FORCE_SIGN
)
605 sign_char
= '+'; // FORCE_SIGN has precedence over SPACE_PREFIX
606 else if ((to_conv
.flags
& FormatFlags::SPACE_PREFIX
) ==
607 FormatFlags::SPACE_PREFIX
)
610 // If to_conv doesn't specify a precision, the precision defaults to 6.
611 const unsigned int precision
= to_conv
.precision
< 0 ? 6 : to_conv
.precision
;
612 bool has_decimal_point
=
613 (precision
> 0) || ((to_conv
.flags
& FormatFlags::ALTERNATE_FORM
) != 0);
615 PaddingWriter
padding_writer(to_conv
, sign_char
);
616 FloatWriter
float_writer(writer
, has_decimal_point
, padding_writer
);
617 FloatToString
<T
> float_converter(static_cast<T
>(float_bits
));
619 size_t digits_written
= 0;
620 int final_exponent
= 0;
622 // Here we would subtract 1 to account for the fact that block 0 counts as a
623 // positive block, but the loop below accounts for this by starting with
624 // subtracting 1 from cur_block.
628 cur_block
= -static_cast<int>(float_converter
.zero_blocks_after_point());
630 cur_block
= static_cast<int>(float_converter
.get_positive_blocks());
635 // If the mantissa is 0, then the number is 0, meaning that looping until a
636 // non-zero block is found will loop forever. The first block is just 0.
638 // This loop finds the first block.
639 while (digits
== 0) {
641 digits
= float_converter
.get_block(cur_block
);
647 const size_t block_width
= IntegerToString
<intmax_t>(digits
).size();
649 final_exponent
= (cur_block
* BLOCK_SIZE
) + static_cast<int>(block_width
- 1);
650 int positive_exponent
= final_exponent
< 0 ? -final_exponent
: final_exponent
;
652 size_t exponent_width
= IntegerToString
<intmax_t>(positive_exponent
).size();
654 // Calculate the total number of digits in the number.
655 // 1 - the digit before the decimal point
656 // 1 - the decimal point (optional)
657 // precision - the number of digits after the decimal point
658 // 1 - the 'e' at the start of the exponent
659 // 1 - the sign at the start of the exponent
660 // max(2, exp width) - the digits of the exponent, min 2.
662 float_writer
.init(1 + (has_decimal_point
? 1 : 0) + precision
+ 2 +
663 (exponent_width
< 2 ? 2 : exponent_width
),
666 // If this block is not the last block
667 if (block_width
<= precision
+ 1) {
668 float_writer
.write_first_block(digits
, true);
669 digits_written
+= block_width
;
673 // For each middle block.
674 for (; digits_written
+ BLOCK_SIZE
< precision
+ 1; --cur_block
) {
675 digits
= float_converter
.get_block(cur_block
);
677 RET_IF_RESULT_NEGATIVE(float_writer
.write_middle_block(digits
));
678 digits_written
+= BLOCK_SIZE
;
681 digits
= float_converter
.get_block(cur_block
);
683 size_t last_block_size
= BLOCK_SIZE
;
685 // if the last block is also the first block, then ignore leading zeroes.
686 if (digits_written
== 0) {
687 last_block_size
= IntegerToString
<intmax_t>(digits
).size();
690 // This tracks if the number is truncated, that meaning that the digits after
691 // last_digit are non-zero.
692 bool truncated
= false;
694 // This is the last block.
695 const size_t maximum
= precision
+ 1 - digits_written
;
696 uint32_t last_digit
= 0;
697 for (uint32_t k
= 0; k
< last_block_size
- maximum
; ++k
) {
701 last_digit
= digits
% 10;
705 // If the last block we read doesn't have the digit after the end of what
706 // we'll print, then we need to read the next block to get that digit.
707 if (maximum
== last_block_size
) {
709 BlockInt extra_block
= float_converter
.get_block(cur_block
);
710 last_digit
= extra_block
/ ((MAX_BLOCK
/ 10) + 1);
711 if (extra_block
% ((MAX_BLOCK
/ 10) + 1) > 0) {
716 RoundDirection round
;
718 // If we've already seen a truncated digit, then we don't need to check any
721 // Check the blocks above the decimal point
722 if (cur_block
>= 0) {
723 // Check every block until the decimal point for non-zero digits.
724 for (int cur_extra_block
= cur_block
- 1; cur_extra_block
>= 0;
726 BlockInt extra_block
= float_converter
.get_block(cur_extra_block
);
727 if (extra_block
> 0) {
733 // If it's still not truncated and there are digits below the decimal point
734 if (!truncated
&& exponent
- MANT_WIDTH
< 0) {
735 // Use the formula from %f.
737 !zero_after_digits(exponent
- MANT_WIDTH
, precision
- final_exponent
,
738 float_bits
.get_explicit_mantissa(), MANT_WIDTH
);
741 round
= get_round_direction(last_digit
, truncated
, is_negative
);
743 RET_IF_RESULT_NEGATIVE(float_writer
.write_last_block(
744 digits
, maximum
, round
, final_exponent
, a
+ 'E' - 'A'));
746 RET_IF_RESULT_NEGATIVE(float_writer
.right_pad());
750 template <typename T
, cpp::enable_if_t
<cpp::is_floating_point_v
<T
>, int> = 0>
751 LIBC_INLINE
int convert_float_dec_auto_typed(Writer
*writer
,
752 const FormatSection
&to_conv
,
753 fputil::FPBits
<T
> float_bits
) {
754 // signed because later we use -MANT_WIDTH
755 constexpr int32_t MANT_WIDTH
= fputil::MantissaWidth
<T
>::VALUE
;
756 bool is_negative
= float_bits
.get_sign();
757 int exponent
= float_bits
.get_explicit_exponent();
758 MantissaInt mantissa
= float_bits
.get_explicit_mantissa();
760 // From the standard: Let P (init_precision) equal the precision if nonzero, 6
761 // if the precision is omitted, or 1 if the precision is zero.
762 const unsigned int init_precision
= to_conv
.precision
<= 0
763 ? (to_conv
.precision
== 0 ? 1 : 6)
766 // Then, if a conversion with style E would have an exponent of X
769 // If P > X >= -4 the conversion is with style F and precision P - (X + 1).
770 // Otherwise, the conversion is with style E and precision P - 1.
772 // For calculating the base 10 exponent, we need to process the number as if
773 // it has style E, so here we calculate the precision we'll use in that case.
774 const unsigned int exp_precision
= init_precision
- 1;
776 FloatToString
<T
> float_converter(static_cast<T
>(float_bits
));
778 // Here we would subtract 1 to account for the fact that block 0 counts as a
779 // positive block, but the loop below accounts for this by starting with
780 // subtracting 1 from cur_block.
784 cur_block
= -static_cast<int>(float_converter
.zero_blocks_after_point());
786 cur_block
= static_cast<int>(float_converter
.get_positive_blocks());
791 // If the mantissa is 0, then the number is 0, meaning that looping until a
792 // non-zero block is found will loop forever.
794 // This loop finds the first non-zero block.
795 while (digits
== 0) {
797 digits
= float_converter
.get_block(cur_block
);
800 // In the case of 0.0, then it's always decimal format. If we don't have alt
801 // form then the trailing zeroes are trimmed to make "0", else the precision
802 // is 1 less than specified by the user.
803 FormatSection new_conv
= to_conv
;
804 if ((to_conv
.flags
& FormatFlags::ALTERNATE_FORM
) != 0) {
805 // This is a style F conversion, making the precision P - 1 - X, but since
806 // this is for the number 0, X (the base 10 exponent) is always 0.
807 new_conv
.precision
= init_precision
- 1;
809 new_conv
.precision
= 0;
811 return convert_float_decimal_typed
<T
>(writer
, new_conv
, float_bits
);
814 const size_t block_width
= IntegerToString
<intmax_t>(digits
).size();
816 size_t digits_checked
= 0;
817 // TODO: look into unifying trailing_zeroes and trailing_nines. The number can
818 // end in a nine or a zero, but not both.
819 size_t trailing_zeroes
= 0;
820 size_t trailing_nines
= 0;
822 base_10_exp
= (cur_block
* BLOCK_SIZE
) + static_cast<int>(block_width
- 1);
824 // If the first block is not also the last block
825 if (block_width
<= exp_precision
+ 1) {
826 const DecimalString
buf(digits
);
827 const cpp::string_view int_to_str
= buf
.view();
829 for (size_t i
= 0; i
< block_width
; ++i
) {
830 if (int_to_str
[i
] == '9') {
833 } else if (int_to_str
[i
] == '0') {
841 digits_checked
+= block_width
;
845 // Handle middle blocks
846 for (; digits_checked
+ BLOCK_SIZE
< exp_precision
+ 1; --cur_block
) {
847 digits
= float_converter
.get_block(cur_block
);
848 digits_checked
+= BLOCK_SIZE
;
849 if (digits
== MAX_BLOCK
) {
852 } else if (digits
== 0) {
853 trailing_zeroes
+= 9;
856 // The block is neither all nines nor all zeroes, so we need to figure out
857 // what it ends with.
860 BlockInt copy_of_digits
= digits
;
861 int cur_last_digit
= copy_of_digits
% 10;
862 // We only care if it ends in nines or zeroes.
863 while (copy_of_digits
> 0 &&
864 (cur_last_digit
== 9 || cur_last_digit
== 0)) {
865 // If the next digit is not the same as the previous one, then there are
866 // no more contiguous trailing digits.
867 if ((copy_of_digits
% 10) != cur_last_digit
) {
870 if (cur_last_digit
== 9) {
872 } else if (cur_last_digit
== 0) {
877 copy_of_digits
/= 10;
882 // Handle the last block
884 digits
= float_converter
.get_block(cur_block
);
886 size_t last_block_size
= BLOCK_SIZE
;
888 const DecimalString
buf(digits
);
889 const cpp::string_view int_to_str
= buf
.view();
891 size_t implicit_leading_zeroes
= BLOCK_SIZE
- int_to_str
.size();
893 // if the last block is also the first block, then ignore leading zeroes.
894 if (digits_checked
== 0) {
895 last_block_size
= int_to_str
.size();
896 implicit_leading_zeroes
= 0;
899 unsigned int digits_requested
=
900 (exp_precision
+ 1) - static_cast<unsigned int>(digits_checked
);
902 int digits_to_check
=
903 digits_requested
- static_cast<int>(implicit_leading_zeroes
);
904 if (digits_to_check
< 0) {
908 // If the block is not the maximum size, that means it has leading
909 // zeroes, and zeroes are not nines.
910 if (implicit_leading_zeroes
> 0) {
914 // But leading zeroes are zeroes (that could be trailing). We take the
915 // minimum of the leading zeroes and digits requested because if there are
916 // more requested digits than leading zeroes we shouldn't count those.
918 (implicit_leading_zeroes
> digits_requested
? digits_requested
919 : implicit_leading_zeroes
);
921 // Check the upper digits of this block.
922 for (int i
= 0; i
< digits_to_check
; ++i
) {
923 if (int_to_str
[i
] == '9') {
926 } else if (int_to_str
[i
] == '0') {
935 bool truncated
= false;
937 // Find the digit after the lowest digit that we'll actually print to
938 // determine the rounding.
939 const uint32_t maximum
=
940 exp_precision
+ 1 - static_cast<uint32_t>(digits_checked
);
941 uint32_t last_digit
= 0;
942 for (uint32_t k
= 0; k
< last_block_size
- maximum
; ++k
) {
946 last_digit
= digits
% 10;
950 // If the last block we read doesn't have the digit after the end of what
951 // we'll print, then we need to read the next block to get that digit.
952 if (maximum
== last_block_size
) {
954 BlockInt extra_block
= float_converter
.get_block(cur_block
);
955 last_digit
= extra_block
/ ((MAX_BLOCK
/ 10) + 1);
957 if (extra_block
% ((MAX_BLOCK
/ 10) + 1) > 0)
961 // TODO: unify this code across the three float conversions.
962 RoundDirection round
;
964 // If we've already seen a truncated digit, then we don't need to check any
967 // Check the blocks above the decimal point
968 if (cur_block
>= 0) {
969 // Check every block until the decimal point for non-zero digits.
970 for (int cur_extra_block
= cur_block
- 1; cur_extra_block
>= 0;
972 BlockInt extra_block
= float_converter
.get_block(cur_extra_block
);
973 if (extra_block
> 0) {
979 // If it's still not truncated and there are digits below the decimal point
980 if (!truncated
&& exponent
- MANT_WIDTH
< 0) {
981 // Use the formula from %f.
983 !zero_after_digits(exponent
- MANT_WIDTH
, exp_precision
- base_10_exp
,
984 float_bits
.get_explicit_mantissa(), MANT_WIDTH
);
988 round
= get_round_direction(last_digit
, truncated
, is_negative
);
991 if (round
== RoundDirection::Up
) {
993 } else if (round
== RoundDirection::Down
) {
996 // RoundDirection is even, so check the lowest digit that will be printed.
999 // maximum is the number of digits that will remain in digits after getting
1000 // last_digit. If it's greater than zero, we can just check the lowest digit
1003 low_digit
= digits
% 10;
1005 // Else if there are trailing nines, then the low digit is a nine, same
1007 if (trailing_nines
> 0) {
1009 } else if (trailing_zeroes
> 0) {
1012 // If there are no trailing zeroes or nines, then the round direction
1013 // doesn't actually matter here. Since this conversion passes off the
1014 // value to another one for final conversion, rounding only matters to
1015 // determine if the exponent is higher than expected (with an all nine
1016 // number) or to determine the trailing zeroes to trim. In this case
1017 // low_digit is set to 0, but it could be set to any number.
1022 round_up
= (low_digit
% 2) != 0;
1025 digits_checked
+= digits_requested
;
1026 LIBC_ASSERT(digits_checked
== init_precision
);
1027 // At this point we should have checked all the digits requested by the
1028 // precision. We may increment this number 1 more if we round up all of the
1029 // digits, but at this point in the code digits_checked should always equal
1033 // If all the digits that would be printed are nines, then rounding up means
1034 // that the base 10 exponent is one higher and all those nines turn to
1035 // zeroes (e.g. 999 -> 1000).
1036 if (trailing_nines
== init_precision
) {
1038 trailing_zeroes
= digits_checked
;
1041 // If there are trailing nines, they turn into trailing zeroes when
1042 // they're rounded up.
1043 if (trailing_nines
> 0) {
1044 trailing_zeroes
+= trailing_nines
;
1045 } else if (trailing_zeroes
> 0) {
1046 // If there are trailing zeroes, then the last digit will be rounded up
1047 // to a 1 so they aren't trailing anymore.
1048 trailing_zeroes
= 0;
1053 // if P > X >= -4, the conversion is with style f (or F) and precision equals
1055 if (static_cast<int>(init_precision
) > base_10_exp
&& base_10_exp
>= -4) {
1056 FormatSection new_conv
= to_conv
;
1057 const int conv_precision
= init_precision
- (base_10_exp
+ 1);
1059 if ((to_conv
.flags
& FormatFlags::ALTERNATE_FORM
) != 0) {
1060 new_conv
.precision
= conv_precision
;
1062 // If alt form isn't set, then we need to determine the number of trailing
1063 // zeroes and set the precision such that they are removed.
1066 Here's a diagram of an example:
1068 printf("%.15g", 22.25);
1070 +--- init_precision = 15
1072 +-------------------+
1074 | ++--- trimmed_precision = 2
1076 22.250000000000000000
1080 base_10_exp + 1 = 2 --+ +--- trailing_zeroes = 11
1082 int trimmed_precision
= static_cast<int>(
1083 digits_checked
- (base_10_exp
+ 1) - trailing_zeroes
);
1084 if (trimmed_precision
< 0) {
1085 trimmed_precision
= 0;
1087 new_conv
.precision
= (trimmed_precision
> conv_precision
)
1089 : trimmed_precision
;
1092 return convert_float_decimal_typed
<T
>(writer
, new_conv
, float_bits
);
1094 // otherwise, the conversion is with style e (or E) and precision equals
1096 const int conv_precision
= init_precision
- 1;
1097 FormatSection new_conv
= to_conv
;
1098 if ((to_conv
.flags
& FormatFlags::ALTERNATE_FORM
) != 0) {
1099 new_conv
.precision
= conv_precision
;
1101 // If alt form isn't set, then we need to determine the number of trailing
1102 // zeroes and set the precision such that they are removed.
1103 int trimmed_precision
=
1104 static_cast<int>(digits_checked
- 1 - trailing_zeroes
);
1105 if (trimmed_precision
< 0) {
1106 trimmed_precision
= 0;
1108 new_conv
.precision
= (trimmed_precision
> conv_precision
)
1110 : trimmed_precision
;
1112 return convert_float_dec_exp_typed
<T
>(writer
, new_conv
, float_bits
);
1116 // TODO: unify the float converters to remove the duplicated checks for inf/nan.
1117 LIBC_INLINE
int convert_float_decimal(Writer
*writer
,
1118 const FormatSection
&to_conv
) {
1119 if (to_conv
.length_modifier
== LengthModifier::L
) {
1120 fputil::FPBits
<long double>::UIntType float_raw
= to_conv
.conv_val_raw
;
1121 fputil::FPBits
<long double> float_bits(float_raw
);
1122 if (!float_bits
.is_inf_or_nan()) {
1123 return convert_float_decimal_typed
<long double>(writer
, to_conv
,
1127 fputil::FPBits
<double>::UIntType float_raw
=
1128 static_cast<fputil::FPBits
<double>::UIntType
>(to_conv
.conv_val_raw
);
1129 fputil::FPBits
<double> float_bits(float_raw
);
1130 if (!float_bits
.is_inf_or_nan()) {
1131 return convert_float_decimal_typed
<double>(writer
, to_conv
, float_bits
);
1135 return convert_inf_nan(writer
, to_conv
);
1138 LIBC_INLINE
int convert_float_dec_exp(Writer
*writer
,
1139 const FormatSection
&to_conv
) {
1140 if (to_conv
.length_modifier
== LengthModifier::L
) {
1141 fputil::FPBits
<long double>::UIntType float_raw
= to_conv
.conv_val_raw
;
1142 fputil::FPBits
<long double> float_bits(float_raw
);
1143 if (!float_bits
.is_inf_or_nan()) {
1144 return convert_float_dec_exp_typed
<long double>(writer
, to_conv
,
1148 fputil::FPBits
<double>::UIntType float_raw
=
1149 static_cast<fputil::FPBits
<double>::UIntType
>(to_conv
.conv_val_raw
);
1150 fputil::FPBits
<double> float_bits(float_raw
);
1151 if (!float_bits
.is_inf_or_nan()) {
1152 return convert_float_dec_exp_typed
<double>(writer
, to_conv
, float_bits
);
1156 return convert_inf_nan(writer
, to_conv
);
1159 LIBC_INLINE
int convert_float_dec_auto(Writer
*writer
,
1160 const FormatSection
&to_conv
) {
1161 if (to_conv
.length_modifier
== LengthModifier::L
) {
1162 fputil::FPBits
<long double>::UIntType float_raw
= to_conv
.conv_val_raw
;
1163 fputil::FPBits
<long double> float_bits(float_raw
);
1164 if (!float_bits
.is_inf_or_nan()) {
1165 return convert_float_dec_auto_typed
<long double>(writer
, to_conv
,
1169 fputil::FPBits
<double>::UIntType float_raw
=
1170 static_cast<fputil::FPBits
<double>::UIntType
>(to_conv
.conv_val_raw
);
1171 fputil::FPBits
<double> float_bits(float_raw
);
1172 if (!float_bits
.is_inf_or_nan()) {
1173 return convert_float_dec_auto_typed
<double>(writer
, to_conv
, float_bits
);
1177 return convert_inf_nan(writer
, to_conv
);
1180 } // namespace printf_core
1181 } // namespace LIBC_NAMESPACE
1183 #endif // LLVM_LIBC_SRC_STDIO_PRINTF_CORE_FLOAT_DEC_CONVERTER_H