TEST_F(TestIronBeeModuleRulesLua, operator_test) { const ib_operator_t *op; void *instance_data; ib_num_t result; ib_field_t* field1; const char* op_name = "test_module_rules_lua.lua"; const char* rule_name = "luarule001"; char* str1 = (char *)ib_mpool_strdup(ib_engine->mp, "string 1"); ASSERT_TRUE(str1); // Create field 1. ASSERT_EQ(IB_OK, ib_field_create( &field1, ib_engine->mp, IB_FIELD_NAME("field1"), IB_FTYPE_NULSTR, ib_ftype_nulstr_in(str1) ) ); /* Configure the operator. */ configureIronBee(); // Ensure that the operator exists. ASSERT_EQ(IB_OK, ib_operator_lookup(ib_engine, op_name, &op) ); ASSERT_EQ(IB_OK, ib_operator_inst_create(op, ib_context_main(ib_engine), IB_OP_CAPABILITY_NON_STREAM, rule_name, &instance_data)); performTx(); // Attempt to match. ASSERT_EQ(IB_OK, ib_operator_inst_execute(op, instance_data, ib_tx, field1, NULL, &result)); // This time we should succeed. ASSERT_TRUE(result); }
TEST_F(CoreOperatorsTest, NeTest) { ib_status_t status; ib_num_t call_result; ib_operator_inst_t *op; ib_rule_t *rule = NULL; /* Not used by this operator. */ status = ib_operator_inst_create(ib_engine, NULL, rule, IB_OP_FLAG_PHASE, "ne", "1", IB_OPINST_FLAG_NONE, &op); ASSERT_EQ(IB_OK, status); // call contains ib_field_t *field; const ib_num_t matching = 2; const ib_num_t nonmatching = 1; ib_field_create( &field, ib_engine_pool_main_get(ib_engine), IB_FIELD_NAME("testfield"), IB_FTYPE_NUM, ib_ftype_num_in(&matching) ); ib_rule_exec_t rule_exec; memset(&rule_exec, 0, sizeof(rule_exec)); rule_exec.ib = ib_engine; rule_exec.tx = ib_tx; rule_exec.rule = rule; ib_field_setv(field, ib_ftype_num_in(&matching)); status = ib_operator_execute(&rule_exec, op, field, &call_result); ASSERT_EQ(IB_OK, status); EXPECT_EQ(1, call_result); ib_field_setv(field, ib_ftype_num_in(&nonmatching)); status = ib_operator_execute(&rule_exec, op, field, &call_result); ASSERT_EQ(IB_OK, status); EXPECT_EQ(0, call_result); }
TEST_F(CoreOperatorsTest, ContainsTest) { ib_status_t status; ib_num_t call_result; ib_operator_inst_t *op; ib_rule_t *rule = NULL; /* Not used by this operator. */ status = ib_operator_inst_create(ib_engine, NULL, rule, IB_OP_FLAG_PHASE, "contains", "needle", IB_OPINST_FLAG_NONE, &op); ASSERT_EQ(IB_OK, status); // call contains ib_field_t *field; const char *matching = "data with needle in it"; const char *nonmatching = "non matching string"; ib_field_create( &field, ib_engine_pool_main_get(ib_engine), IB_FIELD_NAME("testfield"), IB_FTYPE_NULSTR, NULL ); ib_rule_exec_t rule_exec; memset(&rule_exec, 0, sizeof(rule_exec)); rule_exec.ib = ib_engine; rule_exec.rule = rule; ib_field_setv(field, ib_ftype_nulstr_in(matching)); status = ib_operator_execute(&rule_exec, op, field, &call_result); ASSERT_EQ(IB_OK, status); EXPECT_EQ(1, call_result); ib_field_setv(field, ib_ftype_nulstr_in(nonmatching)); status = ib_operator_execute(&rule_exec, op, field, &call_result); ASSERT_EQ(IB_OK, status); EXPECT_EQ(0, call_result); }
TEST_F(CoreOperatorsTest, ContainsTest) { ib_status_t status; ib_num_t call_result; const ib_operator_t *op; void *instance_data; status = ib_operator_lookup(ib_engine, "contains", &op); ASSERT_EQ(IB_OK, status); status = ib_operator_inst_create(op, ib_context_main(ib_engine), IB_OP_CAPABILITY_NON_STREAM, "needle", &instance_data); ASSERT_EQ(IB_OK, status); // call contains ib_field_t *field; const char *matching = "data with needle in it"; const char *nonmatching = "non matching string"; ib_field_create( &field, ib_engine_pool_main_get(ib_engine), IB_FIELD_NAME("testfield"), IB_FTYPE_NULSTR, NULL ); ib_field_setv(field, ib_ftype_nulstr_in(matching)); status = ib_operator_inst_execute(op, instance_data, ib_tx, field, NULL, &call_result); ASSERT_EQ(IB_OK, status); EXPECT_EQ(1, call_result); ib_field_setv(field, ib_ftype_nulstr_in(nonmatching)); status = ib_operator_inst_execute(op, instance_data, ib_tx, field, NULL, &call_result); ASSERT_EQ(IB_OK, status); EXPECT_EQ(0, call_result); }
TEST_F(CoreOperatorsTest, NeTest) { ib_status_t status; ib_num_t call_result; const ib_operator_t *op; void *instance_data; status = ib_operator_lookup(ib_engine, "ne", &op); ASSERT_EQ(IB_OK, status); status = ib_operator_inst_create(op, ib_context_main(ib_engine), IB_OP_CAPABILITY_NON_STREAM, "1", &instance_data); ASSERT_EQ(IB_OK, status); // call contains ib_field_t *field; const ib_num_t matching = 2; const ib_num_t nonmatching = 1; ib_field_create( &field, ib_engine_pool_main_get(ib_engine), IB_FIELD_NAME("testfield"), IB_FTYPE_NUM, ib_ftype_num_in(&matching) ); ib_field_setv(field, ib_ftype_num_in(&matching)); status = ib_operator_inst_execute(op, instance_data, ib_tx, field, NULL, &call_result); ASSERT_EQ(IB_OK, status); EXPECT_EQ(1, call_result); ib_field_setv(field, ib_ftype_num_in(&nonmatching)); status = ib_operator_inst_execute(op, instance_data, ib_tx, field, NULL, &call_result); ASSERT_EQ(IB_OK, status); EXPECT_EQ(0, call_result); }
OperatorInstance OperatorInstance::create( MemoryManager memory_manager, Context context, ConstOperator op, ib_flags_t required_capabilities, const char* parameters ) { ib_operator_inst_t* opinst; throw_if_error( ib_operator_inst_create( &opinst, memory_manager.ib(), context.ib(), op.ib(), required_capabilities, parameters ) ); return OperatorInstance(opinst); }
TEST_F(OperatorTest, OperatorCallTest) { ib_status_t status; ib_num_t call_result; void *instance_data; ib_operator_t *op; const ib_operator_t *cop; status = ib_operator_create_and_register( &op, ib_engine, "test_op", IB_OP_CAPABILITY_NON_STREAM, test_create_fn, NULL, NULL, NULL, test_execute_fn, NULL ); ASSERT_EQ(IB_OK, status); status = ib_operator_lookup(ib_engine, "test_op", &cop); ASSERT_EQ(IB_OK, status); status = ib_operator_inst_create(op, ib_context_main(ib_engine), IB_OP_CAPABILITY_NON_STREAM, "INVALID", &instance_data); ASSERT_EQ(IB_EINVAL, status); status = ib_operator_inst_create(op, ib_context_main(ib_engine), IB_OP_CAPABILITY_NON_STREAM, "data", &instance_data); ASSERT_EQ(IB_OK, status); ib_field_t *field; const char *matching = "data matching string"; const char *nonmatching = "non matching string"; ib_field_create( &field, ib_engine_pool_main_get(ib_engine), IB_FIELD_NAME("testfield"), IB_FTYPE_NULSTR, NULL ); ib_field_setv(field, ib_ftype_nulstr_in(matching)); status = ib_operator_inst_execute(op, instance_data, ib_tx, field, NULL, &call_result); ASSERT_EQ(IB_OK, status); EXPECT_EQ(1, call_result); ib_field_setv(field, ib_ftype_nulstr_in(nonmatching)); status = ib_operator_inst_execute(op, instance_data, ib_tx, field, NULL, &call_result); ASSERT_EQ(IB_OK, status); EXPECT_EQ(0, call_result); status = ib_operator_inst_destroy(op, instance_data); ASSERT_EQ(IB_OK, status); }
TEST_F(PcreModuleTest, test_pcre_operator) { ib_field_t *outfield; ib_num_t result; ib_field_t *capture; const ib_operator_t *op; ib_operator_inst_t *opinst; ASSERT_EQ(IB_OK, ib_operator_lookup(ib_engine, IB_S2SL("pcre"), &op)); // Create the operator instance. ASSERT_EQ( IB_OK, ib_operator_inst_create( &opinst, ib_engine_mm_main_get(ib_engine), ib_context_main(ib_engine), op, IB_OP_CAPABILITY_NONE, "string\\s2" ) ); // Attempt to match. ASSERT_EQ( IB_OK, ib_operator_inst_execute( opinst, rule_exec1.tx, field1, NULL, &result ) ); // We should fail. ASSERT_FALSE(result); // Attempt to match again. ASSERT_EQ( IB_OK, ib_operator_inst_execute( opinst, rule_exec1.tx, field2, NULL, &result ) ); // This time we should succeed. ASSERT_TRUE(result); // Should be no capture set */ outfield = getTarget1(IB_TX_CAPTURE":0"); ASSERT_FALSE(outfield); // Create the operator instance. ASSERT_EQ( IB_OK, ib_operator_inst_create( &opinst, ib_engine_mm_main_get(ib_engine), ib_context_main(ib_engine), op, IB_OP_CAPABILITY_NONE, "(string 2)" ) ); // Attempt to match. ASSERT_EQ( IB_OK, ib_operator_inst_execute( opinst, rule_exec1.tx, field1, NULL, &result ) ); // We should fail. ASSERT_FALSE(result); // Attempt to match again. ASSERT_EQ( IB_OK, ib_operator_inst_execute( opinst, rule_exec1.tx, field2, NULL, &result ) ); // This time we should succeed. ASSERT_TRUE(result); // Should be no capture (CAPTURE flag not set for rule 1) outfield = getTarget1(IB_TX_CAPTURE":0"); ASSERT_FALSE(outfield); // Create the operator instance. ASSERT_EQ( IB_OK, ib_operator_inst_create( &opinst, ib_engine_mm_main_get(ib_engine), ib_context_main(ib_engine), op, IB_OP_CAPABILITY_NONE, "(string 2)" ) ); ASSERT_EQ(IB_OK, ib_capture_acquire( rule_exec2.tx, NULL, &capture)); // Attempt to match again. ASSERT_EQ( IB_OK, ib_operator_inst_execute( opinst, rule_exec1.tx, field2, capture, &result ) ); // This time we should succeed. ASSERT_TRUE(result); // Should be a capture (CAPTURE flag is set for rule 2) outfield = getTarget1(IB_TX_CAPTURE":0"); ASSERT_TRUE(outfield); }
TEST_F(OperatorTest, OperatorCallTest) { ib_status_t status; ib_num_t call_result; ib_rule_t *rule = NULL; /* Unused by this operator. */ ib_operator_inst_t *op; status = ib_operator_register(ib_engine, "test_op", IB_OP_FLAG_PHASE, test_create_fn, NULL, test_destroy_fn, NULL, test_execute_fn, NULL); ASSERT_EQ(IB_OK, status); status = ib_operator_inst_create(ib_engine, NULL, rule, IB_OP_FLAG_PHASE, "test_op", "INVALID", IB_OPINST_FLAG_NONE, &op); ASSERT_EQ(IB_EINVAL, status); status = ib_operator_inst_create(ib_engine, NULL, rule, IB_OP_FLAG_PHASE, "test_op", "data", IB_OPINST_FLAG_NONE, &op); ASSERT_EQ(IB_OK, status); ib_rule_exec_t rule_exec; memset(&rule_exec, 0, sizeof(rule_exec)); rule_exec.ib = ib_engine; rule_exec.rule = rule; ib_field_t *field; const char *matching = "data matching string"; const char *nonmatching = "non matching string"; ib_field_create( &field, ib_engine_pool_main_get(ib_engine), IB_FIELD_NAME("testfield"), IB_FTYPE_NULSTR, NULL ); ib_field_setv(field, ib_ftype_nulstr_in(matching)); status = ib_operator_execute(&rule_exec, op, field, &call_result); ASSERT_EQ(IB_OK, status); EXPECT_EQ(1, call_result); ib_field_setv(field, ib_ftype_nulstr_in(nonmatching)); status = ib_operator_execute(&rule_exec, op, field, &call_result); ASSERT_EQ(IB_OK, status); EXPECT_EQ(0, call_result); status = ib_operator_inst_destroy(op); ASSERT_EQ(IB_OK, status); }
/** * Called by RuleExt lua:. * * @param[in] cp Configuration parser. * @param[in] rule Rule under construction. * @param[in] tag Should be "lua". * @param[in] location What comes after "lua:". * @param[in] cbdata Callback data; unused. * @return * - IB_OK on success. * - IB_EINVAL if Lua not available or not called for "lua" tag. * - Other error code if loading or registration fails. */ static ib_status_t modlua_rule_driver( ib_cfgparser_t *cp, ib_rule_t *rule, const char *tag, const char *location, void *cbdata ) { assert(cp != NULL); assert(cp->ib != NULL); assert(tag != NULL); assert(location != NULL); ib_status_t rc; const char *slash; const char *name; ib_operator_t *op; ib_operator_inst_t *opinst; ib_engine_t *ib = cp->ib; modlua_cfg_t *cfg = NULL; ib_context_t *ctx = NULL; modlua_rules_cbdata_t *modlua_rules_cbdata = (modlua_rules_cbdata_t *)cbdata; /* This cbdata is passed on to the implementation. Validate it here. */ assert(modlua_rules_cbdata != NULL); assert(modlua_rules_cbdata->module != NULL); if (strncmp(tag, "lua", 3) != 0) { ib_cfg_log_error(cp, "Lua rule driver called for non-lua tag."); return IB_EINVAL; } rc = ib_cfgparser_context_current(cp, &ctx); if (rc != IB_OK) { ib_cfg_log_error(cp, "Failed to retrieve current context."); return rc; } rc = modlua_cfg_get(ib, ctx, &cfg); if (rc != IB_OK) { return rc; } rc = ib_lua_load_func( cp->ib, cfg->L, location, ib_rule_id(rule)); if (rc != IB_OK) { ib_cfg_log_error(cp, "Failed to load lua file \"%s\"", location); return rc; } /* Record that we need to reload this rule in each TX. */ rc = modlua_record_reload( cp->ib, cfg, MODLUA_RELOAD_RULE, NULL, ib_rule_id(rule), location); if (rc != IB_OK) { ib_cfg_log_error( cp, "Failed to record lua file \"%s\" to reload", location); return rc; } slash = strrchr(location, '/'); if (slash == NULL) { name = location; } else { name = slash + 1; } rc = ib_operator_create_and_register( &op, cp->ib, name, IB_OP_CAPABILITY_NONE, &lua_operator_create, modlua_rules_cbdata, NULL, NULL, &lua_operator_execute, modlua_rules_cbdata ); if (rc != IB_OK) { ib_cfg_log_error(cp, "Error registering lua operator \"%s\": %s", name, ib_status_to_string(rc)); return rc; } rc = ib_operator_inst_create(&opinst, ib_engine_mm_main_get(cp->ib), ctx, op, ib_rule_required_op_flags(rule), ib_rule_id(rule)); /* becomes instance_data */ if (rc != IB_OK) { ib_cfg_log_error(cp, "Error instantiating lua operator " "for rule \"%s\": %s", name, ib_status_to_string(rc)); return rc; } rc = ib_rule_set_operator(cp->ib, rule, opinst); if (rc != IB_OK) { ib_cfg_log_error(cp, "Error associating lua operator \"%s\" " "with rule \"%s\": %s", name, ib_rule_id(rule), ib_status_to_string(rc)); return rc; } return IB_OK; }