diff --git a/gcc/cp/ChangeLog b/gcc/cp/ChangeLog index 44fbf964dfb..3bf63ffeb36 100644 --- a/gcc/cp/ChangeLog +++ b/gcc/cp/ChangeLog @@ -1,3 +1,10 @@ +Mon Mar 15 21:57:16 1999 Kaveh R. Ghazi + + * lex.c: Don't include setjmp.h. + (parse_float): New static function. + (pf_args): New struct. + (real_yylex): Use them in call to `do_float_handler'. + 1999-03-15 Mark Mitchell * decl.c (xref_basetypes): Set CLASSTYPE_VBASECLASSES here. diff --git a/gcc/cp/lex.c b/gcc/cp/lex.c index 700597ab547..1ed8f0afa76 100644 --- a/gcc/cp/lex.c +++ b/gcc/cp/lex.c @@ -27,7 +27,6 @@ Boston, MA 02111-1307, USA. */ #include "config.h" #include "system.h" -#include #include "input.h" #include "tree.h" #include "lex.h" @@ -85,6 +84,7 @@ static int token_cmp PROTO((int *, int *)); #endif #endif static void begin_definition_of_inclass_inline PROTO((struct pending_inline*)); +static void parse_float PROTO((PTR)); /* Given a file name X, return the nondirectory portion. Keep in mind that X can be computed more than once. */ @@ -3181,6 +3181,103 @@ identifier_typedecl_value (node) return NULL_TREE; } +struct pf_args +{ + /* Input */ + /* I/O */ + char *p; + int c; + int imag; + tree type; + /* Output */ + REAL_VALUE_TYPE value; +}; + +static void +parse_float (data) + PTR data; +{ + struct pf_args * args = (struct pf_args *) data; + int fflag = 0, lflag = 0; + /* Copy token_buffer now, while it has just the number + and not the suffixes; once we add `f' or `i', + REAL_VALUE_ATOF may not work any more. */ + char *copy = (char *) alloca (args->p - token_buffer + 1); + bcopy (token_buffer, copy, args->p - token_buffer + 1); + + while (1) + { + int lose = 0; + + /* Read the suffixes to choose a data type. */ + switch (args->c) + { + case 'f': case 'F': + if (fflag) + error ("more than one `f' in numeric constant"); + fflag = 1; + break; + + case 'l': case 'L': + if (lflag) + error ("more than one `l' in numeric constant"); + lflag = 1; + break; + + case 'i': case 'I': + if (args->imag) + error ("more than one `i' or `j' in numeric constant"); + else if (pedantic) + pedwarn ("ANSI C++ forbids imaginary numeric constants"); + args->imag = 1; + break; + + default: + lose = 1; + } + + if (lose) + break; + + if (args->p >= token_buffer + maxtoken - 3) + args->p = extend_token_buffer (args->p); + *(args->p++) = args->c; + *(args->p) = 0; + args->c = getch (); + } + + /* The second argument, machine_mode, of REAL_VALUE_ATOF + tells the desired precision of the binary result + of decimal-to-binary conversion. */ + + if (fflag) + { + if (lflag) + error ("both `f' and `l' in floating constant"); + + args->type = float_type_node; + args->value = REAL_VALUE_ATOF (copy, TYPE_MODE (args->type)); + /* A diagnostic is required here by some ANSI C testsuites. + This is not pedwarn, become some people don't want + an error for this. */ + if (REAL_VALUE_ISINF (args->value) && pedantic) + warning ("floating point number exceeds range of `float'"); + } + else if (lflag) + { + args->type = long_double_type_node; + args->value = REAL_VALUE_ATOF (copy, TYPE_MODE (args->type)); + if (REAL_VALUE_ISINF (args->value) && pedantic) + warning ("floating point number exceeds range of `long double'"); + } + else + { + args->value = REAL_VALUE_ATOF (copy, TYPE_MODE (args->type)); + if (REAL_VALUE_ISINF (args->value) && pedantic) + warning ("floating point number exceeds range of `double'"); + } +} + int real_yylex () { @@ -3716,7 +3813,7 @@ real_yylex () int exceeds_double = 0; int imag = 0; REAL_VALUE_TYPE value; - jmp_buf handler; + struct pf_args args; /* Read explicit exponent if any, and put it in tokenbuf. */ @@ -3745,97 +3842,31 @@ real_yylex () *p = 0; errno = 0; + /* Setup input for parse_float() */ + args.p = p; + args.c = c; + args.imag = imag; + args.type = type; + /* Convert string to a double, checking for overflow. */ - if (setjmp (handler)) + if (do_float_handler (parse_float, (PTR) &args)) { - error ("floating constant out of range"); - value = dconst0; + /* Receive output from parse_float() */ + value = args.value; } else { - int fflag = 0, lflag = 0; - /* Copy token_buffer now, while it has just the number - and not the suffixes; once we add `f' or `i', - REAL_VALUE_ATOF may not work any more. */ - char *copy = (char *) alloca (p - token_buffer + 1); - bcopy (token_buffer, copy, p - token_buffer + 1); - - set_float_handler (handler); - - while (1) - { - int lose = 0; - - /* Read the suffixes to choose a data type. */ - switch (c) - { - case 'f': case 'F': - if (fflag) - error ("more than one `f' in numeric constant"); - fflag = 1; - break; - - case 'l': case 'L': - if (lflag) - error ("more than one `l' in numeric constant"); - lflag = 1; - break; - - case 'i': case 'I': - if (imag) - error ("more than one `i' or `j' in numeric constant"); - else if (pedantic) - pedwarn ("ANSI C++ forbids imaginary numeric constants"); - imag = 1; - break; - - default: - lose = 1; - } - - if (lose) - break; - - if (p >= token_buffer + maxtoken - 3) - p = extend_token_buffer (p); - *p++ = c; - *p = 0; - c = getch (); - } - - /* The second argument, machine_mode, of REAL_VALUE_ATOF - tells the desired precision of the binary result - of decimal-to-binary conversion. */ - - if (fflag) - { - if (lflag) - error ("both `f' and `l' in floating constant"); - - type = float_type_node; - value = REAL_VALUE_ATOF (copy, TYPE_MODE (type)); - /* A diagnostic is required here by some ANSI C testsuites. - This is not pedwarn, become some people don't want - an error for this. */ - if (REAL_VALUE_ISINF (value) && pedantic) - warning ("floating point number exceeds range of `float'"); - } - else if (lflag) - { - type = long_double_type_node; - value = REAL_VALUE_ATOF (copy, TYPE_MODE (type)); - if (REAL_VALUE_ISINF (value) && pedantic) - warning ("floating point number exceeds range of `long double'"); - } - else - { - value = REAL_VALUE_ATOF (copy, TYPE_MODE (type)); - if (REAL_VALUE_ISINF (value) && pedantic) - warning ("floating point number exceeds range of `double'"); - } - - set_float_handler (NULL_PTR); + /* We got an exception from parse_float() */ + error ("floating constant out of range"); + value = dconst0; } + + /* Receive output from parse_float() */ + p = args.p; + c = args.c; + imag = args.imag; + type = args.type; + #ifdef ERANGE if (errno == ERANGE && pedantic) {