mirror of
https://github.com/zeek/zeek.git
synced 2025-10-04 23:58:20 +00:00
BIT-1384: Remove -O (optimize scripts) command-line option.
This commit is contained in:
parent
da24fa40a5
commit
b42706f0b5
8 changed files with 47 additions and 1003 deletions
573
src/Expr.cc
573
src/Expr.cc
|
@ -249,18 +249,6 @@ NameExpr::~NameExpr()
|
||||||
Unref(id);
|
Unref(id);
|
||||||
}
|
}
|
||||||
|
|
||||||
Expr* NameExpr::Simplify(SimplifyType simp_type)
|
|
||||||
{
|
|
||||||
if ( simp_type != SIMPLIFY_LHS && id->IsConst() )
|
|
||||||
{
|
|
||||||
Val* v = Eval(0);
|
|
||||||
if ( v )
|
|
||||||
return new ConstExpr(v);
|
|
||||||
}
|
|
||||||
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
|
|
||||||
Val* NameExpr::Eval(Frame* f) const
|
Val* NameExpr::Eval(Frame* f) const
|
||||||
{
|
{
|
||||||
Val* v;
|
Val* v;
|
||||||
|
@ -410,11 +398,6 @@ void ConstExpr::ExprDescribe(ODesc* d) const
|
||||||
val->Describe(d);
|
val->Describe(d);
|
||||||
}
|
}
|
||||||
|
|
||||||
Expr* ConstExpr::Simplify(SimplifyType /* simp_type */)
|
|
||||||
{
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
|
|
||||||
Val* ConstExpr::Eval(Frame* /* f */) const
|
Val* ConstExpr::Eval(Frame* /* f */) const
|
||||||
{
|
{
|
||||||
return Value()->Ref();
|
return Value()->Ref();
|
||||||
|
@ -457,16 +440,6 @@ UnaryExpr::~UnaryExpr()
|
||||||
Unref(op);
|
Unref(op);
|
||||||
}
|
}
|
||||||
|
|
||||||
Expr* UnaryExpr::Simplify(SimplifyType simp_type)
|
|
||||||
{
|
|
||||||
if ( IsError() )
|
|
||||||
return this;
|
|
||||||
|
|
||||||
op = simplify_expr(op, simp_type);
|
|
||||||
Canonicize();
|
|
||||||
return DoSimplify();
|
|
||||||
}
|
|
||||||
|
|
||||||
Val* UnaryExpr::Eval(Frame* f) const
|
Val* UnaryExpr::Eval(Frame* f) const
|
||||||
{
|
{
|
||||||
if ( IsError() )
|
if ( IsError() )
|
||||||
|
@ -516,11 +489,6 @@ TraversalCode UnaryExpr::Traverse(TraversalCallback* cb) const
|
||||||
HANDLE_TC_EXPR_POST(tc);
|
HANDLE_TC_EXPR_POST(tc);
|
||||||
}
|
}
|
||||||
|
|
||||||
Expr* UnaryExpr::DoSimplify()
|
|
||||||
{
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
|
|
||||||
Val* UnaryExpr::Fold(Val* v) const
|
Val* UnaryExpr::Fold(Val* v) const
|
||||||
{
|
{
|
||||||
return v->Ref();
|
return v->Ref();
|
||||||
|
@ -573,19 +541,6 @@ BinaryExpr::~BinaryExpr()
|
||||||
Unref(op2);
|
Unref(op2);
|
||||||
}
|
}
|
||||||
|
|
||||||
Expr* BinaryExpr::Simplify(SimplifyType /* simp_type */)
|
|
||||||
{
|
|
||||||
if ( IsError() )
|
|
||||||
return this;
|
|
||||||
|
|
||||||
SimplifyOps();
|
|
||||||
|
|
||||||
if ( BothConst() )
|
|
||||||
return new ConstExpr(Fold(op1->ExprVal(), op2->ExprVal()));
|
|
||||||
else
|
|
||||||
return DoSimplify();
|
|
||||||
}
|
|
||||||
|
|
||||||
Val* BinaryExpr::Eval(Frame* f) const
|
Val* BinaryExpr::Eval(Frame* f) const
|
||||||
{
|
{
|
||||||
if ( IsError() )
|
if ( IsError() )
|
||||||
|
@ -687,11 +642,6 @@ TraversalCode BinaryExpr::Traverse(TraversalCallback* cb) const
|
||||||
HANDLE_TC_EXPR_POST(tc);
|
HANDLE_TC_EXPR_POST(tc);
|
||||||
}
|
}
|
||||||
|
|
||||||
Expr* BinaryExpr::DoSimplify()
|
|
||||||
{
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
|
|
||||||
void BinaryExpr::ExprDescribe(ODesc* d) const
|
void BinaryExpr::ExprDescribe(ODesc* d) const
|
||||||
{
|
{
|
||||||
op1->Describe(d);
|
op1->Describe(d);
|
||||||
|
@ -703,13 +653,6 @@ void BinaryExpr::ExprDescribe(ODesc* d) const
|
||||||
op2->Describe(d);
|
op2->Describe(d);
|
||||||
}
|
}
|
||||||
|
|
||||||
void BinaryExpr::SimplifyOps()
|
|
||||||
{
|
|
||||||
op1 = simplify_expr(op1, SIMPLIFY_GENERAL);
|
|
||||||
op2 = simplify_expr(op2, SIMPLIFY_GENERAL);
|
|
||||||
Canonicize();
|
|
||||||
}
|
|
||||||
|
|
||||||
Val* BinaryExpr::Fold(Val* v1, Val* v2) const
|
Val* BinaryExpr::Fold(Val* v1, Val* v2) const
|
||||||
{
|
{
|
||||||
InternalTypeTag it = v1->Type()->InternalType();
|
InternalTypeTag it = v1->Type()->InternalType();
|
||||||
|
@ -1147,21 +1090,6 @@ NotExpr::NotExpr(Expr* arg_op) : UnaryExpr(EXPR_NOT, arg_op)
|
||||||
SetType(base_type(TYPE_BOOL));
|
SetType(base_type(TYPE_BOOL));
|
||||||
}
|
}
|
||||||
|
|
||||||
Expr* NotExpr::DoSimplify()
|
|
||||||
{
|
|
||||||
op = simplify_expr(op, SIMPLIFY_GENERAL);
|
|
||||||
Canonicize();
|
|
||||||
|
|
||||||
if ( op->Tag() == EXPR_NOT )
|
|
||||||
// !!x == x
|
|
||||||
return ((NotExpr*) op)->Op()->Ref();
|
|
||||||
|
|
||||||
if ( op->IsConst() )
|
|
||||||
return new ConstExpr(Fold(op->ExprVal()));
|
|
||||||
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
|
|
||||||
Val* NotExpr::Fold(Val* v) const
|
Val* NotExpr::Fold(Val* v) const
|
||||||
{
|
{
|
||||||
return new Val(! v->InternalInt(), type->Tag());
|
return new Val(! v->InternalInt(), type->Tag());
|
||||||
|
@ -1207,22 +1135,6 @@ PosExpr::PosExpr(Expr* arg_op) : UnaryExpr(EXPR_POSITIVE, arg_op)
|
||||||
SetType(base_result_type);
|
SetType(base_result_type);
|
||||||
}
|
}
|
||||||
|
|
||||||
Expr* PosExpr::DoSimplify()
|
|
||||||
{
|
|
||||||
op = simplify_expr(op, SIMPLIFY_GENERAL);
|
|
||||||
Canonicize();
|
|
||||||
|
|
||||||
TypeTag t = op->Type()->Tag();
|
|
||||||
|
|
||||||
if ( t == TYPE_DOUBLE || t == TYPE_INTERVAL || t == TYPE_INT )
|
|
||||||
return op->Ref();
|
|
||||||
|
|
||||||
if ( op->IsConst() && ! is_vector(op->ExprVal()) )
|
|
||||||
return new ConstExpr(Fold(op->ExprVal()));
|
|
||||||
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
|
|
||||||
Val* PosExpr::Fold(Val* v) const
|
Val* PosExpr::Fold(Val* v) const
|
||||||
{
|
{
|
||||||
TypeTag t = v->Type()->Tag();
|
TypeTag t = v->Type()->Tag();
|
||||||
|
@ -1273,27 +1185,6 @@ NegExpr::NegExpr(Expr* arg_op) : UnaryExpr(EXPR_NEGATE, arg_op)
|
||||||
SetType(base_result_type);
|
SetType(base_result_type);
|
||||||
}
|
}
|
||||||
|
|
||||||
Expr* NegExpr::DoSimplify()
|
|
||||||
{
|
|
||||||
op = simplify_expr(op, SIMPLIFY_GENERAL);
|
|
||||||
Canonicize();
|
|
||||||
|
|
||||||
if ( op->Tag() == EXPR_NEGATE )
|
|
||||||
// -(-x) == x
|
|
||||||
return ((NegExpr*) op)->Op()->Ref();
|
|
||||||
|
|
||||||
if ( op->IsConst() && ! is_vector(op->ExprVal()) )
|
|
||||||
return new ConstExpr(Fold(op->ExprVal()));
|
|
||||||
|
|
||||||
if ( op->Tag() == EXPR_SUB )
|
|
||||||
{ // -(a-b) == b-a
|
|
||||||
SubExpr* s = (SubExpr*) op;
|
|
||||||
return new SubExpr(s->Op2()->Ref(), s->Op1()->Ref());
|
|
||||||
}
|
|
||||||
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
|
|
||||||
Val* NegExpr::Fold(Val* v) const
|
Val* NegExpr::Fold(Val* v) const
|
||||||
{
|
{
|
||||||
if ( v->Type()->Tag() == TYPE_DOUBLE )
|
if ( v->Type()->Tag() == TYPE_DOUBLE )
|
||||||
|
@ -1396,24 +1287,6 @@ AddExpr::AddExpr(Expr* arg_op1, Expr* arg_op2)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
Expr* AddExpr::DoSimplify()
|
|
||||||
{
|
|
||||||
// If there's a constant, then it's in op1, since Canonicize()
|
|
||||||
// makes sure of that.
|
|
||||||
if ( op1->IsZero() )
|
|
||||||
return op2->Ref();
|
|
||||||
|
|
||||||
else if ( op1->Tag() == EXPR_NEGATE )
|
|
||||||
// (-a)+b = b-a
|
|
||||||
return new AddExpr(op2->Ref(), ((NegExpr*) op1)->Op()->Ref());
|
|
||||||
|
|
||||||
else if ( op2->Tag() == EXPR_NEGATE )
|
|
||||||
// a+(-b) == a-b
|
|
||||||
return new SubExpr(op1->Ref(), ((NegExpr*) op2)->Op()->Ref());
|
|
||||||
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
|
|
||||||
void AddExpr::Canonicize()
|
void AddExpr::Canonicize()
|
||||||
{
|
{
|
||||||
if ( expr_greater(op2, op1) ||
|
if ( expr_greater(op2, op1) ||
|
||||||
|
@ -1532,21 +1405,6 @@ SubExpr::SubExpr(Expr* arg_op1, Expr* arg_op2)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
Expr* SubExpr::DoSimplify()
|
|
||||||
{
|
|
||||||
if ( op1->IsZero() )
|
|
||||||
return new NegExpr(op2->Ref());
|
|
||||||
|
|
||||||
else if ( op2->IsZero() )
|
|
||||||
return op1->Ref();
|
|
||||||
|
|
||||||
else if ( op2->Tag() == EXPR_NEGATE )
|
|
||||||
// a-(-b) = a+b
|
|
||||||
return new AddExpr(op1->Ref(), ((NegExpr*) op2)->Op()->Ref());
|
|
||||||
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
|
|
||||||
IMPLEMENT_SERIAL(SubExpr, SER_SUB_EXPR);
|
IMPLEMENT_SERIAL(SubExpr, SER_SUB_EXPR);
|
||||||
|
|
||||||
bool SubExpr::DoSerialize(SerialInfo* info) const
|
bool SubExpr::DoSerialize(SerialInfo* info) const
|
||||||
|
@ -1648,27 +1506,6 @@ TimesExpr::TimesExpr(Expr* arg_op1, Expr* arg_op2)
|
||||||
ExprError("requires arithmetic operands");
|
ExprError("requires arithmetic operands");
|
||||||
}
|
}
|
||||||
|
|
||||||
Expr* TimesExpr::DoSimplify()
|
|
||||||
{
|
|
||||||
// If there's a constant, then it's in op1, since Canonicize()
|
|
||||||
// makes sure of that.
|
|
||||||
if ( op1->IsConst() )
|
|
||||||
{
|
|
||||||
if ( op1->IsZero() )
|
|
||||||
{
|
|
||||||
if ( IsVector(op2->Type()->Tag()) )
|
|
||||||
return this;
|
|
||||||
else
|
|
||||||
return make_zero(type);
|
|
||||||
}
|
|
||||||
|
|
||||||
else if ( op1->IsOne() )
|
|
||||||
return op2->Ref();
|
|
||||||
}
|
|
||||||
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
|
|
||||||
void TimesExpr::Canonicize()
|
void TimesExpr::Canonicize()
|
||||||
{
|
{
|
||||||
if ( expr_greater(op2, op1) || op2->Type()->Tag() == TYPE_INTERVAL ||
|
if ( expr_greater(op2, op1) || op2->Type()->Tag() == TYPE_INTERVAL ||
|
||||||
|
@ -1741,31 +1578,6 @@ Val* DivideExpr::AddrFold(Val* v1, Val* v2) const
|
||||||
return new SubNetVal(v1->AsAddr(), mask);
|
return new SubNetVal(v1->AsAddr(), mask);
|
||||||
}
|
}
|
||||||
|
|
||||||
Expr* DivideExpr::DoSimplify()
|
|
||||||
{
|
|
||||||
if ( IsError() )
|
|
||||||
return this;
|
|
||||||
|
|
||||||
if ( op1->Type()->Tag() == TYPE_ADDR )
|
|
||||||
return this;
|
|
||||||
|
|
||||||
if ( is_vector(op1) || is_vector(op2) )
|
|
||||||
return this;
|
|
||||||
|
|
||||||
if ( op2->IsConst() )
|
|
||||||
{
|
|
||||||
if ( op2->IsOne() )
|
|
||||||
return op1->Ref();
|
|
||||||
else if ( op2->IsZero() )
|
|
||||||
Error("zero divisor");
|
|
||||||
}
|
|
||||||
|
|
||||||
else if ( same_expr(op1, op2) )
|
|
||||||
return make_one(type);
|
|
||||||
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
|
|
||||||
IMPLEMENT_SERIAL(DivideExpr, SER_DIVIDE_EXPR);
|
IMPLEMENT_SERIAL(DivideExpr, SER_DIVIDE_EXPR);
|
||||||
|
|
||||||
bool DivideExpr::DoSerialize(SerialInfo* info) const
|
bool DivideExpr::DoSerialize(SerialInfo* info) const
|
||||||
|
@ -1800,31 +1612,6 @@ ModExpr::ModExpr(Expr* arg_op1, Expr* arg_op2)
|
||||||
ExprError("requires integral operands");
|
ExprError("requires integral operands");
|
||||||
}
|
}
|
||||||
|
|
||||||
Expr* ModExpr::DoSimplify()
|
|
||||||
{
|
|
||||||
if ( IsError() )
|
|
||||||
return this;
|
|
||||||
|
|
||||||
TypeTag bt1 = op1->Type()->Tag();
|
|
||||||
TypeTag bt2 = op2->Type()->Tag();
|
|
||||||
|
|
||||||
if ( IsVector(bt1) || IsVector(bt2) )
|
|
||||||
return this;
|
|
||||||
|
|
||||||
if ( op2->IsConst() )
|
|
||||||
{
|
|
||||||
if ( op2->IsOne() )
|
|
||||||
return make_zero(type);
|
|
||||||
else if ( op2->IsZero() )
|
|
||||||
Error("zero modulus");
|
|
||||||
}
|
|
||||||
|
|
||||||
else if ( same_expr(op1, op2) )
|
|
||||||
return make_zero(type);
|
|
||||||
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
|
|
||||||
IMPLEMENT_SERIAL(ModExpr, SER_MOD_EXPR);
|
IMPLEMENT_SERIAL(ModExpr, SER_MOD_EXPR);
|
||||||
|
|
||||||
bool ModExpr::DoSerialize(SerialInfo* info) const
|
bool ModExpr::DoSerialize(SerialInfo* info) const
|
||||||
|
@ -2011,37 +1798,6 @@ Val* BoolExpr::Eval(Frame* f) const
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
Expr* BoolExpr::DoSimplify()
|
|
||||||
{
|
|
||||||
if ( op1->IsConst() && ! is_vector(op1) )
|
|
||||||
{
|
|
||||||
if ( op1->IsZero() )
|
|
||||||
// F && x or F || x
|
|
||||||
return (tag == EXPR_AND) ? make_zero(type) : op2->Ref();
|
|
||||||
else
|
|
||||||
// T && x or T || x
|
|
||||||
return (tag == EXPR_AND) ? op2->Ref() : make_one(type);
|
|
||||||
}
|
|
||||||
|
|
||||||
else if ( op2->IsConst() && ! is_vector(op2) )
|
|
||||||
{
|
|
||||||
if ( op1->IsZero() )
|
|
||||||
// x && F or x || F
|
|
||||||
return (tag == EXPR_AND) ? make_zero(type) : op1->Ref();
|
|
||||||
else
|
|
||||||
// x && T or x || T
|
|
||||||
return (tag == EXPR_AND) ? op1->Ref() : make_one(type);
|
|
||||||
}
|
|
||||||
|
|
||||||
else if ( same_expr(op1, op2) )
|
|
||||||
{
|
|
||||||
Warn("redundant boolean operation");
|
|
||||||
return op1->Ref();
|
|
||||||
}
|
|
||||||
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
|
|
||||||
IMPLEMENT_SERIAL(BoolExpr, SER_BOOL_EXPR);
|
IMPLEMENT_SERIAL(BoolExpr, SER_BOOL_EXPR);
|
||||||
|
|
||||||
bool BoolExpr::DoSerialize(SerialInfo* info) const
|
bool BoolExpr::DoSerialize(SerialInfo* info) const
|
||||||
|
@ -2128,22 +1884,6 @@ void EqExpr::Canonicize()
|
||||||
SwapOps();
|
SwapOps();
|
||||||
}
|
}
|
||||||
|
|
||||||
Expr* EqExpr::DoSimplify()
|
|
||||||
{
|
|
||||||
if ( same_expr(op1, op2) && ! is_vector(op1) )
|
|
||||||
{
|
|
||||||
if ( ! optimize )
|
|
||||||
Warn("redundant comparison");
|
|
||||||
|
|
||||||
if ( tag == EXPR_EQ )
|
|
||||||
return make_one(type);
|
|
||||||
else
|
|
||||||
return make_zero(type);
|
|
||||||
}
|
|
||||||
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
|
|
||||||
Val* EqExpr::Fold(Val* v1, Val* v2) const
|
Val* EqExpr::Fold(Val* v1, Val* v2) const
|
||||||
{
|
{
|
||||||
if ( op1->Type()->Tag() == TYPE_PATTERN )
|
if ( op1->Type()->Tag() == TYPE_PATTERN )
|
||||||
|
@ -2207,22 +1947,6 @@ RelExpr::RelExpr(BroExprTag arg_tag, Expr* arg_op1, Expr* arg_op2)
|
||||||
ExprError("illegal comparison");
|
ExprError("illegal comparison");
|
||||||
}
|
}
|
||||||
|
|
||||||
Expr* RelExpr::DoSimplify()
|
|
||||||
{
|
|
||||||
if ( same_expr(op1, op2) )
|
|
||||||
{
|
|
||||||
Warn("redundant comparison");
|
|
||||||
// Here we use the fact that the canonical form of
|
|
||||||
// a RelExpr only uses EXPR_LE or EXPR_LT.
|
|
||||||
if ( tag == EXPR_LE )
|
|
||||||
return make_one(type);
|
|
||||||
else
|
|
||||||
return make_zero(type);
|
|
||||||
}
|
|
||||||
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
|
|
||||||
void RelExpr::Canonicize()
|
void RelExpr::Canonicize()
|
||||||
{
|
{
|
||||||
if ( tag == EXPR_GT )
|
if ( tag == EXPR_GT )
|
||||||
|
@ -2314,25 +2038,6 @@ CondExpr::~CondExpr()
|
||||||
Unref(op3);
|
Unref(op3);
|
||||||
}
|
}
|
||||||
|
|
||||||
Expr* CondExpr::Simplify(SimplifyType /* simp_type */)
|
|
||||||
{
|
|
||||||
op1 = simplify_expr(op1, SIMPLIFY_GENERAL);
|
|
||||||
op2 = simplify_expr(op2, SIMPLIFY_GENERAL);
|
|
||||||
op3 = simplify_expr(op3, SIMPLIFY_GENERAL);
|
|
||||||
|
|
||||||
if ( op1->IsConst() && ! is_vector(op1) )
|
|
||||||
{
|
|
||||||
Val* v = op1->ExprVal();
|
|
||||||
return (v->IsZero() ? op3 : op2)->Ref();
|
|
||||||
}
|
|
||||||
|
|
||||||
if ( op1->Tag() == EXPR_NOT )
|
|
||||||
return new CondExpr(((NotExpr*) op1)->Op()->Ref(),
|
|
||||||
op3->Ref(), op2->Ref());
|
|
||||||
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
|
|
||||||
Val* CondExpr::Eval(Frame* f) const
|
Val* CondExpr::Eval(Frame* f) const
|
||||||
{
|
{
|
||||||
if ( ! is_vector(op1) )
|
if ( ! is_vector(op1) )
|
||||||
|
@ -2684,13 +2389,6 @@ bool AssignExpr::TypeCheckArithmetics(TypeTag bt1, TypeTag bt2)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
Expr* AssignExpr::Simplify(SimplifyType /* simp_type */)
|
|
||||||
{
|
|
||||||
op1 = simplify_expr(op1, SIMPLIFY_LHS);
|
|
||||||
op2 = simplify_expr(op2, SIMPLIFY_GENERAL);
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
|
|
||||||
Val* AssignExpr::Eval(Frame* f) const
|
Val* AssignExpr::Eval(Frame* f) const
|
||||||
{
|
{
|
||||||
if ( is_init )
|
if ( is_init )
|
||||||
|
@ -3006,13 +2704,6 @@ Expr* IndexExpr::MakeLvalue()
|
||||||
return new RefExpr(this);
|
return new RefExpr(this);
|
||||||
}
|
}
|
||||||
|
|
||||||
Expr* IndexExpr::Simplify(SimplifyType simp_type)
|
|
||||||
{
|
|
||||||
op1 = simplify_expr(op1, simp_type);
|
|
||||||
op2 = simplify_expr(op2, SIMPLIFY_GENERAL);
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
|
|
||||||
Val* IndexExpr::Eval(Frame* f) const
|
Val* IndexExpr::Eval(Frame* f) const
|
||||||
{
|
{
|
||||||
Val* v1 = op1->Eval(f);
|
Val* v1 = op1->Eval(f);
|
||||||
|
@ -3264,12 +2955,6 @@ Expr* FieldExpr::MakeLvalue()
|
||||||
return new RefExpr(this);
|
return new RefExpr(this);
|
||||||
}
|
}
|
||||||
|
|
||||||
Expr* FieldExpr::Simplify(SimplifyType simp_type)
|
|
||||||
{
|
|
||||||
op = simplify_expr(op, simp_type);
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
|
|
||||||
int FieldExpr::CanDel() const
|
int FieldExpr::CanDel() const
|
||||||
{
|
{
|
||||||
return td->FindAttr(ATTR_DEFAULT) || td->FindAttr(ATTR_OPTIONAL);
|
return td->FindAttr(ATTR_DEFAULT) || td->FindAttr(ATTR_OPTIONAL);
|
||||||
|
@ -3995,73 +3680,6 @@ ArithCoerceExpr::ArithCoerceExpr(Expr* arg_op, TypeTag t)
|
||||||
ExprError("bad coercion value");
|
ExprError("bad coercion value");
|
||||||
}
|
}
|
||||||
|
|
||||||
Expr* ArithCoerceExpr::DoSimplify()
|
|
||||||
{
|
|
||||||
if ( is_vector(op) )
|
|
||||||
return this;
|
|
||||||
|
|
||||||
InternalTypeTag my_int = type->InternalType();
|
|
||||||
InternalTypeTag op_int = op->Type()->InternalType();
|
|
||||||
|
|
||||||
if ( my_int == TYPE_INTERNAL_UNSIGNED )
|
|
||||||
my_int = TYPE_INTERNAL_INT;
|
|
||||||
if ( op_int == TYPE_INTERNAL_UNSIGNED )
|
|
||||||
op_int = TYPE_INTERNAL_INT;
|
|
||||||
|
|
||||||
if ( my_int == op_int )
|
|
||||||
return op->Ref();
|
|
||||||
|
|
||||||
if ( op->IsConst() )
|
|
||||||
{
|
|
||||||
if ( my_int == TYPE_INTERNAL_INT )
|
|
||||||
{
|
|
||||||
if ( op_int != TYPE_INTERNAL_DOUBLE )
|
|
||||||
Internal("bad coercion in CoerceExpr::DoSimplify");
|
|
||||||
double d = op->ExprVal()->InternalDouble();
|
|
||||||
bro_int_t i = bro_int_t(d);
|
|
||||||
|
|
||||||
if ( i < 0 &&
|
|
||||||
type->InternalType() == TYPE_INTERNAL_UNSIGNED )
|
|
||||||
Warn("coercion produces negative count value");
|
|
||||||
|
|
||||||
if ( d != double(i) )
|
|
||||||
Warn("coercion loses precision");
|
|
||||||
|
|
||||||
return new ConstExpr(new Val(i, type->Tag()));
|
|
||||||
}
|
|
||||||
|
|
||||||
if ( my_int == TYPE_INTERNAL_DOUBLE )
|
|
||||||
{
|
|
||||||
if ( op_int == TYPE_INTERNAL_INT )
|
|
||||||
{
|
|
||||||
bro_int_t i = op->ExprVal()->InternalInt();
|
|
||||||
double d = double(i);
|
|
||||||
|
|
||||||
if ( i != bro_int_t(d) )
|
|
||||||
Warn("coercion loses precision");
|
|
||||||
|
|
||||||
return new ConstExpr(new Val(d, type->Tag()));
|
|
||||||
}
|
|
||||||
|
|
||||||
if ( op_int == TYPE_INTERNAL_UNSIGNED )
|
|
||||||
{
|
|
||||||
bro_uint_t u = op->ExprVal()->InternalUnsigned();
|
|
||||||
double d = double(u);
|
|
||||||
|
|
||||||
if ( u != (bro_uint_t) (d) )
|
|
||||||
Warn("coercion loses precision");
|
|
||||||
|
|
||||||
return new ConstExpr(new Val(d, type->Tag()));
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
Internal("bad coercion in CoerceExpr::DoSimplify");
|
|
||||||
}
|
|
||||||
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
|
|
||||||
Val* ArithCoerceExpr::FoldSingleVal(Val* v, InternalTypeTag t) const
|
Val* ArithCoerceExpr::FoldSingleVal(Val* v, InternalTypeTag t) const
|
||||||
{
|
{
|
||||||
switch ( t ) {
|
switch ( t ) {
|
||||||
|
@ -4550,22 +4168,6 @@ int ScheduleExpr::IsPure() const
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
Expr* ScheduleExpr::Simplify(SimplifyType simp_type)
|
|
||||||
{
|
|
||||||
when = when->Simplify(simp_type);
|
|
||||||
Expr* generic_event = event->Simplify(simp_type);
|
|
||||||
|
|
||||||
if ( ! generic_event )
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
if ( generic_event->Tag() != EXPR_CALL )
|
|
||||||
Internal("bad event type in ScheduleExpr::Simplify");
|
|
||||||
|
|
||||||
event = (EventExpr*) generic_event;
|
|
||||||
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
|
|
||||||
Val* ScheduleExpr::Eval(Frame* f) const
|
Val* ScheduleExpr::Eval(Frame* f) const
|
||||||
{
|
{
|
||||||
if ( terminating )
|
if ( terminating )
|
||||||
|
@ -4898,20 +4500,6 @@ int CallExpr::IsPure() const
|
||||||
return pure;
|
return pure;
|
||||||
}
|
}
|
||||||
|
|
||||||
Expr* CallExpr::Simplify(SimplifyType /* simp_type */)
|
|
||||||
{
|
|
||||||
if ( IsError() )
|
|
||||||
return this;
|
|
||||||
|
|
||||||
func = simplify_expr(func, SIMPLIFY_GENERAL);
|
|
||||||
args = simplify_expr_list(args, SIMPLIFY_GENERAL);
|
|
||||||
|
|
||||||
if ( IsPure() )
|
|
||||||
return new ConstExpr(Eval(0));
|
|
||||||
else
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
|
|
||||||
Val* CallExpr::Eval(Frame* f) const
|
Val* CallExpr::Eval(Frame* f) const
|
||||||
{
|
{
|
||||||
if ( IsError() )
|
if ( IsError() )
|
||||||
|
@ -5064,14 +4652,6 @@ EventExpr::~EventExpr()
|
||||||
Unref(args);
|
Unref(args);
|
||||||
}
|
}
|
||||||
|
|
||||||
Expr* EventExpr::Simplify(SimplifyType /* simp_type */)
|
|
||||||
{
|
|
||||||
if ( ! IsError() )
|
|
||||||
args = simplify_expr_list(args, SIMPLIFY_GENERAL);
|
|
||||||
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
|
|
||||||
Val* EventExpr::Eval(Frame* f) const
|
Val* EventExpr::Eval(Frame* f) const
|
||||||
{
|
{
|
||||||
if ( IsError() )
|
if ( IsError() )
|
||||||
|
@ -5178,17 +4758,6 @@ int ListExpr::AllConst() const
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
Expr* ListExpr::Simplify(SimplifyType /* simp_type */)
|
|
||||||
{
|
|
||||||
loop_over_list(exprs, i)
|
|
||||||
exprs.replace(i, simplify_expr(exprs[i], SIMPLIFY_GENERAL));
|
|
||||||
|
|
||||||
// Note that we do *not* simplify a list with one element
|
|
||||||
// to just that element. The assumption that simplify_expr(ListExpr*)
|
|
||||||
// returns a ListExpr* is widespread.
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
|
|
||||||
Val* ListExpr::Eval(Frame* f) const
|
Val* ListExpr::Eval(Frame* f) const
|
||||||
{
|
{
|
||||||
ListVal* v = new ListVal(TYPE_ANY);
|
ListVal* v = new ListVal(TYPE_ANY);
|
||||||
|
@ -5820,25 +5389,6 @@ int check_and_promote_exprs_to_type(ListExpr*& elements, BroType* type)
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
Expr* simplify_expr(Expr* e, SimplifyType simp_type)
|
|
||||||
{
|
|
||||||
if ( ! e )
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
for ( Expr* s = e->Simplify(simp_type); s != e; s = e->Simplify(simp_type) )
|
|
||||||
{
|
|
||||||
Unref(e);
|
|
||||||
e = s;
|
|
||||||
}
|
|
||||||
|
|
||||||
return e;
|
|
||||||
}
|
|
||||||
|
|
||||||
ListExpr* simplify_expr_list(ListExpr* l, SimplifyType simp_type)
|
|
||||||
{
|
|
||||||
return (ListExpr*) simplify_expr(l, simp_type);
|
|
||||||
}
|
|
||||||
|
|
||||||
val_list* eval_list(Frame* f, const ListExpr* l)
|
val_list* eval_list(Frame* f, const ListExpr* l)
|
||||||
{
|
{
|
||||||
const expr_list& e = l->Exprs();
|
const expr_list& e = l->Exprs();
|
||||||
|
@ -5864,129 +5414,6 @@ val_list* eval_list(Frame* f, const ListExpr* l)
|
||||||
return v;
|
return v;
|
||||||
}
|
}
|
||||||
|
|
||||||
int same_expr(const Expr* e1, const Expr* e2)
|
|
||||||
{
|
|
||||||
if ( e1 == e2 )
|
|
||||||
return 1;
|
|
||||||
|
|
||||||
if ( e1->Tag() != e2->Tag() || ! same_type(e1->Type(), e2->Type()) )
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
if ( e1->IsError() || e2->IsError() )
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
switch ( e1->Tag() ) {
|
|
||||||
case EXPR_NAME:
|
|
||||||
{
|
|
||||||
const NameExpr* n1 = (NameExpr*) e1;
|
|
||||||
const NameExpr* n2 = (NameExpr*) e2;
|
|
||||||
return n1->Id() == n2->Id();
|
|
||||||
}
|
|
||||||
|
|
||||||
case EXPR_CONST:
|
|
||||||
{
|
|
||||||
const ConstExpr* c1 = (ConstExpr*) e1;
|
|
||||||
const ConstExpr* c2 = (ConstExpr*) e2;
|
|
||||||
return same_val(c1->Value(), c2->Value());
|
|
||||||
}
|
|
||||||
|
|
||||||
case EXPR_INCR:
|
|
||||||
case EXPR_DECR:
|
|
||||||
case EXPR_NOT:
|
|
||||||
case EXPR_NEGATE:
|
|
||||||
case EXPR_POSITIVE:
|
|
||||||
case EXPR_REF:
|
|
||||||
case EXPR_RECORD_CONSTRUCTOR:
|
|
||||||
case EXPR_TABLE_CONSTRUCTOR:
|
|
||||||
case EXPR_SET_CONSTRUCTOR:
|
|
||||||
case EXPR_VECTOR_CONSTRUCTOR:
|
|
||||||
case EXPR_FIELD_ASSIGN:
|
|
||||||
case EXPR_ARITH_COERCE:
|
|
||||||
case EXPR_RECORD_COERCE:
|
|
||||||
case EXPR_TABLE_COERCE:
|
|
||||||
case EXPR_FLATTEN:
|
|
||||||
{
|
|
||||||
const UnaryExpr* u1 = (UnaryExpr*) e1;
|
|
||||||
const UnaryExpr* u2 = (UnaryExpr*) e2;
|
|
||||||
return same_expr(u1->Op(), u2->Op());
|
|
||||||
}
|
|
||||||
|
|
||||||
case EXPR_FIELD:
|
|
||||||
{
|
|
||||||
const FieldExpr* f1 = (FieldExpr*) e1;
|
|
||||||
const FieldExpr* f2 = (FieldExpr*) e2;
|
|
||||||
return same_expr(f1->Op(), f2->Op()) &&
|
|
||||||
f1->Field() == f2->Field();
|
|
||||||
}
|
|
||||||
|
|
||||||
case EXPR_SCHEDULE:
|
|
||||||
{
|
|
||||||
const ScheduleExpr* s1 = (ScheduleExpr*) e1;
|
|
||||||
const ScheduleExpr* s2 = (ScheduleExpr*) e2;
|
|
||||||
return same_expr(s1->When(), s2->When()) &&
|
|
||||||
same_expr(s1->Event(), s2->Event());
|
|
||||||
}
|
|
||||||
|
|
||||||
case EXPR_ADD:
|
|
||||||
case EXPR_ADD_TO:
|
|
||||||
case EXPR_SUB:
|
|
||||||
case EXPR_REMOVE_FROM:
|
|
||||||
case EXPR_TIMES:
|
|
||||||
case EXPR_DIVIDE:
|
|
||||||
case EXPR_MOD:
|
|
||||||
case EXPR_AND:
|
|
||||||
case EXPR_OR:
|
|
||||||
case EXPR_LT:
|
|
||||||
case EXPR_LE:
|
|
||||||
case EXPR_EQ:
|
|
||||||
case EXPR_NE:
|
|
||||||
case EXPR_GE:
|
|
||||||
case EXPR_GT:
|
|
||||||
case EXPR_ASSIGN:
|
|
||||||
case EXPR_MATCH:
|
|
||||||
case EXPR_INDEX:
|
|
||||||
case EXPR_IN:
|
|
||||||
{
|
|
||||||
const BinaryExpr* b1 = (BinaryExpr*) e1;
|
|
||||||
const BinaryExpr* b2 = (BinaryExpr*) e2;
|
|
||||||
return same_expr(b1->Op1(), b2->Op1()) &&
|
|
||||||
same_expr(b1->Op2(), b2->Op2());
|
|
||||||
}
|
|
||||||
|
|
||||||
case EXPR_LIST:
|
|
||||||
{
|
|
||||||
const ListExpr* l1 = (ListExpr*) e1;
|
|
||||||
const ListExpr* l2 = (ListExpr*) e2;
|
|
||||||
|
|
||||||
const expr_list& le1 = l1->Exprs();
|
|
||||||
const expr_list& le2 = l2->Exprs();
|
|
||||||
|
|
||||||
if ( le1.length() != le2.length() )
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
loop_over_list(le1, i)
|
|
||||||
if ( ! same_expr(le1[i], le2[i]) )
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
case EXPR_CALL:
|
|
||||||
{
|
|
||||||
const CallExpr* c1 = (CallExpr*) e1;
|
|
||||||
const CallExpr* c2 = (CallExpr*) e2;
|
|
||||||
|
|
||||||
return same_expr(c1->Func(), c2->Func()) &&
|
|
||||||
c1->IsPure() && same_expr(c1->Args(), c2->Args());
|
|
||||||
}
|
|
||||||
|
|
||||||
default:
|
|
||||||
reporter->InternalError("bad tag in same_expr()");
|
|
||||||
}
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
int expr_greater(const Expr* e1, const Expr* e2)
|
int expr_greater(const Expr* e1, const Expr* e2)
|
||||||
{
|
{
|
||||||
return int(e1->Tag()) > int(e2->Tag());
|
return int(e1->Tag()) > int(e2->Tag());
|
||||||
|
|
69
src/Expr.h
69
src/Expr.h
|
@ -47,11 +47,6 @@ typedef enum {
|
||||||
#define NUM_EXPRS (int(EXPR_FLATTEN) + 1)
|
#define NUM_EXPRS (int(EXPR_FLATTEN) + 1)
|
||||||
} BroExprTag;
|
} BroExprTag;
|
||||||
|
|
||||||
typedef enum {
|
|
||||||
SIMPLIFY_GENERAL, // regular simplification
|
|
||||||
SIMPLIFY_LHS, // simplify as the LHS of an assignment
|
|
||||||
} SimplifyType;
|
|
||||||
|
|
||||||
extern const char* expr_name(BroExprTag t);
|
extern const char* expr_name(BroExprTag t);
|
||||||
|
|
||||||
class Stmt;
|
class Stmt;
|
||||||
|
@ -72,11 +67,6 @@ public:
|
||||||
|
|
||||||
Expr* Ref() { ::Ref(this); return this; }
|
Expr* Ref() { ::Ref(this); return this; }
|
||||||
|
|
||||||
// Returns a fully simplified version of the expression (this
|
|
||||||
// may be the same expression, or a newly created one). simp_type
|
|
||||||
// gives the context of the simplification.
|
|
||||||
virtual Expr* Simplify(SimplifyType simp_type) = 0;
|
|
||||||
|
|
||||||
// Evaluates the expression and returns a corresponding Val*,
|
// Evaluates the expression and returns a corresponding Val*,
|
||||||
// or nil if the expression's value isn't fixed.
|
// or nil if the expression's value isn't fixed.
|
||||||
virtual Val* Eval(Frame* f) const = 0;
|
virtual Val* Eval(Frame* f) const = 0;
|
||||||
|
@ -230,7 +220,6 @@ public:
|
||||||
|
|
||||||
ID* Id() const { return id; }
|
ID* Id() const { return id; }
|
||||||
|
|
||||||
Expr* Simplify(SimplifyType simp_type);
|
|
||||||
Val* Eval(Frame* f) const;
|
Val* Eval(Frame* f) const;
|
||||||
void Assign(Frame* f, Val* v, Opcode op = OP_ASSIGN);
|
void Assign(Frame* f, Val* v, Opcode op = OP_ASSIGN);
|
||||||
Expr* MakeLvalue();
|
Expr* MakeLvalue();
|
||||||
|
@ -257,7 +246,6 @@ public:
|
||||||
|
|
||||||
Val* Value() const { return val; }
|
Val* Value() const { return val; }
|
||||||
|
|
||||||
Expr* Simplify(SimplifyType simp_type);
|
|
||||||
Val* Eval(Frame* f) const;
|
Val* Eval(Frame* f) const;
|
||||||
|
|
||||||
TraversalCode Traverse(TraversalCallback* cb) const;
|
TraversalCode Traverse(TraversalCallback* cb) const;
|
||||||
|
@ -276,9 +264,6 @@ class UnaryExpr : public Expr {
|
||||||
public:
|
public:
|
||||||
Expr* Op() const { return op; }
|
Expr* Op() const { return op; }
|
||||||
|
|
||||||
// Simplifies the operand and calls DoSimplify().
|
|
||||||
virtual Expr* Simplify(SimplifyType simp_type);
|
|
||||||
|
|
||||||
// UnaryExpr::Eval correctly handles vector types. Any child
|
// UnaryExpr::Eval correctly handles vector types. Any child
|
||||||
// class that overrides Eval() should be modified to handle
|
// class that overrides Eval() should be modified to handle
|
||||||
// vectors correctly as necessary.
|
// vectors correctly as necessary.
|
||||||
|
@ -297,10 +282,6 @@ protected:
|
||||||
|
|
||||||
void ExprDescribe(ODesc* d) const;
|
void ExprDescribe(ODesc* d) const;
|
||||||
|
|
||||||
// Can be overridden by subclasses that want to take advantage
|
|
||||||
// of UnaryExpr's Simplify() method.
|
|
||||||
virtual Expr* DoSimplify();
|
|
||||||
|
|
||||||
// Returns the expression folded using the given constant.
|
// Returns the expression folded using the given constant.
|
||||||
virtual Val* Fold(Val* v) const;
|
virtual Val* Fold(Val* v) const;
|
||||||
|
|
||||||
|
@ -314,9 +295,6 @@ public:
|
||||||
Expr* Op1() const { return op1; }
|
Expr* Op1() const { return op1; }
|
||||||
Expr* Op2() const { return op2; }
|
Expr* Op2() const { return op2; }
|
||||||
|
|
||||||
// Simplifies both operands, folds them if constant,
|
|
||||||
// otherwise calls DoSimplify().
|
|
||||||
virtual Expr* Simplify(SimplifyType simp_type);
|
|
||||||
int IsPure() const;
|
int IsPure() const;
|
||||||
|
|
||||||
// BinaryExpr::Eval correctly handles vector types. Any child
|
// BinaryExpr::Eval correctly handles vector types. Any child
|
||||||
|
@ -340,10 +318,6 @@ protected:
|
||||||
}
|
}
|
||||||
virtual ~BinaryExpr();
|
virtual ~BinaryExpr();
|
||||||
|
|
||||||
// Can be overridden by subclasses that want to take advantage
|
|
||||||
// of BinaryExpr's Simplify() method.
|
|
||||||
virtual Expr* DoSimplify();
|
|
||||||
|
|
||||||
// Returns the expression folded using the given constants.
|
// Returns the expression folded using the given constants.
|
||||||
virtual Val* Fold(Val* v1, Val* v2) const;
|
virtual Val* Fold(Val* v1, Val* v2) const;
|
||||||
|
|
||||||
|
@ -356,9 +330,6 @@ protected:
|
||||||
|
|
||||||
int BothConst() const { return op1->IsConst() && op2->IsConst(); }
|
int BothConst() const { return op1->IsConst() && op2->IsConst(); }
|
||||||
|
|
||||||
// Simplify both operands and canonicize.
|
|
||||||
void SimplifyOps();
|
|
||||||
|
|
||||||
// Exchange op1 and op2.
|
// Exchange op1 and op2.
|
||||||
void SwapOps();
|
void SwapOps();
|
||||||
|
|
||||||
|
@ -414,7 +385,6 @@ protected:
|
||||||
friend class Expr;
|
friend class Expr;
|
||||||
NotExpr() { }
|
NotExpr() { }
|
||||||
|
|
||||||
Expr* DoSimplify();
|
|
||||||
Val* Fold(Val* v) const;
|
Val* Fold(Val* v) const;
|
||||||
|
|
||||||
DECLARE_SERIAL(NotExpr);
|
DECLARE_SERIAL(NotExpr);
|
||||||
|
@ -428,7 +398,6 @@ protected:
|
||||||
friend class Expr;
|
friend class Expr;
|
||||||
PosExpr() { }
|
PosExpr() { }
|
||||||
|
|
||||||
Expr* DoSimplify();
|
|
||||||
Val* Fold(Val* v) const;
|
Val* Fold(Val* v) const;
|
||||||
|
|
||||||
DECLARE_SERIAL(PosExpr);
|
DECLARE_SERIAL(PosExpr);
|
||||||
|
@ -442,7 +411,6 @@ protected:
|
||||||
friend class Expr;
|
friend class Expr;
|
||||||
NegExpr() { }
|
NegExpr() { }
|
||||||
|
|
||||||
Expr* DoSimplify();
|
|
||||||
Val* Fold(Val* v) const;
|
Val* Fold(Val* v) const;
|
||||||
|
|
||||||
DECLARE_SERIAL(NegExpr);
|
DECLARE_SERIAL(NegExpr);
|
||||||
|
@ -470,8 +438,6 @@ protected:
|
||||||
friend class Expr;
|
friend class Expr;
|
||||||
AddExpr() { }
|
AddExpr() { }
|
||||||
|
|
||||||
Expr* DoSimplify();
|
|
||||||
|
|
||||||
DECLARE_SERIAL(AddExpr);
|
DECLARE_SERIAL(AddExpr);
|
||||||
|
|
||||||
};
|
};
|
||||||
|
@ -508,8 +474,6 @@ protected:
|
||||||
friend class Expr;
|
friend class Expr;
|
||||||
SubExpr() { }
|
SubExpr() { }
|
||||||
|
|
||||||
Expr* DoSimplify();
|
|
||||||
|
|
||||||
DECLARE_SERIAL(SubExpr);
|
DECLARE_SERIAL(SubExpr);
|
||||||
|
|
||||||
};
|
};
|
||||||
|
@ -523,8 +487,6 @@ protected:
|
||||||
friend class Expr;
|
friend class Expr;
|
||||||
TimesExpr() { }
|
TimesExpr() { }
|
||||||
|
|
||||||
Expr* DoSimplify();
|
|
||||||
|
|
||||||
DECLARE_SERIAL(TimesExpr);
|
DECLARE_SERIAL(TimesExpr);
|
||||||
|
|
||||||
};
|
};
|
||||||
|
@ -538,7 +500,6 @@ protected:
|
||||||
DivideExpr() { }
|
DivideExpr() { }
|
||||||
|
|
||||||
Val* AddrFold(Val* v1, Val* v2) const;
|
Val* AddrFold(Val* v1, Val* v2) const;
|
||||||
Expr* DoSimplify();
|
|
||||||
|
|
||||||
DECLARE_SERIAL(DivideExpr);
|
DECLARE_SERIAL(DivideExpr);
|
||||||
|
|
||||||
|
@ -552,8 +513,6 @@ protected:
|
||||||
friend class Expr;
|
friend class Expr;
|
||||||
ModExpr() { }
|
ModExpr() { }
|
||||||
|
|
||||||
Expr* DoSimplify();
|
|
||||||
|
|
||||||
DECLARE_SERIAL(ModExpr);
|
DECLARE_SERIAL(ModExpr);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -568,8 +527,6 @@ protected:
|
||||||
friend class Expr;
|
friend class Expr;
|
||||||
BoolExpr() { }
|
BoolExpr() { }
|
||||||
|
|
||||||
Expr* DoSimplify();
|
|
||||||
|
|
||||||
DECLARE_SERIAL(BoolExpr);
|
DECLARE_SERIAL(BoolExpr);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -582,8 +539,6 @@ protected:
|
||||||
friend class Expr;
|
friend class Expr;
|
||||||
EqExpr() { }
|
EqExpr() { }
|
||||||
|
|
||||||
Expr* DoSimplify();
|
|
||||||
|
|
||||||
Val* Fold(Val* v1, Val* v2) const;
|
Val* Fold(Val* v1, Val* v2) const;
|
||||||
|
|
||||||
DECLARE_SERIAL(EqExpr);
|
DECLARE_SERIAL(EqExpr);
|
||||||
|
@ -598,8 +553,6 @@ protected:
|
||||||
friend class Expr;
|
friend class Expr;
|
||||||
RelExpr() { }
|
RelExpr() { }
|
||||||
|
|
||||||
Expr* DoSimplify();
|
|
||||||
|
|
||||||
DECLARE_SERIAL(RelExpr);
|
DECLARE_SERIAL(RelExpr);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -612,7 +565,6 @@ public:
|
||||||
const Expr* Op2() const { return op2; }
|
const Expr* Op2() const { return op2; }
|
||||||
const Expr* Op3() const { return op3; }
|
const Expr* Op3() const { return op3; }
|
||||||
|
|
||||||
Expr* Simplify(SimplifyType simp_type);
|
|
||||||
Val* Eval(Frame* f) const;
|
Val* Eval(Frame* f) const;
|
||||||
int IsPure() const;
|
int IsPure() const;
|
||||||
|
|
||||||
|
@ -652,7 +604,6 @@ public:
|
||||||
AssignExpr(Expr* op1, Expr* op2, int is_init, Val* val = 0, attr_list* attrs = 0);
|
AssignExpr(Expr* op1, Expr* op2, int is_init, Val* val = 0, attr_list* attrs = 0);
|
||||||
virtual ~AssignExpr() { Unref(val); }
|
virtual ~AssignExpr() { Unref(val); }
|
||||||
|
|
||||||
Expr* Simplify(SimplifyType simp_type);
|
|
||||||
Val* Eval(Frame* f) const;
|
Val* Eval(Frame* f) const;
|
||||||
void EvalIntoAggregate(const BroType* t, Val* aggr, Frame* f) const;
|
void EvalIntoAggregate(const BroType* t, Val* aggr, Frame* f) const;
|
||||||
BroType* InitType() const;
|
BroType* InitType() const;
|
||||||
|
@ -683,7 +634,6 @@ public:
|
||||||
void Add(Frame* f);
|
void Add(Frame* f);
|
||||||
void Delete(Frame* f);
|
void Delete(Frame* f);
|
||||||
|
|
||||||
Expr* Simplify(SimplifyType simp_type);
|
|
||||||
void Assign(Frame* f, Val* v, Opcode op = OP_ASSIGN);
|
void Assign(Frame* f, Val* v, Opcode op = OP_ASSIGN);
|
||||||
Expr* MakeLvalue();
|
Expr* MakeLvalue();
|
||||||
|
|
||||||
|
@ -714,7 +664,6 @@ public:
|
||||||
|
|
||||||
int CanDel() const;
|
int CanDel() const;
|
||||||
|
|
||||||
Expr* Simplify(SimplifyType simp_type);
|
|
||||||
void Assign(Frame* f, Val* v, Opcode op = OP_ASSIGN);
|
void Assign(Frame* f, Val* v, Opcode op = OP_ASSIGN);
|
||||||
void Delete(Frame* f);
|
void Delete(Frame* f);
|
||||||
|
|
||||||
|
@ -866,8 +815,6 @@ protected:
|
||||||
friend class Expr;
|
friend class Expr;
|
||||||
ArithCoerceExpr() { }
|
ArithCoerceExpr() { }
|
||||||
|
|
||||||
Expr* DoSimplify();
|
|
||||||
|
|
||||||
Val* FoldSingleVal(Val* v, InternalTypeTag t) const;
|
Val* FoldSingleVal(Val* v, InternalTypeTag t) const;
|
||||||
Val* Fold(Val* v) const;
|
Val* Fold(Val* v) const;
|
||||||
|
|
||||||
|
@ -962,8 +909,6 @@ public:
|
||||||
|
|
||||||
int IsPure() const;
|
int IsPure() const;
|
||||||
|
|
||||||
Expr* Simplify(SimplifyType simp_type);
|
|
||||||
|
|
||||||
Val* Eval(Frame* f) const;
|
Val* Eval(Frame* f) const;
|
||||||
|
|
||||||
Expr* When() const { return when; }
|
Expr* When() const { return when; }
|
||||||
|
@ -1007,7 +952,6 @@ public:
|
||||||
|
|
||||||
int IsPure() const;
|
int IsPure() const;
|
||||||
|
|
||||||
Expr* Simplify(SimplifyType simp_type);
|
|
||||||
Val* Eval(Frame* f) const;
|
Val* Eval(Frame* f) const;
|
||||||
|
|
||||||
TraversalCode Traverse(TraversalCallback* cb) const;
|
TraversalCode Traverse(TraversalCallback* cb) const;
|
||||||
|
@ -1033,7 +977,6 @@ public:
|
||||||
ListExpr* Args() const { return args; }
|
ListExpr* Args() const { return args; }
|
||||||
EventHandlerPtr Handler() const { return handler; }
|
EventHandlerPtr Handler() const { return handler; }
|
||||||
|
|
||||||
Expr* Simplify(SimplifyType simp_type);
|
|
||||||
Val* Eval(Frame* f) const;
|
Val* Eval(Frame* f) const;
|
||||||
|
|
||||||
TraversalCode Traverse(TraversalCallback* cb) const;
|
TraversalCode Traverse(TraversalCallback* cb) const;
|
||||||
|
@ -1068,7 +1011,6 @@ public:
|
||||||
// True if the entire list represents constant values.
|
// True if the entire list represents constant values.
|
||||||
int AllConst() const;
|
int AllConst() const;
|
||||||
|
|
||||||
Expr* Simplify(SimplifyType simp_type);
|
|
||||||
Val* Eval(Frame* f) const;
|
Val* Eval(Frame* f) const;
|
||||||
|
|
||||||
BroType* InitType() const;
|
BroType* InitType() const;
|
||||||
|
@ -1127,21 +1069,10 @@ extern int check_and_promote_exprs(ListExpr*& elements, TypeList* types);
|
||||||
extern int check_and_promote_args(ListExpr*& args, RecordType* types);
|
extern int check_and_promote_args(ListExpr*& args, RecordType* types);
|
||||||
extern int check_and_promote_exprs_to_type(ListExpr*& elements, BroType* type);
|
extern int check_and_promote_exprs_to_type(ListExpr*& elements, BroType* type);
|
||||||
|
|
||||||
// Returns a fully simplified form of the expression. Note that passed
|
|
||||||
// expression and its subexpressions may be modified, Unref()'d, etc.
|
|
||||||
Expr* simplify_expr(Expr* e, SimplifyType simp_type);
|
|
||||||
|
|
||||||
// Returns a simplified ListExpr - guaranteed to still be a ListExpr,
|
|
||||||
// even if it only contains one expr.
|
|
||||||
ListExpr* simplify_expr_list(ListExpr* l, SimplifyType simp_type);
|
|
||||||
|
|
||||||
// Returns a ListExpr simplified down to a list a values, or a nil
|
// Returns a ListExpr simplified down to a list a values, or a nil
|
||||||
// pointer if they couldn't all be reduced.
|
// pointer if they couldn't all be reduced.
|
||||||
val_list* eval_list(Frame* f, const ListExpr* l);
|
val_list* eval_list(Frame* f, const ListExpr* l);
|
||||||
|
|
||||||
// Returns true if two expressions are identical.
|
|
||||||
extern int same_expr(const Expr* e1, const Expr* e2);
|
|
||||||
|
|
||||||
// Returns true if e1 is "greater" than e2 - here "greater" is just
|
// Returns true if e1 is "greater" than e2 - here "greater" is just
|
||||||
// a heuristic, used with commutative operators to put them into
|
// a heuristic, used with commutative operators to put them into
|
||||||
// a canonical form.
|
// a canonical form.
|
||||||
|
|
369
src/Stmt.cc
369
src/Stmt.cc
|
@ -79,11 +79,6 @@ bool Stmt::SetLocationInfo(const Location* start, const Location* end)
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
Stmt* Stmt::Simplify()
|
|
||||||
{
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
|
|
||||||
int Stmt::IsPure() const
|
int Stmt::IsPure() const
|
||||||
{
|
{
|
||||||
return 0;
|
return 0;
|
||||||
|
@ -201,18 +196,6 @@ Val* ExprListStmt::Exec(Frame* f, stmt_flow_type& flow) const
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
Stmt* ExprListStmt::Simplify()
|
|
||||||
{
|
|
||||||
l = simplify_expr_list(l, SIMPLIFY_GENERAL);
|
|
||||||
DoSimplify();
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
|
|
||||||
Stmt* ExprListStmt::DoSimplify()
|
|
||||||
{
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
|
|
||||||
void ExprListStmt::Describe(ODesc* d) const
|
void ExprListStmt::Describe(ODesc* d) const
|
||||||
{
|
{
|
||||||
Stmt::Describe(d);
|
Stmt::Describe(d);
|
||||||
|
@ -383,17 +366,6 @@ Val* ExprStmt::DoExec(Frame* /* f */, Val* /* v */, stmt_flow_type& /* flow */)
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
Stmt* ExprStmt::Simplify()
|
|
||||||
{
|
|
||||||
e = simplify_expr(e, SIMPLIFY_GENERAL);
|
|
||||||
return DoSimplify();
|
|
||||||
}
|
|
||||||
|
|
||||||
Stmt* ExprStmt::DoSimplify()
|
|
||||||
{
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
|
|
||||||
int ExprStmt::IsPure() const
|
int ExprStmt::IsPure() const
|
||||||
{
|
{
|
||||||
return ! e || e->IsPure();
|
return ! e || e->IsPure();
|
||||||
|
@ -490,33 +462,6 @@ Val* IfStmt::DoExec(Frame* f, Val* v, stmt_flow_type& flow) const
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
Stmt* IfStmt::DoSimplify()
|
|
||||||
{
|
|
||||||
s1 = simplify_stmt(s1);
|
|
||||||
s2 = simplify_stmt(s2);
|
|
||||||
|
|
||||||
if ( e->IsConst() )
|
|
||||||
{
|
|
||||||
if ( ! optimize )
|
|
||||||
Warn("constant in conditional");
|
|
||||||
|
|
||||||
return e->IsZero() ? s2->Ref() : s1->Ref();
|
|
||||||
}
|
|
||||||
|
|
||||||
if ( e->Tag() == EXPR_NOT )
|
|
||||||
{
|
|
||||||
Stmt* t = s1;
|
|
||||||
s1 = s2;
|
|
||||||
s2 = t;
|
|
||||||
|
|
||||||
e = new NotExpr(e);
|
|
||||||
|
|
||||||
return Simplify();
|
|
||||||
}
|
|
||||||
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
|
|
||||||
int IfStmt::IsPure() const
|
int IfStmt::IsPure() const
|
||||||
{
|
{
|
||||||
return e->IsPure() && s1->IsPure() && s2->IsPure();
|
return e->IsPure() && s1->IsPure() && s2->IsPure();
|
||||||
|
@ -602,7 +547,7 @@ static BroStmtTag get_last_stmt_tag(const Stmt* stmt)
|
||||||
}
|
}
|
||||||
|
|
||||||
Case::Case(ListExpr* c, Stmt* arg_s)
|
Case::Case(ListExpr* c, Stmt* arg_s)
|
||||||
: cases(simplify_expr_list(c, SIMPLIFY_GENERAL)), s(arg_s)
|
: cases(c), s(arg_s)
|
||||||
{
|
{
|
||||||
BroStmtTag t = get_last_stmt_tag(Body());
|
BroStmtTag t = get_last_stmt_tag(Body());
|
||||||
|
|
||||||
|
@ -729,8 +674,8 @@ SwitchStmt::SwitchStmt(Expr* index, case_list* arg_cases) :
|
||||||
|
|
||||||
loop_over_list(*cases, i)
|
loop_over_list(*cases, i)
|
||||||
{
|
{
|
||||||
const Case* c = (*cases)[i];
|
Case* c = (*cases)[i];
|
||||||
const ListExpr* le = c->Cases();
|
ListExpr* le = c->Cases();
|
||||||
|
|
||||||
if ( le )
|
if ( le )
|
||||||
{
|
{
|
||||||
|
@ -740,10 +685,53 @@ SwitchStmt::SwitchStmt(Expr* index, case_list* arg_cases) :
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
const expr_list& exprs = le->Exprs();
|
expr_list& exprs = le->Exprs();
|
||||||
|
|
||||||
loop_over_list(exprs, j)
|
loop_over_list(exprs, j)
|
||||||
{
|
{
|
||||||
|
if ( ! exprs[j]->IsConst() )
|
||||||
|
{
|
||||||
|
Expr* expr = exprs[j];
|
||||||
|
|
||||||
|
switch ( expr->Tag() ) {
|
||||||
|
// Simplify trivial unary plus/minus expressions on consts.
|
||||||
|
case EXPR_NEGATE:
|
||||||
|
{
|
||||||
|
NegExpr* ne = (NegExpr*)(expr);
|
||||||
|
|
||||||
|
if ( ne->Op()->IsConst() )
|
||||||
|
Unref(exprs.replace(j, new ConstExpr(ne->Eval(0))));
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
|
||||||
|
case EXPR_POSITIVE:
|
||||||
|
{
|
||||||
|
PosExpr* pe = (PosExpr*)(expr);
|
||||||
|
|
||||||
|
if ( pe->Op()->IsConst() )
|
||||||
|
Unref(exprs.replace(j, new ConstExpr(pe->Eval(0))));
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
|
||||||
|
case EXPR_NAME:
|
||||||
|
{
|
||||||
|
NameExpr* ne = (NameExpr*)(expr);
|
||||||
|
|
||||||
|
if ( ne->Id()->IsConst() )
|
||||||
|
{
|
||||||
|
Val* v = ne->Eval(0);
|
||||||
|
|
||||||
|
if ( v )
|
||||||
|
Unref(exprs.replace(j, new ConstExpr(v)));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
|
||||||
|
default:
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
if ( ! exprs[j]->IsConst() )
|
if ( ! exprs[j]->IsConst() )
|
||||||
exprs[j]->Error("case label expression isn't constant");
|
exprs[j]->Error("case label expression isn't constant");
|
||||||
else
|
else
|
||||||
|
@ -845,36 +833,6 @@ Val* SwitchStmt::DoExec(Frame* f, Val* v, stmt_flow_type& flow) const
|
||||||
return rval;
|
return rval;
|
||||||
}
|
}
|
||||||
|
|
||||||
Stmt* SwitchStmt::DoSimplify()
|
|
||||||
{
|
|
||||||
loop_over_list(*cases, i)
|
|
||||||
{
|
|
||||||
Case* c = (*cases)[i];
|
|
||||||
ListExpr* new_cases = simplify_expr_list(c->Cases(), SIMPLIFY_GENERAL);
|
|
||||||
Stmt* new_body = simplify_stmt(c->Body());
|
|
||||||
|
|
||||||
if ( new_cases != c->Cases() || new_body != c->Body() )
|
|
||||||
{
|
|
||||||
cases->replace(i, new Case(new_cases, new_body));
|
|
||||||
Unref(c);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if ( e->IsConst() )
|
|
||||||
{
|
|
||||||
// Could possibly remove all case labels before the one
|
|
||||||
// that will match, but may be tricky to tell if any
|
|
||||||
// subsequent ones can also be removed since it depends
|
|
||||||
// on the evaluation of the body executing a break/return
|
|
||||||
// statement. Then still need a way to bypass the lookup
|
|
||||||
// DoExec for it to be beneficial.
|
|
||||||
if ( ! optimize )
|
|
||||||
Warn("constant in switch");
|
|
||||||
}
|
|
||||||
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
|
|
||||||
int SwitchStmt::IsPure() const
|
int SwitchStmt::IsPure() const
|
||||||
{
|
{
|
||||||
if ( ! e->IsPure() )
|
if ( ! e->IsPure() )
|
||||||
|
@ -1212,17 +1170,6 @@ Val* WhileStmt::Exec(Frame* f, stmt_flow_type& flow) const
|
||||||
return rval;
|
return rval;
|
||||||
}
|
}
|
||||||
|
|
||||||
Stmt* WhileStmt::Simplify()
|
|
||||||
{
|
|
||||||
loop_condition = simplify_expr(loop_condition, SIMPLIFY_GENERAL);
|
|
||||||
|
|
||||||
if ( loop_condition->IsConst() && loop_condition->IsZero() )
|
|
||||||
return new NullStmt();
|
|
||||||
|
|
||||||
body = simplify_stmt(body);
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
|
|
||||||
IMPLEMENT_SERIAL(WhileStmt, SER_WHILE_STMT);
|
IMPLEMENT_SERIAL(WhileStmt, SER_WHILE_STMT);
|
||||||
|
|
||||||
bool WhileStmt::DoSerialize(SerialInfo* info) const
|
bool WhileStmt::DoSerialize(SerialInfo* info) const
|
||||||
|
@ -1416,21 +1363,6 @@ Val* ForStmt::DoExec(Frame* f, Val* v, stmt_flow_type& flow) const
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
Stmt* ForStmt::DoSimplify()
|
|
||||||
{
|
|
||||||
body = simplify_stmt(body);
|
|
||||||
|
|
||||||
if ( e->IsConst() )
|
|
||||||
{
|
|
||||||
const PDict(TableEntryVal)* vt = e->ExprVal()->AsTable();
|
|
||||||
|
|
||||||
if ( vt->Length() == 0 )
|
|
||||||
return new NullStmt();
|
|
||||||
}
|
|
||||||
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
|
|
||||||
int ForStmt::IsPure() const
|
int ForStmt::IsPure() const
|
||||||
{
|
{
|
||||||
return e->IsPure() && body->IsPure();
|
return e->IsPure() && body->IsPure();
|
||||||
|
@ -1774,20 +1706,6 @@ Val* StmtList::Exec(Frame* f, stmt_flow_type& flow) const
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
Stmt* StmtList::Simplify()
|
|
||||||
{
|
|
||||||
if ( stmts.length() == 0 )
|
|
||||||
return new NullStmt();
|
|
||||||
|
|
||||||
if ( stmts.length() == 1 )
|
|
||||||
return stmts[0]->Ref();
|
|
||||||
|
|
||||||
loop_over_list(stmts, i)
|
|
||||||
stmts.replace(i, simplify_stmt(stmts[i]));
|
|
||||||
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
|
|
||||||
int StmtList::IsPure() const
|
int StmtList::IsPure() const
|
||||||
{
|
{
|
||||||
loop_over_list(stmts, i)
|
loop_over_list(stmts, i)
|
||||||
|
@ -1909,17 +1827,6 @@ Val* EventBodyList::Exec(Frame* f, stmt_flow_type& flow) const
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
Stmt* EventBodyList::Simplify()
|
|
||||||
{
|
|
||||||
if ( stmts.length() <= 1 )
|
|
||||||
// Don't simplify these, we don't want to lose our
|
|
||||||
// "execute even across returns" property.
|
|
||||||
return this;
|
|
||||||
|
|
||||||
else
|
|
||||||
return StmtList::Simplify();
|
|
||||||
}
|
|
||||||
|
|
||||||
void EventBodyList::Describe(ODesc* d) const
|
void EventBodyList::Describe(ODesc* d) const
|
||||||
{
|
{
|
||||||
if ( d->IsReadable() && stmts.length() > 0 )
|
if ( d->IsReadable() && stmts.length() > 0 )
|
||||||
|
@ -2168,19 +2075,6 @@ Val* WhenStmt::Exec(Frame* f, stmt_flow_type& flow) const
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
Stmt* WhenStmt::Simplify()
|
|
||||||
{
|
|
||||||
cond = simplify_expr(cond, SIMPLIFY_GENERAL);
|
|
||||||
s1 = simplify_stmt(s1);
|
|
||||||
if ( s2 )
|
|
||||||
s2 = simplify_stmt(s2);
|
|
||||||
|
|
||||||
if ( cond->IsPure() )
|
|
||||||
Warn("non-varying expression in when clause");
|
|
||||||
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
|
|
||||||
int WhenStmt::IsPure() const
|
int WhenStmt::IsPure() const
|
||||||
{
|
{
|
||||||
return cond->IsPure() && s1->IsPure() && (! s2 || s2->IsPure());
|
return cond->IsPure() && s1->IsPure() && (! s2 || s2->IsPure());
|
||||||
|
@ -2276,172 +2170,3 @@ bool WhenStmt::DoUnserialize(UnserialInfo* info)
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
Stmt* simplify_stmt(Stmt* s)
|
|
||||||
{
|
|
||||||
for ( Stmt* ss = s->Simplify(); ss != s; ss = s->Simplify() )
|
|
||||||
{
|
|
||||||
Unref(s);
|
|
||||||
s = ss;
|
|
||||||
}
|
|
||||||
|
|
||||||
return s;
|
|
||||||
}
|
|
||||||
|
|
||||||
int same_stmt(const Stmt* s1, const Stmt* s2)
|
|
||||||
{
|
|
||||||
if ( s1 == s2 )
|
|
||||||
return 1;
|
|
||||||
|
|
||||||
if ( s1->Tag() != s2->Tag() )
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
switch ( s1->Tag() ) {
|
|
||||||
case STMT_PRINT:
|
|
||||||
{
|
|
||||||
const ListExpr* l1 = ((const ExprListStmt*) s1)->ExprList();
|
|
||||||
const ListExpr* l2 = ((const ExprListStmt*) s2)->ExprList();
|
|
||||||
return same_expr(l1, l2);
|
|
||||||
}
|
|
||||||
|
|
||||||
case STMT_ADD:
|
|
||||||
case STMT_DELETE:
|
|
||||||
case STMT_RETURN:
|
|
||||||
case STMT_EXPR:
|
|
||||||
case STMT_EVENT:
|
|
||||||
{
|
|
||||||
const ExprStmt* e1 = (const ExprStmt*) s1;
|
|
||||||
const ExprStmt* e2 = (const ExprStmt*) s2;
|
|
||||||
return same_expr(e1->StmtExpr(), e2->StmtExpr());
|
|
||||||
}
|
|
||||||
|
|
||||||
case STMT_FOR:
|
|
||||||
{
|
|
||||||
const ForStmt* f1 = (const ForStmt*) s1;
|
|
||||||
const ForStmt* f2 = (const ForStmt*) s2;
|
|
||||||
|
|
||||||
return f1->LoopVar() == f2->LoopVar() &&
|
|
||||||
same_expr(f1->LoopExpr(), f2->LoopExpr()) &&
|
|
||||||
same_stmt(f1->LoopBody(), f2->LoopBody());
|
|
||||||
}
|
|
||||||
|
|
||||||
case STMT_IF:
|
|
||||||
{
|
|
||||||
const IfStmt* i1 = (const IfStmt*) s1;
|
|
||||||
const IfStmt* i2 = (const IfStmt*) s2;
|
|
||||||
|
|
||||||
if ( ! same_expr(i1->StmtExpr(), i2->StmtExpr()) )
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
if ( i1->TrueBranch() || i2->TrueBranch() )
|
|
||||||
{
|
|
||||||
if ( ! i1->TrueBranch() || ! i2->TrueBranch() )
|
|
||||||
return 0;
|
|
||||||
if ( ! same_stmt(i1->TrueBranch(), i2->TrueBranch()) )
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
if ( i1->FalseBranch() || i2->FalseBranch() )
|
|
||||||
{
|
|
||||||
if ( ! i1->FalseBranch() || ! i2->FalseBranch() )
|
|
||||||
return 0;
|
|
||||||
if ( ! same_stmt(i1->FalseBranch(), i2->FalseBranch()) )
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
case STMT_SWITCH:
|
|
||||||
{
|
|
||||||
const SwitchStmt* sw1 = (const SwitchStmt*) s1;
|
|
||||||
const SwitchStmt* sw2 = (const SwitchStmt*) s2;
|
|
||||||
|
|
||||||
if ( ! same_expr(sw1->StmtExpr(), sw2->StmtExpr()) )
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
const case_list* c1 = sw1->Cases();
|
|
||||||
const case_list* c2 = sw1->Cases();
|
|
||||||
|
|
||||||
if ( c1->length() != c2->length() )
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
loop_over_list(*c1, i)
|
|
||||||
{
|
|
||||||
if ( ! same_expr((*c1)[i]->Cases(), (*c2)[i]->Cases()) )
|
|
||||||
return 0;
|
|
||||||
if ( ! same_stmt((*c1)[i]->Body(), (*c2)[i]->Body()) )
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
case STMT_LIST:
|
|
||||||
case STMT_EVENT_BODY_LIST:
|
|
||||||
{
|
|
||||||
const stmt_list& l1 = ((const StmtList*) s1)->Stmts();
|
|
||||||
const stmt_list& l2 = ((const StmtList*) s2)->Stmts();
|
|
||||||
|
|
||||||
if ( l1.length() != l2.length() )
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
loop_over_list(l1, i)
|
|
||||||
if ( ! same_stmt(l1[i], l2[i]) )
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
case STMT_INIT:
|
|
||||||
{
|
|
||||||
const id_list* i1 = ((const InitStmt*) s1)->Inits();
|
|
||||||
const id_list* i2 = ((const InitStmt*) s2)->Inits();
|
|
||||||
|
|
||||||
if ( i1->length() != i2->length() )
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
loop_over_list(*i1, i)
|
|
||||||
if ( (*i1)[i] != (*i2)[i] )
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
case STMT_WHEN:
|
|
||||||
{
|
|
||||||
const WhenStmt* w1 = (const WhenStmt*) s1;
|
|
||||||
const WhenStmt* w2 = (const WhenStmt*) s2;
|
|
||||||
|
|
||||||
if ( ! same_expr(w1->Cond(), w2->Cond()) )
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
if ( ! same_stmt(w1->Body(), w2->Body()) )
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
if ( w1->TimeoutBody() || w2->TimeoutBody() )
|
|
||||||
{
|
|
||||||
if ( ! w1->TimeoutBody() || ! w2->TimeoutBody() )
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
if ( ! same_expr(w1->TimeoutExpr(), w2->TimeoutExpr()) )
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
if ( ! same_stmt(w1->TimeoutBody(), w2->TimeoutBody()) )
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
case STMT_NEXT:
|
|
||||||
case STMT_BREAK:
|
|
||||||
case STMT_NULL:
|
|
||||||
return 1;
|
|
||||||
|
|
||||||
default:
|
|
||||||
reporter->Error("bad tag in same_stmt()");
|
|
||||||
}
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
21
src/Stmt.h
21
src/Stmt.h
|
@ -33,10 +33,6 @@ public:
|
||||||
{ return Stmt::SetLocationInfo(loc, loc); }
|
{ return Stmt::SetLocationInfo(loc, loc); }
|
||||||
bool SetLocationInfo(const Location* start, const Location* end);
|
bool SetLocationInfo(const Location* start, const Location* end);
|
||||||
|
|
||||||
// Returns a fully simplified version of the statement (this
|
|
||||||
// may be the same statement, or a newly created one).
|
|
||||||
virtual Stmt* Simplify();
|
|
||||||
|
|
||||||
// True if the statement has no side effects, false otherwise.
|
// True if the statement has no side effects, false otherwise.
|
||||||
virtual int IsPure() const;
|
virtual int IsPure() const;
|
||||||
|
|
||||||
|
@ -112,9 +108,6 @@ protected:
|
||||||
Val* Exec(Frame* f, stmt_flow_type& flow) const;
|
Val* Exec(Frame* f, stmt_flow_type& flow) const;
|
||||||
virtual Val* DoExec(val_list* vals, stmt_flow_type& flow) const = 0;
|
virtual Val* DoExec(val_list* vals, stmt_flow_type& flow) const = 0;
|
||||||
|
|
||||||
Stmt* Simplify();
|
|
||||||
virtual Stmt* DoSimplify();
|
|
||||||
|
|
||||||
void Describe(ODesc* d) const;
|
void Describe(ODesc* d) const;
|
||||||
void PrintVals(ODesc* d, val_list* vals, int offset) const;
|
void PrintVals(ODesc* d, val_list* vals, int offset) const;
|
||||||
|
|
||||||
|
@ -156,12 +149,8 @@ protected:
|
||||||
|
|
||||||
virtual Val* DoExec(Frame* f, Val* v, stmt_flow_type& flow) const;
|
virtual Val* DoExec(Frame* f, Val* v, stmt_flow_type& flow) const;
|
||||||
|
|
||||||
Stmt* Simplify();
|
|
||||||
int IsPure() const;
|
int IsPure() const;
|
||||||
|
|
||||||
// Called by Simplify(), after the expression's been simplified.
|
|
||||||
virtual Stmt* DoSimplify();
|
|
||||||
|
|
||||||
DECLARE_SERIAL(ExprStmt);
|
DECLARE_SERIAL(ExprStmt);
|
||||||
|
|
||||||
Expr* e;
|
Expr* e;
|
||||||
|
@ -184,7 +173,6 @@ protected:
|
||||||
IfStmt() { s1 = s2 = 0; }
|
IfStmt() { s1 = s2 = 0; }
|
||||||
|
|
||||||
Val* DoExec(Frame* f, Val* v, stmt_flow_type& flow) const;
|
Val* DoExec(Frame* f, Val* v, stmt_flow_type& flow) const;
|
||||||
Stmt* DoSimplify();
|
|
||||||
int IsPure() const;
|
int IsPure() const;
|
||||||
|
|
||||||
DECLARE_SERIAL(IfStmt);
|
DECLARE_SERIAL(IfStmt);
|
||||||
|
@ -237,7 +225,6 @@ protected:
|
||||||
SwitchStmt() { cases = 0; default_case_idx = -1; comp_hash = 0; }
|
SwitchStmt() { cases = 0; default_case_idx = -1; comp_hash = 0; }
|
||||||
|
|
||||||
Val* DoExec(Frame* f, Val* v, stmt_flow_type& flow) const;
|
Val* DoExec(Frame* f, Val* v, stmt_flow_type& flow) const;
|
||||||
Stmt* DoSimplify();
|
|
||||||
int IsPure() const;
|
int IsPure() const;
|
||||||
|
|
||||||
DECLARE_SERIAL(SwitchStmt);
|
DECLARE_SERIAL(SwitchStmt);
|
||||||
|
@ -329,7 +316,6 @@ protected:
|
||||||
{ loop_condition = 0; body = 0; }
|
{ loop_condition = 0; body = 0; }
|
||||||
|
|
||||||
Val* Exec(Frame* f, stmt_flow_type& flow) const;
|
Val* Exec(Frame* f, stmt_flow_type& flow) const;
|
||||||
Stmt* Simplify();
|
|
||||||
|
|
||||||
DECLARE_SERIAL(WhileStmt);
|
DECLARE_SERIAL(WhileStmt);
|
||||||
|
|
||||||
|
@ -359,7 +345,6 @@ protected:
|
||||||
ForStmt() { loop_vars = 0; body = 0; }
|
ForStmt() { loop_vars = 0; body = 0; }
|
||||||
|
|
||||||
Val* DoExec(Frame* f, Val* v, stmt_flow_type& flow) const;
|
Val* DoExec(Frame* f, Val* v, stmt_flow_type& flow) const;
|
||||||
Stmt* DoSimplify();
|
|
||||||
|
|
||||||
DECLARE_SERIAL(ForStmt);
|
DECLARE_SERIAL(ForStmt);
|
||||||
|
|
||||||
|
@ -442,7 +427,6 @@ public:
|
||||||
TraversalCode Traverse(TraversalCallback* cb) const;
|
TraversalCode Traverse(TraversalCallback* cb) const;
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
Stmt* Simplify();
|
|
||||||
int IsPure() const;
|
int IsPure() const;
|
||||||
|
|
||||||
DECLARE_SERIAL(StmtList);
|
DECLARE_SERIAL(StmtList);
|
||||||
|
@ -464,7 +448,6 @@ public:
|
||||||
// bool IsTopmost() { return topmost; }
|
// bool IsTopmost() { return topmost; }
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
Stmt* Simplify();
|
|
||||||
|
|
||||||
DECLARE_SERIAL(EventBodyList);
|
DECLARE_SERIAL(EventBodyList);
|
||||||
|
|
||||||
|
@ -522,7 +505,6 @@ public:
|
||||||
|
|
||||||
Val* Exec(Frame* f, stmt_flow_type& flow) const;
|
Val* Exec(Frame* f, stmt_flow_type& flow) const;
|
||||||
int IsPure() const;
|
int IsPure() const;
|
||||||
Stmt* Simplify();
|
|
||||||
|
|
||||||
const Expr* Cond() const { return cond; }
|
const Expr* Cond() const { return cond; }
|
||||||
const Stmt* Body() const { return s1; }
|
const Stmt* Body() const { return s1; }
|
||||||
|
@ -545,7 +527,4 @@ protected:
|
||||||
bool is_return;
|
bool is_return;
|
||||||
};
|
};
|
||||||
|
|
||||||
extern Stmt* simplify_stmt(Stmt* s);
|
|
||||||
extern int same_stmt(const Stmt* s1, const Stmt* s2);
|
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
|
@ -64,9 +64,6 @@ static void make_var(ID* id, BroType* t, init_class c, Expr* init,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if ( init && optimize )
|
|
||||||
init = init->Simplify(SIMPLIFY_GENERAL);
|
|
||||||
|
|
||||||
if ( t && t->IsSet() )
|
if ( t && t->IsSet() )
|
||||||
{ // Check for set with explicit elements.
|
{ // Check for set with explicit elements.
|
||||||
SetType* st = t->AsTableType()->AsSetType();
|
SetType* st = t->AsTableType()->AsSetType();
|
||||||
|
|
|
@ -46,6 +46,4 @@ extern vector<string> params;
|
||||||
class Stmt;
|
class Stmt;
|
||||||
extern Stmt* stmts; // global statements
|
extern Stmt* stmts; // global statements
|
||||||
|
|
||||||
extern int optimize;
|
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
|
@ -115,7 +115,6 @@ ProfileLogger* profiling_logger = 0;
|
||||||
ProfileLogger* segment_logger = 0;
|
ProfileLogger* segment_logger = 0;
|
||||||
SampleLogger* sample_logger = 0;
|
SampleLogger* sample_logger = 0;
|
||||||
int signal_val = 0;
|
int signal_val = 0;
|
||||||
int optimize = 0;
|
|
||||||
int do_notice_analysis = 0;
|
int do_notice_analysis = 0;
|
||||||
extern char version[];
|
extern char version[];
|
||||||
char* command_line_policy = 0;
|
char* command_line_policy = 0;
|
||||||
|
@ -192,7 +191,6 @@ void usage()
|
||||||
fprintf(stderr, " -I|--print-id <ID name> | print out given ID\n");
|
fprintf(stderr, " -I|--print-id <ID name> | print out given ID\n");
|
||||||
fprintf(stderr, " -K|--md5-hashkey <hashkey> | set key for MD5-keyed hashing\n");
|
fprintf(stderr, " -K|--md5-hashkey <hashkey> | set key for MD5-keyed hashing\n");
|
||||||
fprintf(stderr, " -N|--print-plugins | print available plugins and exit (-NN for verbose)\n");
|
fprintf(stderr, " -N|--print-plugins | print available plugins and exit (-NN for verbose)\n");
|
||||||
fprintf(stderr, " -O|--optimize | optimize policy script\n");
|
|
||||||
fprintf(stderr, " -P|--prime-dns | prime DNS\n");
|
fprintf(stderr, " -P|--prime-dns | prime DNS\n");
|
||||||
fprintf(stderr, " -Q|--time | print execution time summary to stderr\n");
|
fprintf(stderr, " -Q|--time | print execution time summary to stderr\n");
|
||||||
fprintf(stderr, " -R|--replay <events.bst> | replay events\n");
|
fprintf(stderr, " -R|--replay <events.bst> | replay events\n");
|
||||||
|
@ -496,7 +494,6 @@ int main(int argc, char** argv)
|
||||||
{"set-seed", required_argument, 0, 'J'},
|
{"set-seed", required_argument, 0, 'J'},
|
||||||
{"md5-hashkey", required_argument, 0, 'K'},
|
{"md5-hashkey", required_argument, 0, 'K'},
|
||||||
{"print-plugins", no_argument, 0, 'N'},
|
{"print-plugins", no_argument, 0, 'N'},
|
||||||
{"optimize", no_argument, 0, 'O'},
|
|
||||||
{"prime-dns", no_argument, 0, 'P'},
|
{"prime-dns", no_argument, 0, 'P'},
|
||||||
{"replay", required_argument, 0, 'R'},
|
{"replay", required_argument, 0, 'R'},
|
||||||
{"debug-rules", no_argument, 0, 'S'},
|
{"debug-rules", no_argument, 0, 'S'},
|
||||||
|
@ -659,10 +656,6 @@ int main(int argc, char** argv)
|
||||||
++print_plugins;
|
++print_plugins;
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 'O':
|
|
||||||
optimize = 1;
|
|
||||||
break;
|
|
||||||
|
|
||||||
case 'P':
|
case 'P':
|
||||||
if ( dns_type != DNS_DEFAULT )
|
if ( dns_type != DNS_DEFAULT )
|
||||||
usage();
|
usage();
|
||||||
|
|
|
@ -272,9 +272,6 @@ static bool has_attr(const attr_list* al, attr_tag tag)
|
||||||
bro:
|
bro:
|
||||||
decl_list stmt_list
|
decl_list stmt_list
|
||||||
{
|
{
|
||||||
if ( optimize )
|
|
||||||
$2 = $2->Simplify();
|
|
||||||
|
|
||||||
if ( stmts )
|
if ( stmts )
|
||||||
stmts->AsStmtList()->Stmts().append($2);
|
stmts->AsStmtList()->Stmts().append($2);
|
||||||
else
|
else
|
||||||
|
@ -1173,9 +1170,6 @@ func_body:
|
||||||
|
|
||||||
'}'
|
'}'
|
||||||
{
|
{
|
||||||
if ( optimize )
|
|
||||||
$4 = $4->Simplify();
|
|
||||||
|
|
||||||
end_func($4, $1);
|
end_func($4, $1);
|
||||||
}
|
}
|
||||||
;
|
;
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue