diff options
Diffstat (limited to 'strings')
-rw-r--r-- | strings/strtod.c | 17 |
1 files changed, 14 insertions, 3 deletions
diff --git a/strings/strtod.c b/strings/strtod.c index 4c3f31bc00c..92a4700cfc4 100644 --- a/strings/strtod.c +++ b/strings/strtod.c @@ -2,7 +2,7 @@ An alternative implementation of "strtod()" that is both simplier, and thread-safe. - From mit-threads as bundled with MySQL 3.22 + From mit-threads as bundled with MySQL 3.23 SQL:2003 specifies a number as @@ -46,6 +46,7 @@ double my_strtod(const char *str, char **end) double result= 0.0; int negative, ndigits; const char *old_str; + my_bool overflow=0; while (my_isspace(&my_charset_latin1, *str)) str++; @@ -90,12 +91,16 @@ double my_strtod(const char *str, char **end) double scaler= 1.0; while (my_isdigit (&my_charset_latin1, *str)) { - exp= exp*10 + *str - '0'; + if (exp < 9999) /* protection against exp overflow */ + exp= exp*10 + *str - '0'; str++; } if (exp >= 1000) { - result= neg ? 0.0 : HUGE_VAL; + if (neg) + result= 0.0; + else + overflow= 1; goto done; } while (exp >= 100) @@ -115,6 +120,12 @@ done: if (end) *end = (char *)str; + if (overflow || isinf(result)) + { + result= DBL_MAX; + errno= EOVERFLOW; + } + return negative ? -result : result; } |