diff options
author | arphaman <arphaman@gmail.com> | 2013-09-14 13:03:23 +0100 |
---|---|---|
committer | arphaman <arphaman@gmail.com> | 2013-09-14 13:03:23 +0100 |
commit | 8faf776a94e8145925f13c157801fd364ca648d6 (patch) | |
tree | 5731d90b5f6633c0fff6dc9d3b532ceab44382a4 | |
parent | 145e670d60b8868b1c0b3653f0483c16ee69d6b8 (diff) | |
download | flang-8faf776a94e8145925f13c157801fd364ca648d6.tar.gz |
fixed parsing for programs which begin with type statements
-rw-r--r-- | lib/Parse/Parser.cpp | 20 | ||||
-rw-r--r-- | test/Parser/minimalAmbiguous.f95 | 4 |
2 files changed, 18 insertions, 6 deletions
diff --git a/lib/Parse/Parser.cpp b/lib/Parse/Parser.cpp index 07c6e5dac8..f5c57866b5 100644 --- a/lib/Parse/Parser.cpp +++ b/lib/Parse/Parser.cpp @@ -600,7 +600,8 @@ bool Parser::ParseProgramUnit() { case tok::kw_LOGICAL: case tok::kw_DOUBLEPRECISION: case tok::kw_DOUBLECOMPLEX: - ParseTypedExternalSubprogram(FunctionDecl::NoAttributes); + if(ParseTypedExternalSubprogram(FunctionDecl::NoAttributes)) + ParseMainProgram(); break; case tok::kw_RECURSIVE: ParseRecursiveExternalSubprogram(); @@ -809,12 +810,14 @@ bool Parser::ParseExternalSubprogram() { } bool Parser::ParseTypedExternalSubprogram(int Attr) { + auto ReparseLoc = LocFirstStmtToken; DeclSpec ReturnType; ParseDeclarationTypeSpec(ReturnType); + bool IsRecursive = (Attr & FunctionDecl::Recursive) != 0; if(Tok.isAtStartOfStatement()) goto err; - if(!(Attr & FunctionDecl::Recursive)) { + if(!IsRecursive) { if(Features.FixedForm) ReLexAmbiguousIdentifier(fixedForm::KeywordMatcher(fixedForm::KeywordFilter(tok::kw_RECURSIVE, tok::kw_FUNCTION))); @@ -828,11 +831,16 @@ bool Parser::ParseTypedExternalSubprogram(int Attr) { goto err; if(Features.FixedForm) ReLexAmbiguousIdentifier(fixedForm::KeywordMatcher(fixedForm::KeywordFilter(tok::kw_FUNCTION))); - if(Tok.is(tok::kw_FUNCTION)) - return ParseExternalSubprogram(ReturnType, Attr); + if(Tok.is(tok::kw_FUNCTION)) { + ParseExternalSubprogram(ReturnType, Attr); + return false; + } err: - Diag.Report(getExpectedLoc(), diag::err_expected_kw) - << "function"; + if(IsRecursive) { + Diag.Report(getExpectedLoc(), diag::err_expected_kw) + << "function"; + SkipUntilNextStatement(); + } else StartStatementReparse(ReparseLoc); return true; } diff --git a/test/Parser/minimalAmbiguous.f95 b/test/Parser/minimalAmbiguous.f95 new file mode 100644 index 0000000000..2ed490f1ea --- /dev/null +++ b/test/Parser/minimalAmbiguous.f95 @@ -0,0 +1,4 @@ +! RUN: %flang -fsyntax-only < %s +INTEGER I +I = 0 +END |