------- Comment #11 from burnus at gcc dot gnu dot org  2010-06-25 09:17 -------
(In reply to comment #10)
> What language is GAMESS written in? 

Fortran, of course. See: http://www.spec.org/cpu2006/Docs/416.gamess.html
and http://www.msg.ameslab.gov/GAMESS/GAMESS.html

> The above simply is not Fortran.  EQUIVALENCE is a specification-statement.
> It cannot appear after an executable-statement.

Well, it is invalid code - based on a valid Fortran code. If you use Delta to
reduce a test case (cf. http://gcc.gnu.org/wiki/A_guide_to_testcase_reduction),
it simply removes lines of the source code using a constraint. I think
Sebastian's constraint was that it segfaults. This seemingly happens for the
unmodified gamess due to a Graphite bug - but also due to a buggy error
recovery in gfortran.

Thus, this PR is about an ice-on-INVALID-code and error-recovery bug, thus, it
has a lower priority than wrong-code bugs; nevertheless, it is a regression.

 * * *

Regarding the PR: For the test case in comment 0, one finds in gdb:

(gdb) p eq->expr->symtree->n.sym
$1 = (gfc_symbol *) 0x13fae6d
(gdb) p eq->expr->symtree->n.sym->name
$2 = 0x0
(gdb) p eq->expr->symtree->n.sym->ts
$3 = {type = 0, kind = 0, u = {derived = 0x0, cl = 0x0}, interface = 0x0,
is_c_interop = 0, is_iso_c = 0, f90_type = 0}

That means that the symbol is only half present, i.e. it exists in the symtree,
but seemingly, the values have not been set.


The next item in the list is eq->eq, for which
  (gdb) p eq->eq->expr
  $8 = (gfc_expr *) 0x1395700
  (gdb) p eq->eq->expr->symtree
  $9 = (gfc_symtree *) 0x13a3110
but
  (gdb) p eq->eq->expr->symtree->n.sym
  $10 = (gfc_symbol *) 0x0

Thus, for the case, adding a patch like in comment 1 and in comment 5 works.
Even with both checks added, it will fail later (for comment 0's test case)
because of
  12642         if (sym->ns->proc_name
as sym->ns == NULL.

One can, of course, put more checks in, e.g., whether
eq->expr->symtree->n.sym->name == NULL or whether sym->ns == NULL, but the
question is whether one should not fix it earlier.

Currently, the program is walked like this:

  parse_progunit -> parse_executable -> next_statement

if the next_statement is not an executable statement (which ST_EQUIVALENCE is
not), parse_executable returns - and parse_progunit calls:
      unexpected_statement (st);
      reject_statement ();

Thus, seemingly, reject_statement leaves the symtree in a half-existing state.
It calls:  gfc_undo_symbols () and undo_new_statement (). I think the former
one only does a partial cleanup.


-- 


http://gcc.gnu.org/bugzilla/show_bug.cgi?id=44660

Reply via email to