aboutsummaryrefslogtreecommitdiffstats
path: root/src/libutil
diff options
context:
space:
mode:
authorVsevolod Stakhov <vsevolod@highsecure.ru>2020-02-10 19:28:41 +0000
committerVsevolod Stakhov <vsevolod@highsecure.ru>2020-02-10 21:12:13 +0000
commit7630467d757c27fab944cda366e78ac82d45ff55 (patch)
tree85b4abaf3b2dae9272ca0792f8a8655346992cfa /src/libutil
parent4de514b49c2891c4e628c3aae4428641f8785cb3 (diff)
downloadrspamd-7630467d757c27fab944cda366e78ac82d45ff55.tar.gz
rspamd-7630467d757c27fab944cda366e78ac82d45ff55.zip
[Rework] More logger refactoring
Diffstat (limited to 'src/libutil')
-rw-r--r--src/libutil/logger.c505
-rw-r--r--src/libutil/logger.h67
-rw-r--r--src/libutil/logger_console.c4
-rw-r--r--src/libutil/logger_file.c80
-rw-r--r--src/libutil/logger_private.h7
-rw-r--r--src/libutil/logger_syslog.c6
6 files changed, 288 insertions, 381 deletions
diff --git a/src/libutil/logger.c b/src/libutil/logger.c
index f2ab3f611..af71665fd 100644
--- a/src/libutil/logger.c
+++ b/src/libutil/logger.c
@@ -24,6 +24,7 @@
static rspamd_logger_t *default_logger = NULL;
+static rspamd_logger_t *emergency_logger = NULL;
static struct rspamd_log_modules *log_modules = NULL;
guint rspamd_task_log_id = (guint)-1;
@@ -32,268 +33,190 @@ RSPAMD_CONSTRUCTOR(rspamd_task_log_init)
rspamd_task_log_id = rspamd_logger_add_debug_module("task");
}
-
-/* Logging utility functions */
-gint
-rspamd_log_open_priv (rspamd_logger_t *rspamd_log, uid_t uid, gid_t gid)
+rspamd_logger_t *
+rspamd_log_default_logger (void)
{
- gint nfd;
+ return default_logger;
+}
- if (!rspamd_log->opened) {
+rspamd_logger_t *
+rspamd_log_emergency_logger (void)
+{
+ return emergency_logger;
+}
- switch (rspamd_log->log_type) {
- case RSPAMD_LOG_CONSOLE:
- /* Dup stderr fd to simplify processing */
- nfd = dup (STDERR_FILENO);
+void
+rspamd_log_set_log_level (rspamd_logger_t *logger, gint level)
+{
+ g_assert (logger != NULL);
- if (nfd == -1) {
- return -1;
- }
- if (rspamd_log->fd != -1) {
- /*
- * Postponed closing (e.g. when we switch from
- * LOG_FILE to LOG_CONSOLE)
- */
- close (rspamd_log->fd);
- }
+ logger->log_level = level;
+}
- rspamd_log->fd = nfd;
+void
+rspamd_log_set_log_flags (rspamd_logger_t *logger, gint flags)
+{
+ g_assert (logger != NULL);
- if (isatty (STDERR_FILENO)) {
- rspamd_log->flags |= RSPAMD_LOG_FLAG_TTY;
- }
- break;
- case RSPAMD_LOG_SYSLOG:
-#ifdef HAVE_SYSLOG_H
- openlog ("rspamd", LOG_NDELAY | LOG_PID,
- rspamd_log->log_facility);
- rspamd_log->no_lock = TRUE;
- if (rspamd_log->fd != -1) {
- /*
- * Postponed closing (e.g. when we switch from
- * LOG_FILE to LOG_SYSLOG)
- */
- close (rspamd_log->fd);
- }
-#else
- return -1;
-#endif
- break;
- case RSPAMD_LOG_FILE:
- nfd = rspamd_try_open_log_fd (rspamd_log, uid, gid);
+ logger->flags = flags;
+}
- if (nfd == -1) {
- return -1;
- }
+void
+rspamd_log_close (rspamd_logger_t *logger)
+{
+ g_assert (logger != NULL);
- if (rspamd_log->fd != -1) {
- /*
- * Postponed closing (e.g. when we switch from
- * LOG_CONSOLE to LOG_FILE)
- */
- close (rspamd_log->fd);
- }
+ if (logger->debug_ip) {
+ rspamd_map_helper_destroy_radix (logger->debug_ip);
+ }
- rspamd_log->fd = nfd;
- rspamd_log->no_lock = TRUE;
- break;
- default:
- return -1;
- }
+ if (logger->pk) {
+ rspamd_pubkey_unref (logger->pk);
+ }
- rspamd_log->opened = TRUE;
- rspamd_log->enabled = TRUE;
+ if (logger->keypair) {
+ rspamd_keypair_unref (logger->keypair);
}
- return 0;
-}
+ logger->ops.dtor (logger, logger->ops.specific);
+ /* TODO: Do we really need that ? */
+ if (logger == default_logger) {
+ default_logger = NULL;
+ }
-void
-rspamd_log_close_priv (rspamd_logger_t *rspamd_log, gboolean termination, uid_t uid, gid_t gid)
-{
+ if (logger == emergency_logger) {
+ emergency_logger = NULL;
+ }
- rspamd_log_flush (rspamd_log);
- rspamd_log_reset_repeated (rspamd_log);
+ if (!logger->pool) {
+ g_free (logger);
+ }
+}
- if (rspamd_log->opened) {
- switch (rspamd_log->type) {
- case RSPAMD_LOG_SYSLOG:
-#ifdef HAVE_SYSLOG_H
- closelog ();
-#endif
- break;
- case RSPAMD_LOG_FILE:
- if (rspamd_log->fd != -1) {
-#if _POSIX_SYNCHRONIZED_IO > 0
- if (fdatasync (rspamd_log->fd) == -1) {
- msg_err ("error syncing log file: %s", strerror (errno));
- }
-#else
- if (fsync (rspamd_log->fd) == -1) {
- msg_err ("error syncing log file: %s", strerror (errno));
- }
-#endif
- close (rspamd_log->fd);
- rspamd_log->fd = -1;
- }
- break;
- case RSPAMD_LOG_CONSOLE:
- /*
- * Console logging is special: it is usually a last resort when
- * we have errors or something like that.
- *
- * Hence, we need to postpone it's closing to the moment
- * when we open (in a reliable matter!) a new logging
- * facility.
- */
- break;
- }
+bool
+rspamd_log_reopen (rspamd_logger_t *rspamd_log, struct rspamd_config *cfg,
+ uid_t uid, gid_t gid)
+{
+ void *nspec;
+ GError *err = NULL;
- rspamd_log->enabled = FALSE;
- rspamd_log->opened = FALSE;
- }
+ g_assert (rspamd_log != NULL);
- if (termination) {
- g_free (rspamd_log->log_file);
- rspamd_log->log_file = NULL;
- g_free (rspamd_log);
- }
+ nspec = rspamd_log->ops.reload (rspamd_log, cfg, rspamd_log->ops.specific,
+ uid, gid, &err);
}
-gint
-rspamd_log_reopen_priv (rspamd_logger_t *rspamd_log, uid_t uid, gid_t gid)
+static void
+rspamd_emergency_logger_dtor (gpointer d)
{
- if (rspamd_log->type == RSPAMD_LOG_FILE) {
- rspamd_log_flush (rspamd_log);
- rspamd_log_reset_repeated (rspamd_log);
+ rspamd_logger_t *logger = (rspamd_logger_t *)d;
- gint newfd = rspamd_try_open_log_fd (rspamd_log, uid, gid);
+ rspamd_log_close (logger);
+}
- if (newfd != -1) {
- rspamd_log_close_priv (rspamd_log, FALSE, uid, gid);
- rspamd_log->fd = newfd;
+rspamd_logger_t *
+rspamd_log_init (rspamd_mempool_t *pool)
+{
+ rspamd_logger_t *logger;
+ GError *err = NULL;
- rspamd_log->opened = TRUE;
- rspamd_log->enabled = TRUE;
- }
+ g_assert (default_logger == NULL);
+ g_assert (emergency_logger == NULL);
- /* Do nothing, use old settings */
+ if (pool) {
+ logger = rspamd_mempool_alloc0 (pool, sizeof (rspamd_logger_t));
+ logger->mtx = rspamd_mempool_get_mutex (pool);
}
else {
- /* Straightforward */
- rspamd_log_close_priv (rspamd_log, FALSE, uid, gid);
-
- if (rspamd_log_open_priv (rspamd_log, uid, gid) == 0) {
- return 0;
- }
+ logger = g_malloc0 (sizeof (rspamd_logger_t));
}
- return -1;
-}
-/**
- * Open log file or initialize other structures
- */
-gint
-rspamd_log_open (rspamd_logger_t *logger)
-{
- return rspamd_log_open_priv (logger, -1, -1);
-}
+ logger->pool = pool;
+ logger->process_type = "main";
-/**
- * Close log file or destroy other structures
- */
-void
-rspamd_log_close (rspamd_logger_t *logger, gboolean termination)
-{
- rspamd_log_close_priv (logger, termination, -1, -1);
-}
+ const struct rspamd_logger_funcs *funcs = &console_log_funcs;
+ memcpy (&logger->ops, funcs, sizeof (*funcs));
-/**
- * Close and open log again
- */
-gint
-rspamd_log_reopen (rspamd_logger_t *logger)
-{
- return rspamd_log_reopen_priv (logger, -1, -1);
+ logger->ops.specific = logger->ops.init (logger, NULL, -1, -1, &err);
+
+ if (logger->ops.specific == NULL) {
+ rspamd_fprintf (stderr, "fatal error: cannot init console logging: %e\n",
+ err);
+ g_error_free (err);
+
+ exit (EXIT_FAILURE);
+ }
+
+ default_logger = logger;
+ emergency_logger = logger;
+
+ rspamd_mempool_add_destructor (pool, rspamd_emergency_logger_dtor,
+ emergency_logger);
+
+ return logger;
}
-/*
- * Setup logger
- */
-void
-rspamd_set_logger (struct rspamd_config *cfg,
- GQuark ptype,
- rspamd_logger_t **plogger,
- rspamd_mempool_t *pool)
+rspamd_logger_t *
+rspamd_log_open_specific (rspamd_mempool_t *pool,
+ struct rspamd_config *cfg,
+ const gchar *ptype,
+ uid_t uid, gid_t gid)
{
rspamd_logger_t *logger;
+ GError *err = NULL;
- if (plogger == NULL || *plogger == NULL) {
- logger = g_malloc0 (sizeof (rspamd_logger_t));
- logger->fd = -1;
-
- if (cfg->log_error_elts > 0 && pool) {
- logger->errlog = rspamd_mempool_alloc0_shared (pool,
- sizeof (*logger->errlog));
- logger->errlog->pool = pool;
- logger->errlog->max_elts = cfg->log_error_elts;
- logger->errlog->elt_len = cfg->log_error_elt_maxlen;
- logger->errlog->elts = rspamd_mempool_alloc0_shared (pool,
- sizeof (struct rspamd_logger_error_elt) * cfg->log_error_elts +
- cfg->log_error_elt_maxlen * cfg->log_error_elts);
- }
-
- if (pool) {
- logger->mtx = rspamd_mempool_get_mutex (pool);
- }
+ g_assert (default_logger == NULL);
+ g_assert (emergency_logger == NULL);
- if (plogger) {
- *plogger = logger;
- }
+ if (pool) {
+ logger = rspamd_mempool_alloc0 (pool, sizeof (rspamd_logger_t));
+ logger->mtx = rspamd_mempool_get_mutex (pool);
}
else {
- logger = *plogger;
+ logger = g_malloc0 (sizeof (rspamd_logger_t));
}
- logger->type = cfg->log_type;
- logger->pid = getpid ();
- logger->process_type = ptype;
+ logger->pool = pool;
- switch (cfg->log_type) {
- case RSPAMD_LOG_CONSOLE:
- logger->log_func = file_log_function;
- break;
- case RSPAMD_LOG_SYSLOG:
- logger->log_func = syslog_log_function;
- break;
- case RSPAMD_LOG_FILE:
- logger->log_func = file_log_function;
- break;
+ if (cfg->log_error_elts > 0 && pool) {
+ logger->errlog = rspamd_mempool_alloc0_shared (pool,
+ sizeof (*logger->errlog));
+ logger->errlog->pool = pool;
+ logger->errlog->max_elts = cfg->log_error_elts;
+ logger->errlog->elt_len = cfg->log_error_elt_maxlen;
+ logger->errlog->elts = rspamd_mempool_alloc0_shared (pool,
+ sizeof (struct rspamd_logger_error_elt) * cfg->log_error_elts +
+ cfg->log_error_elt_maxlen * cfg->log_error_elts);
}
- logger->log_type = cfg->log_type;
+ const struct rspamd_logger_funcs *funcs = NULL;
- if (!(logger->flags & RSPAMD_LOG_FLAG_ENFORCED)) {
- logger->log_level = cfg->log_level;
+ switch (cfg->log_type) {
+ case RSPAMD_LOG_CONSOLE:
+ funcs = &console_log_funcs;
+ break;
+ case RSPAMD_LOG_SYSLOG:
+ funcs = &syslog_log_funcs;
+ break;
+ case RSPAMD_LOG_FILE:
+ funcs = &file_log_funcs;
+ break;
}
- logger->log_buffered = cfg->log_buffered;
- logger->log_silent_workers = cfg->log_silent_workers;
- logger->log_buf_size = cfg->log_buf_size;
+ g_assert (funcs != NULL);
+ memcpy (&logger->ops, funcs, sizeof (*funcs));
- if (logger->log_file) {
- g_free (logger->log_file);
- logger->log_file = NULL;
- }
- if (cfg->log_file) {
- logger->log_file = g_strdup (cfg->log_file);
+ logger->pid = getpid ();
+ logger->process_type = ptype;
+
+ if (!(logger->flags & RSPAMD_LOG_FLAG_ENFORCED)) {
+ logger->log_level = cfg->log_level;
}
logger->flags = cfg->log_flags;
-
/* Set up conditional logging */
if (cfg->debug_ip_map != NULL) {
/* Try to add it as map first of all */
@@ -309,20 +232,6 @@ rspamd_set_logger (struct rspamd_config *cfg,
NULL,
NULL);
}
- else if (logger->debug_ip) {
- rspamd_map_helper_destroy_radix (logger->debug_ip);
- logger->debug_ip = NULL;
- }
-
- if (logger->pk) {
- rspamd_pubkey_unref (logger->pk);
- }
- logger->pk = NULL;
-
- if (logger->keypair) {
- rspamd_keypair_unref (logger->keypair);
- }
- logger->keypair = NULL;
if (cfg->log_encryption_key) {
logger->pk = rspamd_pubkey_ref (cfg->log_encryption_key);
@@ -334,14 +243,29 @@ rspamd_set_logger (struct rspamd_config *cfg,
default_logger = logger;
}
+
/**
* Used after fork() for updating structure params
*/
void
-rspamd_log_update_pid (GQuark ptype, rspamd_logger_t *rspamd_log)
+rspamd_log_on_fork (GQuark ptype, struct rspamd_config *cfg,
+ rspamd_logger_t *logger)
{
- rspamd_log->pid = getpid ();
- rspamd_log->process_type = g_quark_to_string (ptype);
+ logger->pid = getpid ();
+ logger->process_type = g_quark_to_string (ptype);
+
+ if (logger->ops.on_fork) {
+ GError *err = NULL;
+
+ bool ret = logger->ops.on_fork (logger, cfg, logger->ops.specific, &err);
+
+ if (!ret && emergency_logger) {
+ rspamd_common_log_function (emergency_logger, G_LOG_LEVEL_CRITICAL,
+ "logger", NULL, G_STRFUNC,
+ "cannot update logging on fork: %e", err);
+ g_error_free (err);
+ }
+ }
}
static inline gboolean
@@ -455,13 +379,14 @@ rspamd_log_write_ringbuffer (rspamd_logger_t *rspamd_log,
g_atomic_int_set (&elt->completed, 1);
}
-void
+bool
rspamd_common_logv (rspamd_logger_t *rspamd_log, gint level_flags,
const gchar *module, const gchar *id, const gchar *function,
const gchar *fmt, va_list args)
{
gchar logbuf[RSPAMD_LOGBUF_SIZE], *end;
gint level = level_flags & (RSPAMD_LOG_LEVEL_MASK & G_LOG_LEVEL_MASK), mod_id;
+ bool ret = false;
if (G_UNLIKELY (rspamd_log == NULL)) {
rspamd_log = default_logger;
@@ -491,23 +416,23 @@ rspamd_common_logv (rspamd_logger_t *rspamd_log, gint level_flags,
encrypted = rspamd_log_encrypt_message (logbuf, end, &enc_len,
rspamd_log);
- rspamd_log->log_func (module, id,
+ ret = rspamd_log->ops.log (module, id,
function,
level_flags,
encrypted,
enc_len,
rspamd_log,
- rspamd_log->log_arg);
+ rspamd_log->ops.specific);
g_free (encrypted);
}
else {
- rspamd_log->log_func (module, id,
+ ret = rspamd_log->ops.log (module, id,
function,
level_flags,
logbuf,
end - logbuf,
rspamd_log,
- rspamd_log->log_arg);
+ rspamd_log->ops.specific);
}
switch (level) {
@@ -530,12 +455,14 @@ rspamd_common_logv (rspamd_logger_t *rspamd_log, gint level_flags,
}
}
}
+
+ return ret;
}
/**
* This log functions select real logger and write message if level is less or equal to configured log level
*/
-void
+bool
rspamd_common_log_function (rspamd_logger_t *rspamd_log,
gint level_flags,
const gchar *module, const gchar *id,
@@ -546,19 +473,21 @@ rspamd_common_log_function (rspamd_logger_t *rspamd_log,
va_list vp;
va_start (vp, fmt);
- rspamd_common_logv (rspamd_log, level_flags, module, id, function, fmt, vp);
+ bool ret = rspamd_common_logv (rspamd_log, level_flags, module, id, function, fmt, vp);
va_end (vp);
+
+ return ret;
}
-void
+bool
rspamd_default_logv (gint level_flags, const gchar *module, const gchar *id,
const gchar *function,
const gchar *fmt, va_list args)
{
- rspamd_common_logv (NULL, level_flags, module, id, function, fmt, args);
+ return rspamd_common_logv (NULL, level_flags, module, id, function, fmt, args);
}
-void
+bool
rspamd_default_log_function (gint level_flags,
const gchar *module, const gchar *id,
const gchar *function, const gchar *fmt, ...)
@@ -567,64 +496,20 @@ rspamd_default_log_function (gint level_flags,
va_list vp;
va_start (vp, fmt);
- rspamd_default_logv (level_flags, module, id, function, fmt, vp);
+ bool ret = rspamd_default_logv (level_flags, module, id, function, fmt, vp);
va_end (vp);
-}
-
-
-/**
- * Syslog interface for logging
- */
-static void
-syslog_log_function (const gchar *module, const gchar *id,
- const gchar *function,
- gint level_flags,
- const gchar *message,
- gsize mlen,
- rspamd_logger_t *rspamd_log,
- gpointer arg)
-{
-#ifdef HAVE_SYSLOG_H
- struct {
- GLogLevelFlags glib_level;
- gint syslog_level;
- } levels_match[] = {
- {G_LOG_LEVEL_DEBUG, LOG_DEBUG},
- {G_LOG_LEVEL_INFO, LOG_INFO},
- {G_LOG_LEVEL_WARNING, LOG_WARNING},
- {G_LOG_LEVEL_CRITICAL, LOG_ERR}
- };
- unsigned i;
- gint syslog_level;
-
- if (!(level_flags & RSPAMD_LOG_FORCED) && !rspamd_log->enabled) {
- return;
- }
- /* Detect level */
- syslog_level = LOG_DEBUG;
- for (i = 0; i < G_N_ELEMENTS (levels_match); i ++) {
- if (level_flags & levels_match[i].glib_level) {
- syslog_level = levels_match[i].syslog_level;
- break;
- }
- }
-
- syslog (syslog_level, "<%.*s>; %s; %s: %*.s",
- LOG_ID, id != NULL ? id : "",
- module != NULL ? module : "",
- function != NULL ? function : "",
- (gint)mlen, message);
-#endif
+ return ret;
}
+
/**
* Main file interface for logging
*/
/**
* Write log line depending on ip
*/
-void
+bool
rspamd_conditional_debug (rspamd_logger_t *rspamd_log,
rspamd_inet_addr_t *addr, const gchar *module, const gchar *id,
const gchar *function, const gchar *fmt, ...)
@@ -645,7 +530,7 @@ rspamd_conditional_debug (rspamd_logger_t *rspamd_log,
if (rspamd_log->debug_ip && addr != NULL) {
if (rspamd_match_radix_map_addr (rspamd_log->debug_ip,
addr) == NULL) {
- return;
+ return false;
}
}
@@ -653,17 +538,19 @@ rspamd_conditional_debug (rspamd_logger_t *rspamd_log,
end = rspamd_vsnprintf (logbuf, sizeof (logbuf), fmt, vp);
*end = '\0';
va_end (vp);
- rspamd_log->log_func (module, id,
+ return rspamd_log->ops.log (module, id,
function,
G_LOG_LEVEL_DEBUG | RSPAMD_LOG_FORCED,
logbuf,
end - logbuf,
rspamd_log,
- rspamd_log->log_arg);
+ rspamd_log->ops.specific);
}
+
+ return false;
}
-void
+bool
rspamd_conditional_debug_fast (rspamd_logger_t *rspamd_log,
rspamd_inet_addr_t *addr,
guint mod_id, const gchar *module, const gchar *id,
@@ -682,7 +569,7 @@ rspamd_conditional_debug_fast (rspamd_logger_t *rspamd_log,
if (rspamd_log->debug_ip && addr != NULL) {
if (rspamd_match_radix_map_addr (rspamd_log->debug_ip, addr)
== NULL) {
- return;
+ return false;
}
}
@@ -690,17 +577,19 @@ rspamd_conditional_debug_fast (rspamd_logger_t *rspamd_log,
end = rspamd_vsnprintf (logbuf, sizeof (logbuf), fmt, vp);
*end = '\0';
va_end (vp);
- rspamd_log->log_func (module, id,
+ return rspamd_log->ops.log (module, id,
function,
G_LOG_LEVEL_DEBUG | RSPAMD_LOG_FORCED,
logbuf,
end - logbuf,
rspamd_log,
- rspamd_log->log_arg);
+ rspamd_log->ops.specific);
}
+
+ return false;
}
-void
+bool
rspamd_conditional_debug_fast_num_id (rspamd_logger_t *rspamd_log,
rspamd_inet_addr_t *addr,
guint mod_id, const gchar *module, guint64 id,
@@ -719,7 +608,7 @@ rspamd_conditional_debug_fast_num_id (rspamd_logger_t *rspamd_log,
if (rspamd_log->debug_ip && addr != NULL) {
if (rspamd_match_radix_map_addr (rspamd_log->debug_ip, addr)
== NULL) {
- return;
+ return false;
}
}
@@ -728,14 +617,16 @@ rspamd_conditional_debug_fast_num_id (rspamd_logger_t *rspamd_log,
end = rspamd_vsnprintf (logbuf, sizeof (logbuf), fmt, vp);
*end = '\0';
va_end (vp);
- rspamd_log->log_func (module, idbuf,
+ return rspamd_log->ops.log (module, idbuf,
function,
G_LOG_LEVEL_DEBUG | RSPAMD_LOG_FORCED,
logbuf,
end - logbuf,
rspamd_log,
- rspamd_log->log_arg);
+ rspamd_log->ops.specific);
}
+
+ return false;
}
/**
@@ -751,13 +642,13 @@ rspamd_glib_log_function (const gchar *log_domain,
if (rspamd_log->enabled &&
rspamd_logger_need_log (rspamd_log, log_level, -1)) {
- rspamd_log->log_func ("glib", NULL,
+ rspamd_log->ops.log ("glib", NULL,
NULL,
log_level,
message,
strlen (message),
rspamd_log,
- rspamd_log->log_arg);
+ rspamd_log->ops.specific);
}
}
@@ -951,26 +842,8 @@ rspamd_logger_configure_modules (GHashTable *mods_enabled)
}
}
-rspamd_logger_t*
-rspamd_logger_get_singleton (void)
-{
- return default_logger;
-}
-
struct rspamd_logger_funcs*
rspamd_logger_set_log_function (rspamd_logger_t *logger,
- struct rspamd_logger_funcs *nfuncs);
+ struct rspamd_logger_funcs *nfuncs)
{
- if (logger == NULL) {
- logger = default_logger;
- }
-
- g_assert (logger != NULL);
-
- rspamd_log_func_t old_func = logger->log_func;
-
- logger->log_func = nfunc;
- logger->log_arg = narg;
-
- return old_func;
} \ No newline at end of file
diff --git a/src/libutil/logger.h b/src/libutil/logger.h
index e98905f76..f8ecbf1ee 100644
--- a/src/libutil/logger.h
+++ b/src/libutil/logger.h
@@ -33,6 +33,10 @@ typedef void * (*rspamd_log_init_func) (rspamd_logger_t *logger,
struct rspamd_config *cfg,
uid_t uid, gid_t gid,
GError **err);
+typedef bool (*rspamd_log_on_fork_func) (rspamd_logger_t *logger,
+ struct rspamd_config *cfg,
+ gpointer arg,
+ GError **err);
typedef void* (*rspamd_log_reload_func) (rspamd_logger_t *logger,
struct rspamd_config *cfg,
gpointer arg,
@@ -46,59 +50,74 @@ struct rspamd_logger_funcs {
rspamd_log_reload_func reload;
rspamd_log_dtor_func dtor;
rspamd_log_func_t log;
+ rspamd_log_on_fork_func on_fork;
gpointer specific;
};
#define RSPAMD_LOGBUF_SIZE 8192
/**
- * Init logger
+ * Opens a new (initial) logger with console type
+ * This logger is also used as an emergency logger
+ * @return new rspamd logger object
*/
-void rspamd_set_logger (struct rspamd_config *cfg,
- GQuark ptype,
- rspamd_logger_t **plogger,
- rspamd_mempool_t *pool);
+rspamd_logger_t * rspamd_log_open_emergency (rspamd_mempool_t *pool);
/**
- * Open log file or initialize other structures
+ * Open specific (configured logging)
+ * @param pool
+ * @param config
+ * @param uid
+ * @param gid
+ * @return
*/
-bool rspamd_log_open (rspamd_logger_t *logger);
+rspamd_logger_t * rspamd_log_open_specific (rspamd_mempool_t *pool,
+ struct rspamd_config *config,
+ const gchar *ptype,
+ uid_t uid, gid_t gid);
/**
- * Close log file or destroy other structures
+ * Set log level (from GLogLevelFlags)
+ * @param logger
+ * @param level
*/
-bool rspamd_log_close (rspamd_logger_t *logger, gboolean termination);
-
+void rspamd_log_set_log_level (rspamd_logger_t *logger, gint level);
/**
- * Close and open log again
+ * Set log flags (from enum rspamd_log_flags)
+ * @param logger
+ * @param flags
*/
-bool rspamd_log_reopen (rspamd_logger_t *logger);
+void rspamd_log_set_log_flags (rspamd_logger_t *logger, gint flags);
/**
- * Open log file or initialize other structures for privileged processes
+ * Close log file or destroy other structures
*/
-bool rspamd_log_open_priv (rspamd_logger_t *logger, uid_t uid, gid_t gid);
+void rspamd_log_close (rspamd_logger_t *logger);
+
-/**
- * Close log file or destroy other structures for privileged processes
- */
-void rspamd_log_close_priv (rspamd_logger_t *logger, gboolean termination, uid_t uid, gid_t gid);
+
+rspamd_logger_t * rspamd_log_default_logger (void);
+rspamd_logger_t * rspamd_log_emergency_logger (void);
/**
* Close and open log again for privileged processes
*/
-bool rspamd_log_reopen_priv (rspamd_logger_t *logger, uid_t uid, gid_t gid);
+bool rspamd_log_reopen (rspamd_logger_t *logger, struct rspamd_config *cfg,
+ uid_t uid, gid_t gid);
/**
* Set log pid
*/
-void rspamd_log_update_pid (GQuark ptype, rspamd_logger_t *logger);
+void rspamd_log_on_fork (GQuark ptype, struct rspamd_config *cfg,
+ rspamd_logger_t *logger);
/**
* Log function that is compatible for glib messages
*/
void rspamd_glib_log_function (const gchar *log_domain,
- GLogLevelFlags log_level, const gchar *message, gpointer arg);
+ GLogLevelFlags log_level,
+ const gchar *message,
+ gpointer arg);
/**
* Log function for printing glib assertions
@@ -208,12 +227,6 @@ const guint64 *rspamd_log_counters (rspamd_logger_t *logger);
ucl_object_t *rspamd_log_errorbuf_export (const rspamd_logger_t *logger);
/**
- * Returns the current logger object
- * @return
- */
-rspamd_logger_t *rspamd_logger_get_singleton (void);
-
-/**
* Sets new logger functions and initialise logging if needed
* @param logger
* @param nfuncs
diff --git a/src/libutil/logger_console.c b/src/libutil/logger_console.c
index c410bdd79..fae12ea11 100644
--- a/src/libutil/logger_console.c
+++ b/src/libutil/logger_console.c
@@ -63,7 +63,7 @@ rspamd_log_console_init (rspamd_logger_t *logger, struct rspamd_config *cfg,
priv = g_malloc0 (sizeof (*priv));
priv->log_color = (logger->flags & RSPAMD_LOG_FLAG_COLOR);
- priv->log_rspamadm (logger->flags & RSPAMD_LOG_FLAG_RSPAMADM);
+ priv->log_rspamadm = (logger->flags & RSPAMD_LOG_FLAG_RSPAMADM);
if (priv->log_rspamadm) {
priv->fd = dup (STDOUT_FILENO);
@@ -78,7 +78,7 @@ rspamd_log_console_init (rspamd_logger_t *logger, struct rspamd_config *cfg,
g_set_error (err, CONSOLE_LOG_QUARK, errno,
"open_log: cannot dup console fd: %s, %s\n",
strerror (errno));
- rspamd_log_console_dtor (priv);
+ rspamd_log_console_dtor (logger, priv);
return NULL;
}
diff --git a/src/libutil/logger_file.c b/src/libutil/logger_file.c
index b4bb6208b..9a242ac61 100644
--- a/src/libutil/logger_file.c
+++ b/src/libutil/logger_file.c
@@ -261,44 +261,42 @@ rspamd_log_reset_repeated (rspamd_logger_t *rspamd_log,
gchar tmpbuf[256];
gssize r;
- if (rspamd_log->opened) {
- if (priv->repeats > REPEATS_MIN) {
- r = rspamd_snprintf (tmpbuf,
- sizeof (tmpbuf),
- "Last message repeated %ud times",
- priv->repeats - REPEATS_MIN);
- priv->repeats = 0;
-
- if (priv->saved_message) {
- rspamd_log_file_log (priv->saved_module,
- priv->saved_id,
- priv->saved_function,
- priv->saved_loglevel | RSPAMD_LOG_FORCED,
- priv->saved_message,
- priv->saved_mlen,
- rspamd_log,
- priv);
-
- g_free (priv->saved_message);
- g_free (priv->saved_function);
- g_free (priv->saved_module);
- g_free (priv->saved_id);
- priv->saved_message = NULL;
- priv->saved_function = NULL;
- priv->saved_module = NULL;
- priv->saved_id = NULL;
- }
-
- /* It is safe to use temporary buffer here as it is not static */
- rspamd_log_file_log (NULL, NULL,
- G_STRFUNC,
+ if (priv->repeats > REPEATS_MIN) {
+ r = rspamd_snprintf (tmpbuf,
+ sizeof (tmpbuf),
+ "Last message repeated %ud times",
+ priv->repeats - REPEATS_MIN);
+ priv->repeats = 0;
+
+ if (priv->saved_message) {
+ rspamd_log_file_log (priv->saved_module,
+ priv->saved_id,
+ priv->saved_function,
priv->saved_loglevel | RSPAMD_LOG_FORCED,
- tmpbuf,
- r,
+ priv->saved_message,
+ priv->saved_mlen,
rspamd_log,
priv);
- rspamd_log_flush (rspamd_log, priv);
+
+ g_free (priv->saved_message);
+ g_free (priv->saved_function);
+ g_free (priv->saved_module);
+ g_free (priv->saved_id);
+ priv->saved_message = NULL;
+ priv->saved_function = NULL;
+ priv->saved_module = NULL;
+ priv->saved_id = NULL;
}
+
+ /* It is safe to use temporary buffer here as it is not static */
+ rspamd_log_file_log (NULL, NULL,
+ G_STRFUNC,
+ priv->saved_loglevel | RSPAMD_LOG_FORCED,
+ tmpbuf,
+ r,
+ rspamd_log,
+ priv);
+ rspamd_log_flush (rspamd_log, priv);
}
}
@@ -340,7 +338,7 @@ rspamd_log_file_init (rspamd_logger_t *logger, struct rspamd_config *cfg,
{
struct rspamd_file_logger_priv *priv;
- if (!cfg->cfg_name) {
+ if (!cfg || !cfg->cfg_name) {
g_set_error (err, FILE_LOG_QUARK, EINVAL,
"no log file specified");
return NULL;
@@ -585,3 +583,15 @@ rspamd_log_file_reload (rspamd_logger_t *logger, struct rspamd_config *cfg,
return npriv;
}
+
+bool
+rspamd_log_file_on_fork (rspamd_logger_t *logger, struct rspamd_config *cfg,
+ gpointer arg, GError **err)
+{
+ struct rspamd_file_logger_priv *priv = (struct rspamd_file_logger_priv *)arg;
+
+ rspamd_log_reset_repeated (logger, priv);
+ rspamd_log_flush (logger, priv);
+
+ return true;
+} \ No newline at end of file
diff --git a/src/libutil/logger_private.h b/src/libutil/logger_private.h
index 84ec3b026..f4b6fe8d6 100644
--- a/src/libutil/logger_private.h
+++ b/src/libutil/logger_private.h
@@ -70,12 +70,12 @@ struct rspamd_logger_s {
gboolean enabled;
gboolean is_debug;
gboolean no_lock;
- gboolean opened;
pid_t pid;
const gchar *process_type;
struct rspamd_radix_map_helper *debug_ip;
rspamd_mempool_mutex_t *mtx;
+ rspamd_mempool_t *pool;
guint64 log_cnt[4];
};
@@ -98,12 +98,15 @@ bool rspamd_log_file_log (const gchar *module, const gchar *id,
gsize mlen,
rspamd_logger_t *rspamd_log,
gpointer arg);
+bool rspamd_log_file_on_fork (rspamd_logger_t *logger, struct rspamd_config *cfg,
+ gpointer arg, GError **err);
const static struct rspamd_logger_funcs file_log_funcs = {
.init = rspamd_log_file_init,
.dtor = rspamd_log_file_dtor,
.reload = rspamd_log_file_reload,
.log = rspamd_log_file_log,
+ .on_fork = rspamd_log_file_on_fork,
};
/*
@@ -127,6 +130,7 @@ const static struct rspamd_logger_funcs syslog_log_funcs = {
.dtor = rspamd_log_syslog_dtor,
.reload = rspamd_log_syslog_reload,
.log = rspamd_log_syslog_log,
+ .on_fork = NULL,
};
/*
@@ -150,6 +154,7 @@ const static struct rspamd_logger_funcs console_log_funcs = {
.dtor = rspamd_log_console_dtor,
.reload = rspamd_log_console_reload,
.log = rspamd_log_console_log,
+ .on_fork = NULL,
};
#endif
diff --git a/src/libutil/logger_syslog.c b/src/libutil/logger_syslog.c
index 15afabdb9..5a295b288 100644
--- a/src/libutil/logger_syslog.c
+++ b/src/libutil/logger_syslog.c
@@ -34,6 +34,12 @@ rspamd_log_syslog_init (rspamd_logger_t *logger, struct rspamd_config *cfg,
{
struct rspamd_syslog_logger_priv *priv;
+ if (!cfg) {
+ g_set_error (err, SYSLOG_LOG_QUARK, EINVAL,
+ "no log config specified");
+ return NULL;
+ }
+
priv = g_malloc0 (sizeof (*priv));
priv->log_facility = cfg->log_facility;