mirror of
https://github.com/RGBCube/serenity
synced 2025-07-25 14:57:35 +00:00
LibC: Implement strtod()
This commit is contained in:
parent
b8ac14a873
commit
fe1df9e9fb
1 changed files with 68 additions and 4 deletions
|
@ -256,10 +256,74 @@ int putenv(char* new_var)
|
||||||
|
|
||||||
double strtod(const char* str, char** endptr)
|
double strtod(const char* str, char** endptr)
|
||||||
{
|
{
|
||||||
(void)str;
|
size_t len = strlen(str);
|
||||||
(void)endptr;
|
size_t weight = 1;
|
||||||
dbgprintf("LibC: strtod: '%s'\n", str);
|
int exp_val = 0;
|
||||||
ASSERT_NOT_REACHED();
|
double value = 0.0f;
|
||||||
|
double fraction = 0.0f;
|
||||||
|
bool has_sign = false;
|
||||||
|
bool is_negative = false;
|
||||||
|
bool is_fractional = false;
|
||||||
|
bool is_scientific = false;
|
||||||
|
|
||||||
|
if (str[0] == '-') {
|
||||||
|
is_negative = true;
|
||||||
|
has_sign = true;
|
||||||
|
}
|
||||||
|
if (str[0] == '+') {
|
||||||
|
has_sign = true;
|
||||||
|
}
|
||||||
|
size_t i;
|
||||||
|
for (i = has_sign; i < len; i++) {
|
||||||
|
|
||||||
|
// Looks like we're about to start working on the fractional part
|
||||||
|
if (str[i] == '.') {
|
||||||
|
is_fractional = true;
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (str[i] == 'e' || str[i] == 'E') {
|
||||||
|
if (str[i + 1] == '-' || str[i + 1] == '+')
|
||||||
|
exp_val = atoi(str + i + 2);
|
||||||
|
else
|
||||||
|
exp_val = atoi(str + i + 1);
|
||||||
|
|
||||||
|
is_scientific = true;
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (str[i] < '0' || str[i] > '9' || exp_val != 0)
|
||||||
|
continue;
|
||||||
|
|
||||||
|
if (is_fractional) {
|
||||||
|
fraction *= 10;
|
||||||
|
fraction += str[i] - '0';
|
||||||
|
weight *= 10;
|
||||||
|
} else {
|
||||||
|
value = value * 10;
|
||||||
|
value += str[i] - '0';
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fraction /= weight;
|
||||||
|
value += fraction;
|
||||||
|
|
||||||
|
if (is_scientific) {
|
||||||
|
bool divide = exp_val < 0;
|
||||||
|
if (divide)
|
||||||
|
exp_val *= -1;
|
||||||
|
|
||||||
|
for (int i = 0; i < exp_val; i++) {
|
||||||
|
if (divide)
|
||||||
|
value /= 10;
|
||||||
|
else
|
||||||
|
value *= 10;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
//FIXME: Not entirely sure if this is correct, but seems to work.
|
||||||
|
if (endptr)
|
||||||
|
*endptr = const_cast<char*>(str + i);
|
||||||
|
return is_negative ? -value : value;
|
||||||
}
|
}
|
||||||
|
|
||||||
long double strtold(const char* str, char** endptr)
|
long double strtold(const char* str, char** endptr)
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue