[svn-commits] kpfleming: branch kpfleming/dynamic_logger_levels r191954 - in /team/kpflemin...

SVN commits to the Digium repositories svn-commits at lists.digium.com
Mon May 4 03:49:37 CDT 2009


Author: kpfleming
Date: Mon May  4 03:49:28 2009
New Revision: 191954

URL: http://svn.digium.com/svn-view/asterisk?view=rev&rev=191954
Log:
store away some work in progress


Added:
    team/kpfleming/dynamic_logger_levels/
      - copied from r191953, trunk/
Modified:
    team/kpfleming/dynamic_logger_levels/include/asterisk/logger.h
    team/kpfleming/dynamic_logger_levels/main/logger.c

Modified: team/kpfleming/dynamic_logger_levels/include/asterisk/logger.h
URL: http://svn.digium.com/svn-view/asterisk/team/kpfleming/dynamic_logger_levels/include/asterisk/logger.h?view=diff&rev=191954&r1=191953&r2=191954
==============================================================================
--- team/kpfleming/dynamic_logger_levels/include/asterisk/logger.h (original)
+++ team/kpfleming/dynamic_logger_levels/include/asterisk/logger.h Mon May  4 03:49:28 2009
@@ -193,6 +193,23 @@
  * \return the debug level
  */
 unsigned int ast_verbose_get_by_file(const char *file);
+
+/*!
+ * \brief Register a new logger level
+ * \param name The name of the level to be registered
+ * \retval -1 if an error occurs
+ * \retval non-zero level to be used with ast_log for sending messages to this level
+ * \since 1.6.3
+ */
+int ast_logger_register_level(const char *name);
+
+/*!
+ * \brief Unregister a previously registered logger level
+ * \param name The name of the level to be unregistered
+ * \return nothing
+ * \since 1.6.3
+ */
+void ast_logger_unregister_level(const char *name);
 
 /*!
  * \brief Log a DEBUG message

Modified: team/kpfleming/dynamic_logger_levels/main/logger.c
URL: http://svn.digium.com/svn-view/asterisk/team/kpfleming/dynamic_logger_levels/main/logger.c?view=diff&rev=191954&r1=191953&r2=191954
==============================================================================
--- team/kpfleming/dynamic_logger_levels/main/logger.c (original)
+++ team/kpfleming/dynamic_logger_levels/main/logger.c Mon May  4 03:49:28 2009
@@ -96,7 +96,7 @@
 static char exec_after_rotate[256] = "";
 
 static int filesize_reload_needed;
-static int global_logmask = -1;
+static unsigned int global_logmask = 0xFFFF;
 
 enum rotatestrategy {
 	SEQUENTIAL = 1 << 0,     /* Original method - create a new file, in order */
@@ -117,13 +117,15 @@
 };
 
 struct logchannel {
-	int logmask;			/* What to log to this channel */
+	unsigned int logmask;		/* What to log to this channel */
 	int disabled;			/* If this channel is disabled or not */
 	int facility; 			/* syslog facility */
 	enum logtypes type;		/* Type of log channel */
 	FILE *fileptr;			/* logfile logging file pointer */
-	char filename[256];		/* Filename */
+	char filename[PATH_MAX];	/* Filename */
 	AST_LIST_ENTRY(logchannel) list;
+	int lineno;			/* Line number from configuration file */
+	char components[0];		/* Components (levels) from last config load */
 };
 
 static AST_RWLIST_HEAD_STATIC(logchannels, logchannel);
@@ -180,11 +182,16 @@
 AST_THREADSTORAGE(log_buf);
 #define LOG_BUF_INIT_SIZE       256
 
-static int make_components(const char *s, int lineno)
+static const char *dynamic_levels[16];
+
+AST_MUTEX_DEFINE_STATIC(dynamic_levels_lock);
+
+static unsigned int make_components(const char *s, int lineno)
 {
 	char *w;
-	int res = 0;
+	unsigned int res = 0;
 	char *stringp = ast_strdupa(s);
+	unsigned int x;
 
 	while ((w = strsep(&stringp, ","))) {
 		w = ast_skip_blanks(w);
@@ -201,7 +208,19 @@
 		else if (!strcasecmp(w, "dtmf"))
 			res |= (1 << __LOG_DTMF);
 		else {
-			fprintf(stderr, "Logfile Warning: Unknown keyword '%s' at line %d of logger.conf\n", w, lineno);
+			int found = 0;
+
+			for (x = 0; x < ARRAY_LEN(dynamic_levels); x++) {
+				if (!strcasecmp(w, dynamic_levels[x])) {
+					res |= (1 << (x + 16));
+					found = 1;
+					break;
+				}
+			}
+			if (!found) {
+				fprintf(stderr, "Logfile Warning: Unknown keyword '%s' at line %d of logger.conf\n",
+					w, lineno);
+			}
 		}
 	}
 
@@ -216,8 +235,11 @@
 	CODE *cptr;
 #endif
 
-	if (ast_strlen_zero(channel) || !(chan = ast_calloc(1, sizeof(*chan))))
+	if (ast_strlen_zero(channel) || !(chan = ast_calloc(1, sizeof(*chan) + strlen(components) + 1)))
 		return NULL;
+
+	strcpy(chan->components, components);
+	chan->lineno = lineno;
 
 	if (!strcasecmp(channel, "console")) {
 		chan->type = LOGTYPE_CONSOLE;
@@ -292,7 +314,7 @@
 		}
 
 		chan->type = LOGTYPE_SYSLOG;
-		snprintf(chan->filename, sizeof(chan->filename), "%s", channel);
+		ast_copy_string(chan->filename, channel, sizeof(chan->filename));
 		openlog("asterisk", LOG_PID, chan->facility);
 	} else {
 		if (channel[0] == '/') {
@@ -308,14 +330,14 @@
 		} else {
 			snprintf(chan->filename, sizeof(chan->filename), "%s/%s", ast_config_AST_LOG_DIR, channel);
 		}
-		chan->fileptr = fopen(chan->filename, "a");
-		if (!chan->fileptr) {
+		if (!(chan->fileptr = fopen(chan->filename, "a"))) {
 			/* Can't log here, since we're called with a lock */
 			fprintf(stderr, "Logger Warning: Unable to open log file '%s': %s\n", chan->filename, strerror(errno));
 		} 
 		chan->type = LOGTYPE_FILE;
 	}
-	chan->logmask = make_components(components, lineno);
+	chan->logmask = make_components(chan->components, lineno);
+
 	return chan;
 }
 
@@ -352,7 +374,7 @@
 		if (!(chan = ast_calloc(1, sizeof(*chan))))
 			return;
 		chan->type = LOGTYPE_CONSOLE;
-		chan->logmask = 28; /*warning,notice,error */
+		chan->logmask = __LOG_WARNING | __LOG_NOTICE | __LOG_ERROR;
 		if (!locked)
 			AST_RWLIST_WRLOCK(&logchannels);
 		AST_RWLIST_INSERT_HEAD(&logchannels, chan, list);
@@ -717,7 +739,7 @@
 	if (a->argc < 5)
 		return CLI_SHOWUSAGE;
 
-	for (x = 0; x <= NUMLOGLEVELS; x++) {
+	for (x = 0; x < ARRAY_LEN(levels); x++) {
 		if (!strcasecmp(a->argv[3], levels[x])) {
 			level = x;
 			break;
@@ -756,6 +778,8 @@
 	ast_cli(a->fd, "-------------\n");
 	AST_RWLIST_RDLOCK(&logchannels);
 	AST_RWLIST_TRAVERSE(&logchannels, chan, list) {
+		unsigned int level;
+
 		ast_cli(a->fd, FORMATL, chan->filename, chan->type == LOGTYPE_CONSOLE ? "Console" : (chan->type == LOGTYPE_SYSLOG ? "Syslog" : "File"),
 			chan->disabled ? "Disabled" : "Enabled");
 		ast_cli(a->fd, " - ");
@@ -771,6 +795,11 @@
 			ast_cli(a->fd, "Notice ");
 		if (chan->logmask & (1 << __LOG_ERROR)) 
 			ast_cli(a->fd, "Error ");
+		for (level = 0; level < ARRAY_LEN(dynamic_levels); level++) {
+			if (chan->logmask & (1 << (level + 16))) {
+				ast_cli(a->fd, "%s ", dynamic_levels[level]);
+			}
+		}
 		ast_cli(a->fd, "\n");
 	}
 	AST_RWLIST_UNLOCK(&logchannels);
@@ -1283,3 +1312,96 @@
 	
 	return cur ? 0 : -1;
 }
+
+static void update_logchannels(void)
+{
+	struct logchannel *cur;
+
+	AST_RWLIST_WRLOCK(&logchannels);
+
+	global_logmask = 0;
+
+	AST_RWLIST_TRAVERSE(&logchannels, cur, list) {
+		cur->logmask = make_components(cur->components, cur->lineno);
+		global_logmask |= cur->logmask;
+	}
+
+	AST_RWLIST_UNLOCK(&logchannels);
+}
+
+int ast_logger_register_level(const char *name)
+{
+	unsigned int level;
+	unsigned int available = 0;
+
+	for (level = 0; level < ARRAY_LEN(levels); level++) {
+		if (!strcasecmp(levels[level], name)) {
+			ast_log(LOG_WARNING,
+				"Unable to register dynamic logger level '%s': a standard logger level uses that name.\n",
+				name);
+			
+			return -1;
+		}
+	}
+
+	ast_mutex_lock(&dynamic_levels_lock);
+
+	for (level = 0; level < ARRAY_LEN(dynamic_levels); level++) {
+		if (!dynamic_levels[level]) {
+			available = level + 16;
+			continue;
+		}
+
+		if (!strcasecmp(dynamic_levels[level], name)) {
+			ast_log(LOG_WARNING,
+				"Unable to register dynamic logger level '%s': a level is already registered with that name.\n",
+				name);
+			ast_mutex_unlock(&dynamic_levels_lock);
+			
+			return -1;
+		}
+	}
+
+	if (!available) {
+		ast_log(LOG_WARNING,
+			"Unable to register dynamic logger level '%s'; maximum number of levels registered.\n",
+			name);
+		ast_mutex_unlock(&dynamic_levels_lock);
+
+		return -1;
+	}
+
+	dynamic_levels[available - 16] = name;
+
+	ast_mutex_unlock(&dynamic_levels_lock);
+
+	ast_debug(1, "Registered dynamic logger level '%s' with index %d.\n", name, available);
+
+	update_logchannels();
+
+	return available;
+}
+
+void ast_logger_unregister_level(const char *name)
+{
+	unsigned int x;
+
+	ast_mutex_lock(&dynamic_levels_lock);
+
+	for (x = 0; x < ARRAY_LEN(dynamic_levels); x++) {
+		if (strcasecmp(dynamic_levels[x], name)) {
+			continue;
+		}
+
+		dynamic_levels[x] = NULL;
+		break;
+	}
+
+	ast_mutex_unlock(&dynamic_levels_lock);
+
+	if (x < ARRAY_LEN(dynamic_levels)) {
+		ast_debug(1, "Unregistered dynamic logger level '%s' with index %d.\n", name, x);
+
+		update_logchannels();
+	}
+}




More information about the svn-commits mailing list