From fb5b443cba6feeb441d928af22844a540b3e5cf8 Mon Sep 17 00:00:00 2001
From: Stephan Bosch <stephan@rename-it.nl>
Date: Sun, 8 Nov 2009 21:03:30 +0100
Subject: [PATCH] Added i_debug support.

---
 src/lib-sieve/Makefile.am                |   6 +-
 src/lib-sieve/sieve-error-private.h      |   8 +-
 src/lib-sieve/sieve-error.c              | 219 +++++++++++++----------
 src/lib-sieve/sieve-error.h              |  21 +++
 src/plugins/lda-sieve/lda-sieve-plugin.c |  22 +--
 5 files changed, 168 insertions(+), 108 deletions(-)

diff --git a/src/lib-sieve/Makefile.am b/src/lib-sieve/Makefile.am
index e293c39cf..10d3818e9 100644
--- a/src/lib-sieve/Makefile.am
+++ b/src/lib-sieve/Makefile.am
@@ -139,8 +139,8 @@ headers = \
 	sieve.h
 
 if INSTALL_HEADERS
-	pkginc_libdir=$(dovecot_pkgincludedir)/sieve
-	pkginc_lib_HEADERS = $(headers)
+  pkginc_libdir=$(dovecot_pkgincludedir)/sieve
+  pkginc_lib_HEADERS = $(headers)
 else
-	noinst_HEADERS = $(headers)
+  noinst_HEADERS = $(headers)
 endif
diff --git a/src/lib-sieve/sieve-error-private.h b/src/lib-sieve/sieve-error-private.h
index 7746e04c1..b7d541ac0 100644
--- a/src/lib-sieve/sieve-error-private.h
+++ b/src/lib-sieve/sieve-error-private.h
@@ -19,13 +19,14 @@ struct sieve_error_handler {
 	unsigned int errors;
 	unsigned int warnings;
 
-	/* Should we copy log to i_error, i_warning and i_info? */
+	/* Should we copy log to i_error, i_warning, i_info and i_debug? */
 	bool log_master;
 
-	/* Should the errorhandler handle or discard info log?
+	/* Should the errorhandler handle or discard info/debug log?
 	 * (This does not influence the previous setting)
 	 */
 	bool log_info;
+	bool log_debug;
 
 	void (*verror)
 		(struct sieve_error_handler *ehandler, const char *location,
@@ -36,6 +37,9 @@ struct sieve_error_handler {
 	void (*vinfo)
 		(struct sieve_error_handler *ehandler, const char *location,
 			const char *fmt, va_list args);
+	void (*vdebug)
+		(struct sieve_error_handler *ehandler, const char *location,
+			const char *fmt, va_list args);
 
 	void (*free)
 		(struct sieve_error_handler *ehandler);
diff --git a/src/lib-sieve/sieve-error.c b/src/lib-sieve/sieve-error.c
index 9f02da4c5..5c48e700a 100644
--- a/src/lib-sieve/sieve-error.c
+++ b/src/lib-sieve/sieve-error.c
@@ -49,22 +49,25 @@ const char *sieve_error_script_location
  * Main error functions
  */
 
+static void sieve_vcopy_master
+(const char *location, sieve_error_vfunc_t error_vfunc, 
+	const char *fmt, va_list args)
+{
+	va_list args_copy;
+
+	VA_COPY(args_copy, args);
+
+	error_vfunc(_sieve_system_ehandler, location, fmt, args_copy);
+}
+
 void sieve_verror
 	(struct sieve_error_handler *ehandler, const char *location, 
 		const char *fmt, va_list args)
 {
 	if ( ehandler == NULL ) return;
 	
-	if ( ehandler->log_master ) {
-		va_list args_copy;
-
-		VA_COPY(args_copy, args);
-
-		if ( location == NULL || *location == '\0' )
-			sieve_sys_error("%s", t_strdup_vprintf(fmt, args_copy));
-		else
-			sieve_sys_error("%s: %s", location, t_strdup_vprintf(fmt, args_copy));
-	}
+	if ( ehandler->log_master )
+		sieve_vcopy_master(location, sieve_verror, fmt, args);
 
 	if ( sieve_errors_more_allowed(ehandler) ) {
 		if ( ehandler->verror != NULL )
@@ -81,17 +84,9 @@ void sieve_vwarning
 {
 	if ( ehandler == NULL ) return;
 
-	if ( ehandler->log_master ) {
-		va_list args_copy;
+	if ( ehandler->log_master )
+		sieve_vcopy_master(location, sieve_vwarning, fmt, args);
 
-		VA_COPY(args_copy, args);
-
-		if ( location == NULL || *location == '\0' )
-			sieve_sys_warning("%s", t_strdup_vprintf(fmt, args_copy));
-		else
-			sieve_sys_warning("%s: %s", location, t_strdup_vprintf(fmt, args_copy));
-	}
-	
 	if ( ehandler->vwarning != NULL )	
 		ehandler->vwarning(ehandler, location, fmt, args);
 
@@ -105,22 +100,26 @@ void sieve_vinfo
 {
 	if ( ehandler == NULL ) return;
 
-	if ( ehandler->log_master ) {
-		va_list args_copy;
-
-		VA_COPY(args_copy, args);
+	if ( ehandler->log_master )
+		sieve_vcopy_master(location, sieve_vinfo, fmt, args);
 
-
-		if ( location == NULL || *location == '\0' )
-			sieve_sys_info("%s", t_strdup_vprintf(fmt, args_copy));
-		else	
-			sieve_sys_info("%s: %s", location, t_strdup_vprintf(fmt, args_copy));
-	}
-	
 	if ( ehandler->log_info && ehandler->vinfo != NULL )	
 		ehandler->vinfo(ehandler, location, fmt, args);
 }
 
+void sieve_vdebug
+	(struct sieve_error_handler *ehandler, const char *location,
+		const char *fmt, va_list args)
+{
+	if ( ehandler == NULL ) return;
+
+	if ( ehandler->log_master )
+		sieve_vcopy_master(location, sieve_vdebug, fmt, args);
+
+	if ( ehandler->log_debug && ehandler->vdebug != NULL )
+		ehandler->vdebug(ehandler, location, fmt, args);
+}
+
 void sieve_vcritical
 	(struct sieve_error_handler *ehandler, const char *location, 
 		const char *fmt, va_list args)
@@ -178,6 +177,12 @@ void sieve_error_handler_accept_infolog
 	ehandler->log_info = enable;	
 }
 
+void sieve_error_handler_accept_debuglog
+	(struct sieve_error_handler *ehandler, bool enable)
+{
+	ehandler->log_debug = enable;
+}
+
 void sieve_error_handler_copy_masterlog
 	(struct sieve_error_handler *ehandler, bool enable)
 {
@@ -273,14 +278,26 @@ static void sieve_master_vinfo
 		i_info("sieve: %s: %s", location, t_strdup_vprintf(fmt, args));
 }
 
+static void sieve_master_vdebug
+(struct sieve_error_handler *ehandler ATTR_UNUSED, const char *location,
+	const char *fmt, va_list args) 
+{
+	if ( ehandler->log_master ) return;
+
+	if ( location == NULL || *location == '\0' )
+		i_debug("sieve: %s", t_strdup_vprintf(fmt, args));
+	else
+		i_debug("sieve: %s: %s", location, t_strdup_vprintf(fmt, args));
+}
+
 struct sieve_error_handler *sieve_master_ehandler_create
 (unsigned int max_errors) 
 {
 	pool_t pool;
 	struct sieve_error_handler *ehandler;
-	
-	/* Pool is not strictly necessary, but other handler types will need a pool,
-	 * so this one will have one too.
+
+	/* Pool is not strictly necessary, but other handler types will need
+	 * a pool, so this one will have one too.
 	 */
 	pool = pool_alloconly_create
 		("master_error_handler", sizeof(struct sieve_error_handler));
@@ -290,17 +307,20 @@ struct sieve_error_handler *sieve_master_ehandler_create
 	ehandler->verror = sieve_master_verror;
 	ehandler->vwarning = sieve_master_vwarning;
 	ehandler->vinfo = sieve_master_vinfo;
-	
-	return ehandler;	
+	ehandler->vdebug = sieve_master_vdebug;
+
+	return ehandler;
 }
 
 struct sieve_error_handler _sieve_system_ehandler_object = {
 	NULL, 0, 0, 0, 0,
 	FALSE,
 	TRUE,
+	TRUE,
 	sieve_master_verror,
 	sieve_master_vwarning,
 	sieve_master_vinfo,
+	sieve_master_vdebug,
 	NULL
 };
 
@@ -325,44 +345,52 @@ void sieve_system_ehandler_reset(void)
  * - Output errors directly to stderror 
  */
 
-static void sieve_stderr_verror
-(struct sieve_error_handler *ehandler ATTR_UNUSED, const char *location, 
-	const char *fmt, va_list args) 
+static void sieve_stderr_vmessage
+(struct sieve_error_handler *ehandler ATTR_UNUSED, const char *prefix,
+	const char *location, const char *fmt, va_list args) 
 {
 	if ( location == NULL || *location == '\0' )
-		fprintf(stderr, "error: %s.\n", t_strdup_vprintf(fmt, args));
+		fprintf(stderr, "%s: %s.\n", prefix, t_strdup_vprintf(fmt, args));
 	else
-		fprintf(stderr, "%s: error: %s.\n", location, t_strdup_vprintf(fmt, args));
+		fprintf(stderr, "%s: %s: %s.\n", location, prefix, t_strdup_vprintf(fmt, args));
+}
+
+static void sieve_stderr_verror
+(struct sieve_error_handler *ehandler, const char *location,
+	const char *fmt, va_list args) 
+{
+	sieve_stderr_vmessage(ehandler, "error", location, fmt, args);
 }
 
 static void sieve_stderr_vwarning
-(struct sieve_error_handler *ehandler ATTR_UNUSED, const char *location, 
+(struct sieve_error_handler *ehandler, const char *location,
 	const char *fmt, va_list args) 
 {
-	if ( location == NULL || *location == '\0' )
-		fprintf(stderr, "warning: %s.\n", t_strdup_vprintf(fmt, args));
-	else
-		fprintf(stderr, "%s: warning: %s.\n", location, t_strdup_vprintf(fmt, args));
+	sieve_stderr_vmessage(ehandler, "warning", location, fmt, args);
 }
 
 static void sieve_stderr_vinfo
-(struct sieve_error_handler *ehandler ATTR_UNUSED, const char *location, 
+(struct sieve_error_handler *ehandler, const char *location,
 	const char *fmt, va_list args) 
 {
-	if ( location == NULL || *location == '\0' )
-		fprintf(stderr, "info: %s.\n", t_strdup_vprintf(fmt, args));
-	else
-		fprintf(stderr, "%s: info: %s.\n", location, t_strdup_vprintf(fmt, args));
+	sieve_stderr_vmessage(ehandler, "info", location, fmt, args);
+}
+
+static void sieve_stderr_vdebug
+(struct sieve_error_handler *ehandler, const char *location,
+	const char *fmt, va_list args) 
+{
+	sieve_stderr_vmessage(ehandler, "debug", location, fmt, args);
 }
 
 struct sieve_error_handler *sieve_stderr_ehandler_create
-(unsigned int max_errors) 
+(unsigned int max_errors)
 {
 	pool_t pool;
 	struct sieve_error_handler *ehandler;
-	
-	/* Pool is not strictly necessary, but other handler types will need a pool,
-	 * so this one will have one too.
+
+	/* Pool is not strictly necessary, but other handler types will need
+	 * a pool, so this one will have one too.
 	 */
 	pool = pool_alloconly_create
 		("stderr_error_handler", sizeof(struct sieve_error_handler));
@@ -372,8 +400,9 @@ struct sieve_error_handler *sieve_stderr_ehandler_create
 	ehandler->verror = sieve_stderr_verror;
 	ehandler->vwarning = sieve_stderr_vwarning;
 	ehandler->vinfo = sieve_stderr_vinfo;
-	
-	return ehandler;	
+	ehandler->vdebug = sieve_stderr_vdebug;
+
+	return ehandler;
 }
 
 /* String buffer error handler
@@ -388,16 +417,16 @@ struct sieve_strbuf_ehandler {
 	bool crlf;
 };
 
-static void sieve_strbuf_verror
-(struct sieve_error_handler *ehandler, const char *location,
-    const char *fmt, va_list args)
+static void sieve_strbuf_vmessage
+(struct sieve_error_handler *ehandler, const char *prefix, 
+	const char *location, const char *fmt, va_list args)
 {
 	struct sieve_strbuf_ehandler *handler =
 		(struct sieve_strbuf_ehandler *) ehandler;
 
 	if ( location != NULL && *location != '\0' )
 		str_printfa(handler->errors, "%s: ", location);
-	str_append(handler->errors, "error: ");
+	str_printfa(handler->errors, "%s: ", prefix);
 	str_vprintfa(handler->errors, fmt, args);
 
 	if ( !handler->crlf )
@@ -406,40 +435,32 @@ static void sieve_strbuf_verror
 		str_append(handler->errors, ".\r\n");
 }
 
-static void sieve_strbuf_vwarning
+static void sieve_strbuf_verror
 (struct sieve_error_handler *ehandler, const char *location,
     const char *fmt, va_list args)
 {
-	struct sieve_strbuf_ehandler *handler =
-		(struct sieve_strbuf_ehandler *) ehandler;
-
-	if ( location != NULL && *location != '\0' )
-		str_printfa(handler->errors, "%s: ", location);
-	str_printfa(handler->errors, "warning: ");
-	str_vprintfa(handler->errors, fmt, args);
+	sieve_strbuf_vmessage(ehandler, "error", location, fmt, args);
+}
 
-	if ( !handler->crlf )
-		str_append(handler->errors, ".\n");
-	else
-		str_append(handler->errors, ".\r\n");
+static void sieve_strbuf_vwarning
+(struct sieve_error_handler *ehandler, const char *location,
+    const char *fmt, va_list args)
+{
+	sieve_strbuf_vmessage(ehandler, "warning", location, fmt, args);
 }
 
 static void sieve_strbuf_vinfo
 (struct sieve_error_handler *ehandler, const char *location,
     const char *fmt, va_list args)
 {
-	struct sieve_strbuf_ehandler *handler =
-		(struct sieve_strbuf_ehandler *) ehandler;
-
-	if ( location != NULL && *location != '\0' )
-		str_printfa(handler->errors, "%s: ", location);	
-	str_printfa(handler->errors, "info: ");
-	str_vprintfa(handler->errors, fmt, args);
+	sieve_strbuf_vmessage(ehandler, "info", location, fmt, args);
+}
 
-	if ( !handler->crlf )
-		str_append(handler->errors, ".\n");
-	else
-		str_append(handler->errors, ".\r\n");
+static void sieve_strbuf_vdebug
+(struct sieve_error_handler *ehandler, const char *location,
+    const char *fmt, va_list args)
+{
+	sieve_strbuf_vmessage(ehandler, "debug", location, fmt, args);
 }
 
 struct sieve_error_handler *sieve_strbuf_ehandler_create
@@ -451,12 +472,13 @@ struct sieve_error_handler *sieve_strbuf_ehandler_create
 	pool = pool_alloconly_create("strbuf_error_handler", 256);
 	ehandler = p_new(pool, struct sieve_strbuf_ehandler, 1);
 	ehandler->errors = strbuf;
-    
+
 	sieve_error_handler_init(&ehandler->handler, pool, max_errors);
 
 	ehandler->handler.verror = sieve_strbuf_verror;
 	ehandler->handler.vwarning = sieve_strbuf_vwarning;
 	ehandler->handler.vinfo = sieve_strbuf_vinfo;
+	ehandler->handler.vdebug = sieve_strbuf_vdebug;
 
 	ehandler->crlf = crlf;
 
@@ -654,6 +676,18 @@ static void sieve_logfile_vinfo
 	sieve_logfile_vprintf(handler, location, "info", fmt, args);
 }
 
+static void sieve_logfile_vdebug
+(struct sieve_error_handler *ehandler, const char *location,
+	const char *fmt, va_list args)
+{
+	struct sieve_logfile_ehandler *handler =
+		(struct sieve_logfile_ehandler *) ehandler;
+
+	if ( !handler->started ) sieve_logfile_start(handler);
+
+	sieve_logfile_vprintf(handler, location, "debug", fmt, args);
+}
+
 static void sieve_logfile_free
 (struct sieve_error_handler *ehandler)
 {
@@ -672,28 +706,29 @@ static void sieve_logfile_free
 }
 
 struct sieve_error_handler *sieve_logfile_ehandler_create
-(const char *logfile, unsigned int max_errors) 
+(const char *logfile, unsigned int max_errors)
 {
 	pool_t pool;
 	struct sieve_logfile_ehandler *ehandler;
-	
-	pool = pool_alloconly_create("logfile_error_handler", 256);	
+
+	pool = pool_alloconly_create("logfile_error_handler", 256);
 	ehandler = p_new(pool, struct sieve_logfile_ehandler, 1);
 	sieve_error_handler_init(&ehandler->handler, pool, max_errors);
 
 	ehandler->handler.verror = sieve_logfile_verror;
 	ehandler->handler.vwarning = sieve_logfile_vwarning;
 	ehandler->handler.vinfo = sieve_logfile_vinfo;
+	ehandler->handler.vdebug = sieve_logfile_vdebug;
 	ehandler->handler.free = sieve_logfile_free;
-	
-	/* Don't open logfile until something is actually logged. 
+
+	/* Don't open logfile until something is actually logged.
 	 * Let's not pullute the sieve directory with useless logfiles.
 	 */
 	ehandler->logfile = p_strdup(pool, logfile);
 	ehandler->started = FALSE;
 	ehandler->stream = NULL;
 	ehandler->fd = -1;
-	
-	return &(ehandler->handler);	
+
+	return &(ehandler->handler);
 }
 
diff --git a/src/lib-sieve/sieve-error.h b/src/lib-sieve/sieve-error.h
index 9dda47517..e7162be3f 100644
--- a/src/lib-sieve/sieve-error.h
+++ b/src/lib-sieve/sieve-error.h
@@ -33,6 +33,7 @@ extern struct sieve_error_handler *_sieve_system_ehandler;
 #define sieve_sys_error(...) sieve_error(_sieve_system_ehandler, NULL, __VA_ARGS__ )
 #define sieve_sys_warning(...) sieve_warning(_sieve_system_ehandler, NULL, __VA_ARGS__ )
 #define sieve_sys_info(...) sieve_info(_sieve_system_ehandler, NULL, __VA_ARGS__ )
+#define sieve_sys_debug(...) sieve_debug(_sieve_system_ehandler, NULL, __VA_ARGS__ )
 
 void sieve_system_ehandler_set(struct sieve_error_handler *ehandler);
 void sieve_system_ehandler_reset(void);
@@ -57,6 +58,9 @@ void sieve_vwarning
 void sieve_vinfo
 	(struct sieve_error_handler *ehandler, const char *location, 
 		const char *fmt, va_list args); 
+void sieve_vdebug
+	(struct sieve_error_handler *ehandler, const char *location,
+		const char *fmt, va_list args);
 void sieve_vcritical
 	(struct sieve_error_handler *ehandler, const char *location, 
 		const char *fmt, va_list args); 
@@ -70,6 +74,9 @@ inline static void sieve_warning
 inline static void sieve_info
 (struct sieve_error_handler *ehandler, const char *location, 
 	const char *fmt, ...) ATTR_FORMAT(3, 4);
+inline static void sieve_debug
+(struct sieve_error_handler *ehandler, const char *location,
+	const char *fmt, ...) ATTR_FORMAT(3, 4);
 inline static void sieve_critical
 (struct sieve_error_handler *ehandler, const char *location, 
 	const char *fmt, ...) ATTR_FORMAT(3, 4);
@@ -110,6 +117,18 @@ inline static void sieve_info
 	va_end(args);
 }
 
+inline static void sieve_debug
+(struct sieve_error_handler *ehandler, const char *location, 
+	const char *fmt, ...)
+{
+	va_list args;
+	va_start(args, fmt);
+
+	T_BEGIN { sieve_vdebug(ehandler, location, fmt, args); } T_END;
+
+	va_end(args);
+}
+
 inline static void sieve_critical
 (struct sieve_error_handler *ehandler, const char *location, 
 	const char *fmt, ...)
@@ -128,6 +147,8 @@ inline static void sieve_critical
 
 void sieve_error_handler_accept_infolog
 	(struct sieve_error_handler *ehandler, bool enable);
+void sieve_error_handler_accept_debuglog
+	(struct sieve_error_handler *ehandler, bool enable);
 void sieve_error_handler_copy_masterlog
 	(struct sieve_error_handler *ehandler, bool enable);
 
diff --git a/src/plugins/lda-sieve/lda-sieve-plugin.c b/src/plugins/lda-sieve/lda-sieve-plugin.c
index 3883a7f89..4dc0767ad 100644
--- a/src/plugins/lda-sieve/lda-sieve-plugin.c
+++ b/src/plugins/lda-sieve/lda-sieve-plugin.c
@@ -132,7 +132,7 @@ static const char *lda_sieve_get_personal_path(struct mail_user *user)
 		if (*script_path == '\0') {
 			/* disabled */
 			if ( user->mail_debug )
-				sieve_sys_info("empty script path, disabled");
+				sieve_sys_debug("empty script path, disabled");
 			return NULL;
 		}
 
@@ -143,7 +143,7 @@ static const char *lda_sieve_get_personal_path(struct mail_user *user)
 
 			if ( home == NULL || *home == '\0' ) {
 				if ( user->mail_debug )
-					sieve_sys_info("relative script path, but empty home dir");
+					sieve_sys_debug("relative script path, but empty home dir");
 				return NULL;
 			}
 
@@ -226,7 +226,7 @@ static int lda_sieve_open
 		ehandler = srctx->master_ehandler;
 
 	if ( debug )
-		sieve_sys_info("opening script %s", script_path);		
+		sieve_sys_debug("opening script %s", script_path);		
 
 	sieve_error_handler_reset(ehandler);
 
@@ -237,7 +237,7 @@ static int lda_sieve_open
 
 		if ( !exists && ret == 0 ) {
 			if ( debug )
-				sieve_sys_info("script file %s is missing", script_path);
+				sieve_sys_debug("script file %s is missing", script_path);
 		} else {
 			if ( script_path == srctx->user_script && srctx->userlog != NULL ) {
 				sieve_sys_error
@@ -347,7 +347,7 @@ static int lda_sieve_singlescript_execute
 	/* Execute */
 
 	if ( debug )
-		sieve_sys_info("executing compiled script %s", script_file);
+		sieve_sys_debug("executing compiled script %s", script_file);
 
 	if ( user_script ) {
 		ehandler = srctx->user_ehandler;
@@ -640,7 +640,7 @@ static int lda_sieve_deliver_mail
 				sieve_sys_error("stat(%s) failed: %m "
 					"(using global script path in stead)", user_script);
 			else if ( debug )
-				sieve_sys_info("local script path %s doesn't exist "
+				sieve_sys_debug("local script path %s doesn't exist "
 					"(using global script path in stead)", user_script);
 
 			user_script = NULL;
@@ -651,9 +651,9 @@ static int lda_sieve_deliver_mail
 			const char *script = user_script == NULL ? default_script : user_script;
 
 			if ( script == NULL )			
-				sieve_sys_info("user has no valid personal script");
+				sieve_sys_debug("user has no valid personal script");
 			else
-				sieve_sys_info("using sieve path for user's script: %s", script);
+				sieve_sys_debug("using sieve path for user's script: %s", script);
 		}
 
 		/* Check for multiscript */
@@ -678,12 +678,12 @@ static int lda_sieve_deliver_mail
 
 			scriptfiles = array_get(&scripts_before, &count);
 			for ( i = 0; i < count; i ++ ) {
-				sieve_sys_info("executed before user's script(%d): %s", i+1, scriptfiles[i]);				
+				sieve_sys_debug("executed before user's script(%d): %s", i+1, scriptfiles[i]);				
 			}
 
 			scriptfiles = array_get(&scripts_after, &count);
 			for ( i = 0; i < count; i ++ ) {
-				sieve_sys_info("executed after user's script(%d): %s", i+1, scriptfiles[i]);				
+				sieve_sys_debug("executed after user's script(%d): %s", i+1, scriptfiles[i]);				
 			}
 		}
 	
@@ -692,7 +692,7 @@ static int lda_sieve_deliver_mail
 		if ( array_count(&scripts_before) == 0 && array_count(&scripts_after) == 0 &&
 			user_script == NULL && default_script == NULL ) {
 			if ( debug )
-				sieve_sys_info("no scripts to execute: reverting to default delivery.");
+				sieve_sys_debug("no scripts to execute: reverting to default delivery.");
 
 			/* No error, but no delivery by this plugin either. A return value of <= 0 for a 
 			 * deliver plugin is is considered a failure. In deliver itself, saved_mail and 
-- 
GitLab