1169695Skan/* Implementation of strtod for systems with atof. 2169695Skan Copyright (C) 1991, 1995, 2002 Free Software Foundation, Inc. 3169695Skan 4169695SkanThis file is part of the libiberty library. This library is free 5169695Skansoftware; you can redistribute it and/or modify it under the 6169695Skanterms of the GNU General Public License as published by the 7169695SkanFree Software Foundation; either version 2, or (at your option) 8169695Skanany later version. 9169695Skan 10169695SkanThis library is distributed in the hope that it will be useful, 11169695Skanbut WITHOUT ANY WARRANTY; without even the implied warranty of 12169695SkanMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13169695SkanGNU General Public License for more details. 14169695Skan 15169695SkanYou should have received a copy of the GNU General Public License 16169695Skanalong with GNU CC; see the file COPYING. If not, write to 17169695Skanthe Free Software Foundation, 51 Franklin Street - Fifth Floor, Boston, MA 02110-1301, USA. 18169695Skan 19169695SkanAs a special exception, if you link this library with files 20169695Skancompiled with a GNU compiler to produce an executable, this does not cause 21169695Skanthe resulting executable to be covered by the GNU General Public License. 22169695SkanThis exception does not however invalidate any other reasons why 23169695Skanthe executable file might be covered by the GNU General Public License. */ 24169695Skan 25169695Skan/* 26169695Skan 27169695Skan@deftypefn Supplemental double strtod (const char *@var{string}, char **@var{endptr}) 28169695Skan 29169695SkanThis ISO C function converts the initial portion of @var{string} to a 30169695Skan@code{double}. If @var{endptr} is not @code{NULL}, a pointer to the 31169695Skancharacter after the last character used in the conversion is stored in 32169695Skanthe location referenced by @var{endptr}. If no conversion is 33169695Skanperformed, zero is returned and the value of @var{string} is stored in 34169695Skanthe location referenced by @var{endptr}. 35169695Skan 36169695Skan@end deftypefn 37169695Skan 38169695Skan*/ 39169695Skan 40169695Skan#include "ansidecl.h" 41169695Skan#include "safe-ctype.h" 42169695Skan 43169695Skanextern double atof (const char *); 44169695Skan 45169695Skan/* Disclaimer: this is currently just used by CHILL in GDB and therefore 46169695Skan has not been tested well. It may have been tested for nothing except 47169695Skan that it compiles. */ 48169695Skan 49169695Skandouble 50169695Skanstrtod (char *str, char **ptr) 51169695Skan{ 52169695Skan char *p; 53169695Skan 54169695Skan if (ptr == (char **)0) 55169695Skan return atof (str); 56169695Skan 57169695Skan p = str; 58169695Skan 59169695Skan while (ISSPACE (*p)) 60169695Skan ++p; 61169695Skan 62169695Skan if (*p == '+' || *p == '-') 63169695Skan ++p; 64169695Skan 65169695Skan /* INF or INFINITY. */ 66169695Skan if ((p[0] == 'i' || p[0] == 'I') 67169695Skan && (p[1] == 'n' || p[1] == 'N') 68169695Skan && (p[2] == 'f' || p[2] == 'F')) 69169695Skan { 70169695Skan if ((p[3] == 'i' || p[3] == 'I') 71169695Skan && (p[4] == 'n' || p[4] == 'N') 72169695Skan && (p[5] == 'i' || p[5] == 'I') 73169695Skan && (p[6] == 't' || p[6] == 'T') 74169695Skan && (p[7] == 'y' || p[7] == 'Y')) 75169695Skan { 76169695Skan *ptr = p + 8; 77169695Skan return atof (str); 78169695Skan } 79169695Skan else 80169695Skan { 81169695Skan *ptr = p + 3; 82169695Skan return atof (str); 83169695Skan } 84169695Skan } 85169695Skan 86169695Skan /* NAN or NAN(foo). */ 87169695Skan if ((p[0] == 'n' || p[0] == 'N') 88169695Skan && (p[1] == 'a' || p[1] == 'A') 89169695Skan && (p[2] == 'n' || p[2] == 'N')) 90169695Skan { 91169695Skan p += 3; 92169695Skan if (*p == '(') 93169695Skan { 94169695Skan ++p; 95169695Skan while (*p != '\0' && *p != ')') 96169695Skan ++p; 97169695Skan if (*p == ')') 98169695Skan ++p; 99169695Skan } 100169695Skan *ptr = p; 101169695Skan return atof (str); 102169695Skan } 103169695Skan 104169695Skan /* digits, with 0 or 1 periods in it. */ 105169695Skan if (ISDIGIT (*p) || *p == '.') 106169695Skan { 107169695Skan int got_dot = 0; 108169695Skan while (ISDIGIT (*p) || (!got_dot && *p == '.')) 109169695Skan { 110169695Skan if (*p == '.') 111169695Skan got_dot = 1; 112169695Skan ++p; 113169695Skan } 114169695Skan 115169695Skan /* Exponent. */ 116169695Skan if (*p == 'e' || *p == 'E') 117169695Skan { 118169695Skan int i; 119169695Skan i = 1; 120169695Skan if (p[i] == '+' || p[i] == '-') 121169695Skan ++i; 122169695Skan if (ISDIGIT (p[i])) 123169695Skan { 124169695Skan while (ISDIGIT (p[i])) 125169695Skan ++i; 126169695Skan *ptr = p + i; 127169695Skan return atof (str); 128169695Skan } 129169695Skan } 130169695Skan *ptr = p; 131169695Skan return atof (str); 132169695Skan } 133169695Skan /* Didn't find any digits. Doesn't look like a number. */ 134169695Skan *ptr = str; 135169695Skan return 0.0; 136169695Skan} 137