changeset 14919:225c64ed0439

lib-dict: Fixed hang if async commit's callback did more dict access. Specifically this fixes a hang with dict-quota plugin when user didn't exist and quota was changed before calculating it.
author Timo Sirainen <tss@iki.fi>
date Fri, 22 Feb 2013 13:51:02 +0200
parents 81ea622b6394
children 0a932ba1f01f
files src/lib-dict/dict-client.c
diffstat 1 files changed, 7 insertions(+), 5 deletions(-) [+]
line wrap: on
line diff
--- a/src/lib-dict/dict-client.c	Fri Feb 22 12:19:36 2013 +0200
+++ b/src/lib-dict/dict-client.c	Fri Feb 22 13:51:02 2013 +0200
@@ -262,15 +262,17 @@
 		i_error("dict-client: Unknown transaction id %u", id);
 		return;
 	}
-	if (ctx->callback != NULL)
-		ctx->callback(ret, ctx->context);
 
-	DLLIST_REMOVE(&dict->transactions, ctx);
-	i_free(ctx);
-
+	/* the callback may call the dict code again, so remove this
+	   transaction before calling it */
 	i_assert(dict->async_commits > 0);
 	if (--dict->async_commits == 0)
 		io_remove(&dict->io);
+	DLLIST_REMOVE(&dict->transactions, ctx);
+
+	if (ctx->callback != NULL)
+		ctx->callback(ret, ctx->context);
+	i_free(ctx);
 }
 
 static ssize_t client_dict_read_timeout(struct client_dict *dict)