Warning: This file is not a C or C++ file. It does not have highlighting.

1//===-- Decimal Float Converter for printf ----------------------*- C++ -*-===//
2//
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
6//
7//===----------------------------------------------------------------------===//
8
9#ifndef LLVM_LIBC_SRC_STDIO_PRINTF_CORE_FLOAT_DEC_CONVERTER_H
10#define LLVM_LIBC_SRC_STDIO_PRINTF_CORE_FLOAT_DEC_CONVERTER_H
11
12#include "src/__support/CPP/string_view.h"
13#include "src/__support/FPUtil/FPBits.h"
14#include "src/__support/FPUtil/rounding_mode.h"
15#include "src/__support/big_int.h" // is_big_int_v
16#include "src/__support/ctype_utils.h"
17#include "src/__support/float_to_string.h"
18#include "src/__support/integer_to_string.h"
19#include "src/__support/libc_assert.h"
20#include "src/__support/macros/config.h"
21#include "src/stdio/printf_core/converter_utils.h"
22#include "src/stdio/printf_core/core_structs.h"
23#include "src/stdio/printf_core/float_inf_nan_converter.h"
24#include "src/stdio/printf_core/writer.h"
25
26#include <inttypes.h>
27#include <stddef.h>
28
29namespace LIBC_NAMESPACE_DECL {
30namespace printf_core {
31
32using StorageType = fputil::FPBits<long double>::StorageType;
33using DecimalString = IntegerToString<intmax_t>;
34using ExponentString =
35 IntegerToString<intmax_t, radix::Dec::WithWidth<2>::WithSign>;
36
37// Returns true if value is divisible by 2^p.
38template <typename T>
39LIBC_INLINE constexpr cpp::enable_if_t<cpp::is_integral_v<T> || is_big_int_v<T>,
40 bool>
41multiple_of_power_of_2(T value, uint32_t p) {
42 return (value & ((T(1) << p) - 1)) == 0;
43}
44
45constexpr size_t BLOCK_SIZE = 9;
46constexpr uint32_t MAX_BLOCK = 999999999;
47
48// constexpr size_t BLOCK_SIZE = 18;
49// constexpr uint32_t MAX_BLOCK = 999999999999999999;
50constexpr char DECIMAL_POINT = '.';
51
52LIBC_INLINE RoundDirection get_round_direction(int last_digit, bool truncated,
53 Sign sign) {
54 switch (fputil::quick_get_round()) {
55 case FE_TONEAREST:
56 // Round to nearest, if it's exactly halfway then round to even.
57 if (last_digit != 5) {
58 return last_digit > 5 ? RoundDirection::Up : RoundDirection::Down;
59 } else {
60 return !truncated ? RoundDirection::Even : RoundDirection::Up;
61 }
62 case FE_DOWNWARD:
63 if (sign.is_neg() && (truncated || last_digit > 0)) {
64 return RoundDirection::Up;
65 } else {
66 return RoundDirection::Down;
67 }
68 case FE_UPWARD:
69 if (sign.is_pos() && (truncated || last_digit > 0)) {
70 return RoundDirection::Up;
71 } else {
72 return RoundDirection::Down;
73 }
74 return sign.is_neg() ? RoundDirection::Down : RoundDirection::Up;
75 case FE_TOWARDZERO:
76 return RoundDirection::Down;
77 default:
78 return RoundDirection::Down;
79 }
80}
81
82template <typename T>
83LIBC_INLINE constexpr cpp::enable_if_t<cpp::is_integral_v<T> || is_big_int_v<T>,
84 bool>
85zero_after_digits(int32_t base_2_exp, int32_t digits_after_point, T mantissa,
86 const int32_t mant_width) {
87 const int32_t required_twos = -base_2_exp - digits_after_point - 1;
88 // Add 8 to mant width since this is a loose bound.
89 const bool has_trailing_zeros =
90 required_twos <= 0 ||
91 (required_twos < (mant_width + 8) &&
92 multiple_of_power_of_2(mantissa, static_cast<uint32_t>(required_twos)));
93 return has_trailing_zeros;
94}
95
96template <WriteMode write_mode> class PaddingWriter {
97 bool left_justified = false;
98 bool leading_zeroes = false;
99 char sign_char = 0;
100 size_t min_width = 0;
101
102public:
103 LIBC_INLINE PaddingWriter() {}
104 LIBC_INLINE PaddingWriter(const FormatSection &to_conv, char init_sign_char)
105 : left_justified((to_conv.flags & FormatFlags::LEFT_JUSTIFIED) > 0),
106 leading_zeroes((to_conv.flags & FormatFlags::LEADING_ZEROES) > 0),
107 sign_char(init_sign_char),
108 min_width(to_conv.min_width > 0 ? to_conv.min_width : 0) {}
109
110 LIBC_INLINE int write_left_padding(Writer<write_mode> *writer,
111 size_t total_digits) {
112 // The pattern is (spaces) (sign) (zeroes), but only one of spaces and
113 // zeroes can be written, and only if the padding amount is positive.
114 int padding_amount =
115 static_cast<int>(min_width - total_digits - (sign_char > 0 ? 1 : 0));
116 if (left_justified || padding_amount < 0) {
117 if (sign_char > 0) {
118 RET_IF_RESULT_NEGATIVE(writer->write(sign_char));
119 }
120 return 0;
121 }
122 if (!leading_zeroes) {
123 RET_IF_RESULT_NEGATIVE(writer->write(' ', padding_amount));
124 }
125 if (sign_char > 0) {
126 RET_IF_RESULT_NEGATIVE(writer->write(sign_char));
127 }
128 if (leading_zeroes) {
129 RET_IF_RESULT_NEGATIVE(writer->write('0', padding_amount));
130 }
131 return 0;
132 }
133
134 LIBC_INLINE int write_right_padding(Writer<write_mode> *writer,
135 size_t total_digits) {
136 // If and only if the conversion is left justified, there may be trailing
137 // spaces.
138 int padding_amount =
139 static_cast<int>(min_width - total_digits - (sign_char > 0 ? 1 : 0));
140 if (left_justified && padding_amount > 0) {
141 RET_IF_RESULT_NEGATIVE(writer->write(' ', padding_amount));
142 }
143 return 0;
144 }
145};
146
147/*
148 We only need to round a given segment if all of the segments below it are
149 the max (or this is the last segment). This means that we don't have to
150 write those initially, we can just keep the most recent non-maximal
151 segment and a counter of the number of maximal segments. When we reach a
152 non-maximal segment, we write the stored segment as well as as many 9s as
153 are necessary. Alternately, if we reach the end and have to round up, then
154 we round the stored segment, and write zeroes following it. If this
155 crosses the decimal point, then we have to shift it one space to the
156 right.
157 This FloatWriter class does the buffering and counting, and writes to the
158 output when necessary.
159*/
160template <WriteMode write_mode> class FloatWriter {
161 char block_buffer[BLOCK_SIZE]; // The buffer that holds a block.
162 size_t buffered_digits = 0; // The number of digits held in the buffer.
163 bool has_written = false; // True once any digits have been output.
164 size_t max_block_count = 0; // The # of blocks of all 9s currently buffered.
165 size_t total_digits = 0; // The number of digits that will be output.
166 size_t digits_before_decimal = 0; // The # of digits to write before the '.'
167 size_t total_digits_written = 0; // The # of digits that have been output.
168 bool has_decimal_point; // True if the number has a decimal point.
169 Writer<write_mode> *writer; // Writes to the final output.
170 PaddingWriter<write_mode>
171 padding_writer; // Handles prefixes/padding, uses total_digits.
172
173 LIBC_INLINE int flush_buffer(bool round_up_max_blocks = false) {
174 const char MAX_BLOCK_DIGIT = (round_up_max_blocks ? '0' : '9');
175
176 // Write the most recent buffered block, and mark has_written
177 if (!has_written) {
178 has_written = true;
179 RET_IF_RESULT_NEGATIVE(
180 padding_writer.write_left_padding(writer, total_digits));
181 }
182
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
185 // point.
186 if (total_digits_written < digits_before_decimal &&
187 total_digits_written + buffered_digits >= digits_before_decimal &&
188 has_decimal_point) {
189 // digits_to_write > 0 guaranteed by outer if
190 size_t digits_to_write = digits_before_decimal - total_digits_written;
191 // Write the digits before the decimal point.
192 RET_IF_RESULT_NEGATIVE(writer->write({block_buffer, digits_to_write}));
193 RET_IF_RESULT_NEGATIVE(writer->write(DECIMAL_POINT));
194 if (buffered_digits > digits_to_write) {
195 // Write the digits after the decimal point.
196 RET_IF_RESULT_NEGATIVE(
197 writer->write({block_buffer + digits_to_write,
198 (buffered_digits - digits_to_write)}));
199 }
200 // add 1 for the decimal point
201 total_digits_written += buffered_digits + 1;
202 // Mark the buffer as empty.
203 buffered_digits = 0;
204 }
205
206 // Clear the buffered digits.
207 if (buffered_digits > 0) {
208 RET_IF_RESULT_NEGATIVE(writer->write({block_buffer, buffered_digits}));
209 total_digits_written += buffered_digits;
210 buffered_digits = 0;
211 }
212
213 // if the decimal point is the next character, or is in the range covered
214 // by the max blocks, write the appropriate digits and the decimal point.
215 if (total_digits_written < digits_before_decimal &&
216 total_digits_written + BLOCK_SIZE * max_block_count >=
217 digits_before_decimal &&
218 has_decimal_point) {
219 // digits_to_write > 0 guaranteed by outer if
220 size_t digits_to_write = digits_before_decimal - total_digits_written;
221 RET_IF_RESULT_NEGATIVE(writer->write(MAX_BLOCK_DIGIT, digits_to_write));
222 RET_IF_RESULT_NEGATIVE(writer->write(DECIMAL_POINT));
223 if ((BLOCK_SIZE * max_block_count) > digits_to_write) {
224 RET_IF_RESULT_NEGATIVE(writer->write(
225 MAX_BLOCK_DIGIT, (BLOCK_SIZE * max_block_count) - digits_to_write));
226 }
227 // add 1 for the decimal point
228 total_digits_written += BLOCK_SIZE * max_block_count + 1;
229 // clear the buffer of max blocks
230 max_block_count = 0;
231 }
232
233 // Clear the buffer of max blocks
234 if (max_block_count > 0) {
235 RET_IF_RESULT_NEGATIVE(
236 writer->write(MAX_BLOCK_DIGIT, max_block_count * BLOCK_SIZE));
237 total_digits_written += max_block_count * BLOCK_SIZE;
238 max_block_count = 0;
239 }
240 return 0;
241 }
242
243 // -exponent will never overflow because all long double types we support
244 // have at most 15 bits of mantissa and the C standard defines an int as
245 // being at least 16 bits.
246 static_assert(fputil::FPBits<long double>::EXP_LEN < (sizeof(int) * 8));
247
248public:
249 LIBC_INLINE FloatWriter(Writer<write_mode> *init_writer,
250 bool init_has_decimal_point,
251 const PaddingWriter<write_mode> &init_padding_writer)
252 : has_decimal_point(init_has_decimal_point), writer(init_writer),
253 padding_writer(init_padding_writer) {}
254
255 LIBC_INLINE void init(size_t init_total_digits,
256 size_t init_digits_before_decimal) {
257 total_digits = init_total_digits;
258 digits_before_decimal = init_digits_before_decimal;
259 }
260
261 LIBC_INLINE void write_first_block(BlockInt block, bool exp_format = false) {
262 const DecimalString buf(block);
263 const cpp::string_view int_to_str = buf.view();
264 size_t digits_buffered = int_to_str.size();
265 // Block Buffer is guaranteed to not overflow since block cannot have more
266 // than BLOCK_SIZE digits.
267 // TODO: Replace with memcpy
268 for (size_t count = 0; count < digits_buffered; ++count) {
269 block_buffer[count] = int_to_str[count];
270 }
271 buffered_digits = digits_buffered;
272
273 // In the exponent format (%e) we know how many digits will be written even
274 // before calculating any blocks, whereas the decimal format (%f) has to
275 // write all of the blocks that would come before the decimal place.
276 if (!exp_format) {
277 total_digits += digits_buffered;
278 digits_before_decimal += digits_buffered;
279 }
280 }
281
282 LIBC_INLINE int write_middle_block(BlockInt block) {
283 if (block == MAX_BLOCK) { // Buffer max blocks in case of rounding
284 ++max_block_count;
285 } else { // If a non-max block has been found
286 RET_IF_RESULT_NEGATIVE(flush_buffer());
287
288 // Now buffer the current block. We add 1 + MAX_BLOCK to force the
289 // leading zeroes, and drop the leading one. This is probably inefficient,
290 // but it works. See https://xkcd.com/2021/
291 const DecimalString buf(block + (MAX_BLOCK + 1));
292 const cpp::string_view int_to_str = buf.view();
293 // TODO: Replace with memcpy
294 for (size_t count = 0; count < BLOCK_SIZE; ++count) {
295 block_buffer[count] = int_to_str[count + 1];
296 }
297
298 buffered_digits = BLOCK_SIZE;
299 }
300 return 0;
301 }
302
303 LIBC_INLINE int write_last_block(BlockInt block, size_t block_digits,
304 RoundDirection round, int exponent = 0,
305 char exp_char = '\0') {
306 bool has_exp = (exp_char != '\0');
307
308 char end_buff[BLOCK_SIZE];
309
310 {
311 const DecimalString buf(block + (MAX_BLOCK + 1));
312 const cpp::string_view int_to_str = buf.view();
313
314 // copy the last block_digits characters into the start of end_buff.
315 // TODO: Replace with memcpy
316 for (size_t count = 0; count < block_digits; ++count) {
317 end_buff[count] = int_to_str[count + 1 + (BLOCK_SIZE - block_digits)];
318 }
319 }
320
321 char low_digit = '0';
322 if (block_digits > 0) {
323 low_digit = end_buff[block_digits - 1];
324 } else if (max_block_count > 0) {
325 low_digit = '9';
326 } else if (buffered_digits > 0) {
327 low_digit = block_buffer[buffered_digits - 1];
328 }
329
330 bool round_up_max_blocks = false;
331
332 // Round up
333 if (round == RoundDirection::Up ||
334 (round == RoundDirection::Even && low_digit % 2 != 0)) {
335 bool has_carry = true;
336 round_up_max_blocks = true; // if we're rounding up, we might need to
337 // round up the max blocks that are buffered.
338
339 // handle the low block that we're adding
340 for (int count = static_cast<int>(block_digits) - 1;
341 count >= 0 && has_carry; --count) {
342 if (end_buff[count] == '9') {
343 end_buff[count] = '0';
344 } else {
345 end_buff[count] += 1;
346 has_carry = false;
347 round_up_max_blocks = false; // If the low block isn't all nines, then
348 // the max blocks aren't rounded up.
349 }
350 }
351 // handle the high block that's buffered
352 for (int count = static_cast<int>(buffered_digits) - 1;
353 count >= 0 && has_carry; --count) {
354 if (block_buffer[count] == '9') {
355 block_buffer[count] = '0';
356 } else {
357 block_buffer[count] += 1;
358 has_carry = false;
359 }
360 }
361
362 // has_carry should only be true here if every previous digit is 9, which
363 // implies that the number has never been written.
364 if (has_carry /* && !has_written */) {
365 if (has_exp) { // This is in %e style
366 // Since this is exponential notation, we don't write any more digits
367 // but we do increment the exponent.
368 ++exponent;
369
370 const ExponentString buf(exponent);
371 const cpp::string_view int_to_str = buf.view();
372
373 // TODO: also change this to calculate the width of the number more
374 // efficiently.
375 size_t exponent_width = int_to_str.size();
376 size_t number_digits =
377 buffered_digits + (max_block_count * BLOCK_SIZE) + block_digits;
378
379 // Here we have to recalculate the total number of digits since the
380 // exponent's width may have changed. We're only adding 1 to exponent
381 // width since exp_str appends the sign.
382 total_digits =
383 (has_decimal_point ? 1 : 0) + number_digits + 1 + exponent_width;
384
385 // Normally write_left_padding is called by flush_buffer but since
386 // we're rounding up all of the digits, the ones in the buffer are
387 // wrong and can't be flushed.
388 RET_IF_RESULT_NEGATIVE(
389 padding_writer.write_left_padding(writer, total_digits));
390 // Now we know we need to print a leading 1, the decimal point, and
391 // then zeroes after it.
392 RET_IF_RESULT_NEGATIVE(writer->write('1'));
393 // digits_before_decimal - 1 to account for the leading '1'
394 if (has_decimal_point) {
395 RET_IF_RESULT_NEGATIVE(writer->write(DECIMAL_POINT));
396 // This is just the length of the number, not including the decimal
397 // point, or exponent.
398
399 if (number_digits > 1) {
400 RET_IF_RESULT_NEGATIVE(writer->write('0', number_digits - 1));
401 }
402 }
403 RET_IF_RESULT_NEGATIVE(writer->write(exp_char));
404 RET_IF_RESULT_NEGATIVE(writer->write(int_to_str));
405
406 total_digits_written = total_digits;
407 return WRITE_OK;
408 } else { // This is in %f style
409 ++total_digits;
410 ++digits_before_decimal;
411 // Normally write_left_padding is called by flush_buffer but since
412 // we're rounding up all of the digits, the ones in the buffer are
413 // wrong and can't be flushed.
414 RET_IF_RESULT_NEGATIVE(
415 padding_writer.write_left_padding(writer, total_digits));
416 // Now we know we need to print a leading 1, zeroes up to the decimal
417 // point, the decimal point, and then finally digits after it.
418 RET_IF_RESULT_NEGATIVE(writer->write('1'));
419 // digits_before_decimal - 1 to account for the leading '1'
420 RET_IF_RESULT_NEGATIVE(writer->write('0', digits_before_decimal - 1));
421 if (has_decimal_point) {
422 RET_IF_RESULT_NEGATIVE(writer->write(DECIMAL_POINT));
423 // add one to digits_before_decimal to account for the decimal point
424 // itself.
425 if (total_digits > digits_before_decimal + 1) {
426 RET_IF_RESULT_NEGATIVE(writer->write(
427 '0', total_digits - (digits_before_decimal + 1)));
428 }
429 }
430 total_digits_written = total_digits;
431 return WRITE_OK;
432 }
433 }
434 }
435 // Either we intend to round down, or the rounding up is complete. Flush the
436 // buffers.
437
438 RET_IF_RESULT_NEGATIVE(flush_buffer(round_up_max_blocks));
439
440 // And then write the final block. It's written via the buffer so that if
441 // this is also the first block, the decimal point will be placed correctly.
442
443 // TODO: Replace with memcpy
444 for (size_t count = 0; count < block_digits; ++count) {
445 block_buffer[count] = end_buff[count];
446 }
447 buffered_digits = block_digits;
448 RET_IF_RESULT_NEGATIVE(flush_buffer());
449
450 if (has_exp) {
451 RET_IF_RESULT_NEGATIVE(writer->write(exp_char));
452 const ExponentString buf(exponent);
453 RET_IF_RESULT_NEGATIVE(writer->write(buf.view()));
454 }
455 total_digits_written = total_digits;
456
457 return WRITE_OK;
458 }
459
460 LIBC_INLINE int write_zeroes(uint32_t num_zeroes) {
461 RET_IF_RESULT_NEGATIVE(flush_buffer());
462 RET_IF_RESULT_NEGATIVE(writer->write('0', num_zeroes));
463 return 0;
464 }
465
466 LIBC_INLINE int right_pad() {
467 return padding_writer.write_right_padding(writer, total_digits);
468 }
469};
470
471// Class-template auto deduction helpers, add more if needed.
472FloatWriter(Writer<WriteMode::FILL_BUFF_AND_DROP_OVERFLOW>, bool,
473 const PaddingWriter<WriteMode::FILL_BUFF_AND_DROP_OVERFLOW>)
474 -> FloatWriter<WriteMode::FILL_BUFF_AND_DROP_OVERFLOW>;
475FloatWriter(Writer<WriteMode::RESIZE_AND_FILL_BUFF>, bool,
476 const PaddingWriter<WriteMode::RESIZE_AND_FILL_BUFF>)
477 -> FloatWriter<WriteMode::RESIZE_AND_FILL_BUFF>;
478FloatWriter(Writer<WriteMode::FLUSH_TO_STREAM>, bool,
479 const PaddingWriter<WriteMode::FLUSH_TO_STREAM>)
480 -> FloatWriter<WriteMode::FLUSH_TO_STREAM>;
481
482// This implementation is based on the Ryu Printf algorithm by Ulf Adams:
483// Ulf Adams. 2019. Ryƫ revisited: printf floating point conversion.
484// Proc. ACM Program. Lang. 3, OOPSLA, Article 169 (October 2019), 23 pages.
485// https://doi.org/10.1145/3360595
486template <typename T, WriteMode write_mode,
487 cpp::enable_if_t<cpp::is_floating_point_v<T>, int> = 0>
488LIBC_INLINE int convert_float_decimal_typed(Writer<write_mode> *writer,
489 const FormatSection &to_conv,
490 fputil::FPBits<T> float_bits) {
491 // signed because later we use -FRACTION_LEN
492 constexpr int32_t FRACTION_LEN = fputil::FPBits<T>::FRACTION_LEN;
493 int exponent = float_bits.get_explicit_exponent();
494
495 char sign_char = 0;
496
497 if (float_bits.is_neg())
498 sign_char = '-';
499 else if ((to_conv.flags & FormatFlags::FORCE_SIGN) == FormatFlags::FORCE_SIGN)
500 sign_char = '+'; // FORCE_SIGN has precedence over SPACE_PREFIX
501 else if ((to_conv.flags & FormatFlags::SPACE_PREFIX) ==
502 FormatFlags::SPACE_PREFIX)
503 sign_char = ' ';
504
505 // If to_conv doesn't specify a precision, the precision defaults to 6.
506 const unsigned int precision = to_conv.precision < 0 ? 6 : to_conv.precision;
507 bool has_decimal_point =
508 (precision > 0) || ((to_conv.flags & FormatFlags::ALTERNATE_FORM) != 0);
509
510 // nonzero is false until a nonzero digit is found. It is used to determine if
511 // leading zeroes should be printed, since before the first digit they are
512 // ignored.
513 bool nonzero = false;
514
515 PaddingWriter<write_mode> padding_writer(to_conv, sign_char);
516 FloatWriter float_writer(writer, has_decimal_point, padding_writer);
517 FloatToString<T> float_converter(float_bits.get_val());
518
519 const size_t positive_blocks = float_converter.get_positive_blocks();
520
521 // This loop iterates through the number a block at a time until it finds a
522 // block that is not zero or it hits the decimal point. This is because all
523 // zero blocks before the first nonzero digit or the decimal point are
524 // ignored (no leading zeroes, at least at this stage).
525 for (int32_t i = static_cast<int32_t>(positive_blocks) - 1; i >= 0; --i) {
526 BlockInt digits = float_converter.get_positive_block(i);
527 if (nonzero) {
528 RET_IF_RESULT_NEGATIVE(float_writer.write_middle_block(digits));
529 } else if (digits != 0) {
530 size_t blocks_before_decimal = i;
531 float_writer.init((blocks_before_decimal * BLOCK_SIZE) +
532 (has_decimal_point ? 1 : 0) + precision,
533 blocks_before_decimal * BLOCK_SIZE);
534 float_writer.write_first_block(digits);
535
536 nonzero = true;
537 }
538 }
539
540 // if we haven't yet found a valid digit, buffer a zero.
541 if (!nonzero) {
542 float_writer.init((has_decimal_point ? 1 : 0) + precision, 0);
543 float_writer.write_first_block(0);
544 }
545
546 if (exponent < FRACTION_LEN) {
547 const uint32_t blocks = (precision / static_cast<uint32_t>(BLOCK_SIZE)) + 1;
548 uint32_t i = 0;
549 // if all the blocks we should write are zero
550 if (blocks <= float_converter.zero_blocks_after_point()) {
551 i = blocks; // just write zeroes up to precision
552 RET_IF_RESULT_NEGATIVE(float_writer.write_zeroes(precision));
553 } else if (i < float_converter.zero_blocks_after_point()) {
554 // else if there are some blocks that are zeroes
555 i = static_cast<uint32_t>(float_converter.zero_blocks_after_point());
556 // write those blocks as zeroes.
557 RET_IF_RESULT_NEGATIVE(float_writer.write_zeroes(9 * i));
558 }
559 // for each unwritten block
560 for (; i < blocks; ++i) {
561 if (float_converter.is_lowest_block(i)) {
562 const uint32_t fill = precision - 9 * i;
563 RET_IF_RESULT_NEGATIVE(float_writer.write_zeroes(fill));
564 break;
565 }
566 BlockInt digits = float_converter.get_negative_block(i);
567 if (i < blocks - 1) {
568 RET_IF_RESULT_NEGATIVE(float_writer.write_middle_block(digits));
569 } else {
570
571 const uint32_t maximum =
572 static_cast<uint32_t>(precision - BLOCK_SIZE * i);
573 uint32_t last_digit = 0;
574 for (uint32_t k = 0; k < BLOCK_SIZE - maximum; ++k) {
575 last_digit = digits % 10;
576 digits /= 10;
577 }
578 RoundDirection round;
579 const bool truncated = !zero_after_digits(
580 exponent - FRACTION_LEN, precision,
581 float_bits.get_explicit_mantissa(), FRACTION_LEN);
582 round = get_round_direction(last_digit, truncated, float_bits.sign());
583
584 RET_IF_RESULT_NEGATIVE(
585 float_writer.write_last_block(digits, maximum, round));
586 break;
587 }
588 }
589 } else {
590 RET_IF_RESULT_NEGATIVE(float_writer.write_zeroes(precision));
591 }
592 RET_IF_RESULT_NEGATIVE(float_writer.right_pad());
593 return WRITE_OK;
594}
595
596template <typename T, WriteMode write_mode,
597 cpp::enable_if_t<cpp::is_floating_point_v<T>, int> = 0>
598LIBC_INLINE int convert_float_dec_exp_typed(Writer<write_mode> *writer,
599 const FormatSection &to_conv,
600 fputil::FPBits<T> float_bits) {
601 // signed because later we use -FRACTION_LEN
602 constexpr int32_t FRACTION_LEN = fputil::FPBits<T>::FRACTION_LEN;
603 int exponent = float_bits.get_explicit_exponent();
604 StorageType mantissa = float_bits.get_explicit_mantissa();
605
606 char sign_char = 0;
607
608 if (float_bits.is_neg())
609 sign_char = '-';
610 else if ((to_conv.flags & FormatFlags::FORCE_SIGN) == FormatFlags::FORCE_SIGN)
611 sign_char = '+'; // FORCE_SIGN has precedence over SPACE_PREFIX
612 else if ((to_conv.flags & FormatFlags::SPACE_PREFIX) ==
613 FormatFlags::SPACE_PREFIX)
614 sign_char = ' ';
615
616 // If to_conv doesn't specify a precision, the precision defaults to 6.
617 const unsigned int precision = to_conv.precision < 0 ? 6 : to_conv.precision;
618 bool has_decimal_point =
619 (precision > 0) || ((to_conv.flags & FormatFlags::ALTERNATE_FORM) != 0);
620
621 PaddingWriter<write_mode> padding_writer(to_conv, sign_char);
622 FloatWriter float_writer(writer, has_decimal_point, padding_writer);
623 FloatToString<T> float_converter(float_bits.get_val());
624
625 size_t digits_written = 0;
626 int final_exponent = 0;
627
628 // Here we would subtract 1 to account for the fact that block 0 counts as a
629 // positive block, but the loop below accounts for this by starting with
630 // subtracting 1 from cur_block.
631 int cur_block;
632
633 if (exponent < 0) {
634 cur_block = -static_cast<int>(float_converter.zero_blocks_after_point());
635 } else {
636 cur_block = static_cast<int>(float_converter.get_positive_blocks());
637 }
638
639 BlockInt digits = 0;
640
641 // If the mantissa is 0, then the number is 0, meaning that looping until a
642 // non-zero block is found will loop forever. The first block is just 0.
643 if (mantissa != 0) {
644 // This loop finds the first block.
645 while (digits == 0) {
646 --cur_block;
647 digits = float_converter.get_block(cur_block);
648 }
649 } else {
650 cur_block = 0;
651 }
652
653 const size_t block_width = IntegerToString<intmax_t>(digits).size();
654
655 final_exponent = static_cast<int>(cur_block * BLOCK_SIZE) +
656 static_cast<int>(block_width - 1);
657 int positive_exponent = final_exponent < 0 ? -final_exponent : final_exponent;
658
659 size_t exponent_width = IntegerToString<intmax_t>(positive_exponent).size();
660
661 // Calculate the total number of digits in the number.
662 // 1 - the digit before the decimal point
663 // 1 - the decimal point (optional)
664 // precision - the number of digits after the decimal point
665 // 1 - the 'e' at the start of the exponent
666 // 1 - the sign at the start of the exponent
667 // max(2, exp width) - the digits of the exponent, min 2.
668
669 float_writer.init(1 + (has_decimal_point ? 1 : 0) + precision + 2 +
670 (exponent_width < 2 ? 2 : exponent_width),
671 1);
672
673 // If this block is not the last block
674 if (block_width <= precision + 1) {
675 float_writer.write_first_block(digits, true);
676 digits_written += block_width;
677 --cur_block;
678 }
679
680 // For each middle block.
681 for (; digits_written + BLOCK_SIZE < precision + 1; --cur_block) {
682 digits = float_converter.get_block(cur_block);
683
684 RET_IF_RESULT_NEGATIVE(float_writer.write_middle_block(digits));
685 digits_written += BLOCK_SIZE;
686 }
687
688 digits = float_converter.get_block(cur_block);
689
690 size_t last_block_size = BLOCK_SIZE;
691
692 // if the last block is also the first block, then ignore leading zeroes.
693 if (digits_written == 0) {
694 last_block_size = IntegerToString<intmax_t>(digits).size();
695 }
696
697 // This tracks if the number is truncated, that meaning that the digits after
698 // last_digit are non-zero.
699 bool truncated = false;
700
701 // This is the last block.
702 const size_t maximum = precision + 1 - digits_written;
703 uint32_t last_digit = 0;
704 for (uint32_t k = 0; k < last_block_size - maximum; ++k) {
705 if (last_digit > 0)
706 truncated = true;
707
708 last_digit = digits % 10;
709 digits /= 10;
710 }
711
712 // If the last block we read doesn't have the digit after the end of what
713 // we'll print, then we need to read the next block to get that digit.
714 if (maximum == last_block_size) {
715 --cur_block;
716 BlockInt extra_block = float_converter.get_block(cur_block);
717 last_digit = extra_block / ((MAX_BLOCK / 10) + 1);
718 if (extra_block % ((MAX_BLOCK / 10) + 1) > 0) {
719 truncated = true;
720 }
721 }
722
723 RoundDirection round;
724
725 // If we've already seen a truncated digit, then we don't need to check any
726 // more.
727 if (!truncated) {
728 // Check the blocks above the decimal point
729 if (cur_block >= 0) {
730 // Check every block until the decimal point for non-zero digits.
731 for (int cur_extra_block = cur_block - 1; cur_extra_block >= 0;
732 --cur_extra_block) {
733 BlockInt extra_block = float_converter.get_block(cur_extra_block);
734 if (extra_block > 0) {
735 truncated = true;
736 break;
737 }
738 }
739 }
740 // If it's still not truncated and there are digits below the decimal point
741 if (!truncated && exponent - FRACTION_LEN < 0) {
742 // Use the formula from %f.
743 truncated = !zero_after_digits(
744 exponent - FRACTION_LEN, precision - final_exponent,
745 float_bits.get_explicit_mantissa(), FRACTION_LEN);
746 }
747 }
748 round = get_round_direction(last_digit, truncated, float_bits.sign());
749
750 RET_IF_RESULT_NEGATIVE(float_writer.write_last_block(
751 digits, maximum, round, final_exponent,
752 internal::islower(to_conv.conv_name) ? 'e' : 'E'));
753
754 RET_IF_RESULT_NEGATIVE(float_writer.right_pad());
755 return WRITE_OK;
756}
757
758template <typename T, WriteMode write_mode,
759 cpp::enable_if_t<cpp::is_floating_point_v<T>, int> = 0>
760LIBC_INLINE int convert_float_dec_auto_typed(Writer<write_mode> *writer,
761 const FormatSection &to_conv,
762 fputil::FPBits<T> float_bits) {
763 // signed because later we use -FRACTION_LEN
764 constexpr int32_t FRACTION_LEN = fputil::FPBits<T>::FRACTION_LEN;
765 int exponent = float_bits.get_explicit_exponent();
766 StorageType mantissa = float_bits.get_explicit_mantissa();
767
768 // From the standard: Let P (init_precision) equal the precision if nonzero, 6
769 // if the precision is omitted, or 1 if the precision is zero.
770 const unsigned int init_precision = to_conv.precision <= 0
771 ? (to_conv.precision == 0 ? 1 : 6)
772 : to_conv.precision;
773
774 // Then, if a conversion with style E would have an exponent of X
775 // (base_10_exp):
776 int base_10_exp = 0;
777 // If P > X >= -4 the conversion is with style F and precision P - (X + 1).
778 // Otherwise, the conversion is with style E and precision P - 1.
779
780 // For calculating the base 10 exponent, we need to process the number as if
781 // it has style E, so here we calculate the precision we'll use in that case.
782 const unsigned int exp_precision = init_precision - 1;
783
784 FloatToString<T> float_converter(float_bits.get_val());
785
786 // Here we would subtract 1 to account for the fact that block 0 counts as a
787 // positive block, but the loop below accounts for this by starting with
788 // subtracting 1 from cur_block.
789 int cur_block;
790
791 if (exponent < 0) {
792 cur_block = -static_cast<int>(float_converter.zero_blocks_after_point());
793 } else {
794 cur_block = static_cast<int>(float_converter.get_positive_blocks());
795 }
796
797 BlockInt digits = 0;
798
799 // If the mantissa is 0, then the number is 0, meaning that looping until a
800 // non-zero block is found will loop forever.
801 if (mantissa != 0) {
802 // This loop finds the first non-zero block.
803 while (digits == 0) {
804 --cur_block;
805 digits = float_converter.get_block(cur_block);
806 }
807 } else {
808 // In the case of 0.0, then it's always decimal format. If we don't have alt
809 // form then the trailing zeroes are trimmed to make "0", else the precision
810 // is 1 less than specified by the user.
811 FormatSection new_conv = to_conv;
812 if ((to_conv.flags & FormatFlags::ALTERNATE_FORM) != 0) {
813 // This is a style F conversion, making the precision P - 1 - X, but since
814 // this is for the number 0, X (the base 10 exponent) is always 0.
815 new_conv.precision = init_precision - 1;
816 } else {
817 new_conv.precision = 0;
818 }
819 return convert_float_decimal_typed<T>(writer, new_conv, float_bits);
820 }
821
822 const size_t block_width = IntegerToString<intmax_t>(digits).size();
823
824 size_t digits_checked = 0;
825 // TODO: look into unifying trailing_zeroes and trailing_nines. The number can
826 // end in a nine or a zero, but not both.
827 size_t trailing_zeroes = 0;
828 size_t trailing_nines = 0;
829
830 base_10_exp = static_cast<int>(cur_block * BLOCK_SIZE) +
831 static_cast<int>(block_width - 1);
832
833 // If the first block is not also the last block
834 if (block_width <= exp_precision + 1) {
835 const DecimalString buf(digits);
836 const cpp::string_view int_to_str = buf.view();
837
838 for (size_t i = 0; i < block_width; ++i) {
839 if (int_to_str[i] == '9') {
840 ++trailing_nines;
841 trailing_zeroes = 0;
842 } else if (int_to_str[i] == '0') {
843 ++trailing_zeroes;
844 trailing_nines = 0;
845 } else {
846 trailing_nines = 0;
847 trailing_zeroes = 0;
848 }
849 }
850 digits_checked += block_width;
851 --cur_block;
852 }
853
854 // Handle middle blocks
855 for (; digits_checked + BLOCK_SIZE < exp_precision + 1; --cur_block) {
856 digits = float_converter.get_block(cur_block);
857 digits_checked += BLOCK_SIZE;
858 if (digits == MAX_BLOCK) {
859 trailing_nines += 9;
860 trailing_zeroes = 0;
861 } else if (digits == 0) {
862 trailing_zeroes += 9;
863 trailing_nines = 0;
864 } else {
865 // The block is neither all nines nor all zeroes, so we need to figure out
866 // what it ends with.
867 trailing_nines = 0;
868 trailing_zeroes = 0;
869 BlockInt copy_of_digits = digits;
870 BlockInt cur_last_digit = copy_of_digits % 10;
871 // We only care if it ends in nines or zeroes.
872 while (copy_of_digits > 0 &&
873 (cur_last_digit == 9 || cur_last_digit == 0)) {
874 // If the next digit is not the same as the previous one, then there are
875 // no more contiguous trailing digits.
876 if (copy_of_digits % 10 != cur_last_digit) {
877 break;
878 }
879 if (cur_last_digit == 9) {
880 ++trailing_nines;
881 } else if (cur_last_digit == 0) {
882 ++trailing_zeroes;
883 } else {
884 break;
885 }
886 copy_of_digits /= 10;
887 }
888 }
889 }
890
891 // Handle the last block
892
893 digits = float_converter.get_block(cur_block);
894
895 size_t last_block_size = BLOCK_SIZE;
896
897 const DecimalString buf(digits);
898 const cpp::string_view int_to_str = buf.view();
899
900 size_t implicit_leading_zeroes = BLOCK_SIZE - int_to_str.size();
901
902 // if the last block is also the first block, then ignore leading zeroes.
903 if (digits_checked == 0) {
904 last_block_size = int_to_str.size();
905 implicit_leading_zeroes = 0;
906 }
907
908 unsigned int digits_requested =
909 (exp_precision + 1) - static_cast<unsigned int>(digits_checked);
910
911 int digits_to_check =
912 digits_requested - static_cast<int>(implicit_leading_zeroes);
913 if (digits_to_check < 0) {
914 digits_to_check = 0;
915 }
916
917 // If the block is not the maximum size, that means it has leading
918 // zeroes, and zeroes are not nines.
919 if (implicit_leading_zeroes > 0) {
920 trailing_nines = 0;
921 }
922
923 // But leading zeroes are zeroes (that could be trailing). We take the
924 // minimum of the leading zeroes and digits requested because if there are
925 // more requested digits than leading zeroes we shouldn't count those.
926 trailing_zeroes +=
927 (implicit_leading_zeroes > digits_requested ? digits_requested
928 : implicit_leading_zeroes);
929
930 // Check the upper digits of this block.
931 for (int i = 0; i < digits_to_check; ++i) {
932 if (int_to_str[i] == '9') {
933 ++trailing_nines;
934 trailing_zeroes = 0;
935 } else if (int_to_str[i] == '0') {
936 ++trailing_zeroes;
937 trailing_nines = 0;
938 } else {
939 trailing_nines = 0;
940 trailing_zeroes = 0;
941 }
942 }
943
944 bool truncated = false;
945
946 // Find the digit after the lowest digit that we'll actually print to
947 // determine the rounding.
948 const uint32_t maximum =
949 exp_precision + 1 - static_cast<uint32_t>(digits_checked);
950 uint32_t last_digit = 0;
951 for (uint32_t k = 0; k < last_block_size - maximum; ++k) {
952 if (last_digit > 0)
953 truncated = true;
954
955 last_digit = digits % 10;
956 digits /= 10;
957 }
958
959 // If the last block we read doesn't have the digit after the end of what
960 // we'll print, then we need to read the next block to get that digit.
961 if (maximum == last_block_size) {
962 --cur_block;
963 BlockInt extra_block = float_converter.get_block(cur_block);
964 last_digit = extra_block / ((MAX_BLOCK / 10) + 1);
965
966 if (extra_block % ((MAX_BLOCK / 10) + 1) > 0)
967 truncated = true;
968 }
969
970 // TODO: unify this code across the three float conversions.
971 RoundDirection round;
972
973 // If we've already seen a truncated digit, then we don't need to check any
974 // more.
975 if (!truncated) {
976 // Check the blocks above the decimal point
977 if (cur_block >= 0) {
978 // Check every block until the decimal point for non-zero digits.
979 for (int cur_extra_block = cur_block - 1; cur_extra_block >= 0;
980 --cur_extra_block) {
981 BlockInt extra_block = float_converter.get_block(cur_extra_block);
982 if (extra_block > 0) {
983 truncated = true;
984 break;
985 }
986 }
987 }
988 // If it's still not truncated and there are digits below the decimal point
989 if (!truncated && exponent - FRACTION_LEN < 0) {
990 // Use the formula from %f.
991 truncated = !zero_after_digits(
992 exponent - FRACTION_LEN, exp_precision - base_10_exp,
993 float_bits.get_explicit_mantissa(), FRACTION_LEN);
994 }
995 }
996
997 round = get_round_direction(last_digit, truncated, float_bits.sign());
998
999 bool round_up;
1000 if (round == RoundDirection::Up) {
1001 round_up = true;
1002 } else if (round == RoundDirection::Down) {
1003 round_up = false;
1004 } else {
1005 // RoundDirection is even, so check the lowest digit that will be printed.
1006 uint32_t low_digit;
1007
1008 // maximum is the number of digits that will remain in digits after getting
1009 // last_digit. If it's greater than zero, we can just check the lowest digit
1010 // in digits.
1011 if (maximum > 0) {
1012 low_digit = digits % 10;
1013 } else {
1014 // Else if there are trailing nines, then the low digit is a nine, same
1015 // with zeroes.
1016 if (trailing_nines > 0) {
1017 low_digit = 9;
1018 } else if (trailing_zeroes > 0) {
1019 low_digit = 0;
1020 } else {
1021 // If there are no trailing zeroes or nines, then the round direction
1022 // doesn't actually matter here. Since this conversion passes off the
1023 // value to another one for final conversion, rounding only matters to
1024 // determine if the exponent is higher than expected (with an all nine
1025 // number) or to determine the trailing zeroes to trim. In this case
1026 // low_digit is set to 0, but it could be set to any number.
1027
1028 low_digit = 0;
1029 }
1030 }
1031 round_up = (low_digit % 2) != 0;
1032 }
1033
1034 digits_checked += digits_requested;
1035 LIBC_ASSERT(digits_checked == init_precision);
1036 // At this point we should have checked all the digits requested by the
1037 // precision. We may increment this number 1 more if we round up all of the
1038 // digits, but at this point in the code digits_checked should always equal
1039 // init_precision.
1040
1041 if (round_up) {
1042 // If all the digits that would be printed are nines, then rounding up means
1043 // that the base 10 exponent is one higher and all those nines turn to
1044 // zeroes (e.g. 999 -> 1000).
1045 if (trailing_nines == init_precision) {
1046 ++base_10_exp;
1047 trailing_zeroes = digits_checked;
1048 ++digits_checked;
1049 } else {
1050 // If there are trailing nines, they turn into trailing zeroes when
1051 // they're rounded up.
1052 if (trailing_nines > 0) {
1053 trailing_zeroes += trailing_nines;
1054 } else if (trailing_zeroes > 0) {
1055 // If there are trailing zeroes, then the last digit will be rounded up
1056 // to a 1 so they aren't trailing anymore.
1057 trailing_zeroes = 0;
1058 }
1059 }
1060 }
1061
1062 // if P > X >= -4, the conversion is with style f (or F) and precision equals
1063 // P - (X + 1).
1064 if (static_cast<int>(init_precision) > base_10_exp && base_10_exp >= -4) {
1065 FormatSection new_conv = to_conv;
1066 const int conv_precision = init_precision - (base_10_exp + 1);
1067
1068 if ((to_conv.flags & FormatFlags::ALTERNATE_FORM) != 0) {
1069 new_conv.precision = conv_precision;
1070 } else {
1071 // If alt form isn't set, then we need to determine the number of trailing
1072 // zeroes and set the precision such that they are removed.
1073
1074 /*
1075 Here's a diagram of an example:
1076
1077 printf("%.15g", 22.25);
1078
1079 +--- init_precision = 15
1080 |
1081 +-------------------+
1082 | |
1083 | ++--- trimmed_precision = 2
1084 | || |
1085 22.250000000000000000
1086 || | |
1087 ++ +--------------+
1088 | |
1089 base_10_exp + 1 = 2 --+ +--- trailing_zeroes = 11
1090 */
1091 int trimmed_precision = static_cast<int>(
1092 digits_checked - (base_10_exp + 1) - trailing_zeroes);
1093 if (trimmed_precision < 0) {
1094 trimmed_precision = 0;
1095 }
1096 new_conv.precision = (trimmed_precision > conv_precision)
1097 ? conv_precision
1098 : trimmed_precision;
1099 }
1100
1101 return convert_float_decimal_typed<T>(writer, new_conv, float_bits);
1102 } else {
1103 // otherwise, the conversion is with style e (or E) and precision equals
1104 // P - 1
1105 const int conv_precision = init_precision - 1;
1106 FormatSection new_conv = to_conv;
1107 if ((to_conv.flags & FormatFlags::ALTERNATE_FORM) != 0) {
1108 new_conv.precision = conv_precision;
1109 } else {
1110 // If alt form isn't set, then we need to determine the number of trailing
1111 // zeroes and set the precision such that they are removed.
1112 int trimmed_precision =
1113 static_cast<int>(digits_checked - 1 - trailing_zeroes);
1114 if (trimmed_precision < 0) {
1115 trimmed_precision = 0;
1116 }
1117 new_conv.precision = (trimmed_precision > conv_precision)
1118 ? conv_precision
1119 : trimmed_precision;
1120 }
1121 return convert_float_dec_exp_typed<T>(writer, new_conv, float_bits);
1122 }
1123}
1124
1125// TODO: unify the float converters to remove the duplicated checks for inf/nan.
1126
1127template <WriteMode write_mode>
1128LIBC_INLINE int convert_float_decimal(Writer<write_mode> *writer,
1129 const FormatSection &to_conv) {
1130 if (to_conv.length_modifier == LengthModifier::L) {
1131 fputil::FPBits<long double>::StorageType float_raw = to_conv.conv_val_raw;
1132 fputil::FPBits<long double> float_bits(float_raw);
1133 if (!float_bits.is_inf_or_nan()) {
1134 return convert_float_decimal_typed<long double>(writer, to_conv,
1135 float_bits);
1136 }
1137 } else {
1138 fputil::FPBits<double>::StorageType float_raw =
1139 static_cast<fputil::FPBits<double>::StorageType>(to_conv.conv_val_raw);
1140 fputil::FPBits<double> float_bits(float_raw);
1141 if (!float_bits.is_inf_or_nan()) {
1142 return convert_float_decimal_typed<double>(writer, to_conv, float_bits);
1143 }
1144 }
1145
1146 return convert_inf_nan(writer, to_conv);
1147}
1148
1149template <WriteMode write_mode>
1150LIBC_INLINE int convert_float_dec_exp(Writer<write_mode> *writer,
1151 const FormatSection &to_conv) {
1152 if (to_conv.length_modifier == LengthModifier::L) {
1153 fputil::FPBits<long double>::StorageType float_raw = to_conv.conv_val_raw;
1154 fputil::FPBits<long double> float_bits(float_raw);
1155 if (!float_bits.is_inf_or_nan()) {
1156 return convert_float_dec_exp_typed<long double>(writer, to_conv,
1157 float_bits);
1158 }
1159 } else {
1160 fputil::FPBits<double>::StorageType float_raw =
1161 static_cast<fputil::FPBits<double>::StorageType>(to_conv.conv_val_raw);
1162 fputil::FPBits<double> float_bits(float_raw);
1163 if (!float_bits.is_inf_or_nan()) {
1164 return convert_float_dec_exp_typed<double>(writer, to_conv, float_bits);
1165 }
1166 }
1167
1168 return convert_inf_nan(writer, to_conv);
1169}
1170
1171template <WriteMode write_mode>
1172LIBC_INLINE int convert_float_dec_auto(Writer<write_mode> *writer,
1173 const FormatSection &to_conv) {
1174 if (to_conv.length_modifier == LengthModifier::L) {
1175 fputil::FPBits<long double>::StorageType float_raw = to_conv.conv_val_raw;
1176 fputil::FPBits<long double> float_bits(float_raw);
1177 if (!float_bits.is_inf_or_nan()) {
1178 return convert_float_dec_auto_typed<long double>(writer, to_conv,
1179 float_bits);
1180 }
1181 } else {
1182 fputil::FPBits<double>::StorageType float_raw =
1183 static_cast<fputil::FPBits<double>::StorageType>(to_conv.conv_val_raw);
1184 fputil::FPBits<double> float_bits(float_raw);
1185 if (!float_bits.is_inf_or_nan()) {
1186 return convert_float_dec_auto_typed<double>(writer, to_conv, float_bits);
1187 }
1188 }
1189
1190 return convert_inf_nan(writer, to_conv);
1191}
1192
1193} // namespace printf_core
1194} // namespace LIBC_NAMESPACE_DECL
1195
1196#endif // LLVM_LIBC_SRC_STDIO_PRINTF_CORE_FLOAT_DEC_CONVERTER_H
1197

Warning: This file is not a C or C++ file. It does not have highlighting.

source code of libc/src/stdio/printf_core/float_dec_converter.h