]> granicus.if.org Git - icinga2/commitdiff
Implement the %, ^, %=, ^=, &= and |= operators
authorGunnar Beutner <gunnar@beutner.name>
Tue, 25 Nov 2014 16:04:20 +0000 (17:04 +0100)
committerGunnar Beutner <gunnar@beutner.name>
Tue, 25 Nov 2014 16:16:34 +0000 (17:16 +0100)
fixes #7813

lib/config/config_lexer.ll
lib/config/config_parser.yy
lib/config/expression.cpp
lib/config/expression.hpp

index de8c393648a67a91eabb8ebcca34872e2e8e059e..8f17c33b4efb80559609948ca13056d5c2d6d2e5 100644 (file)
@@ -278,10 +278,16 @@ in                                return T_IN;
 -=                             { yylval->csop = OpSetSubtract; return T_SET_SUBTRACT; }
 \*=                            { yylval->csop = OpSetMultiply; return T_SET_MULTIPLY; }
 \/=                            { yylval->csop = OpSetDivide; return T_SET_DIVIDE; }
+\%=                            { yylval->csop = OpSetModulo; return T_SET_MODULO; }
+\^=                            { yylval->csop = OpSetXor; return T_SET_XOR; }
+\&=                            { yylval->csop = OpSetBinaryAnd; return T_SET_BINARY_AND; }
+\|=                            { yylval->csop = OpSetBinaryOr; return T_SET_BINARY_OR; }
 \+                             return T_PLUS;
 \-                             return T_MINUS;
 \*                             return T_MULTIPLY;
 \/                             return T_DIVIDE_OP;
+\%                             return T_MODULO;
+\^                             return T_XOR;
 \&                             return T_BINARY_AND;
 \|                             return T_BINARY_OR;
 \<                             return T_LESS_THAN;
index 43f0899d2b7c70542d77d8218cbe3d09b45d93ee..1d6679c66366680e937edce14a969a928d3b0b86 100644 (file)
@@ -114,6 +114,10 @@ static void MakeRBinaryOp(Expression** result, Expression *left, Expression *rig
 %token <csop> T_SET_SUBTRACT "-= (T_SET_SUBTRACT)"
 %token <csop> T_SET_MULTIPLY "*= (T_SET_MULTIPLY)"
 %token <csop> T_SET_DIVIDE "/= (T_SET_DIVIDE)"
+%token <csop> T_SET_MODULO "%= (T_SET_MODULO)"
+%token <csop> T_SET_XOR "^= (T_SET_XOR)"
+%token <csop> T_SET_BINARY_AND "&= (T_SET_BINARY_AND)"
+%token <csop> T_SET_BINARY_OR "|= (T_SET_BINARY_OR)"
 
 %token T_SHIFT_LEFT "<< (T_SHIFT_LEFT)"
 %token T_SHIFT_RIGHT ">> (T_SHIFT_RIGHT)"
@@ -129,6 +133,8 @@ static void MakeRBinaryOp(Expression** result, Expression *left, Expression *rig
 %token T_MINUS "- (T_MINUS)"
 %token T_MULTIPLY "* (T_MULTIPLY)"
 %token T_DIVIDE_OP "/ (T_DIVIDE_OP)"
+%token T_MODULO "% (T_MODULO)"
+%token T_XOR "^ (T_XOR)"
 %token T_BINARY_AND "& (T_BINARY_AND)"
 %token T_BINARY_OR "| (T_BINARY_OR)"
 %token T_LESS_THAN "< (T_LESS_THAN)"
@@ -203,8 +209,9 @@ static void MakeRBinaryOp(Expression** result, Expression *left, Expression *rig
 %left T_LOGICAL_AND
 %left T_LOCAL T_RETURN
 %left T_IDENTIFIER
-%left T_SET T_SET_ADD T_SET_SUBTRACT T_SET_MULTIPLY T_SET_DIVIDE
+%left T_SET T_SET_ADD T_SET_SUBTRACT T_SET_MULTIPLY T_SET_DIVIDE T_SET_MODULO T_SET_XOR T_SET_BINARY_AND T_SET_BINARY_OR
 %left T_BINARY_OR
+%left T_XOR T_MODULO
 %left T_BINARY_AND
 %left T_IN T_NOT_IN
 %nonassoc T_EQUAL T_NOT_EQUAL
@@ -560,6 +567,10 @@ combined_set_op: T_SET
        | T_SET_SUBTRACT
        | T_SET_MULTIPLY
        | T_SET_DIVIDE
+       | T_SET_MODULO
+       | T_SET_XOR
+       | T_SET_BINARY_AND
+       | T_SET_BINARY_OR
        {
                $$ = $1;
        }
@@ -802,6 +813,8 @@ rterm_without_indexer: T_STRING
        | rterm T_MINUS rterm { MakeRBinaryOp<SubtractExpression>(&$$, $1, $3, @1, @3); }
        | rterm T_MULTIPLY rterm { MakeRBinaryOp<MultiplyExpression>(&$$, $1, $3, @1, @3); }
        | rterm T_DIVIDE_OP rterm { MakeRBinaryOp<DivideExpression>(&$$, $1, $3, @1, @3); }
+       | rterm T_MODULO rterm { MakeRBinaryOp<ModuloExpression>(&$$, $1, $3, @1, @3); }
+       | rterm T_XOR rterm { MakeRBinaryOp<XorExpression>(&$$, $1, $3, @1, @3); }
        | T_FUNCTION identifier '(' identifier_items ')' use_specifier rterm_scope
        {
                DictExpression *aexpr = dynamic_cast<DictExpression *>($7);
index 895e00026cb22ecd2b73b5521f6592695711820a..8fcdcd177ae287fa0a49455b20ec1dd52c705be3 100644 (file)
@@ -124,6 +124,16 @@ Value DivideExpression::DoEvaluate(VMFrame& frame, DebugHint *dhint) const
        return m_Operand1->Evaluate(frame) / m_Operand2->Evaluate(frame);
 }
 
+Value ModuloExpression::DoEvaluate(VMFrame& frame, DebugHint *dhint) const
+{
+       return (long)m_Operand1->Evaluate(frame) % (long)m_Operand2->Evaluate(frame);
+}
+
+Value XorExpression::DoEvaluate(VMFrame& frame, DebugHint *dhint) const
+{
+       return (long)m_Operand1->Evaluate(frame) ^ (long)m_Operand2->Evaluate(frame);
+}
+
 Value BinaryAndExpression::DoEvaluate(VMFrame& frame, DebugHint *dhint) const
 {
        return m_Operand1->Evaluate(frame) & m_Operand2->Evaluate(frame);
@@ -337,6 +347,18 @@ Value SetExpression::DoEvaluate(VMFrame& frame, DebugHint *dhint) const
                        case OpSetDivide:
                                right = DivideExpression(lhs, rhs, m_DebugInfo).Evaluate(frame, dhint);
                                break;
+                       case OpSetModulo:
+                               right = ModuloExpression(lhs, rhs, m_DebugInfo).Evaluate(frame, dhint);
+                               break;
+                       case OpSetXor:
+                               right = XorExpression(lhs, rhs, m_DebugInfo).Evaluate(frame, dhint);
+                               break;
+                       case OpSetBinaryAnd:
+                               right = BinaryAndExpression(lhs, rhs, m_DebugInfo).Evaluate(frame, dhint);
+                               break;
+                       case OpSetBinaryOr:
+                               right = BinaryOrExpression(lhs, rhs, m_DebugInfo).Evaluate(frame, dhint);
+                               break;
                        default:
                                VERIFY(!"Invalid opcode.");
                }
index f7ef9deeaa786e3e84a501f51769b9c6d47205aa..e98c69745fd7ba10d87279eb37084f714021ace9 100644 (file)
@@ -98,7 +98,11 @@ enum CombinedSetOp
        OpSetAdd,
        OpSetSubtract,
        OpSetMultiply,
-       OpSetDivide
+       OpSetDivide,
+       OpSetModulo,
+       OpSetXor,
+       OpSetBinaryAnd,
+       OpSetBinaryOr
 };
 
 class InterruptExecutionError : virtual public std::exception, virtual public boost::exception
@@ -309,7 +313,29 @@ public:
 protected:
        virtual Value DoEvaluate(VMFrame& frame, DebugHint *dhint) const;
 };
-       
+
+class I2_CONFIG_API ModuloExpression : public BinaryExpression
+{
+public:
+       ModuloExpression(Expression *operand1, Expression *operand2, const DebugInfo& debugInfo = DebugInfo())
+               : BinaryExpression(operand1, operand2, debugInfo)
+       { }
+
+protected:
+       virtual Value DoEvaluate(VMFrame& frame, DebugHint *dhint) const;
+};
+
+class I2_CONFIG_API XorExpression : public BinaryExpression
+{
+public:
+       XorExpression(Expression *operand1, Expression *operand2, const DebugInfo& debugInfo = DebugInfo())
+               : BinaryExpression(operand1, operand2, debugInfo)
+       { }
+
+protected:
+       virtual Value DoEvaluate(VMFrame& frame, DebugHint *dhint) const;
+};
+
 class I2_CONFIG_API BinaryAndExpression : public BinaryExpression
 {
 public: