aboutsummaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
authorTobias Brunner <tobias@strongswan.org>2012-10-04 18:07:42 +0200
committerTobias Brunner <tobias@strongswan.org>2012-10-18 14:42:10 +0200
commitd35d6691807d7a675aaadd3a5b085ad60af16794 (patch)
treed0e05c25ca8fa15a28829348ecd19a448aa54e74 /src
parent18a8893e8ea593cf41575c666693bb3c3ef30a66 (diff)
downloadstrongswan-d35d6691807d7a675aaadd3a5b085ad60af16794.tar.bz2
strongswan-d35d6691807d7a675aaadd3a5b085ad60af16794.tar.xz
Make syslog and file loggers configurable at runtime
Diffstat (limited to 'src')
-rw-r--r--src/charon-nm/charon-nm.c2
-rw-r--r--src/charon/charon.c52
-rw-r--r--src/conftest/conftest.c17
-rw-r--r--src/frontends/android/jni/libandroidbridge/charonservice.c16
-rw-r--r--src/libcharon/bus/listeners/file_logger.c106
-rw-r--r--src/libcharon/bus/listeners/file_logger.h29
-rw-r--r--src/libcharon/bus/listeners/sys_logger.c32
-rw-r--r--src/libcharon/bus/listeners/sys_logger.h11
8 files changed, 185 insertions, 80 deletions
diff --git a/src/charon-nm/charon-nm.c b/src/charon-nm/charon-nm.c
index 35e906778..4857c9979 100644
--- a/src/charon-nm/charon-nm.c
+++ b/src/charon-nm/charon-nm.c
@@ -125,7 +125,7 @@ static void initialize_logger()
debug_t group;
level_t def;
- sys_logger = sys_logger_create(LOG_DAEMON, FALSE);
+ sys_logger = sys_logger_create(LOG_DAEMON);
def = lib->settings->get_int(lib->settings,
"charon-nm.syslog.default", 1);
for (group = 0; group < DBG_MAX; group++)
diff --git a/src/charon/charon.c b/src/charon/charon.c
index bd36c72f4..ba3e8fb21 100644
--- a/src/charon/charon.c
+++ b/src/charon/charon.c
@@ -250,8 +250,6 @@ static void initialize_loggers(bool use_stderr, level_t levels[])
int loggers_defined = 0;
debug_t group;
level_t def;
- bool append, ike_name;
- FILE *file;
/* setup sysloggers */
identifier = lib->settings->get_str(lib->settings,
@@ -266,20 +264,22 @@ static void initialize_loggers(bool use_stderr, level_t levels[])
{
loggers_defined++;
- ike_name = lib->settings->get_bool(lib->settings,
- "charon.syslog.%s.ike_name", FALSE, facility);
if (streq(facility, "daemon"))
{
- sys_logger = sys_logger_create(LOG_DAEMON, ike_name);
+ sys_logger = sys_logger_create(LOG_DAEMON);
}
else if (streq(facility, "auth"))
{
- sys_logger = sys_logger_create(LOG_AUTHPRIV, ike_name);
+ sys_logger = sys_logger_create(LOG_AUTHPRIV);
}
else
{
continue;
}
+ sys_logger->set_options(sys_logger,
+ lib->settings->get_bool(lib->settings,
+ "charon.syslog.%s.ike_name", FALSE, facility));
+
def = lib->settings->get_int(lib->settings,
"charon.syslog.%s.default", 1, facility);
for (group = 0; group < DBG_MAX; group++)
@@ -300,36 +300,17 @@ static void initialize_loggers(bool use_stderr, level_t levels[])
while (enumerator->enumerate(enumerator, &filename))
{
loggers_defined++;
- if (streq(filename, "stderr"))
- {
- file = stderr;
- }
- else if (streq(filename, "stdout"))
- {
- file = stdout;
- }
- else
- {
- append = lib->settings->get_bool(lib->settings,
- "charon.filelog.%s.append", TRUE, filename);
- file = fopen(filename, append ? "a" : "w");
- if (file == NULL)
- {
- DBG1(DBG_DMN, "opening file %s for logging failed: %s",
- filename, strerror(errno));
- continue;
- }
- if (lib->settings->get_bool(lib->settings,
- "charon.filelog.%s.flush_line", FALSE, filename))
- {
- setlinebuf(file);
- }
- }
- file_logger = file_logger_create(file,
+ file_logger = file_logger_create(filename);
+ file_logger->set_options(file_logger,
lib->settings->get_str(lib->settings,
"charon.filelog.%s.time_format", NULL, filename),
lib->settings->get_bool(lib->settings,
"charon.filelog.%s.ike_name", FALSE, filename));
+ file_logger->open(file_logger,
+ lib->settings->get_bool(lib->settings,
+ "charon.filelog.%s.flush_line", FALSE, filename),
+ lib->settings->get_bool(lib->settings,
+ "charon.filelog.%s.append", TRUE, filename));
def = lib->settings->get_int(lib->settings,
"charon.filelog.%s.default", 1, filename);
for (group = 0; group < DBG_MAX; group++)
@@ -349,10 +330,11 @@ static void initialize_loggers(bool use_stderr, level_t levels[])
if (!loggers_defined)
{
/* set up default stdout file_logger */
- file_logger = file_logger_create(stdout, NULL, FALSE);
+ file_logger = file_logger_create("stdout");
+ file_logger->open(file_logger, FALSE, FALSE);
charon->file_loggers->insert_last(charon->file_loggers, file_logger);
/* set up default daemon sys_logger */
- sys_logger = sys_logger_create(LOG_DAEMON, FALSE);
+ sys_logger = sys_logger_create(LOG_DAEMON);
charon->sys_loggers->insert_last(charon->sys_loggers, sys_logger);
for (group = 0; group < DBG_MAX; group++)
{
@@ -366,7 +348,7 @@ static void initialize_loggers(bool use_stderr, level_t levels[])
charon->bus->add_logger(charon->bus, &sys_logger->logger);
/* set up default auth sys_logger */
- sys_logger = sys_logger_create(LOG_AUTHPRIV, FALSE);
+ sys_logger = sys_logger_create(LOG_AUTHPRIV);
sys_logger->set_level(sys_logger, DBG_ANY, LEVEL_AUDIT);
charon->sys_loggers->insert_last(charon->sys_loggers, sys_logger);
charon->bus->add_logger(charon->bus, &sys_logger->logger);
diff --git a/src/conftest/conftest.c b/src/conftest/conftest.c
index 8df5d6fc2..bb4c5ed97 100644
--- a/src/conftest/conftest.c
+++ b/src/conftest/conftest.c
@@ -26,6 +26,7 @@
#include "config.h"
#include "hooks/hook.h"
+#include <bus/listeners/file_logger.h>
#include <threading/thread.h>
#include <credentials/certificates/x509.h>
@@ -383,7 +384,6 @@ static void load_loggers(file_logger_t *logger)
{
enumerator_t *enumerator;
char *section;
- FILE *file;
load_log_levels(logger, "stdout");
@@ -392,14 +392,9 @@ static void load_loggers(file_logger_t *logger)
{
if (!streq(section, "stdout"))
{
- file = fopen(section, "w");
- if (file == NULL)
- {
- fprintf(stderr, "opening file %s for logging failed: %s",
- section, strerror(errno));
- continue;
- }
- logger = file_logger_create(file, NULL, FALSE);
+ logger = file_logger_create(section);
+ logger->set_options(logger, NULL, FALSE);
+ logger->open(logger, FALSE, FALSE);
load_log_levels(logger, section);
charon->bus->add_logger(charon->bus, &logger->logger);
conftest->loggers->insert_last(conftest->loggers, logger);
@@ -447,7 +442,9 @@ int main(int argc, char *argv[])
);
lib->credmgr->add_set(lib->credmgr, &conftest->creds->set);
- logger = file_logger_create(stdout, NULL, FALSE);
+ logger = file_logger_create("stdout");
+ logger->set_options(logger, NULL, FALSE);
+ logger->open(logger, FALSE, FALSE);
logger->set_level(logger, DBG_ANY, LEVEL_CTRL);
charon->bus->add_logger(charon->bus, &logger->logger);
conftest->loggers->insert_last(conftest->loggers, logger);
diff --git a/src/frontends/android/jni/libandroidbridge/charonservice.c b/src/frontends/android/jni/libandroidbridge/charonservice.c
index 1fde9887b..1756eda25 100644
--- a/src/frontends/android/jni/libandroidbridge/charonservice.c
+++ b/src/frontends/android/jni/libandroidbridge/charonservice.c
@@ -136,20 +136,10 @@ static void initialize_logger(char *logfile)
{
file_logger_t *file_logger;
debug_t group;
- FILE *file;
- /* truncate an existing file */
- file = fopen(logfile, "w");
- if (!file)
- {
- DBG1(DBG_DMN, "opening file %s for logging failed: %s",
- logfile, strerror(errno));
- return;
- }
- /* flush each line */
- setlinebuf(file);
-
- file_logger = file_logger_create(file, "%b %e %T", FALSE);
+ file_logger = file_logger_create(logfile);
+ file_logger->set_options(file_logger, "%b %e %T", FALSE);
+ file_logger->open(file_logger, TRUE, FALSE);
for (group = 0; group < DBG_MAX; group++)
{
file_logger->set_level(file_logger, group, ANDROID_DEBUG_LEVEL);
diff --git a/src/libcharon/bus/listeners/file_logger.c b/src/libcharon/bus/listeners/file_logger.c
index 9c8458eb5..68a386d11 100644
--- a/src/libcharon/bus/listeners/file_logger.c
+++ b/src/libcharon/bus/listeners/file_logger.c
@@ -17,10 +17,15 @@
#include <stdio.h>
#include <string.h>
#include <time.h>
+#include <errno.h>
+#include <unistd.h>
+#include <sys/types.h>
#include "file_logger.h"
+#include <daemon.h>
#include <threading/mutex.h>
+#include <threading/rwlock.h>
typedef struct private_file_logger_t private_file_logger_t;
@@ -35,7 +40,12 @@ struct private_file_logger_t {
file_logger_t public;
/**
- * output file
+ * File name of the target
+ */
+ char *filename;
+
+ /**
+ * Current output file
*/
FILE *out;
@@ -58,6 +68,11 @@ struct private_file_logger_t {
* Mutex to ensure multi-line log messages are not torn apart
*/
mutex_t *mutex;
+
+ /**
+ * Lock to read/write options (FD, levels, time_format, etc.)
+ */
+ rwlock_t *lock;
};
METHOD(logger_t, log_, void,
@@ -69,6 +84,12 @@ METHOD(logger_t, log_, void,
struct tm tm;
time_t t;
+ this->lock->read_lock(this->lock);
+ if (!this->out)
+ { /* file is not open */
+ this->lock->unlock(this->lock);
+ return;
+ }
if (this->time_format)
{
t = time(NULL);
@@ -117,17 +138,24 @@ METHOD(logger_t, log_, void,
current = next + 1;
}
this->mutex->unlock(this->mutex);
+ this->lock->unlock(this->lock);
}
METHOD(logger_t, get_level, level_t,
private_file_logger_t *this, debug_t group)
{
- return this->levels[group];
+ level_t level;
+
+ this->lock->read_lock(this->lock);
+ level = this->levels[group];
+ this->lock->unlock(this->lock);
+ return level;
}
METHOD(file_logger_t, set_level, void,
private_file_logger_t *this, debug_t group, level_t level)
{
+ this->lock->write_lock(this->lock);
if (group < DBG_ANY)
{
this->levels[group] = level;
@@ -139,23 +167,81 @@ METHOD(file_logger_t, set_level, void,
this->levels[group] = level;
}
}
+ this->lock->unlock(this->lock);
}
-METHOD(file_logger_t, destroy, void,
- private_file_logger_t *this)
+METHOD(file_logger_t, set_options, void,
+ private_file_logger_t *this, char *time_format, bool ike_name)
{
- if (this->out != stdout && this->out != stderr)
+ this->lock->write_lock(this->lock);
+ free(this->time_format);
+ this->time_format = strdupnull(time_format);
+ this->ike_name = ike_name;
+ this->lock->unlock(this->lock);
+}
+
+/**
+ * Close the current file, if any
+ */
+static void close_file(private_file_logger_t *this)
+{
+ if (this->out && this->out != stdout && this->out != stderr)
{
fclose(this->out);
+ this->out = NULL;
+ }
+}
+
+METHOD(file_logger_t, open_, void,
+ private_file_logger_t *this, bool flush_line, bool append)
+{
+ FILE *file;
+
+ if (streq(this->filename, "stderr"))
+ {
+ file = stderr;
+ }
+ else if (streq(this->filename, "stdout"))
+ {
+ file = stdout;
+ }
+ else
+ {
+ file = fopen(this->filename, append ? "a" : "w");
+ if (file == NULL)
+ {
+ DBG1(DBG_DMN, "opening file %s for logging failed: %s",
+ this->filename, strerror(errno));
+ return;
+ }
+ if (flush_line)
+ {
+ setlinebuf(file);
+ }
}
+ this->lock->write_lock(this->lock);
+ close_file(this);
+ this->out = file;
+ this->lock->unlock(this->lock);
+}
+
+METHOD(file_logger_t, destroy, void,
+ private_file_logger_t *this)
+{
+ this->lock->write_lock(this->lock);
+ close_file(this);
+ this->lock->unlock(this->lock);
this->mutex->destroy(this->mutex);
+ this->lock->destroy(this->lock);
+ free(this->time_format);
+ free(this->filename);
free(this);
}
/*
* Described in header.
*/
-file_logger_t *file_logger_create(FILE *out, char *time_format, bool ike_name)
+file_logger_t *file_logger_create(char *filename)
{
private_file_logger_t *this;
@@ -166,16 +252,16 @@ file_logger_t *file_logger_create(FILE *out, char *time_format, bool ike_name)
.get_level = _get_level,
},
.set_level = _set_level,
+ .set_options = _set_options,
+ .open = _open_,
.destroy = _destroy,
},
- .out = out,
- .time_format = time_format,
- .ike_name = ike_name,
+ .filename = strdup(filename),
.mutex = mutex_create(MUTEX_TYPE_DEFAULT),
+ .lock = rwlock_create(RWLOCK_TYPE_DEFAULT),
);
set_level(this, DBG_ANY, LEVEL_SILENT);
return &this->public;
}
-
diff --git a/src/libcharon/bus/listeners/file_logger.h b/src/libcharon/bus/listeners/file_logger.h
index 85a2690a2..9e5aed50b 100644
--- a/src/libcharon/bus/listeners/file_logger.h
+++ b/src/libcharon/bus/listeners/file_logger.h
@@ -1,4 +1,5 @@
/*
+ * Copyright (C) 2012 Tobias Brunner
* Copyright (C) 2006 Martin Willi
* Hochschule fuer Technik Rapperswil
*
@@ -44,6 +45,22 @@ struct file_logger_t {
void (*set_level) (file_logger_t *this, debug_t group, level_t level);
/**
+ * Set options used by this logger
+ *
+ * @param time_format format of timestamp prefix, as in strftime(), cloned
+ * @param ike_name TRUE to prefix the name of the IKE_SA
+ */
+ void (*set_options) (file_logger_t *this, char *time_format, bool ike_name);
+
+ /**
+ * Open (or reopen) the log file according to the given parameters
+ *
+ * @param flush_line TRUE to flush buffers after every logged line
+ * @param append FALSE to overwrite an existing file, TRUE to append
+ */
+ void (*open) (file_logger_t *this, bool flush_line, bool append);
+
+ /**
* Destroys a file_logger_t object.
*/
void (*destroy) (file_logger_t *this);
@@ -52,11 +69,13 @@ struct file_logger_t {
/**
* Constructor to create a file_logger_t object.
*
- * @param out FILE to write to
- * @param time_format format of timestamp prefix, as in strftime()
- * @param ike_name TRUE to prefix the name of the IKE_SA
- * @return file_logger_t object
+ * The logger has to be opened via file_logger_t.open() before anything is
+ * logged.
+ *
+ * @param filename name of the log file (stderr and stdout are handled
+ * specially), cloned
+ * @return file_logger_t object
*/
-file_logger_t *file_logger_create(FILE *out, char *time_format, bool ike_name);
+file_logger_t *file_logger_create(char *filename);
#endif /** FILE_LOGGER_H_ @}*/
diff --git a/src/libcharon/bus/listeners/sys_logger.c b/src/libcharon/bus/listeners/sys_logger.c
index 53fdefe89..82e2c8e4c 100644
--- a/src/libcharon/bus/listeners/sys_logger.c
+++ b/src/libcharon/bus/listeners/sys_logger.c
@@ -21,6 +21,7 @@
#include "sys_logger.h"
#include <threading/mutex.h>
+#include <threading/rwlock.h>
typedef struct private_sys_logger_t private_sys_logger_t;
@@ -53,6 +54,11 @@ struct private_sys_logger_t {
* Mutex to ensure multi-line log messages are not torn apart
*/
mutex_t *mutex;
+
+ /**
+ * Lock to read/write options (levels, ike_name)
+ */
+ rwlock_t *lock;
};
METHOD(logger_t, log_, void,
@@ -65,6 +71,7 @@ METHOD(logger_t, log_, void,
/* cache group name and optional name string */
snprintf(groupstr, sizeof(groupstr), "%N", debug_names, group);
+ this->lock->read_lock(this->lock);
if (this->ike_name && ike_sa)
{
if (ike_sa->get_peer_cfg(ike_sa))
@@ -78,6 +85,7 @@ METHOD(logger_t, log_, void,
ike_sa->get_unique_id(ike_sa));
}
}
+ this->lock->unlock(this->lock);
/* do a syslog for every line */
this->mutex->lock(this->mutex);
@@ -100,12 +108,18 @@ METHOD(logger_t, log_, void,
METHOD(logger_t, get_level, level_t,
private_sys_logger_t *this, debug_t group)
{
- return this->levels[group];
+ level_t level;
+
+ this->lock->read_lock(this->lock);
+ level = this->levels[group];
+ this->lock->unlock(this->lock);
+ return level;
}
METHOD(sys_logger_t, set_level, void,
private_sys_logger_t *this, debug_t group, level_t level)
{
+ this->lock->write_lock(this->lock);
if (group < DBG_ANY)
{
this->levels[group] = level;
@@ -117,12 +131,21 @@ METHOD(sys_logger_t, set_level, void,
this->levels[group] = level;
}
}
+ this->lock->unlock(this->lock);
+}
+
+METHOD(sys_logger_t, set_options, void,
+ private_sys_logger_t *this, bool ike_name)
+{
+ this->lock->write_lock(this->lock);
+ this->ike_name = ike_name;
+ this->lock->unlock(this->lock);
}
METHOD(sys_logger_t, destroy, void,
private_sys_logger_t *this)
{
- closelog();
+ this->lock->destroy(this->lock);
this->mutex->destroy(this->mutex);
free(this);
}
@@ -130,7 +153,7 @@ METHOD(sys_logger_t, destroy, void,
/*
* Described in header.
*/
-sys_logger_t *sys_logger_create(int facility, bool ike_name)
+sys_logger_t *sys_logger_create(int facility)
{
private_sys_logger_t *this;
@@ -141,11 +164,12 @@ sys_logger_t *sys_logger_create(int facility, bool ike_name)
.get_level = _get_level,
},
.set_level = _set_level,
+ .set_options = _set_options,
.destroy = _destroy,
},
.facility = facility,
- .ike_name = ike_name,
.mutex = mutex_create(MUTEX_TYPE_DEFAULT),
+ .lock = rwlock_create(RWLOCK_TYPE_DEFAULT),
);
set_level(this, DBG_ANY, LEVEL_SILENT);
diff --git a/src/libcharon/bus/listeners/sys_logger.h b/src/libcharon/bus/listeners/sys_logger.h
index fcb6655ca..9a0fee018 100644
--- a/src/libcharon/bus/listeners/sys_logger.h
+++ b/src/libcharon/bus/listeners/sys_logger.h
@@ -1,4 +1,5 @@
/*
+ * Copyright (C) 2012 Tobias Brunner
* Copyright (C) 2006 Martin Willi
* Hochschule fuer Technik Rapperswil
*
@@ -44,6 +45,13 @@ struct sys_logger_t {
void (*set_level) (sys_logger_t *this, debug_t group, level_t level);
/**
+ * Set options used by this logger.
+ *
+ * @param ike_name TRUE to prefix the name of the IKE_SA
+ */
+ void (*set_options) (sys_logger_t *this, bool ike_name);
+
+ /**
* Destroys a sys_logger_t object.
*/
void (*destroy) (sys_logger_t *this);
@@ -53,9 +61,8 @@ struct sys_logger_t {
* Constructor to create a sys_logger_t object.
*
* @param facility syslog facility to use
- * @param ike_name TRUE to prefix the name of the IKE_SA
* @return sys_logger_t object
*/
-sys_logger_t *sys_logger_create(int facility, bool ike_name);
+sys_logger_t *sys_logger_create(int facility);
#endif /** SYS_LOGGER_H_ @}*/