diff options
author | Paul Brook <pbrook@gcc.gnu.org> | 2004-07-03 23:25:46 +0000 |
---|---|---|
committer | Paul Brook <pbrook@gcc.gnu.org> | 2004-07-03 23:25:46 +0000 |
commit | 1107b970c6701a65fbf0e74ad6dbfe329a580352 (patch) | |
tree | 1136b6ff2a39b0f1c3c84d79290dcd083129c622 /gcc/fortran | |
parent | 614ed70a597544644d86a8346e0158acec5886c1 (diff) | |
download | gcc-1107b970c6701a65fbf0e74ad6dbfe329a580352.zip gcc-1107b970c6701a65fbf0e74ad6dbfe329a580352.tar.gz gcc-1107b970c6701a65fbf0e74ad6dbfe329a580352.tar.bz2 |
decl.c (gfc_match_implicit_range): Don't use typespec.
* decl.c (gfc_match_implicit_range): Don't use typespec.
(gfc_match_implicit): Handle character selectors.
* gfortran.h (gfc_set_implicit): Remove prototype.
(gfc_add_new_implicit_range, gfc_merge_new_implicit): Update.
* parse.c (accept_statement): Don't call gfc_set_implicit.
* symbol.c (new_ts): Remove.
(gfc_set_implicit_none): Use same loop bounds as other functions.
(gfc_set_implicit): Remove.
(gfc_clear_new_implicit, gfc_add_new_implicit_range): Only set flags.
(gfc_merge_new_implicit): Combine with gfc_set_implicit.
testsuite/
* gfortran.fortran-torture/compile/implicit_1.f90: New test.
From-SVN: r84063
Diffstat (limited to 'gcc/fortran')
-rw-r--r-- | gcc/fortran/ChangeLog | 13 | ||||
-rw-r--r-- | gcc/fortran/decl.c | 73 | ||||
-rw-r--r-- | gcc/fortran/gfortran.h | 5 | ||||
-rw-r--r-- | gcc/fortran/parse.c | 1 | ||||
-rw-r--r-- | gcc/fortran/symbol.c | 75 |
5 files changed, 86 insertions, 81 deletions
diff --git a/gcc/fortran/ChangeLog b/gcc/fortran/ChangeLog index 89a15bd..a477814 100644 --- a/gcc/fortran/ChangeLog +++ b/gcc/fortran/ChangeLog @@ -1,3 +1,16 @@ +2004-07-04 Paul Brook <paul@codesourcery.com> + + * decl.c (gfc_match_implicit_range): Don't use typespec. + (gfc_match_implicit): Handle character selectors. + * gfortran.h (gfc_set_implicit): Remove prototype. + (gfc_add_new_implicit_range, gfc_merge_new_implicit): Update. + * parse.c (accept_statement): Don't call gfc_set_implicit. + * symbol.c (new_ts): Remove. + (gfc_set_implicit_none): Use same loop bounds as other functions. + (gfc_set_implicit): Remove. + (gfc_clear_new_implicit, gfc_add_new_implicit_range): Only set flags. + (gfc_merge_new_implicit): Combine with gfc_set_implicit. + 2004-06-30 Richard Henderson <rth@redhat.com> * match.c (var_element): Remove unused variable. diff --git a/gcc/fortran/decl.c b/gcc/fortran/decl.c index 5c5b728..94573ac 100644 --- a/gcc/fortran/decl.c +++ b/gcc/fortran/decl.c @@ -1001,7 +1001,7 @@ gfc_match_implicit_none (void) /* Match the letter range(s) of an IMPLICIT statement. */ static match -match_implicit_range (gfc_typespec * ts) +match_implicit_range (void) { int c, c1, c2, inner; locus cur_loc; @@ -1068,7 +1068,7 @@ match_implicit_range (gfc_typespec * ts) conflicts with whatever earlier IMPLICIT statements may have set. This is done when we've successfully finished matching the current one. */ - if (gfc_add_new_implicit_range (c1, c2, ts) != SUCCESS) + if (gfc_add_new_implicit_range (c1, c2) != SUCCESS) goto bad; } @@ -1116,11 +1116,11 @@ gfc_match_implicit (void) return MATCH_ERROR; } - /* First cleanup. */ - gfc_clear_new_implicit (); - do { + /* First cleanup. */ + gfc_clear_new_implicit (); + /* A basic type is mandatory here. */ m = match_type_spec (&ts, 1); if (m == MATCH_ERROR) @@ -1129,39 +1129,56 @@ gfc_match_implicit (void) goto syntax; cur_loc = gfc_current_locus; - m = match_implicit_range (&ts); - - if (m != MATCH_YES && ts.type == BT_CHARACTER) - { - /* looks like we are matching CHARACTER (<len>) (<range>) */ - m = match_char_spec (&ts); - } + m = match_implicit_range (); if (m == MATCH_YES) { - /* Looks like we have the <TYPE> (<RANGE>). */ + /* We may have <TYPE> (<RANGE>). */ gfc_gobble_whitespace (); c = gfc_next_char (); if ((c == '\n') || (c == ',')) - continue; + { + /* Check for CHARACTER with no length parameter. */ + if (ts.type == BT_CHARACTER && !ts.cl) + { + ts.kind = gfc_default_character_kind (); + ts.cl = gfc_get_charlen (); + ts.cl->next = gfc_current_ns->cl_list; + gfc_current_ns->cl_list = ts.cl; + ts.cl->length = gfc_int_expr (1); + } + + /* Record the Successful match. */ + if (gfc_merge_new_implicit (&ts) != SUCCESS) + return MATCH_ERROR; + continue; + } gfc_current_locus = cur_loc; } - /* Last chance -- check <TYPE> (<KIND>) (<RANGE>). */ - m = gfc_match_kind_spec (&ts); - if (m == MATCH_ERROR) - goto error; - if (m == MATCH_NO) + /* Discard the (incorrectly) matched range. */ + gfc_clear_new_implicit (); + + /* Last chance -- check <TYPE> <SELECTOR> (<RANGE>). */ + if (ts.type == BT_CHARACTER) + m = match_char_spec (&ts); + else { - m = gfc_match_old_kind_spec (&ts); - if (m == MATCH_ERROR) - goto error; + m = gfc_match_kind_spec (&ts); if (m == MATCH_NO) - goto syntax; + { + m = gfc_match_old_kind_spec (&ts); + if (m == MATCH_ERROR) + goto error; + if (m == MATCH_NO) + goto syntax; + } } + if (m == MATCH_ERROR) + goto error; - m = match_implicit_range (&ts); + m = match_implicit_range (); if (m == MATCH_ERROR) goto error; if (m == MATCH_NO) @@ -1172,14 +1189,12 @@ gfc_match_implicit (void) if ((c != '\n') && (c != ',')) goto syntax; + if (gfc_merge_new_implicit (&ts) != SUCCESS) + return MATCH_ERROR; } while (c == ','); - /* All we need to now is try to merge the new implicit types back - into the existing types. This will fail if another implicit - type is already defined for a letter. */ - return (gfc_merge_new_implicit () == SUCCESS) ? - MATCH_YES : MATCH_ERROR; + return MATCH_YES; syntax: gfc_syntax_error (ST_IMPLICIT); diff --git a/gcc/fortran/gfortran.h b/gcc/fortran/gfortran.h index d35506a..86113ad 100644 --- a/gcc/fortran/gfortran.h +++ b/gcc/fortran/gfortran.h @@ -1435,10 +1435,9 @@ extern int gfc_index_integer_kind; /* symbol.c */ void gfc_clear_new_implicit (void); -try gfc_add_new_implicit_range (int, int, gfc_typespec *); -try gfc_merge_new_implicit (void); +try gfc_add_new_implicit_range (int, int); +try gfc_merge_new_implicit (gfc_typespec *); void gfc_set_implicit_none (void); -void gfc_set_implicit (void); gfc_typespec *gfc_get_default_type (gfc_symbol *, gfc_namespace *); try gfc_set_default_type (gfc_symbol *, int, gfc_namespace *); diff --git a/gcc/fortran/parse.c b/gcc/fortran/parse.c index 3f9ca81..15a53ea 100644 --- a/gcc/fortran/parse.c +++ b/gcc/fortran/parse.c @@ -1019,7 +1019,6 @@ accept_statement (gfc_statement st) break; case ST_IMPLICIT: - gfc_set_implicit (); break; case ST_FUNCTION: diff --git a/gcc/fortran/symbol.c b/gcc/fortran/symbol.c index 8887741..9208d22 100644 --- a/gcc/fortran/symbol.c +++ b/gcc/fortran/symbol.c @@ -96,13 +96,9 @@ static gfc_symbol *changed_syms = NULL; /*********** IMPLICIT NONE and IMPLICIT statement handlers ***********/ -/* The following static variables hold the default types set by - IMPLICIT statements. We have to store kind information because of - IMPLICIT DOUBLE PRECISION statements. IMPLICIT NONE stores a - BT_UNKNOWN into all elements. The arrays of flags indicate whether - a particular element has been explicitly set or not. */ +/* The following static variable indicates whether a particular element has + been explicitly set or not. */ -static gfc_typespec new_ts[GFC_LETTERS]; static int new_flag[GFC_LETTERS]; @@ -113,48 +109,30 @@ gfc_set_implicit_none (void) { int i; - for (i = 'a'; i <= 'z'; i++) + for (i = 0; i < GFC_LETTERS; i++) { - gfc_clear_ts (&gfc_current_ns->default_type[i - 'a']); - gfc_current_ns->set_flag[i - 'a'] = 1; + gfc_clear_ts (&gfc_current_ns->default_type[i]); + gfc_current_ns->set_flag[i] = 1; } } -/* Sets the implicit types parsed by gfc_match_implicit(). */ +/* Reset the implicit range flags. */ void -gfc_set_implicit (void) -{ - int i; - - for (i = 0; i < GFC_LETTERS; i++) - if (new_flag[i]) - { - gfc_current_ns->default_type[i] = new_ts[i]; - gfc_current_ns->set_flag[i] = 1; - } -} - - -/* Wipe anything a previous IMPLICIT statement may have tried to do. */ -void gfc_clear_new_implicit (void) +gfc_clear_new_implicit (void) { int i; for (i = 0; i < GFC_LETTERS; i++) - { - gfc_clear_ts (&new_ts[i]); - if (new_flag[i]) - new_flag[i] = 0; - } + new_flag[i] = 0; } -/* Prepare for a new implicit range. Sets flags in new_flag[] and - copies the typespec to new_ts[]. */ +/* Prepare for a new implicit range. Sets flags in new_flag[]. */ -try gfc_add_new_implicit_range (int c1, int c2, gfc_typespec * ts) +try +gfc_add_new_implicit_range (int c1, int c2) { int i; @@ -170,7 +148,6 @@ try gfc_add_new_implicit_range (int c1, int c2, gfc_typespec * ts) return FAILURE; } - new_ts[i] = *ts; new_flag[i] = 1; } @@ -178,27 +155,29 @@ try gfc_add_new_implicit_range (int c1, int c2, gfc_typespec * ts) } -/* Add a matched implicit range for gfc_set_implicit(). An implicit - statement has been fully matched at this point. We now need to - check if merging the new implicit types back into the existing - types will work. */ +/* Add a matched implicit range for gfc_set_implicit(). Check if merging + the new implicit types back into the existing types will work. */ try -gfc_merge_new_implicit (void) +gfc_merge_new_implicit (gfc_typespec * ts) { int i; for (i = 0; i < GFC_LETTERS; i++) - if (new_flag[i]) - { - if (gfc_current_ns->set_flag[i]) - { - gfc_error ("Letter %c already has an IMPLICIT type at %C", - i + 'A'); - return FAILURE; - } - } + { + if (new_flag[i]) + { + if (gfc_current_ns->set_flag[i]) + { + gfc_error ("Letter %c already has an IMPLICIT type at %C", + i + 'A'); + return FAILURE; + } + gfc_current_ns->default_type[i] = *ts; + gfc_current_ns->set_flag[i] = 1; + } + } return SUCCESS; } |