This allows registering multiple debug send filters.
};
static struct connection_list *stats_clients;
+struct event_filter **stats_event_filter = NULL;
static void stats_client_connect(struct stats_client *client);
event_filter_unref(&client->filter);
client->filter = filter;
- event_set_global_debug_send_filter(client->filter);
+
+ if (stats_event_filter == NULL)
+ stats_event_filter = event_global_debug_send_filter_register();
+ *stats_event_filter = filter;
return 1;
}
client->filter = event_filter_create();
if (!event_filter_import(client->filter, filter, &error))
i_panic("Failed to import unit test event filter: %s", error);
- event_set_global_debug_send_filter(client->filter);
+
+ if (stats_event_filter == NULL)
+ stats_event_filter = event_global_debug_send_filter_register();
+ *stats_event_filter = client->filter;
return client;
}
stats_client_wait(client, STATS_CLIENT_DEINIT_WAIT);
}
+ if (stats_event_filter != NULL) {
+ i_assert(*stats_event_filter == client->filter);
+ *stats_event_filter = NULL;
+ }
event_filter_unref(&client->filter);
+
connection_deinit(&client->conn);
timeout_remove(&client->to_reconnect);
o_stream_unref(&client->conn.output);
/* Copyright (c) 2017-2018 Dovecot authors, see the included COPYING file */
#include "lib.h"
+#include "array.h"
#include "str.h"
#include "event-filter.h"
#include "lib-event-private.h"
unsigned int event_filter_replace_counter = 1;
static struct event_filter *global_debug_log_filter = NULL;
-static struct event_filter *global_debug_send_filter = NULL;
static struct event_filter *global_core_log_filter = NULL;
+static ARRAY(struct event_filter *) global_debug_send_filters;
#undef e_error
void e_error(struct event *event,
return TRUE;
/* see if debug send filtering matches */
- if (global_debug_send_filter != NULL) {
+ struct event_filter *filter;
+ array_foreach_elem(&global_debug_send_filters, filter) {
struct failure_context ctx = { .type = LOG_TYPE_DEBUG };
- if (event_filter_match_source(global_debug_send_filter, event,
+ if (filter != NULL &&
+ event_filter_match_source(filter, event,
source_filename, source_linenum,
&ctx))
return TRUE;
event_filter_replace_counter++;
}
-void event_set_global_debug_send_filter(struct event_filter *filter)
+struct event_filter **event_global_debug_send_filter_register(void)
{
- event_unset_global_debug_send_filter();
- global_debug_send_filter = filter;
- event_filter_ref(global_debug_send_filter);
- event_filter_replace_counter++;
+ return array_append_space(&global_debug_send_filters);
}
-void event_unset_global_debug_send_filter(void)
+void event_global_debug_send_filter_updated(void)
{
- event_filter_unref(&global_debug_send_filter);
event_filter_replace_counter++;
}
event_filter_unref(&global_core_log_filter);
event_filter_replace_counter++;
}
+
+void event_log_init(void)
+{
+ i_array_init(&global_debug_send_filters, 2);
+}
+
+void event_log_deinit(void)
+{
+ struct event_filter *filter;
+ array_foreach_elem(&global_debug_send_filters, filter)
+ event_filter_unref(&filter);
+ array_free(&global_debug_send_filters);
+}
/* Unset global debug log filter, if one exists. */
void event_unset_global_debug_log_filter(void);
-/* Set the global filter to sending debug events. The debug events are also
- sent if they match the global debug log filter. */
-void event_set_global_debug_send_filter(struct event_filter *filter);
-/* Unset global debug send filter, if one exists. */
-void event_unset_global_debug_send_filter(void);
+/* Register a pointer for updating the global filter to send debug events.
+ The debug events are also sent if they match the global debug log filter. */
+struct event_filter **event_global_debug_send_filter_register(void);
+/* Call when the debug send filter has been updated. */
+void event_global_debug_send_filter_updated(void);
/* Set/replace the global core filter, which abort()s on matching events. */
void event_set_global_core_log_filter(struct event_filter *filter);
/* Unset the global core filter, if one exists. */
void event_unset_global_core_log_filter(void);
+void event_log_init(void);
+void event_log_deinit(void);
+
#endif
i_array_init(&event_registered_categories, 32);
#endif
i_array_init(&event_registered_categories_representative, 16);
+ event_log_init();
}
void lib_event_deinit(void)
struct event_category *category;
#endif
+ event_log_deinit();
event_unset_global_debug_log_filter();
- event_unset_global_debug_send_filter();
event_unset_global_core_log_filter();
for (struct event *event = events; event != NULL; event = event->next) {
i_warning("Event %p leaked (parent=%p): %s:%u",