P4C
The P4 Compiler
Loading...
Searching...
No Matches
removeReturns.h
1/*
2Copyright 2013-present Barefoot Networks, Inc.
3
4Licensed under the Apache License, Version 2.0 (the "License");
5you may not use this file except in compliance with the License.
6You may obtain a copy of the License at
7
8 http://www.apache.org/licenses/LICENSE-2.0
9
10Unless required by applicable law or agreed to in writing, software
11distributed under the License is distributed on an "AS IS" BASIS,
12WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13See the License for the specific language governing permissions and
14limitations under the License.
15*/
16
17#ifndef FRONTENDS_P4_REMOVERETURNS_H_
18#define FRONTENDS_P4_REMOVERETURNS_H_
19
20#include "frontends/common/resolveReferences/referenceMap.h"
21#include "frontends/common/resolveReferences/resolveReferences.h"
22#include "frontends/p4/ternaryBool.h"
23#include "frontends/p4/typeChecking/typeChecker.h"
24#include "ir/ir.h"
25
26namespace P4 {
27using namespace literals;
28
34class HasExits : public Inspector {
35 public:
36 bool hasExits;
37 bool hasReturns;
38 HasExits() : hasExits(false), hasReturns(false) { setName("HasExits"); }
39
40 void postorder(const IR::ExitStatement *) override { hasExits = true; }
41 void postorder(const IR::ReturnStatement *) override { hasReturns = true; }
42};
43
70 /* This pass does not use (inherit from) ControlFlowVisitor, even though it is doing
71 * control flow analysis, as it turns out to be more efficient to do it directly here
72 * by overloading the branching constructs (if/switch/loops) and not cloning the visitor,
73 * because we *only* care about statements (not expressions) locally in a block (and
74 * not across calls), and we only have one bit of data (hasJumped flag). */
75
78 bool hasJumped = false;
79
82 bool movedToIfBranch = false;
83
84 bool preorder(IR::BlockStatement *) override;
85 bool moveFromParentTo(const IR::Statement *&child);
86 bool preorder(IR::IfStatement *) override;
87 bool preorder(IR::SwitchStatement *) override;
88 void postorder(IR::LoopStatement *) override;
89 bool branch() {
90 hasJumped = true;
91 // no need to visit children
92 return false;
93 }
94 bool preorder(IR::BreakStatement *) override { return branch(); }
95 bool preorder(IR::ContinueStatement *) override { return branch(); }
96 bool preorder(IR::ExitStatement *) override { return branch(); }
97 bool preorder(IR::ReturnStatement *) override { return branch(); }
98 // Only visit statements, skip all expressions
99 bool preorder(IR::Expression *) override { return false; }
100
101 public:
103};
104
123 protected:
124 MinimalNameGenerator nameGen;
125 IR::ID returnVar; // one for each context
126 IR::ID returnedValue; // only for functions that return expressions
127 cstring variableName;
128 cstring retValName;
129
130 std::vector<TernaryBool> stack;
131 void push() { stack.push_back(TernaryBool::No); }
132 void pop() { stack.pop_back(); }
133 void set(TernaryBool r) {
134 BUG_CHECK(!stack.empty(), "Empty stack");
135 stack.back() = r;
136 }
137 TernaryBool hasReturned() {
138 BUG_CHECK(!stack.empty(), "Empty stack");
139 return stack.back();
140 }
141
142 public:
143 explicit DoRemoveReturns(cstring varName = "hasReturned"_cs, cstring retValName = "retval"_cs)
144 : variableName(varName), retValName(retValName) {
145 visitDagOnce = false;
146 setName("DoRemoveReturns");
147 }
148
149 const IR::Node *preorder(IR::Function *function) override;
150 const IR::Node *preorder(IR::BlockStatement *statement) override;
151 const IR::Node *preorder(IR::ReturnStatement *statement) override;
152 const IR::Node *preorder(IR::ExitStatement *statement) override;
153 const IR::Node *preorder(IR::IfStatement *statement) override;
154 const IR::Node *preorder(IR::SwitchStatement *statement) override;
155
156 const IR::Node *preorder(IR::P4Action *action) override;
157 const IR::Node *preorder(IR::P4Control *control) override;
158 const IR::Node *preorder(IR::P4Parser *parser) override {
159 prune();
160 return parser;
161 }
162
163 const IR::Node *postorder(IR::LoopStatement *loop) override;
164 profile_t init_apply(const IR::Node *node) override;
165};
166
168 public:
170};
171
172} // namespace P4
173
174#endif /* FRONTENDS_P4_REMOVERETURNS_H_ */
Definition removeReturns.h:122
Definition removeReturns.h:34
Definition node.h:95
Definition visitor.h:400
Definition referenceMap.h:36
Definition visitor.h:372
Definition removeReturns.h:69
Definition pass_manager.h:40
Definition removeReturns.h:167
Definition visitor.h:424
Definition visitor.h:78
Definition cstring.h:85
TODO: this is not really specific to BMV2, it should reside somewhere else.
Definition applyOptionsPragmas.cpp:24
Definition id.h:28