The attach patch fixes a number of shortcomings with
STOP codes in gfortran. The updated comment in the
code nicely summarizes the problem.
/* Match a number or character constant after an (ERROR) STOP or PAUSE
- statement. */
+ statement. The requirements for a stop-code differs in the standards.
+
+ Fortran 95 has
+
+ R840 stop-stmt is STOP [ stop-code ]
+ R841 stop-code is scalar-char-constant
+ or digit [ digit [ digit [ digit [ digit ] ] ] ]
+
+ Fortran 2003 is the same as Fortran 95 except R840 and R841 are now
+ R849 and R850.
+
+ Fortran 2008 has
+
+ R855 stop-stmt is STOP [ stop-code ]
+ R856 allstop-stmt is ALL STOP [ stop-code ]
+ R857 stop-code is scalar-default-char-constant-expr
+ or scalar-int-constant-expr
+*/
So, the F95/2003 "digit [...]" is not a scalar-int-constant-expr.
It sort of looks like a statement label, but of course it is not
a statement label as the stop code does label anything. Currently,
gfortran parses "digit [...]" as an expression. I've added the
necessary checking that "digit [...]" is valid with one exception.
For the code
program foo
stop merge(667, 668, .true.)
end
gfortran with either -std=f95 or -std=f2003 should reject
this code. My patch does not fix this issue, because it
would (1) require a complete rewrite of gfc_match_stopcode
(which I am not willing to do) and (2) it simply is a vastly
unimportant corner case that gives the desired behavior.
A second issue raised by John in PR fortran/77978 is that
for F95/2003, the following is valid free-form source code:
program foo
stop666
end
but is invalid F2008. The patch fixes this bug, too.
OK to commit?