Skip to content

Commit

Permalink
Extend local_copyprop to deal with more stuff in control blocks
Browse files Browse the repository at this point in the history
- track what local actions and abstract method implementations access so
  control locals can be dead code eliminated
- copyprop into local table keys
  • Loading branch information
Chris Dodd committed Mar 10, 2017
1 parent 28c620d commit acc80b5
Show file tree
Hide file tree
Showing 91 changed files with 356 additions and 896 deletions.
12 changes: 12 additions & 0 deletions ir/dbprint-stmt.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -48,3 +48,15 @@ void IR::MethodCallStatement::dbprint(std::ostream &out) const {
out << Prec_Low << methodCall << setprec(prec);
if (!prec) out << ';';
}

void IR::Function::dbprint(std::ostream &out) const {
if (type->returnType) out << type->returnType << ' ';
out << name;
if (type->typeParameters && !type->typeParameters->empty())
out << type->typeParameters;
out << "(" << type->parameters << ") {" << indent;
if (body->components)
for (auto s : *body->components)
out << endl << s;
out << unindent << " }";
}
1 change: 0 additions & 1 deletion ir/ir.def
Original file line number Diff line number Diff line change
Expand Up @@ -402,7 +402,6 @@ class SwitchStatement : Statement {
class Function : Declaration {
Type_Method type;
BlockStatement body;
#nodbprint
}

/////////////////////////////////////////////////////////////
Expand Down
5 changes: 4 additions & 1 deletion ir/visitor.h
Original file line number Diff line number Diff line change
Expand Up @@ -271,7 +271,10 @@ class Backtrack : public virtual Visitor {

class P4WriteContext : public virtual Visitor {
public:
bool isWrite();
bool isWrite(bool root_value = false); // might write based on context
bool isRead(bool root_value = false); // might read based on context
// note that the context might (conservatively) return true for BOTH isWrite and isRead,
// as it might be an 'inout' access or it might be unable to decide.
};

#endif /* _IR_VISITOR_H_ */
45 changes: 42 additions & 3 deletions ir/write_context.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -24,18 +24,18 @@ limitations under the License.
* writing the same value. All you can say for certain is that if this returns 'false'
* the code at this point will not modify the object referred to by the current node */

bool P4WriteContext::isWrite() {
bool P4WriteContext::isWrite(bool root_value) {
const Context *ctxt = getContext();
if (!ctxt || !ctxt->node)
return false;
return root_value;
while (ctxt->child_index == 0 &&
(ctxt->node->is<IR::ArrayIndex>() ||
ctxt->node->is<IR::HeaderStackItemRef>() ||
ctxt->node->is<IR::Slice>() ||
ctxt->node->is<IR::Member>())) {
ctxt = ctxt->parent;
if (!ctxt || !ctxt->node)
return false; }
return root_value; }
if (auto *prim = ctxt->node->to<IR::Primitive>())
return prim->isOutput(ctxt->child_index);
if (ctxt->node->is<IR::AssignmentStatement>())
Expand All @@ -60,3 +60,42 @@ bool P4WriteContext::isWrite() {
return true; }
return false;
}

/* Determine from the Visitor context whether the currently being visited IR node
* denotes something that might be read by the code. This is often conservative
* (we don't know for certain that it is read). We return root_value for top-level
* expressions, and false for expression-statement unused values.
* TODO -- currently returns true for expressions 'read' in annotations.
*/
bool P4WriteContext::isRead(bool root_value) {
const Context *ctxt = getContext();
if (!ctxt || !ctxt->node)
return root_value;
while (ctxt->child_index == 0 &&
(ctxt->node->is<IR::ArrayIndex>() ||
ctxt->node->is<IR::HeaderStackItemRef>() ||
ctxt->node->is<IR::Slice>() ||
ctxt->node->is<IR::Member>())) {
ctxt = ctxt->parent;
if (!ctxt || !ctxt->node)
return root_value; }
if (auto *prim = ctxt->node->to<IR::Primitive>())
return !prim->isOutput(ctxt->child_index);
if (ctxt->node->is<IR::AssignmentStatement>())
return ctxt->child_index != 0;
if (ctxt->node->is<IR::Vector<IR::Expression>>()) {
if (!ctxt->parent || !ctxt->parent->node)
return false;
if (auto *mc = ctxt->parent->node->to<IR::MethodCallExpression>()) {
auto type = mc->method->type->to<IR::Type_Method>();
if (!type) {
/* FIXME -- can't find the type of the method -- should be a BUG? */
return true; }
auto param = type->parameters->getParameter(ctxt->child_index);
return param->direction != IR::Direction::Out; } }
if (ctxt->node->is<IR::IndexedVector<IR::StatOrDecl>>())
return false;
if (ctxt->node->is<IR::IfStatement>())
return ctxt->child_index == 0;
return true;
}
Loading

0 comments on commit acc80b5

Please sign in to comment.