From 6211d99e16267b9b72d206b98f376ee898069d40 Mon Sep 17 00:00:00 2001
From: Stephan Bosch <stephan@rename-it.nl>
Date: Fri, 17 Oct 2014 21:07:36 +0200
Subject: [PATCH] lib-sieve: Flush duplicate database before committing storage
 transactions.

---
 src/lib-sieve/sieve-actions.c            | 9 +++++++++
 src/lib-sieve/sieve-actions.h            | 2 ++
 src/lib-sieve/sieve-result.c             | 7 +++++++
 src/lib-sieve/sieve-types.h              | 2 ++
 src/plugins/lda-sieve/lda-sieve-plugin.c | 9 +++++++++
 5 files changed, 29 insertions(+)

diff --git a/src/lib-sieve/sieve-actions.c b/src/lib-sieve/sieve-actions.c
index 178217098..3d7e04858 100644
--- a/src/lib-sieve/sieve-actions.c
+++ b/src/lib-sieve/sieve-actions.c
@@ -780,6 +780,15 @@ void sieve_action_duplicate_mark
 	senv->duplicate_mark(senv, id, id_size, time);
 }
 
+void sieve_action_duplicate_flush
+(const struct sieve_script_env *senv)
+{
+	if ( senv->duplicate_flush == NULL )
+		return;
+	senv->duplicate_flush(senv);
+}
+
+
 /* Rejecting the mail */
 
 static bool sieve_action_do_reject_mail
diff --git a/src/lib-sieve/sieve-actions.h b/src/lib-sieve/sieve-actions.h
index 19bc139ac..37d952290 100644
--- a/src/lib-sieve/sieve-actions.h
+++ b/src/lib-sieve/sieve-actions.h
@@ -265,6 +265,8 @@ int sieve_action_duplicate_check
 void sieve_action_duplicate_mark
 	(const struct sieve_script_env *senv, const void *id, size_t id_size,
 		time_t time);
+void sieve_action_duplicate_flush
+	(const struct sieve_script_env *senv);
 
 /* Rejecting mail */
 
diff --git a/src/lib-sieve/sieve-result.c b/src/lib-sieve/sieve-result.c
index 3e2813b5b..9b6743fa4 100644
--- a/src/lib-sieve/sieve-result.c
+++ b/src/lib-sieve/sieve-result.c
@@ -1248,8 +1248,10 @@ static int sieve_result_transaction_commit_or_rollback
 	struct sieve_result_action *last,
 	bool *implicit_keep, bool *keep)
 {
+	const struct sieve_script_env *senv = result->action_env.scriptenv;
 	struct sieve_result_action *rac;
 	int commit_status = status;
+	bool dup_flushed = FALSE;
 
 	/* First commit/rollback all storage actions */
 	rac = first;
@@ -1262,6 +1264,11 @@ static int sieve_result_transaction_commit_or_rollback
 			continue;
 		}
 
+		if (!dup_flushed) {
+			sieve_action_duplicate_flush(senv);
+			dup_flushed = TRUE;
+		}
+
 		status = sieve_result_action_commit_or_rollback
 			(result, rac, status, implicit_keep, keep, &commit_status);
 
diff --git a/src/lib-sieve/sieve-types.h b/src/lib-sieve/sieve-types.h
index 293e29888..8567dc4e2 100644
--- a/src/lib-sieve/sieve-types.h
+++ b/src/lib-sieve/sieve-types.h
@@ -206,6 +206,8 @@ struct sieve_script_env {
 	void (*duplicate_mark)
 		(const struct sieve_script_env *senv, const void *id, size_t id_size,
 			time_t time);
+	void (*duplicate_flush)
+		(const struct sieve_script_env *senv);
 
 	/* Interface for rejecting mail */
 	int (*reject_mail)(const struct sieve_script_env *senv,
diff --git a/src/plugins/lda-sieve/lda-sieve-plugin.c b/src/plugins/lda-sieve/lda-sieve-plugin.c
index 406070b73..183c22b63 100644
--- a/src/plugins/lda-sieve/lda-sieve-plugin.c
+++ b/src/plugins/lda-sieve/lda-sieve-plugin.c
@@ -132,6 +132,14 @@ static void lda_sieve_duplicate_mark
 	duplicate_mark(dctx->dup_ctx, id, id_size, senv->user->username, time);
 }
 
+static void lda_sieve_duplicate_flush
+(const struct sieve_script_env *senv)
+{
+	struct mail_deliver_context *dctx =
+		(struct mail_deliver_context *) senv->script_context;
+	duplicate_flush(dctx->dup_ctx);
+}
+
 /*
  * Plugin implementation
  */
@@ -906,6 +914,7 @@ static int lda_sieve_execute
 		scriptenv.smtp_finish = lda_sieve_smtp_finish;
 		scriptenv.duplicate_mark = lda_sieve_duplicate_mark;
 		scriptenv.duplicate_check = lda_sieve_duplicate_check;
+		scriptenv.duplicate_flush = lda_sieve_duplicate_flush;
 		scriptenv.reject_mail = lda_sieve_reject_mail;
 		scriptenv.script_context = (void *) mdctx;
 		scriptenv.exec_status = &estatus;
-- 
GitLab