From: Victor Julien Date: Thu, 12 Feb 2015 14:56:38 +0000 (+0100) Subject: multi-detect: implement unregister-tenant-handler X-Git-Tag: suricata-3.0RC1~210 X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=216638c3428819dd7b4254027d5cd48ea8af0191;p=thirdparty%2Fsuricata.git multi-detect: implement unregister-tenant-handler Remove a tenant handler from the list and apply it. --- diff --git a/src/detect-engine.c b/src/detect-engine.c index bec2c8baed..1634f15cd2 100644 --- a/src/detect-engine.c +++ b/src/detect-engine.c @@ -1771,17 +1771,64 @@ static int DetectEngineTentantRegisterSelector(enum DetectEngineTenantSelectors return 0; } +static int DetectEngineTentantUnregisterSelector(enum DetectEngineTenantSelectors selector, + uint32_t tenant_id, uint32_t traffic_id) +{ + DetectEngineMasterCtx *master = &g_master_de_ctx; + SCMutexLock(&master->lock); + + if (master->tenant_mapping_list == NULL) { + SCMutexUnlock(&master->lock); + return -1; + } + + DetectEngineTenantMapping *prev = NULL; + DetectEngineTenantMapping *map = master->tenant_mapping_list; + while (map) { + if (map->traffic_id == traffic_id && + map->tenant_id == tenant_id) + { + if (prev != NULL) + prev->next = map->next; + else + master->tenant_mapping_list = map->next; + + map->next = NULL; + SCFree(map); + SCLogInfo("tenant handler %u %u %u unregistered", selector, tenant_id, traffic_id); + SCMutexUnlock(&master->lock); + return 0; + } + prev = map; + map = map->next; + } + + SCMutexUnlock(&master->lock); + return -1; +} + int DetectEngineTentantRegisterVlanId(uint32_t tenant_id, uint16_t vlan_id) { return DetectEngineTentantRegisterSelector(TENANT_SELECTOR_VLAN, tenant_id, (uint32_t)vlan_id); } +int DetectEngineTentantUnregisterVlanId(uint32_t tenant_id, uint16_t vlan_id) +{ + return DetectEngineTentantUnregisterSelector(TENANT_SELECTOR_VLAN, tenant_id, (uint32_t)vlan_id); +} + int DetectEngineTentantRegisterPcapFile(uint32_t tenant_id) { SCLogInfo("registering %u %d 0", TENANT_SELECTOR_DIRECT, tenant_id); return DetectEngineTentantRegisterSelector(TENANT_SELECTOR_DIRECT, tenant_id, 0); } +int DetectEngineTentantUnregisterPcapFile(uint32_t tenant_id) +{ + SCLogInfo("unregistering %u %d 0", TENANT_SELECTOR_DIRECT, tenant_id); + return DetectEngineTentantUnregisterSelector(TENANT_SELECTOR_DIRECT, tenant_id, 0); +} + uint32_t DetectEngineTentantGetIdFromPcap(const void *ctx, const Packet *p) { return p->pcap_v.tenant_id; diff --git a/src/detect-engine.h b/src/detect-engine.h index e67bc1c7ae..b263e83bb3 100644 --- a/src/detect-engine.h +++ b/src/detect-engine.h @@ -87,7 +87,9 @@ void DetectEngineReloadSetDone(void); int DetectEngineReloadIsDone(void); int DetectEngineTentantRegisterVlanId(uint32_t tenant_id, uint16_t vlan_id); +int DetectEngineTentantUnregisterVlanId(uint32_t tenant_id, uint16_t vlan_id); int DetectEngineTentantRegisterPcapFile(uint32_t tenant_id); +int DetectEngineTentantUnregisterPcapFile(uint32_t tenant_id); /** * \brief Registers an app inspection engine. diff --git a/src/runmode-unix-socket.c b/src/runmode-unix-socket.c index 81b5839b07..6b4490d784 100644 --- a/src/runmode-unix-socket.c +++ b/src/runmode-unix-socket.c @@ -508,6 +508,88 @@ TmEcode UnixSocketRegisterTenantHandler(json_t *cmd, json_t* answer, void *data) return TM_ECODE_OK; } +/** + * \brief Command to remove a tenant handler + * + * \param cmd the content of command Arguments as a json_t object + * \param answer the json_t object that has to be used to answer + * \param data pointer to data defining the context here a PcapCommand:: + */ +TmEcode UnixSocketUnregisterTenantHandler(json_t *cmd, json_t* answer, void *data) +{ + const char *htype; + json_int_t traffic_id = -1; + + if (!(DetectEngineMultiTenantEnabled())) { + SCLogInfo("error: multi-tenant support not enabled"); + json_object_set_new(answer, "message", json_string("multi-tenant support not enabled")); + return TM_ECODE_FAILED; + } + + /* 1 get tenant id */ + json_t *jarg = json_object_get(cmd, "id"); + if (!json_is_integer(jarg)) { + SCLogInfo("error: command is not a string"); + json_object_set_new(answer, "message", json_string("id is not an integer")); + return TM_ECODE_FAILED; + } + int tenant_id = json_integer_value(jarg); + + /* 2 get tenant handler type */ + jarg = json_object_get(cmd, "htype"); + if (!json_is_string(jarg)) { + SCLogInfo("error: command is not a string"); + json_object_set_new(answer, "message", json_string("command is not a string")); + return TM_ECODE_FAILED; + } + htype = json_string_value(jarg); + + SCLogDebug("add-tenant-handler: %d %s", tenant_id, htype); + + /* 3 get optional hargs */ + json_t *hargs = json_object_get(cmd, "hargs"); + if (hargs != NULL) { + if (!json_is_integer(hargs)) { + SCLogInfo("error: hargs not a number"); + json_object_set_new(answer, "message", json_string("hargs not a number")); + return TM_ECODE_FAILED; + } + traffic_id = json_integer_value(hargs); + } + + /* 4 add to system */ + int r = -1; + if (strcmp(htype, "pcap") == 0) { + r = DetectEngineTentantUnregisterPcapFile(tenant_id); + } else if (strcmp(htype, "vlan") == 0) { + if (traffic_id < 0) { + json_object_set_new(answer, "message", json_string("vlan requires argument")); + return TM_ECODE_FAILED; + } + if (traffic_id > USHRT_MAX) { + json_object_set_new(answer, "message", json_string("vlan argument out of range")); + return TM_ECODE_FAILED; + } + + SCLogInfo("VLAN handler: id %u maps to tenant %u", (uint32_t)traffic_id, tenant_id); + r = DetectEngineTentantUnregisterVlanId(tenant_id, (uint32_t)traffic_id); + } + if (r != 0) { + json_object_set_new(answer, "message", json_string("handler unregister failure")); + return TM_ECODE_FAILED; + } + + /* 5 apply it */ + if (DetectEngineMTApply() < 0) { + json_object_set_new(answer, "message", json_string("couldn't apply settings")); + // TODO cleanup + return TM_ECODE_FAILED; + } + + json_object_set_new(answer, "message", json_string("handler added")); + return TM_ECODE_OK; +} + /** * \brief Command to add a tenant * diff --git a/src/runmode-unix-socket.h b/src/runmode-unix-socket.h index 68e324337c..af74e51533 100644 --- a/src/runmode-unix-socket.h +++ b/src/runmode-unix-socket.h @@ -33,6 +33,7 @@ void UnixSocketPcapFile(TmEcode tm); #ifdef BUILD_UNIX_SOCKET TmEcode UnixSocketRegisterTenantHandler(json_t *cmd, json_t* answer, void *data); +TmEcode UnixSocketUnregisterTenantHandler(json_t *cmd, json_t* answer, void *data); TmEcode UnixSocketRegisterTenant(json_t *cmd, json_t* answer, void *data); TmEcode UnixSocketUnregisterTenant(json_t *cmd, json_t* answer, void *data); #endif diff --git a/src/unix-manager.c b/src/unix-manager.c index 384e590785..43a7949ec0 100644 --- a/src/unix-manager.c +++ b/src/unix-manager.c @@ -900,6 +900,7 @@ static TmEcode UnixManager(ThreadVars *th_v, void *thread_data) UnixManagerRegisterCommand("dump-counters", StatsOutputCounterSocket, NULL, 0); UnixManagerRegisterCommand("reload-rules", UnixManagerReloadRules, NULL, 0); UnixManagerRegisterCommand("register-tenant-handler", UnixSocketRegisterTenantHandler, &command, UNIX_CMD_TAKE_ARGS); + UnixManagerRegisterCommand("unregister-tenant-handler", UnixSocketUnregisterTenantHandler, &command, UNIX_CMD_TAKE_ARGS); UnixManagerRegisterCommand("register-tenant", UnixSocketRegisterTenant, &command, UNIX_CMD_TAKE_ARGS); UnixManagerRegisterCommand("unregister-tenant", UnixSocketUnregisterTenant, &command, UNIX_CMD_TAKE_ARGS);