]> git.ipfire.org Git - thirdparty/suricata.git/commitdiff
multi-tenant: add reload-tenants command
authorVictor Julien <vjulien@oisf.net>
Wed, 9 Aug 2023 07:53:20 +0000 (09:53 +0200)
committerVictor Julien <vjulien@oisf.net>
Fri, 11 Aug 2023 05:16:59 +0000 (07:16 +0200)
Command to reload all tenants. Their original yaml path will be
used.

Ticket: #6267.

python/suricata/sc/suricatasc.py
src/detect-engine.c
src/detect-engine.h
src/runmode-unix-socket.c
src/runmode-unix-socket.h
src/unix-manager.c

index bc7de375360e2feae9d93239850a4710f4ea42f3..fc07037c3d22cb4b12a8549b7508985bde9b2188 100644 (file)
@@ -94,6 +94,7 @@ class SuricataSC:
                 "pcap-last-processed",
                 "pcap-interrupt",
                 "iface-list",
+                "reload-tenants",
                 ]
         self.fn_commands = [
                 "pcap-file",
index 90296c092721f9523466943ebb1362038238deb4..3810cb0a7af4c6058e83c7a50a51daebc76ad4ef 100644 (file)
@@ -3986,6 +3986,39 @@ static int DetectLoaderFuncReloadTenant(void *vctx, int loader_id)
     return 0;
 }
 
+static int DetectLoaderSetupReloadTenants(const int reload_cnt)
+{
+    int ret = 0;
+    DetectEngineMasterCtx *master = &g_master_de_ctx;
+    SCMutexLock(&master->lock);
+
+    DetectEngineCtx *de_ctx = master->list;
+    while (de_ctx) {
+        if (de_ctx->type == DETECT_ENGINE_TYPE_TENANT) {
+            TenantLoaderCtx *t = SCCalloc(1, sizeof(*t));
+            if (t == NULL) {
+                ret = -1;
+                goto error;
+            }
+            t->tenant_id = de_ctx->tenant_id;
+            t->reload_cnt = reload_cnt;
+            int loader_id = de_ctx->loader_id;
+
+            int r = DetectLoaderQueueTask(
+                    loader_id, DetectLoaderFuncReloadTenant, t, DetectLoaderFreeTenant);
+            if (r < 0) {
+                ret = -2;
+                goto error;
+            }
+        }
+
+        de_ctx = de_ctx->next;
+    }
+error:
+    SCMutexUnlock(&master->lock);
+    return ret;
+}
+
 static int DetectLoaderSetupReloadTenant(uint32_t tenant_id, const char *yaml, int reload_cnt)
 {
     DetectEngineCtx *old_de_ctx = DetectEngineGetByTenantId(tenant_id);
@@ -4042,6 +4075,20 @@ int DetectEngineReloadTenantBlocking(uint32_t tenant_id, const char *yaml, int r
     return 0;
 }
 
+/** \brief Reload all tenants and wait for loading to complete
+ */
+int DetectEngineReloadTenantsBlocking(const int reload_cnt)
+{
+    int r = DetectLoaderSetupReloadTenants(reload_cnt);
+    if (r < 0)
+        return r;
+
+    if (DetectLoadersSync() != 0)
+        return -1;
+
+    return 0;
+}
+
 static int DetectEngineMultiTenantSetupLoadLivedevMappings(const ConfNode *mappings_root_node,
         bool failure_fatal)
 {
index f6b4ba154e100715f594f8e536d817b9bfe3f574..a1732b16a99381b24d80228d9d47b265e5e1cce7 100644 (file)
@@ -130,6 +130,7 @@ int DetectEngineReloadIsIdle(void);
 
 int DetectEngineLoadTenantBlocking(uint32_t tenant_id, const char *yaml);
 int DetectEngineReloadTenantBlocking(uint32_t tenant_id, const char *yaml, int reload_cnt);
+int DetectEngineReloadTenantsBlocking(const int reload_cnt);
 
 int DetectEngineTenantRegisterLivedev(uint32_t tenant_id, int device_id);
 int DetectEngineTenantRegisterVlanId(uint32_t tenant_id, uint16_t vlan_id);
index 7de884c9279f1ca323c9a93145f5a415c2fa6677..e695cb8dfbd6a3644c76e50b37d88abadbb71876 100644 (file)
@@ -1124,6 +1124,41 @@ TmEcode UnixSocketReloadTenant(json_t *cmd, json_t* answer, void *data)
     return TM_ECODE_OK;
 }
 
+/**
+ * \brief Command to reload all tenants
+ *
+ * \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 UnixSocketReloadTenants(json_t *cmd, json_t *answer, void *data)
+{
+    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;
+    }
+
+    if (DetectEngineReloadTenantsBlocking(reload_cnt) != 0) {
+        json_object_set_new(answer, "message", json_string("reload tenants failed"));
+        return TM_ECODE_FAILED;
+    }
+
+    reload_cnt++;
+
+    /*  apply to the running system */
+    if (DetectEngineMTApply() < 0) {
+        json_object_set_new(answer, "message", json_string("couldn't apply settings"));
+        // TODO cleanup
+        return TM_ECODE_FAILED;
+    }
+
+    SCLogNotice("reload-tenants complete");
+
+    json_object_set_new(answer, "message", json_string("reloading tenants succeeded"));
+    return TM_ECODE_OK;
+}
+
 /**
  * \brief Command to remove a tenant
  *
index c2fa84aa3235cb421fc0065db0a01357ce5e2af5..af0651f5910b16b3f03e5f0dec14da334edddbe2 100644 (file)
@@ -42,6 +42,7 @@ 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 UnixSocketReloadTenant(json_t *cmd, json_t* answer, void *data);
+TmEcode UnixSocketReloadTenants(json_t *cmd, json_t *answer, void *data);
 TmEcode UnixSocketUnregisterTenant(json_t *cmd, json_t* answer, void *data);
 TmEcode UnixSocketHostbitAdd(json_t *cmd, json_t* answer, void *data);
 TmEcode UnixSocketHostbitRemove(json_t *cmd, json_t* answer, void *data);
index 071bf75a7289d64ca5b65e1b7e22f1fb2fd08d7a..9893553f429e76bfca0860da471f740fe09709c0 100644 (file)
@@ -1099,6 +1099,7 @@ int UnixManagerInit(void)
     UnixManagerRegisterCommand("unregister-tenant-handler", UnixSocketUnregisterTenantHandler, &command, UNIX_CMD_TAKE_ARGS);
     UnixManagerRegisterCommand("register-tenant", UnixSocketRegisterTenant, &command, UNIX_CMD_TAKE_ARGS);
     UnixManagerRegisterCommand("reload-tenant", UnixSocketReloadTenant, &command, UNIX_CMD_TAKE_ARGS);
+    UnixManagerRegisterCommand("reload-tenants", UnixSocketReloadTenants, &command, 0);
     UnixManagerRegisterCommand("unregister-tenant", UnixSocketUnregisterTenant, &command, UNIX_CMD_TAKE_ARGS);
     UnixManagerRegisterCommand("add-hostbit", UnixSocketHostbitAdd, &command, UNIX_CMD_TAKE_ARGS);
     UnixManagerRegisterCommand("remove-hostbit", UnixSocketHostbitRemove, &command, UNIX_CMD_TAKE_ARGS);