From 5ddf67da167315bcc22ca3f576c26984673423fe Mon Sep 17 00:00:00 2001
From: Stephan Bosch <stephan@rename-it.nl>
Date: Thu, 9 Oct 2008 23:24:54 +0200
Subject: [PATCH] Fixed amd64 logging segfault; turns out using same va_args in
 multiple vprintf calls is not possible.

---
 TODO                        |  1 -
 src/lib-sieve/sieve-error.c | 29 +++++++++++++++++++++--------
 2 files changed, 21 insertions(+), 9 deletions(-)

diff --git a/TODO b/TODO
index b7f0e6a0f..abc6eb0b3 100644
--- a/TODO
+++ b/TODO
@@ -5,7 +5,6 @@ Next (in order of descending priority/precedence):
 	- Variables: dump variable identifiers in stead of storage indexes
 * Make sure cmusieve can be replaced seamlessly with the new plugin.
 * Final issues:
-	- Fix amd64 logging segfault
 	- Fix/Report issues listed in 'doc/rfc/RFC Controversy.txt'
 
 
diff --git a/src/lib-sieve/sieve-error.c b/src/lib-sieve/sieve-error.c
index c43d698c1..2ea76d527 100644
--- a/src/lib-sieve/sieve-error.c
+++ b/src/lib-sieve/sieve-error.c
@@ -53,10 +53,14 @@ void sieve_verror
 	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));
+			sieve_sys_error("%s", t_strdup_vprintf(fmt, args_copy));
 		else
-			sieve_sys_error("%s: %s", location, t_strdup_vprintf(fmt, args));
+			sieve_sys_error("%s: %s", location, t_strdup_vprintf(fmt, args_copy));
 	}
 
 	if ( sieve_errors_more_allowed(ehandler) ) {
@@ -73,10 +77,14 @@ void sieve_vwarning
 	if ( ehandler == NULL ) return;
 
 	if ( ehandler->log_master ) {
+		va_list args_copy;
+
+		VA_COPY(args_copy, args);
+
 		if ( location == NULL || *location == '\0' )
-			sieve_sys_warning("%s", t_strdup_vprintf(fmt, args));
+			sieve_sys_warning("%s", t_strdup_vprintf(fmt, args_copy));
 		else
-			sieve_sys_warning("%s: %s", location, t_strdup_vprintf(fmt, args));
+			sieve_sys_warning("%s: %s", location, t_strdup_vprintf(fmt, args_copy));
 	}
 	
 	if ( ehandler->vwarning != NULL )	
@@ -91,10 +99,15 @@ void sieve_vinfo
 	if ( ehandler == NULL ) return;
 
 	if ( ehandler->log_master ) {
+		va_list args_copy;
+
+		VA_COPY(args_copy, args);
+
+
 		if ( location == NULL || *location == '\0' )
-			sieve_sys_info("%s", t_strdup_vprintf(fmt, args));
+			sieve_sys_info("%s", t_strdup_vprintf(fmt, args_copy));
 		else	
-			sieve_sys_info("%s: %s", location, t_strdup_vprintf(fmt, args));
+			sieve_sys_info("%s: %s", location, t_strdup_vprintf(fmt, args_copy));
 	}
 	
 	if ( ehandler->log_info && ehandler->vinfo != NULL )	
@@ -349,7 +362,7 @@ struct sieve_logfile_ehandler {
 
 static void sieve_logfile_vprintf
 (struct sieve_logfile_ehandler *ehandler, const char *location, 
-	const char *prefix,	const char *fmt, va_list args) 
+	const char *prefix, const char *fmt, va_list args) 
 {
 	string_t *outbuf;
 	ssize_t ret = 0, remain;
@@ -379,7 +392,7 @@ static void sieve_logfile_vprintf
 
 	if ( ret < 0 ) {
 		sieve_sys_error(
-			"o_stream_send() failed on logfile %s: %m",	ehandler->logfile);		
+			"o_stream_send() failed on logfile %s: %m", ehandler->logfile);		
 	}
 }
 
-- 
GitLab