[asterisk-commits] rmudgett: branch 1.8 r331461 - /branches/1.8/main/logger.c

SVN commits to the Asterisk project asterisk-commits at lists.digium.com
Wed Aug 10 15:30:04 CDT 2011


Author: rmudgett
Date: Wed Aug 10 15:29:59 2011
New Revision: 331461

URL: http://svnview.digium.com/svn/asterisk?view=rev&rev=331461
Log:
Output of queue log not started until logger reloaded.

ASTERISK-15863 caused a regression with queue logging.  The output of the
queue log is not started until the logger configuration is reloaded.

* Queue log initialization is completely delayed until the first message
is posted to the queue log system.  Including the initial opening of the
queue log file.

* Fixed rotate_file() ROTATE strategy to give the file just rotated out to
the configured exec function after rotate.  Just like the other strategies.

* Fixed logger reload to always post the queue reload entry instead of
just if there is a queue log file.

* Refactored some code to eliminate some redundancy and to reduce stack
utilization.

(closes issue ASTERISK-17036)
JIRA SWP-2952
Reported by: Juan Carlos Valero
Patches:
      jira_asterisk_17036_v1.8.patch (license #5621) patch uploaded by rmudgett
Tested by: rmudgett

(closes issue ASTERISK-18208)
Reported by: Christian Pinedo

Review: https://reviewboard.asterisk.org/r/1333/

Modified:
    branches/1.8/main/logger.c

Modified: branches/1.8/main/logger.c
URL: http://svnview.digium.com/svn/asterisk/branches/1.8/main/logger.c?view=diff&rev=331461&r1=331460&r2=331461
==============================================================================
--- branches/1.8/main/logger.c (original)
+++ branches/1.8/main/logger.c Wed Aug 10 15:29:59 2011
@@ -79,6 +79,7 @@
 static int filesize_reload_needed;
 static unsigned int global_logmask = 0xFFFF;
 static int queuelog_init;
+static int logger_initialized;
 
 static enum rotatestrategy {
 	SEQUENTIAL = 1 << 0,     /* Original method - create a new file, in order */
@@ -397,11 +398,10 @@
 		AST_RWLIST_INSERT_HEAD(&logchannels, chan, list);
 		global_logmask |= chan->logmask;
 	}
+
 	if (qlog) {
-		char tmp[4096];
 		fclose(qlog);
-		snprintf(tmp, sizeof(tmp), "%s/%s", ast_config_AST_LOG_DIR, queue_log_name);
-		qlog = fopen(tmp, "a");
+		qlog = NULL;
 	}
 
 	if (!locked) {
@@ -469,9 +469,25 @@
 	int qlog_len;
 	char time_str[30];
 
+	if (!logger_initialized) {
+		/* You are too early.  We are not open yet! */
+		return;
+	}
 	if (!queuelog_init) {
-		queuelog_init = 1;
-		logger_queue_init();
+		AST_RWLIST_WRLOCK(&logchannels);
+		if (!queuelog_init) {
+			/*
+			 * We have delayed initializing the queue logging system so
+			 * preloaded realtime modules can get up.  We must initialize
+			 * now since someone is trying to log something.
+			 */
+			logger_queue_init();
+			queuelog_init = 1;
+			AST_RWLIST_UNLOCK(&logchannels);
+			ast_queue_log("NONE", "NONE", "NONE", "QUEUESTART", "%s", "");
+		} else {
+			AST_RWLIST_UNLOCK(&logchannels);
+		}
 	}
 
 	if (ast_check_realtime("queue_log")) {
@@ -487,7 +503,8 @@
 			);
 			AST_NONSTANDARD_APP_ARGS(args, qlog_msg, '|');
 			/* Ensure fields are large enough to receive data */
-			ast_realtime_require_field("queue_log", "data1", RQ_CHAR, strlen(S_OR(args.data[0], "")),
+			ast_realtime_require_field("queue_log",
+				"data1", RQ_CHAR, strlen(S_OR(args.data[0], "")),
 				"data2", RQ_CHAR, strlen(S_OR(args.data[1], "")),
 				"data3", RQ_CHAR, strlen(S_OR(args.data[2], "")),
 				"data4", RQ_CHAR, strlen(S_OR(args.data[3], "")),
@@ -609,6 +626,8 @@
 		if (rename(filename, new)) {
 			fprintf(stderr, "Unable to rename file '%s' to '%s'\n", filename, new);
 			res = -1;
+		} else {
+			filename = new;
 		}
 	}
 
@@ -625,9 +644,77 @@
 	return res;
 }
 
+/*!
+ * \internal
+ * \brief Start the realtime queue logging if configured.
+ *
+ * \retval TRUE if not to open queue log file.
+ */
+static int logger_queue_rt_start(void)
+{
+	if (ast_check_realtime("queue_log")) {
+		if (!ast_realtime_require_field("queue_log",
+			"time", RQ_DATETIME, 26,
+			"data1", RQ_CHAR, 20,
+			"data2", RQ_CHAR, 20,
+			"data3", RQ_CHAR, 20,
+			"data4", RQ_CHAR, 20,
+			"data5", RQ_CHAR, 20,
+			SENTINEL)) {
+			logfiles.queue_adaptive_realtime = 1;
+		} else {
+			logfiles.queue_adaptive_realtime = 0;
+		}
+
+		if (!logfiles.queue_log_to_file) {
+			/* Don't open the log file. */
+			return 1;
+		}
+	}
+	return 0;
+}
+
+/*!
+ * \internal
+ * \brief Rotate the queue log file and restart.
+ *
+ * \param queue_rotate Log queue rotation mode.
+ *
+ * \note Assumes logchannels is write locked on entry.
+ *
+ * \retval 0 on success.
+ * \retval -1 on error.
+ */
+static int logger_queue_restart(int queue_rotate)
+{
+	int res = 0;
+	char qfname[PATH_MAX];
+
+	if (logger_queue_rt_start()) {
+		return res;
+	}
+
+	snprintf(qfname, sizeof(qfname), "%s/%s", ast_config_AST_LOG_DIR, queue_log_name);
+	if (qlog) {
+		/* Just in case it was still open. */
+		fclose(qlog);
+		qlog = NULL;
+	}
+	if (queue_rotate) {
+		rotate_file(qfname);
+	}
+
+	/* Open the log file. */
+	qlog = fopen(qfname, "a");
+	if (!qlog) {
+		ast_log(LOG_ERROR, "Unable to create queue log: %s\n", strerror(errno));
+		res = -1;
+	}
+	return res;
+}
+
 static int reload_logger(int rotate)
 {
-	char old[PATH_MAX] = "";
 	int queue_rotate = rotate;
 	struct logchannel *f;
 	int res = 0;
@@ -676,47 +763,15 @@
 
 	init_logger_chain(1 /* locked */);
 
+	ast_unload_realtime("queue_log");
 	if (logfiles.queue_log) {
-		do {
-			ast_unload_realtime("queue_log");
-			if (ast_check_realtime("queue_log")) {
-				if (!ast_realtime_require_field("queue_log",
-						"time", RQ_DATETIME, 26, "data1", RQ_CHAR, 20,
-						"data2", RQ_CHAR, 20, "data3", RQ_CHAR, 20,
-						"data4", RQ_CHAR, 20, "data5", RQ_CHAR, 20, SENTINEL)) {
-					logfiles.queue_adaptive_realtime = 1;
-				} else {
-					logfiles.queue_adaptive_realtime = 0;
-				}
-
-				if (!logfiles.queue_log_to_file) {
-					/* Skip the following section */
-					break;
-				}
-			}
-			if (qlog) {
-				fclose(qlog);
-				qlog = NULL;
-			}
-			snprintf(old, sizeof(old), "%s/%s", ast_config_AST_LOG_DIR, queue_log_name);
-			if (queue_rotate) {
-				rotate_file(old);
-			}
-
-			qlog = fopen(old, "a");
-			if (qlog) {
-				AST_RWLIST_UNLOCK(&logchannels);
-				ast_queue_log("NONE", "NONE", "NONE", "CONFIGRELOAD", "%s", "");
-				AST_RWLIST_WRLOCK(&logchannels);
-				ast_verb(1, "Asterisk Queue Logger restarted\n");
-			} else {
-				ast_log(LOG_ERROR, "Unable to create queue log: %s\n", strerror(errno));
-				res = -1;
-			}
-		} while (0);
-	}
-
-	AST_RWLIST_UNLOCK(&logchannels);
+		res = logger_queue_restart(queue_rotate);
+		AST_RWLIST_UNLOCK(&logchannels);
+		ast_queue_log("NONE", "NONE", "NONE", "CONFIGRELOAD", "%s", "");
+		ast_verb(1, "Asterisk Queue Logger restarted\n");
+	} else {
+		AST_RWLIST_UNLOCK(&logchannels);
+	}
 
 	return res;
 }
@@ -1021,22 +1076,36 @@
 	return NULL;
 }
 
+/*!
+ * \internal
+ * \brief Initialize the logger queue.
+ *
+ * \note Assumes logchannels is write locked on entry.
+ *
+ * \return Nothing
+ */
 static void logger_queue_init(void)
 {
-	/* Preloaded modules are up. */
 	ast_unload_realtime("queue_log");
-	if (logfiles.queue_log && ast_check_realtime("queue_log")) {
-		if (!ast_realtime_require_field("queue_log",
-				"time", RQ_DATETIME, 26, "data1", RQ_CHAR, 20,
-				"data2", RQ_CHAR, 20, "data3", RQ_CHAR, 20,
-				"data4", RQ_CHAR, 20, "data5", RQ_CHAR, 20, SENTINEL)) {
-			logfiles.queue_adaptive_realtime = 1;
-		} else {
-			logfiles.queue_adaptive_realtime = 0;
-		}
-	}
-
-	ast_queue_log("NONE", "NONE", "NONE", "QUEUESTART", "%s", "");
+	if (logfiles.queue_log) {
+		char qfname[PATH_MAX];
+
+		if (logger_queue_rt_start()) {
+			return;
+		}
+
+		/* Open the log file. */
+		snprintf(qfname, sizeof(qfname), "%s/%s", ast_config_AST_LOG_DIR,
+			queue_log_name);
+		if (qlog) {
+			/* Just in case it was already open. */
+			fclose(qlog);
+		}
+		qlog = fopen(qfname, "a");
+		if (!qlog) {
+			ast_log(LOG_ERROR, "Unable to create queue log: %s\n", strerror(errno));
+		}
+	}
 }
 
 int init_logger(void)
@@ -1058,6 +1127,7 @@
 
 	/* create log channels */
 	init_logger_chain(0 /* locked */);
+	logger_initialized = 1;
 
 	return 0;
 }
@@ -1065,6 +1135,8 @@
 void close_logger(void)
 {
 	struct logchannel *f = NULL;
+
+	logger_initialized = 0;
 
 	/* Stop logger thread */
 	AST_LIST_LOCK(&logmsgs);




More information about the asterisk-commits mailing list