1 # Libchrome does not support/require dmg_fp library. Instead, use standard 2 # library. 3 4 --- a/base/strings/string_number_conversions.cc 5 +++ b/base/strings/string_number_conversions.cc 6 @@ -16,7 +16,6 @@ 7 #include "base/numerics/safe_math.h" 8 #include "base/scoped_clear_errno.h" 9 #include "base/strings/utf_string_conversions.h" 10 -#include "base/third_party/dmg_fp/dmg_fp.h" 11 12 namespace base { 13 14 @@ -361,20 +360,35 @@ string16 NumberToString16(unsigned long long value) { 15 } 16 17 std::string NumberToString(double value) { 18 - // According to g_fmt.cc, it is sufficient to declare a buffer of size 32. 19 - char buffer[32]; 20 - dmg_fp::g_fmt(buffer, value); 21 - return std::string(buffer); 22 + auto ret = std::to_string(value); 23 + // If this returned an integer, don't do anything. 24 + if (ret.find('.') == std::string::npos) { 25 + return ret; 26 + } 27 + // Otherwise, it has an annoying tendency to leave trailing zeros. 28 + size_t len = ret.size(); 29 + while (len >= 2 && ret[len - 1] == '0' && ret[len - 2] != '.') { 30 + --len; 31 + } 32 + ret.erase(len); 33 + return ret; 34 } 35 36 base::string16 NumberToString16(double value) { 37 - // According to g_fmt.cc, it is sufficient to declare a buffer of size 32. 38 - char buffer[32]; 39 - dmg_fp::g_fmt(buffer, value); 40 + auto tmp = std::to_string(value); 41 + base::string16 ret(tmp.c_str(), tmp.c_str() + tmp.length()); 42 43 - // The number will be ASCII. This creates the string using the "input 44 - // iterator" variant which promotes from 8-bit to 16-bit via "=". 45 - return base::string16(&buffer[0], &buffer[strlen(buffer)]); 46 + // If this returned an integer, don't do anything. 47 + if (ret.find('.') == std::string::npos) { 48 + return ret; 49 + } 50 + // Otherwise, it has an annoying tendency to leave trailing zeros. 51 + size_t len = ret.size(); 52 + while (len >= 2 && ret[len - 1] == '0' && ret[len - 2] != '.') { 53 + --len; 54 + } 55 + ret.erase(len); 56 + return ret; 57 } 58 59 bool StringToInt(StringPiece input, int* output) { 60 @@ -418,14 +432,10 @@ bool StringToSizeT(StringPiece16 input, size_t* output) { 61 } 62 63 bool StringToDouble(const std::string& input, double* output) { 64 - // Thread-safe? It is on at least Mac, Linux, and Windows. 65 - ScopedClearErrno clear_errno; 66 - 67 char* endptr = nullptr; 68 - *output = dmg_fp::strtod(input.c_str(), &endptr); 69 + *output = strtod(input.c_str(), &endptr); 70 71 // Cases to return false: 72 - // - If errno is ERANGE, there was an overflow or underflow. 73 // - If the input string is empty, there was nothing to parse. 74 // - If endptr does not point to the end of the string, there are either 75 // characters remaining in the string after a parsed number, or the string 76 @@ -433,10 +443,11 @@ bool StringToDouble(const std::string& input, double* output) { 77 // expected end given the string's stated length to correctly catch cases 78 // where the string contains embedded NUL characters. 79 // - If the first character is a space, there was leading whitespace 80 - return errno == 0 && 81 - !input.empty() && 82 + return !input.empty() && 83 input.c_str() + input.length() == endptr && 84 - !isspace(input[0]); 85 + !isspace(input[0]) && 86 + *output != std::numeric_limits<double>::infinity() && 87 + *output != -std::numeric_limits<double>::infinity(); 88 } 89 90 // Note: if you need to add String16ToDouble, first ask yourself if it's 91 --- a/base/strings/string_number_conversions_unittest.cc 92 +++ b/base/strings/string_number_conversions_unittest.cc 93 @@ -754,20 +754,8 @@ TEST(StringNumberConversionsTest, StringToDouble) { 94 {"9e999", HUGE_VAL, false}, 95 {"9e1999", HUGE_VAL, false}, 96 {"9e19999", HUGE_VAL, false}, 97 - {"9e99999999999999999999", HUGE_VAL, false}, 98 - {"-9e307", -9e307, true}, 99 - {"-1.7976e308", -1.7976e308, true}, 100 - {"-1.7977e308", -HUGE_VAL, false}, 101 - {"-1.797693134862315807e+308", -HUGE_VAL, true}, 102 - {"-1.797693134862315808e+308", -HUGE_VAL, false}, 103 - {"-9e308", -HUGE_VAL, false}, 104 - {"-9e309", -HUGE_VAL, false}, 105 - {"-9e999", -HUGE_VAL, false}, 106 - {"-9e1999", -HUGE_VAL, false}, 107 - {"-9e19999", -HUGE_VAL, false}, 108 - {"-9e99999999999999999999", -HUGE_VAL, false}, 109 - 110 - // Test more exponents. 111 + {"9e99999999999999999999", std::numeric_limits<double>::infinity(), false}, 112 + {"-9e99999999999999999999", -std::numeric_limits<double>::infinity(), false}, 113 {"1e-2", 0.01, true}, 114 {"42 ", 42.0, false}, 115 {" 1e-2", 0.01, false}, 116 @@ -797,7 +785,8 @@ TEST(StringNumberConversionsTest, StringToDouble) { 117 for (size_t i = 0; i < arraysize(cases); ++i) { 118 double output; 119 errno = 1; 120 - EXPECT_EQ(cases[i].success, StringToDouble(cases[i].input, &output)); 121 + EXPECT_EQ(cases[i].success, StringToDouble(cases[i].input, &output)) 122 + << "for input=" << cases[i].input << "got output=" << output; 123 if (cases[i].success) 124 EXPECT_EQ(1, errno) << i; // confirm that errno is unchanged. 125 EXPECT_DOUBLE_EQ(cases[i].output, output); 126 @@ -818,13 +807,13 @@ TEST(StringNumberConversionsTest, DoubleToString) { 127 double input; 128 const char* expected; 129 } cases[] = { 130 - {0.0, "0"}, 131 + {0.0, "0.0"}, 132 {1.25, "1.25"}, 133 - {1.33518e+012, "1.33518e+12"}, 134 - {1.33489e+012, "1.33489e+12"}, 135 - {1.33505e+012, "1.33505e+12"}, 136 - {1.33545e+009, "1335450000"}, 137 - {1.33503e+009, "1335030000"}, 138 + {1.33518e+012, "1335180000000.0"}, 139 + {1.33489e+012, "1334890000000.0"}, 140 + {1.33505e+012, "1335050000000.0"}, 141 + {1.33545e+009, "1335450000.0"}, 142 + {1.33503e+009, "1335030000.0"}, 143 }; 144 145 for (size_t i = 0; i < arraysize(cases); ++i) { 146 @@ -836,12 +825,12 @@ TEST(StringNumberConversionsTest, DoubleToString) { 147 const char input_bytes[8] = {0, 0, 0, 0, '\xee', '\x6d', '\x73', '\x42'}; 148 double input = 0; 149 memcpy(&input, input_bytes, arraysize(input_bytes)); 150 - EXPECT_EQ("1335179083776", NumberToString(input)); 151 + EXPECT_EQ("1335179083776.0", NumberToString(input)); 152 const char input_bytes2[8] = 153 {0, 0, 0, '\xa0', '\xda', '\x6c', '\x73', '\x42'}; 154 input = 0; 155 memcpy(&input, input_bytes2, arraysize(input_bytes2)); 156 - EXPECT_EQ("1334890332160", NumberToString(input)); 157 + EXPECT_EQ("1334890332160.0", NumberToString(input)); 158 } 159 160 TEST(StringNumberConversionsTest, HexEncode) { 161