aboutsummaryrefslogtreecommitdiff
path: root/flang/lib/Parser/executable-parsers.cpp
diff options
context:
space:
mode:
authorPeter Klausler <35819229+klausler@users.noreply.github.com>2023-10-16 17:29:25 -0700
committerGitHub <noreply@github.com>2023-10-16 17:29:25 -0700
commit81d04709f86968431ecab1df12a17279d057daa9 (patch)
treea3dc018b6a2b664fcee4194b163d75c732122eb6 /flang/lib/Parser/executable-parsers.cpp
parent11d07d9ef618497b825badee8b4f06a48575606b (diff)
downloadllvm-81d04709f86968431ecab1df12a17279d057daa9.zip
llvm-81d04709f86968431ecab1df12a17279d057daa9.tar.gz
llvm-81d04709f86968431ecab1df12a17279d057daa9.tar.bz2
[flang] Fix construct names on labeled DO (#67622)
Fortran requires that a DO construct with a construct name end with an END DO statement bearing the same name. This is true even if the DO construct begins with a label DO statement; e.g., "constrName: do 10 j=1,10" must end with "10 end do constrName". The compiler presently basically ignores construct names that appear on label DO statements, because only non-label DO statements can be parsed as DO constructs. This causes us to miss some errors, and (worse) breaks the usage of the construct name on CYCLE and EXIT statements. To fix this, this patch changes the parse tree and parser so that a DO construct name on a putative label DO statement causes it to be parsed as a "non-label" DO statement... with a label. Only true old-style labeled DO statements without construct names are now parsed as such. I did not change the class name NonLabelDoStmt -- it's widely used across the front-end, and is the name of a production in the standard's grammar. But now it basically means DoConstructDoStmt. Fixes https://github.com/llvm/llvm-project/issues/67283.
Diffstat (limited to 'flang/lib/Parser/executable-parsers.cpp')
-rw-r--r--flang/lib/Parser/executable-parsers.cpp10
1 files changed, 7 insertions, 3 deletions
diff --git a/flang/lib/Parser/executable-parsers.cpp b/flang/lib/Parser/executable-parsers.cpp
index a61bf2c..892c612 100644
--- a/flang/lib/Parser/executable-parsers.cpp
+++ b/flang/lib/Parser/executable-parsers.cpp
@@ -279,13 +279,17 @@ TYPE_CONTEXT_PARSER("loop control"_en_US,
many(Parser<LocalitySpec>{})))))
// R1121 label-do-stmt -> [do-construct-name :] DO label [loop-control]
+// A label-do-stmt with a do-construct-name is parsed as a nonlabel-do-stmt
+// with an optional label.
TYPE_CONTEXT_PARSER("label DO statement"_en_US,
- construct<LabelDoStmt>(
- maybe(name / ":"), "DO" >> label, maybe(loopControl)))
+ construct<LabelDoStmt>("DO" >> label, maybe(loopControl)))
// R1122 nonlabel-do-stmt -> [do-construct-name :] DO [loop-control]
TYPE_CONTEXT_PARSER("nonlabel DO statement"_en_US,
- construct<NonLabelDoStmt>(maybe(name / ":"), "DO" >> maybe(loopControl)))
+ construct<NonLabelDoStmt>(
+ name / ":", "DO" >> maybe(label), maybe(loopControl)) ||
+ construct<NonLabelDoStmt>(construct<std::optional<Name>>(),
+ construct<std::optional<Label>>(), "DO" >> maybe(loopControl)))
// R1132 end-do-stmt -> END DO [do-construct-name]
TYPE_CONTEXT_PARSER("END DO statement"_en_US,