class ExpressionInliner: private TraversingVisitor
{
private:
+ struct ExpressionUse
+ {
+ RefPtr<Expression> *reference;
+ Block *ref_scope;
+ bool blocked;
+
+ ExpressionUse(): reference(0), ref_scope(0), blocked(false) { }
+ };
+
struct ExpressionInfo
{
- Expression *expression;
+ Assignment::Target target;
+ RefPtr<Expression> expression;
Block *assign_scope;
- RefPtr<Expression> *inline_point;
+ std::vector<ExpressionUse> uses;
bool trivial;
- bool available;
- ExpressionInfo(): expression(0), assign_scope(0), inline_point(0), trivial(false), available(true) { }
+ ExpressionInfo(): expression(0), assign_scope(0), trivial(false) { }
};
- std::map<Assignment::Target, ExpressionInfo> expressions;
+ std::list<ExpressionInfo> expressions;
+ std::map<Assignment::Target, ExpressionInfo *> assignments;
ExpressionInfo *r_ref_info;
- bool r_any_inlined;
bool r_trivial;
- bool mutating;
+ bool access_read;
+ bool access_write;
bool iteration_init;
Block *iteration_body;
const Operator *r_oper;
bool apply(Stage &);
private:
- void inline_expression(Expression &, RefPtr<Expression> &);
- virtual void visit(Block &);
virtual void visit(RefPtr<Expression> &);
virtual void visit(VariableReference &);
virtual void visit(MemberAccess &);
static bool evaluate_relation(const char *, T, T);
template<typename T>
static T evaluate_arithmetic(char, T, T);
+ template<typename T>
+ static T evaluate_int_special_op(char, T, T);
+ template<typename T>
+ void convert_to_result(const Variant &);
void set_result(const Variant &, bool = false);
virtual void visit(RefPtr<Expression> &);
Node *node;
Assignment::Target target;
std::vector<Node *> used_by;
+ unsigned in_loop;
AssignmentInfo(): node(0) { }
};
bool r_side_effects;
bool in_struct;
bool composite_reference;
+ unsigned in_loop;
+ std::vector<Node *> loop_ext_refs;
Assignment::Target r_reference;
std::set<Node *> unused_nodes;