diff options
author | Tobias Schlüter <tobi@gcc.gnu.org> | 2005-10-30 19:09:55 +0100 |
---|---|---|
committer | Tobias Schlüter <tobi@gcc.gnu.org> | 2005-10-30 19:09:55 +0100 |
commit | 25d8f0a2839a99417ab79879fb55f2ead76fcf2a (patch) | |
tree | 3920d0fc1db1a9d875d55587afd2ffefff790a10 /gcc/fortran/arith.c | |
parent | e8299ec258037fb73ee906633760ff1191bf05e1 (diff) | |
download | gcc-25d8f0a2839a99417ab79879fb55f2ead76fcf2a.zip gcc-25d8f0a2839a99417ab79879fb55f2ead76fcf2a.tar.gz gcc-25d8f0a2839a99417ab79879fb55f2ead76fcf2a.tar.bz2 |
arith.c (gfc_enum_initializer): New function.
fortran/
2005-10-30 Gaurav Gautam <gauravga@noida.hcltech.com>
Tobias Schl"uter <tobias.schlueter@physik.uni-muenchen.de>
* arith.c (gfc_enum_initializer): New function.
(gfc_check_integer_range): Made extern.
* decl.c (enumerator_history): New typedef.
(last_initializer, enum_history, max_enum): New variables.
(create_enum_history, gfc_free_enum_history): New functions.
(add_init_expr_to_sym): Call create_enum_history if parsing ENUM.
(variable_decl): Modified to parse enumerator definition.
(match_attr_spec): Add PARAMETER attribute to ENUMERATORs.
(gfc_match_data_decl): Issues error, if match_type_spec do not
return desired return values.
(set_enum_kind, gfc_match_enum, gfc_match_enumerator_def): New
functions.
(gfc_match_end): Deal with END ENUM.
* gfortran.h (gfc_statement): ST_ENUM, ST_ENUMERATOR, ST_END_ENUM
added.
(symbol_attribute): Bit field for enumerator added.
(gfc_options): Add fshort_enums.
(gfc_enum_initializer, gfc_check_integer_range): Add prototypes.
* options.c: Include target.h
(gfc_init_options): Initialize fshort_enums.
(gfc_handle_option): Deal with fshort_enums.
* parse.c (decode_statement): Match ENUM and ENUMERATOR statement.
(gfc_ascii_statement): Deal with the enumerator statements.
(parse_enum): New function to parse enum construct.
(parse_spec): Added case ST_ENUM.
* parse.h (gfc_compile_state): COMP_ENUM added.
(gfc_match_enum, gfc_match_enumerator_def, gfc_free_enum_history):
Prototype added.
* symbol.c (gfc_copy_attr): Copy enumeration attribute.
* lang.opt (fshort-enums): Option added.
testsuite/
2005-10-30 Tobias Schl"uter <tobias.schlueter@physik.uni-muenchen.de>
* gfortran.dg/enum_10.f90, gfortran.dg/enum_10.c: New test.
2005-10-30 Gaurav Gautam <gauravga@noida.hcltech.com>
* gfortran.dg/enum_1.f90, gfortran.dg/enum_2.f90,
gfortran.dg/enum_3.f90, gfortran.dg/enum_4.f90,
gfortran.dg/enum_5.f90, gfortran.dg/enum_6.f90,
gfortran.dg/enum_7.f90, gfortran.dg/enum_8.f90,
gfortran.dg/enum_9.f90,
gfortran.fortran-torture/compile/enum_1.f90,
gfortran.fortran-torture/execute/enum_1.f90,
gfortran.fortran-torture/execute/enum_2.f90,
gfortran.fortran-torture/execute/enum_3.f90,
gfortran.fortran-torture/execute/enum_4.f90: New tests.
From-SVN: r106246
Diffstat (limited to 'gcc/fortran/arith.c')
-rw-r--r-- | gcc/fortran/arith.c | 46 |
1 files changed, 45 insertions, 1 deletions
diff --git a/gcc/fortran/arith.c b/gcc/fortran/arith.c index e0c1f4b..aac3cb4 100644 --- a/gcc/fortran/arith.c +++ b/gcc/fortran/arith.c @@ -339,7 +339,7 @@ gfc_arith_done_1 (void) the range of the kind. Returns ARITH_OK, ARITH_ASYMMETRIC or ARITH_OVERFLOW. */ -static arith +arith gfc_check_integer_range (mpz_t p, int kind) { arith result; @@ -2405,3 +2405,47 @@ gfc_hollerith2logical (gfc_expr * src, int kind) return result; } + +/* Returns an initializer whose value is one higher than the value of the + LAST_INITIALIZER argument. If that is argument is NULL, the + initializers value will be set to zero. The initializer's kind + will be set to gfc_c_int_kind. + + If -fshort-enums is given, the appropriate kind will be selected + later after all enumerators have been parsed. A warning is issued + here if an initializer exceeds gfc_c_int_kind. */ + +gfc_expr * +gfc_enum_initializer (gfc_expr *last_initializer, locus where) +{ + gfc_expr *result; + + result = gfc_get_expr (); + result->expr_type = EXPR_CONSTANT; + result->ts.type = BT_INTEGER; + result->ts.kind = gfc_c_int_kind; + result->where = where; + + mpz_init (result->value.integer); + + if (last_initializer != NULL) + { + mpz_add_ui (result->value.integer, last_initializer->value.integer, 1); + result->where = last_initializer->where; + + if (gfc_check_integer_range (result->value.integer, + gfc_c_int_kind) != ARITH_OK) + { + gfc_error ("Enumerator exceeds the C integer type at %C"); + return NULL; + } + } + else + { + /* Control comes here, if it's the very first enumerator and no + initializer has been given. It will be initialized to ZERO (0). */ + mpz_set_si (result->value.integer, 0); + } + + return result; +} |