Skip to content

Commit 513e4dc

Browse files
authored
[reland][libc][NFC] Use user defined literals to build 128 and 256 bit constants (#81835)
This is a reland of #81746
1 parent 95e8a7c commit 513e4dc

File tree

16 files changed

+2544
-2510
lines changed

16 files changed

+2544
-2510
lines changed

libc/src/__support/integer_literals.h

Lines changed: 11 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -22,19 +22,19 @@
2222
namespace LIBC_NAMESPACE {
2323

2424
LIBC_INLINE constexpr uint8_t operator""_u8(unsigned long long value) {
25-
return value;
25+
return static_cast<uint8_t>(value);
2626
}
2727

2828
LIBC_INLINE constexpr uint16_t operator""_u16(unsigned long long value) {
29-
return value;
29+
return static_cast<uint16_t>(value);
3030
}
3131

3232
LIBC_INLINE constexpr uint32_t operator""_u32(unsigned long long value) {
33-
return value;
33+
return static_cast<uint32_t>(value);
3434
}
3535

3636
LIBC_INLINE constexpr uint64_t operator""_u64(unsigned long long value) {
37-
return value;
37+
return static_cast<uint64_t>(value);
3838
}
3939

4040
namespace internal {
@@ -64,6 +64,7 @@ template <typename T, int base> struct DigitBuffer {
6464
: 0;
6565
LIBC_INLINE_VAR static constexpr size_t MAX_DIGITS =
6666
sizeof(T) * CHAR_BIT / BITS_PER_DIGIT;
67+
LIBC_INLINE_VAR static constexpr uint8_t INVALID_DIGIT = 255;
6768

6869
uint8_t digits[MAX_DIGITS] = {};
6970
size_t size = 0;
@@ -74,26 +75,26 @@ template <typename T, int base> struct DigitBuffer {
7475
}
7576

7677
// Returns the digit for a particular character.
77-
// Returns 255 if the character is invalid.
78+
// Returns INVALID_DIGIT if the character is invalid.
7879
LIBC_INLINE static constexpr uint8_t get_digit_value(const char c) {
7980
const auto to_lower = [](char c) { return c | 32; };
8081
const auto is_digit = [](char c) { return c >= '0' && c <= '9'; };
8182
const auto is_alpha = [](char c) {
8283
return ('a' <= c && c <= 'z') || ('A' <= c && c <= 'Z');
8384
};
8485
if (is_digit(c))
85-
return c - '0';
86+
return static_cast<uint8_t>(c - '0');
8687
if (base > 10 && is_alpha(c))
87-
return to_lower(c) - 'a' + 10;
88-
return 255;
88+
return static_cast<uint8_t>(to_lower(c) - 'a' + 10);
89+
return INVALID_DIGIT;
8990
}
9091

9192
// Adds a single character to this buffer.
9293
LIBC_INLINE constexpr void push(char c) {
9394
if (c == '\'')
9495
return; // ' is valid but not taken into account.
9596
const uint8_t value = get_digit_value(c);
96-
if (value == 255 || size >= MAX_DIGITS) {
97+
if (value == INVALID_DIGIT || size >= MAX_DIGITS) {
9798
// During constant evaluation `__builtin_unreachable` will halt the
9899
// compiler as it is not executable. This is preferable over `assert` that
99100
// will only trigger in debug mode. Also we can't use `static_assert`
@@ -131,7 +132,7 @@ struct Parser<LIBC_NAMESPACE::cpp::BigInt<N, false, uint64_t>> {
131132
// Fast path, we consume blocks of uint64_t and creates the BigInt's
132133
// internal representation directly.
133134
using U64ArrayT = cpp::array<uint64_t, UIntT::WORD_COUNT>;
134-
U64ArrayT array;
135+
U64ArrayT array = {};
135136
size_t size = buffer.size;
136137
const uint8_t *digit_ptr = buffer.digits + size;
137138
for (size_t i = 0; i < array.size(); ++i) {

libc/src/math/generic/CMakeLists.txt

Lines changed: 24 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -622,6 +622,8 @@ add_entrypoint_object(
622622
DEPENDS
623623
.common_constants
624624
.explogxf
625+
libc.include.errno
626+
libc.include.math
625627
libc.src.__support.CPP.bit
626628
libc.src.__support.CPP.optional
627629
libc.src.__support.FPUtil.dyadic_float
@@ -632,10 +634,9 @@ add_entrypoint_object(
632634
libc.src.__support.FPUtil.polyeval
633635
libc.src.__support.FPUtil.rounding_mode
634636
libc.src.__support.FPUtil.triple_double
637+
libc.src.__support.integer_literals
635638
libc.src.__support.macros.optimization
636-
libc.include.errno
637639
libc.src.errno.errno
638-
libc.include.math
639640
COMPILE_OPTIONS
640641
-O3
641642
)
@@ -672,6 +673,8 @@ add_entrypoint_object(
672673
DEPENDS
673674
.common_constants
674675
.explogxf
676+
libc.include.errno
677+
libc.include.math
675678
libc.src.__support.CPP.bit
676679
libc.src.__support.CPP.optional
677680
libc.src.__support.FPUtil.dyadic_float
@@ -682,10 +685,9 @@ add_entrypoint_object(
682685
libc.src.__support.FPUtil.polyeval
683686
libc.src.__support.FPUtil.rounding_mode
684687
libc.src.__support.FPUtil.triple_double
688+
libc.src.__support.integer_literals
685689
libc.src.__support.macros.optimization
686-
libc.include.errno
687690
libc.src.errno.errno
688-
libc.include.math
689691
COMPILE_OPTIONS
690692
-O3
691693
)
@@ -731,6 +733,8 @@ add_entrypoint_object(
731733
DEPENDS
732734
.common_constants
733735
.explogxf
736+
libc.include.errno
737+
libc.include.math
734738
libc.src.__support.CPP.bit
735739
libc.src.__support.CPP.optional
736740
libc.src.__support.FPUtil.dyadic_float
@@ -741,10 +745,9 @@ add_entrypoint_object(
741745
libc.src.__support.FPUtil.polyeval
742746
libc.src.__support.FPUtil.rounding_mode
743747
libc.src.__support.FPUtil.triple_double
748+
libc.src.__support.integer_literals
744749
libc.src.__support.macros.optimization
745-
libc.include.errno
746750
libc.src.errno.errno
747-
libc.include.math
748751
COMPILE_OPTIONS
749752
-O3
750753
)
@@ -791,6 +794,8 @@ add_entrypoint_object(
791794
DEPENDS
792795
.common_constants
793796
.explogxf
797+
libc.include.errno
798+
libc.include.math
794799
libc.src.__support.CPP.bit
795800
libc.src.__support.CPP.optional
796801
libc.src.__support.FPUtil.dyadic_float
@@ -801,10 +806,9 @@ add_entrypoint_object(
801806
libc.src.__support.FPUtil.polyeval
802807
libc.src.__support.FPUtil.rounding_mode
803808
libc.src.__support.FPUtil.triple_double
809+
libc.src.__support.integer_literals
804810
libc.src.__support.macros.optimization
805-
libc.include.errno
806811
libc.src.errno.errno
807-
libc.include.math
808812
COMPILE_OPTIONS
809813
-O3
810814
)
@@ -1074,12 +1078,13 @@ add_entrypoint_object(
10741078
DEPENDS
10751079
.common_constants
10761080
.log_range_reduction
1081+
libc.src.__support.FPUtil.double_double
1082+
libc.src.__support.FPUtil.dyadic_float
10771083
libc.src.__support.FPUtil.fenv_impl
10781084
libc.src.__support.FPUtil.fp_bits
10791085
libc.src.__support.FPUtil.multiply_add
10801086
libc.src.__support.FPUtil.polyeval
1081-
libc.src.__support.FPUtil.double_double
1082-
libc.src.__support.FPUtil.dyadic_float
1087+
libc.src.__support.integer_literals
10831088
libc.src.__support.macros.optimization
10841089
COMPILE_OPTIONS
10851090
-O3
@@ -1110,12 +1115,13 @@ add_entrypoint_object(
11101115
../log1p.h
11111116
DEPENDS
11121117
.common_constants
1118+
libc.src.__support.FPUtil.double_double
1119+
libc.src.__support.FPUtil.dyadic_float
11131120
libc.src.__support.FPUtil.fenv_impl
11141121
libc.src.__support.FPUtil.fp_bits
11151122
libc.src.__support.FPUtil.multiply_add
11161123
libc.src.__support.FPUtil.polyeval
1117-
libc.src.__support.FPUtil.double_double
1118-
libc.src.__support.FPUtil.dyadic_float
1124+
libc.src.__support.integer_literals
11191125
libc.src.__support.macros.optimization
11201126
COMPILE_OPTIONS
11211127
-O3
@@ -1148,12 +1154,13 @@ add_entrypoint_object(
11481154
DEPENDS
11491155
.common_constants
11501156
.log_range_reduction
1157+
libc.src.__support.FPUtil.double_double
1158+
libc.src.__support.FPUtil.dyadic_float
11511159
libc.src.__support.FPUtil.fenv_impl
11521160
libc.src.__support.FPUtil.fp_bits
11531161
libc.src.__support.FPUtil.multiply_add
11541162
libc.src.__support.FPUtil.polyeval
1155-
libc.src.__support.FPUtil.double_double
1156-
libc.src.__support.FPUtil.dyadic_float
1163+
libc.src.__support.integer_literals
11571164
libc.src.__support.macros.optimization
11581165
COMPILE_OPTIONS
11591166
-O3
@@ -1186,12 +1193,13 @@ add_entrypoint_object(
11861193
DEPENDS
11871194
.common_constants
11881195
.log_range_reduction
1196+
libc.src.__support.FPUtil.double_double
1197+
libc.src.__support.FPUtil.dyadic_float
11891198
libc.src.__support.FPUtil.fenv_impl
11901199
libc.src.__support.FPUtil.fp_bits
11911200
libc.src.__support.FPUtil.multiply_add
11921201
libc.src.__support.FPUtil.polyeval
1193-
libc.src.__support.FPUtil.double_double
1194-
libc.src.__support.FPUtil.dyadic_float
1202+
libc.src.__support.integer_literals
11951203
libc.src.__support.macros.optimization
11961204
COMPILE_OPTIONS
11971205
-O3

libc/src/math/generic/exp.cpp

Lines changed: 10 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@
2121
#include "src/__support/FPUtil/rounding_mode.h"
2222
#include "src/__support/FPUtil/triple_double.h"
2323
#include "src/__support/common.h"
24+
#include "src/__support/integer_literals.h"
2425
#include "src/__support/macros/optimization.h" // LIBC_UNLIKELY
2526

2627
#include <errno.h>
@@ -31,6 +32,7 @@ using fputil::DoubleDouble;
3132
using fputil::TripleDouble;
3233
using Float128 = typename fputil::DyadicFloat<128>;
3334
using Sign = fputil::Sign;
35+
using LIBC_NAMESPACE::operator""_u128;
3436

3537
// log2(e)
3638
constexpr double LOG2_E = 0x1.71547652b82fep+0;
@@ -97,21 +99,15 @@ DoubleDouble poly_approx_dd(const DoubleDouble &dx) {
9799
// For |dx| < 2^-13 + 2^-30:
98100
// | output - exp(dx) | < 2^-126.
99101
Float128 poly_approx_f128(const Float128 &dx) {
100-
using MType = typename Float128::MantissaType;
101-
102102
constexpr Float128 COEFFS_128[]{
103-
{Sign::POS, -127, MType({0, 0x8000000000000000})}, // 1.0
104-
{Sign::POS, -127, MType({0, 0x8000000000000000})}, // 1.0
105-
{Sign::POS, -128, MType({0, 0x8000000000000000})}, // 0.5
106-
{Sign::POS, -130, MType({0xaaaaaaaaaaaaaaab, 0xaaaaaaaaaaaaaaaa})}, // 1/6
107-
{Sign::POS, -132,
108-
MType({0xaaaaaaaaaaaaaaab, 0xaaaaaaaaaaaaaaaa})}, // 1/24
109-
{Sign::POS, -134,
110-
MType({0x8888888888888889, 0x8888888888888888})}, // 1/120
111-
{Sign::POS, -137,
112-
MType({0x60b60b60b60b60b6, 0xb60b60b60b60b60b})}, // 1/720
113-
{Sign::POS, -140,
114-
MType({0x00d00d00d00d00d0, 0xd00d00d00d00d00d})}, // 1/5040
103+
{Sign::POS, -127, 0x80000000'00000000'00000000'00000000_u128}, // 1.0
104+
{Sign::POS, -127, 0x80000000'00000000'00000000'00000000_u128}, // 1.0
105+
{Sign::POS, -128, 0x80000000'00000000'00000000'00000000_u128}, // 0.5
106+
{Sign::POS, -130, 0xaaaaaaaa'aaaaaaaa'aaaaaaaa'aaaaaaab_u128}, // 1/6
107+
{Sign::POS, -132, 0xaaaaaaaa'aaaaaaaa'aaaaaaaa'aaaaaaab_u128}, // 1/24
108+
{Sign::POS, -134, 0x88888888'88888888'88888888'88888889_u128}, // 1/120
109+
{Sign::POS, -137, 0xb60b60b6'0b60b60b'60b60b60'b60b60b6_u128}, // 1/720
110+
{Sign::POS, -140, 0xd00d00d0'0d00d00d'00d00d00'd00d00d0_u128}, // 1/5040
115111
};
116112

117113
Float128 p = fputil::polyeval(dx, COEFFS_128[0], COEFFS_128[1], COEFFS_128[2],

libc/src/math/generic/exp10.cpp

Lines changed: 10 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@
2121
#include "src/__support/FPUtil/rounding_mode.h"
2222
#include "src/__support/FPUtil/triple_double.h"
2323
#include "src/__support/common.h"
24+
#include "src/__support/integer_literals.h"
2425
#include "src/__support/macros/optimization.h" // LIBC_UNLIKELY
2526

2627
#include <errno.h>
@@ -31,6 +32,7 @@ using fputil::DoubleDouble;
3132
using fputil::TripleDouble;
3233
using Float128 = typename fputil::DyadicFloat<128>;
3334
using Sign = fputil::Sign;
35+
using LIBC_NAMESPACE::operator""_u128;
3436

3537
// log2(10)
3638
constexpr double LOG2_10 = 0x1.a934f0979a371p+1;
@@ -99,17 +101,15 @@ DoubleDouble poly_approx_dd(const DoubleDouble &dx) {
99101
// For |dx| < 2^-14:
100102
// | output - 10^dx | < 1.5 * 2^-124.
101103
Float128 poly_approx_f128(const Float128 &dx) {
102-
using MType = typename Float128::MantissaType;
103-
104104
constexpr Float128 COEFFS_128[]{
105-
{Sign::POS, -127, MType({0, 0x8000000000000000})}, // 1.0
106-
{Sign::POS, -126, MType({0xea56d62b82d30a2d, 0x935d8dddaaa8ac16})},
107-
{Sign::POS, -126, MType({0x80a99ce75f4d5bdb, 0xa9a92639e753443a})},
108-
{Sign::POS, -126, MType({0x6a4f9d7dbf6c9635, 0x82382c8ef1652304})},
109-
{Sign::POS, -124, MType({0x345787019216c7af, 0x12bd7609fd98c44c})},
110-
{Sign::POS, -127, MType({0xcc41ed7e0d27aee5, 0x450a7ff47535d889})},
111-
{Sign::POS, -130, MType({0x8326bb91a6e7601d, 0xd3f6b844702d636b})},
112-
{Sign::POS, -130, MType({0xfa7b46df314112a9, 0x45b937f0d05bb1cd})},
105+
{Sign::POS, -127, 0x80000000'00000000'00000000'00000000_u128}, // 1.0
106+
{Sign::POS, -126, 0x935d8ddd'aaa8ac16'ea56d62b'82d30a2d_u128},
107+
{Sign::POS, -126, 0xa9a92639'e753443a'80a99ce7'5f4d5bdb_u128},
108+
{Sign::POS, -126, 0x82382c8e'f1652304'6a4f9d7d'bf6c9635_u128},
109+
{Sign::POS, -124, 0x12bd7609'fd98c44c'34578701'9216c7af_u128},
110+
{Sign::POS, -127, 0x450a7ff4'7535d889'cc41ed7e'0d27aee5_u128},
111+
{Sign::POS, -130, 0xd3f6b844'702d636b'8326bb91'a6e7601d_u128},
112+
{Sign::POS, -130, 0x45b937f0'd05bb1cd'fa7b46df'314112a9_u128},
113113
};
114114

115115
Float128 p = fputil::polyeval(dx, COEFFS_128[0], COEFFS_128[1], COEFFS_128[2],

libc/src/math/generic/exp2.cpp

Lines changed: 10 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@
2121
#include "src/__support/FPUtil/rounding_mode.h"
2222
#include "src/__support/FPUtil/triple_double.h"
2323
#include "src/__support/common.h"
24+
#include "src/__support/integer_literals.h"
2425
#include "src/__support/macros/optimization.h" // LIBC_UNLIKELY
2526

2627
#include <errno.h>
@@ -31,6 +32,7 @@ using fputil::DoubleDouble;
3132
using fputil::TripleDouble;
3233
using Float128 = typename fputil::DyadicFloat<128>;
3334
using Sign = fputil::Sign;
35+
using LIBC_NAMESPACE::operator""_u128;
3436

3537
// Error bounds:
3638
// Errors when using double precision.
@@ -88,17 +90,15 @@ DoubleDouble poly_approx_dd(const DoubleDouble &dx) {
8890
// For |dx| < 2^-13 + 2^-30:
8991
// | output - exp(dx) | < 2^-126.
9092
Float128 poly_approx_f128(const Float128 &dx) {
91-
using MType = typename Float128::MantissaType;
92-
9393
constexpr Float128 COEFFS_128[]{
94-
{Sign::POS, -127, MType({0, 0x8000000000000000})}, // 1.0
95-
{Sign::POS, -128, MType({0xc9e3b39803f2f6af, 0xb17217f7d1cf79ab})},
96-
{Sign::POS, -128, MType({0xde2d60dd9c9a1d9f, 0x3d7f7bff058b1d50})},
97-
{Sign::POS, -132, MType({0x9d3b15d9e7fb6897, 0xe35846b82505fc59})},
98-
{Sign::POS, -134, MType({0x184462f6bcd2b9e7, 0x9d955b7dd273b94e})},
99-
{Sign::POS, -137, MType({0x39ea1bb964c51a89, 0xaec3ff3c53398883})},
100-
{Sign::POS, -138, MType({0x842c53418fa8ae61, 0x2861225f345c396a})},
101-
{Sign::POS, -144, MType({0x7abeb5abd5ad2079, 0xffe5fe2d109a319d})},
94+
{Sign::POS, -127, 0x80000000'00000000'00000000'00000000_u128}, // 1.0
95+
{Sign::POS, -128, 0xb17217f7'd1cf79ab'c9e3b398'03f2f6af_u128},
96+
{Sign::POS, -128, 0x3d7f7bff'058b1d50'de2d60dd'9c9a1d9f_u128},
97+
{Sign::POS, -132, 0xe35846b8'2505fc59'9d3b15d9'e7fb6897_u128},
98+
{Sign::POS, -134, 0x9d955b7d'd273b94e'184462f6'bcd2b9e7_u128},
99+
{Sign::POS, -137, 0xaec3ff3c'53398883'39ea1bb9'64c51a89_u128},
100+
{Sign::POS, -138, 0x2861225f'345c396a'842c5341'8fa8ae61_u128},
101+
{Sign::POS, -144, 0xffe5fe2d'109a319d'7abeb5ab'd5ad2079_u128},
102102
};
103103

104104
Float128 p = fputil::polyeval(dx, COEFFS_128[0], COEFFS_128[1], COEFFS_128[2],

0 commit comments

Comments
 (0)