File Coverage

ryu_headers/common.h
Criterion Covered Total %
statement 19 19 100.0
branch 12 22 54.5
condition n/a
subroutine n/a
pod n/a
total 31 41 75.6


line stmt bran cond sub pod time code
1             // Copyright 2018 Ulf Adams
2             //
3             // The contents of this file may be used under the terms of the Apache License,
4             // Version 2.0.
5             //
6             // (See accompanying file LICENSE-Apache or copy at
7             // http://www.apache.org/licenses/LICENSE-2.0)
8             //
9             // Alternatively, the contents of this file may be used under the terms of
10             // the Boost Software License, Version 1.0.
11             // (See accompanying file LICENSE-Boost or copy at
12             // https://www.boost.org/LICENSE_1_0.txt)
13             //
14             // Unless required by applicable law or agreed to in writing, this software
15             // is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16             // KIND, either express or implied.
17             #ifndef RYU_COMMON_H
18             #define RYU_COMMON_H
19              
20             #include
21             #include
22             #include
23              
24             #if defined(_M_IX86) || defined(_M_ARM)
25             #define RYU_32_BIT_PLATFORM
26             #endif
27              
28             // Returns the number of decimal digits in v, which must not contain more than 9 digits.
29 45           static inline uint32_t decimalLength9(const uint32_t v) {
30             // Function precondition: v is not a 10-digit number.
31             // (f2s: 9 digits are sufficient for round-tripping.)
32             // (d2fixed: We print 9-digit blocks.)
33 45 50         assert(v < 1000000000);
34 45 100         if (v >= 100000000) { return 9; }
35 30 50         if (v >= 10000000) { return 8; }
36 30 50         if (v >= 1000000) { return 7; }
37 30 50         if (v >= 100000) { return 6; }
38 30 50         if (v >= 10000) { return 5; }
39 30 50         if (v >= 1000) { return 4; }
40 30 50         if (v >= 100) { return 3; }
41 30 50         if (v >= 10) { return 2; }
42 30           return 1;
43             }
44              
45             // Returns e == 0 ? 1 : [log_2(5^e)]; requires 0 <= e <= 3528.
46             static inline int32_t log2pow5(const int32_t e) {
47             // This approximation works up to the point that the multiplication overflows at e = 3529.
48             // If the multiplication were done in 64 bits, it would fail at 5^4004 which is just greater
49             // than 2^9297.
50             assert(e >= 0);
51             assert(e <= 3528);
52             return (int32_t) ((((uint32_t) e) * 1217359) >> 19);
53             }
54              
55             // Returns e == 0 ? 1 : ceil(log_2(5^e)); requires 0 <= e <= 3528.
56             static inline int32_t pow5bits(const int32_t e) {
57             // This approximation works up to the point that the multiplication overflows at e = 3529.
58             // If the multiplication were done in 64 bits, it would fail at 5^4004 which is just greater
59             // than 2^9297.
60             assert(e >= 0);
61             assert(e <= 3528);
62             return (int32_t) (((((uint32_t) e) * 1217359) >> 19) + 1);
63             }
64              
65             // Returns e == 0 ? 1 : ceil(log_2(5^e)); requires 0 <= e <= 3528.
66             static inline int32_t ceil_log2pow5(const int32_t e) {
67             return log2pow5(e) + 1;
68             }
69              
70             // Returns floor(log_10(2^e)); requires 0 <= e <= 1650.
71 20           static inline uint32_t log10Pow2(const int32_t e) {
72             // The first value this approximation fails for is 2^1651 which is just greater than 10^297.
73 20 50         assert(e >= 0);
74 20 50         assert(e <= 1650);
75 20           return (((uint32_t) e) * 78913) >> 18;
76             }
77              
78             // Returns floor(log_10(5^e)); requires 0 <= e <= 2620.
79             static inline uint32_t log10Pow5(const int32_t e) {
80             // The first value this approximation fails for is 5^2621 which is just greater than 10^1832.
81             assert(e >= 0);
82             assert(e <= 2620);
83             return (((uint32_t) e) * 732923) >> 20;
84             }
85              
86             static inline int copy_special_str(char * const result, const bool sign, const bool exponent, const bool mantissa) {
87             if (mantissa) {
88             memcpy(result, "NaN", 3);
89             return 3;
90             }
91             if (sign) {
92             result[0] = '-';
93             }
94             if (exponent) {
95             memcpy(result + sign, "Infinity", 8);
96             return sign + 8;
97             }
98             memcpy(result + sign, "0E0", 3);
99             return sign + 3;
100             }
101              
102             static inline uint32_t float_to_bits(const float f) {
103             uint32_t bits = 0;
104             memcpy(&bits, &f, sizeof(float));
105             return bits;
106             }
107              
108 70           static inline uint64_t double_to_bits(const double d) {
109 70           uint64_t bits = 0;
110 70           memcpy(&bits, &d, sizeof(double));
111 70           return bits;
112             }
113              
114             #endif // RYU_COMMON_H