1 // Copyright (c) 2018-2019, NVIDIA CORPORATION.  All rights reserved.
2 //
3 // Licensed under the Apache License, Version 2.0 (the "License");
4 // you may not use this file except in compliance with the License.
5 // You may obtain a copy of the License at
6 //
7 //     http://www.apache.org/licenses/LICENSE-2.0
8 //
9 // Unless required by applicable law or agreed to in writing, software
10 // distributed under the License is distributed on an "AS IS" BASIS,
11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 // See the License for the specific language governing permissions and
13 // limitations under the License.
14 
15 #include "user-state.h"
16 #include "basic-parsers.h"
17 #include "grammar.h"
18 #include "openmp-grammar.h"
19 #include "parse-state.h"
20 #include "stmt-parser.h"
21 #include "type-parsers.h"
22 #include <optional>
23 
24 namespace Fortran::parser {
25 
Parse(ParseState & state)26 std::optional<Success> StartNewSubprogram::Parse(ParseState &state) {
27   if (auto *ustate{state.userState()}) {
28     ustate->NewSubprogram();
29   }
30   return {Success{}};
31 }
32 
Parse(ParseState & state)33 std::optional<CapturedLabelDoStmt::resultType> CapturedLabelDoStmt::Parse(
34     ParseState &state) {
35   static constexpr auto parser{statement(indirect(Parser<LabelDoStmt>{}))};
36   auto result{parser.Parse(state)};
37   if (result) {
38     if (auto *ustate{state.userState()}) {
39       ustate->NewDoLabel(std::get<Label>(result->statement.value().t));
40     }
41   }
42   return result;
43 }
44 
45 std::optional<EndDoStmtForCapturedLabelDoStmt::resultType>
Parse(ParseState & state)46 EndDoStmtForCapturedLabelDoStmt::Parse(ParseState &state) {
47   static constexpr auto parser{
48       statement(indirect(construct<EndDoStmt>("END DO" >> maybe(name))))};
49   if (auto enddo{parser.Parse(state)}) {
50     if (enddo->label.has_value()) {
51       if (const auto *ustate{state.userState()}) {
52         if (ustate->IsDoLabel(enddo->label.value())) {
53           return enddo;
54         }
55       }
56     }
57   }
58   return std::nullopt;
59 }
60 
Parse(ParseState & state)61 std::optional<Success> EnterNonlabelDoConstruct::Parse(ParseState &state) {
62   if (auto *ustate{state.userState()}) {
63     ustate->EnterNonlabelDoConstruct();
64   }
65   return {Success{}};
66 }
67 
Parse(ParseState & state)68 std::optional<Success> LeaveDoConstruct::Parse(ParseState &state) {
69   if (auto ustate{state.userState()}) {
70     ustate->LeaveDoConstruct();
71   }
72   return {Success{}};
73 }
74 
Parse(ParseState & state)75 std::optional<Name> OldStructureComponentName::Parse(ParseState &state) {
76   if (std::optional<Name> n{name.Parse(state)}) {
77     if (const auto *ustate{state.userState()}) {
78       if (ustate->IsOldStructureComponent(n->source)) {
79         return n;
80       }
81     }
82   }
83   return std::nullopt;
84 }
85 
Parse(ParseState & state)86 std::optional<DataComponentDefStmt> StructureComponents::Parse(
87     ParseState &state) {
88   static constexpr auto stmt{Parser<DataComponentDefStmt>{}};
89   std::optional<DataComponentDefStmt> defs{stmt.Parse(state)};
90   if (defs.has_value()) {
91     if (auto *ustate{state.userState()}) {
92       for (const auto &decl : std::get<std::list<ComponentDecl>>(defs->t)) {
93         ustate->NoteOldStructureComponent(std::get<Name>(decl.t).source);
94       }
95     }
96   }
97   return defs;
98 }
99 }
100