]> git.ipfire.org Git - thirdparty/dovecot/core.git/commitdiff
lib-master: Add process_shutdown_filter setting
authorsergey.kitov <sergey.kitov@open-xchange.com>
Thu, 16 Dec 2021 09:49:24 +0000 (11:49 +0200)
committertimo.sirainen <timo.sirainen@open-xchange.com>
Wed, 26 Jan 2022 09:11:52 +0000 (09:11 +0000)
src/lib-master/master-service-private.h
src/lib-master/master-service-settings.c
src/lib-master/master-service-settings.h
src/lib-master/master-service.c
src/lib-master/master-service.h

index a23a2cc1e1343f7ca644fa3ba82d5e9e53fd2286..429f2eb71360c7c18f6468ca8b655b5ca1500ed3 100644 (file)
@@ -73,6 +73,7 @@ struct master_service {
 
        struct stats_client *stats_client;
        struct master_service_haproxy_conn *haproxy_conns;
+       struct event_filter *process_shutdown_filter;
 
        bool killed:1;
        bool stopping:1;
index 87845a4352b5c7f8b8bf52e75950358f5d611f1e..f0f0797f43983aa5bf5bcd1e3a15dfce28a354d6 100644 (file)
@@ -46,6 +46,7 @@ static const struct setting_define master_service_setting_defines[] = {
        DEF(STR, log_timestamp),
        DEF(STR, log_debug),
        DEF(STR, log_core_filter),
+       DEF(STR, process_shutdown_filter),
        DEF(STR, syslog_facility),
        DEF(STR, import_environment),
        DEF(STR, stats_writer_socket_path),
@@ -83,6 +84,7 @@ static const struct master_service_settings master_service_default_settings = {
        .log_timestamp = DEFAULT_FAILURE_STAMP_FORMAT,
        .log_debug = "",
        .log_core_filter = "",
+       .process_shutdown_filter = "",
        .syslog_facility = "mail",
        .import_environment = "TZ CORE_OUTOFMEM CORE_ERROR" ENV_SYSTEMD ENV_GDB,
        .stats_writer_socket_path = "stats-writer",
@@ -132,6 +134,12 @@ setting_filter_parse(const char *set_name, const char *set_value,
        return TRUE;
 }
 
+static void
+master_service_set_process_shutdown_filter_wrapper(struct event_filter *filter)
+{
+       master_service_set_process_shutdown_filter(master_service, filter);
+}
+
 static bool
 master_service_settings_check(void *_set, pool_t pool ATTR_UNUSED,
                              const char **error_r)
@@ -155,6 +163,11 @@ master_service_settings_check(void *_set, pool_t pool ATTR_UNUSED,
        if (!setting_filter_parse("log_core_filter", set->log_core_filter,
                                  event_set_global_core_log_filter, error_r))
                return FALSE;
+       if (!setting_filter_parse("process_shutdown_filter",
+                                 set->process_shutdown_filter,
+                                 master_service_set_process_shutdown_filter_wrapper,
+                                 error_r))
+               return FALSE;
        return TRUE;
 }
 /* </settings checks> */
index fc396f9d4990a71ee3ae72686784fed6e4440543..eceec0c6e208cfdea375af1dc7818251c5b7a634 100644 (file)
@@ -19,6 +19,7 @@ struct master_service_settings {
        const char *log_timestamp;
        const char *log_debug;
        const char *log_core_filter;
+       const char *process_shutdown_filter;
        const char *syslog_facility;
        const char *import_environment;
        const char *stats_writer_socket_path;
index fe4812765937d6eae382ac4adb17402ba9b1a889..5adc8be92298080f045e859f254bd6e3a9cf6550 100644 (file)
@@ -132,7 +132,7 @@ sig_state_changed(const siginfo_t *si ATTR_UNUSED, void *context)
 static bool
 master_service_event_callback(struct event *event,
                              enum event_callback_type type,
-                             struct failure_context *ctx ATTR_UNUSED,
+                             struct failure_context *ctx,
                              const char *fmt ATTR_UNUSED,
                              va_list args ATTR_UNUSED)
 {
@@ -142,6 +142,12 @@ master_service_event_callback(struct event *event,
                   inherit the category from them. */
                event_add_category(event, &master_service_category);
        }
+       /* This callback may be called while still in master_service_init().
+          In that case master_service is NULL. */
+       if (type == EVENT_CALLBACK_TYPE_SEND && master_service != NULL &&
+           event_filter_match(master_service->process_shutdown_filter,
+                              event, ctx))
+               master_service_stop_new_connections(master_service);
        return TRUE;
 }
 
@@ -1526,3 +1532,16 @@ bool version_string_verify_full(const char *line, const char *service_name,
        } T_END;
        return ret;
 }
+
+void master_service_set_process_shutdown_filter(struct master_service *service,
+                                               struct event_filter *filter)
+{
+       master_service_unset_process_shutdown_filter(service);
+       service->process_shutdown_filter = filter;
+       event_filter_ref(service->process_shutdown_filter);
+}
+
+void master_service_unset_process_shutdown_filter(struct master_service *service)
+{
+       event_filter_unref(&service->process_shutdown_filter);
+}
index 0ee35b3246142980bb44a55f9ce4692aa19b276d..bd32ad0cc65e8fb0b48528691d6c92f41befb1a0 100644 (file)
@@ -253,4 +253,10 @@ bool version_string_verify_full(const char *line, const char *service_name,
                                unsigned major_version,
                                unsigned int *minor_version_r);
 
+/* Sets process shutdown filter */
+void master_service_set_process_shutdown_filter(struct master_service *service,
+                                               struct event_filter *filter);
+/* Unsets process shutdown filter, if it exists */
+void master_service_unset_process_shutdown_filter(struct master_service *service);
+
 #endif