From 21614cd30d0f23f2535a6e7ffa8dce6dd008eaff Mon Sep 17 00:00:00 2001 From: Vern Paxson Date: Wed, 20 Jun 2018 09:49:29 -0700 Subject: [PATCH] basic code implemented, but there's a memory problem somehwere :-( --- src/Expr.cc | 47 ++++++++++++++++++++++++++++------------------- src/Expr.h | 3 +++ src/parse.y | 36 ++++++++++-------------------------- 3 files changed, 41 insertions(+), 45 deletions(-) diff --git a/src/Expr.cc b/src/Expr.cc index f5c8e66b50..d895e811ab 100644 --- a/src/Expr.cc +++ b/src/Expr.cc @@ -665,6 +665,9 @@ Val* BinaryExpr::Fold(Val* v1, Val* v2) const if ( it == TYPE_INTERNAL_STRING ) return StringFold(v1, v2); + if ( v1->Type()->Tag() == TYPE_PATTERN ) + return PatternFold(v1, v2); + if ( it == TYPE_INTERNAL_ADDR ) return AddrFold(v1, v2); @@ -851,6 +854,21 @@ Val* BinaryExpr::StringFold(Val* v1, Val* v2) const return new Val(result, TYPE_BOOL); } +Val* BinaryExpr::PatternFold(Val* v1, Val* v2) const + { + const RE_Matcher* re1 = v1->AsPattern(); + const RE_Matcher* re2 = v2->AsPattern(); + + if ( tag != EXPR_AND && tag != EXPR_OR ) + BadTag("BinaryExpr::PatternFold"); + + RE_Matcher* res = tag == EXPR_AND ? + RE_Matcher_conjunction(re1, re2) : + RE_Matcher_disjunction(re1, re2); + + return new PatternVal(res); + } + Val* BinaryExpr::AddrFold(Val* v1, Val* v2) const { IPAddr a1 = v1->AsAddr(); @@ -1696,9 +1714,6 @@ BoolExpr::BoolExpr(BroExprTag arg_tag, Expr* arg_op1, Expr* arg_op2) SetType(base_type(TYPE_BOOL)); } - else if ( bt1 == TYPE_PATTERN && bt2 == bt1 ) - SetType(base_type(TYPE_PATTERN)); - else ExprError("requires boolean operands"); } @@ -1708,22 +1723,6 @@ Val* BoolExpr::DoSingleEval(Frame* f, Val* v1, Expr* op2) const if ( ! v1 ) return 0; - if ( Type()->Tag() == TYPE_PATTERN ) - { - Val* v2 = op2->Eval(f); - if ( ! v2 ) - return 0; - - RE_Matcher* re1 = v1->AsPattern(); - RE_Matcher* re2 = v2->AsPattern(); - - RE_Matcher* res = tag == EXPR_AND_AND ? - RE_Matcher_conjunction(re1, re2) : - RE_Matcher_disjunction(re1, re2); - - return new PatternVal(res); - } - if ( tag == EXPR_AND_AND ) { if ( v1->IsZero() ) @@ -1885,6 +1884,16 @@ BitExpr::BitExpr(BroExprTag arg_tag, Expr* arg_op1, Expr* arg_op2) SetType(base_type(TYPE_COUNT)); } + if ( bt1 == TYPE_PATTERN ) + { + if ( bt2 != TYPE_PATTERN ) + ExprError("cannot mix pattern and non-pattern operands"); + else if ( tag == EXPR_XOR ) + ExprError("'^' operator does not apply to patterns"); + else + SetType(base_type(TYPE_PATTERN)); + } + else ExprError("requires \"count\" operands"); } diff --git a/src/Expr.h b/src/Expr.h index 8e8b6cc96b..4229750fb1 100644 --- a/src/Expr.h +++ b/src/Expr.h @@ -327,6 +327,9 @@ protected: // Same for when the constants are strings. virtual Val* StringFold(Val* v1, Val* v2) const; + // Same for when the constants are patterns. + virtual Val* PatternFold(Val* v1, Val* v2) const; + // Same for when the constants are addresses or subnets. virtual Val* AddrFold(Val* v1, Val* v2) const; virtual Val* SubNetFold(Val* v1, Val* v2) const; diff --git a/src/parse.y b/src/parse.y index 6f7a43ae7f..b8f82aa1fb 100644 --- a/src/parse.y +++ b/src/parse.y @@ -2,7 +2,7 @@ // See the file "COPYING" in the main distribution directory for copyright. %} -%expect 78 +%expect 77 %token TOK_ADD TOK_ADD_TO TOK_ADDR TOK_ANY %token TOK_ATENDIF TOK_ATELSE TOK_ATIF TOK_ATIFDEF TOK_ATIFNDEF @@ -49,13 +49,12 @@ %left '$' '[' ']' '(' ')' TOK_HAS_FIELD TOK_HAS_ATTR %type opt_no_test opt_no_test_block opt_deprecated -%type TOK_ID TOK_PATTERN_TEXT single_pattern +%type TOK_ID TOK_PATTERN_TEXT %type local_id global_id def_global_id event_id global_or_event_id resolve_id begin_func %type local_id_list %type init_class %type opt_init %type TOK_CONSTANT -%type pattern %type expr opt_expr init anonymous_function %type event %type stmt stmt_list func_body for_head @@ -720,11 +719,15 @@ expr: $$ = new ConstExpr($1); } - | pattern + | '/' { begin_RE(); } TOK_PATTERN_TEXT { end_RE(); } '/' { - set_location(@1); - $1->Compile(); - $$ = new ConstExpr(new PatternVal($1)); + set_location(@3); + + RE_Matcher* re = new RE_Matcher($3); + delete [] $3; + + re->Compile(); + $$ = new ConstExpr(new PatternVal(re)); } | '|' expr '|' %prec '(' @@ -754,25 +757,6 @@ opt_expr_list: { $$ = new ListExpr(); } ; -pattern: - pattern '|' single_pattern - { - $1->AddPat($3); - delete [] $3; - } - - | single_pattern - { - $$ = new RE_Matcher($1); - delete [] $1; - } - ; - -single_pattern: - '/' { begin_RE(); } TOK_PATTERN_TEXT { end_RE(); } '/' - { $$ = $3; } - ; - enum_body: enum_body_list {