aboutsummaryrefslogtreecommitdiff
path: root/src/lib/log/log.c
diff options
context:
space:
mode:
authorteor <teor@torproject.org>2019-09-04 17:16:49 +1000
committerteor <teor@torproject.org>2019-09-09 14:56:42 +1000
commit1609916c79612b5cc3a9b363a22f1a9035f2f77b (patch)
tree3b67c49c864222489cd01da12a8db120a7311b1c /src/lib/log/log.c
parenta22fbab98690f802ae3bda276078cc7fc767feba (diff)
downloadtor-1609916c79612b5cc3a9b363a22f1a9035f2f77b.tar.gz
tor-1609916c79612b5cc3a9b363a22f1a9035f2f77b.zip
log: Close log and err file descriptors before aborting
Part of 31594.
Diffstat (limited to 'src/lib/log/log.c')
-rw-r--r--src/lib/log/log.c42
1 files changed, 40 insertions, 2 deletions
diff --git a/src/lib/log/log.c b/src/lib/log/log.c
index 2214d4b59d..4adcc5cf57 100644
--- a/src/lib/log/log.c
+++ b/src/lib/log/log.c
@@ -224,6 +224,7 @@ int log_global_min_severity_ = LOG_NOTICE;
static void delete_log(logfile_t *victim);
static void close_log(logfile_t *victim);
+static void close_log_sigsafe(logfile_t *victim);
static char *domain_to_string(log_domain_mask_t domain,
char *buf, size_t buflen);
@@ -833,6 +834,30 @@ logs_free_all(void)
* that happened between here and the end of execution. */
}
+/** Close signal-safe log files.
+ * Closing the log files makes the process and OS flush log buffers.
+ *
+ * This function is safe to call from a signal handler. It should only be
+ * called when shutting down the log or err modules. It is currenly called
+ * by the err module, when terminating the process on an abnormal condition.
+ */
+void
+logs_close_sigsafe(void)
+{
+ logfile_t *victim, *next;
+ /* We can't LOCK_LOGS() in a signal handler, because it may call
+ * signal-unsafe functions. And we can't deallocate memory, either. */
+ next = logfiles;
+ logfiles = NULL;
+ while (next) {
+ victim = next;
+ next = next->next;
+ if (victim->needs_close) {
+ close_log_sigsafe(victim);
+ }
+ }
+}
+
/** Remove and free the log entry <b>victim</b> from the linked-list
* logfiles (it is probably present, but it might not be due to thread
* racing issues). After this function is called, the caller shouldn't
@@ -859,13 +884,26 @@ delete_log(logfile_t *victim)
}
/** Helper: release system resources (but not memory) held by a single
- * logfile_t. */
+ * signal-safe logfile_t. If the log's resources can not be released in
+ * a signal handler, does nothing. */
static void
-close_log(logfile_t *victim)
+close_log_sigsafe(logfile_t *victim)
{
if (victim->needs_close && victim->fd >= 0) {
+ /* We can't do anything useful here if close() fails: we're shutting
+ * down logging, and the err module only does fatal errors. */
close(victim->fd);
victim->fd = -1;
+ }
+}
+
+/** Helper: release system resources (but not memory) held by a single
+ * logfile_t. */
+static void
+close_log(logfile_t *victim)
+{
+ if (victim->needs_close) {
+ close_log_sigsafe(victim);
} else if (victim->is_syslog) {
#ifdef HAVE_SYSLOG_H
if (--syslog_count == 0) {