From 4236767f671c5c7b9c5e6509cd394a6eb05cbb1b Mon Sep 17 00:00:00 2001 From: Timo Sirainen Date: Mon, 10 Oct 2016 13:59:57 +0300 Subject: [PATCH] lmtp: Handle lmtp_user_concurrency_limit before lmtp_rcpt_check_quota The quota lookup is more expensive, so it shouldn't be done unnecessarily. --- src/lmtp/commands.c | 43 ++++++++++++++++++++++++------------------- 1 file changed, 24 insertions(+), 19 deletions(-) diff --git a/src/lmtp/commands.c b/src/lmtp/commands.c index 0602e45f30..73ac0b80e1 100644 --- a/src/lmtp/commands.c +++ b/src/lmtp/commands.c @@ -595,6 +595,23 @@ lmtp_rcpt_to_is_over_quota(struct client *client, return ret; } +static bool cmd_rcpt_finish(struct client *client, struct mail_recipient *rcpt) +{ + int ret; + + if ((ret = lmtp_rcpt_to_is_over_quota(client, rcpt)) != 0) { + if (ret < 0) { + client_send_line(client, ERRSTR_TEMP_MAILBOX_FAIL, + rcpt->address); + } + mail_storage_service_user_free(&rcpt->service_user); + return FALSE; + } + array_append(&client->state.rcpt_to, &rcpt, 1); + client_send_line(client, "250 2.1.5 OK"); + return TRUE; +} + static void rcpt_anvil_lookup_callback(const char *reply, void *context) { struct mail_recipient *rcpt = context; @@ -609,20 +626,17 @@ static void rcpt_anvil_lookup_callback(const char *reply, void *context) i_error("Invalid reply from anvil: %s", reply); } - if (parallel_count < client->lmtp_set->lmtp_user_concurrency_limit) { - client_send_line(client, "250 2.1.5 OK"); - + if (parallel_count >= client->lmtp_set->lmtp_user_concurrency_limit) { + client_send_line(client, ERRSTR_TEMP_USERDB_FAIL_PREFIX + "Too many concurrent deliveries for user", + rcpt->address); + mail_storage_service_user_free(&rcpt->service_user); + } else if (cmd_rcpt_finish(client, rcpt)) { rcpt->anvil_connect_sent = TRUE; input = mail_storage_service_user_get_input(rcpt->service_user); master_service_anvil_send(master_service, t_strconcat( "CONNECT\t", my_pid, "\t", master_service_get_name(master_service), "/", input->username, "\n", NULL)); - array_append(&client->state.rcpt_to, &rcpt, 1); - } else { - client_send_line(client, ERRSTR_TEMP_USERDB_FAIL_PREFIX - "Too many concurrent deliveries for user", - rcpt->address); - mail_storage_service_user_free(&rcpt->service_user); } client_io_reset(client); @@ -722,18 +736,9 @@ int cmd_rcpt(struct client *client, const char *args) rcpt->address = p_strdup(client->state_pool, address); rcpt->detail = p_strdup(client->state_pool, detail); - if ((ret = lmtp_rcpt_to_is_over_quota(client, rcpt)) != 0) { - if (ret < 0) { - client_send_line(client, ERRSTR_TEMP_MAILBOX_FAIL, - rcpt->address); - } - mail_storage_service_user_free(&rcpt->service_user); - return 0; - } if (client->lmtp_set->lmtp_user_concurrency_limit == 0) { - array_append(&client->state.rcpt_to, &rcpt, 1); - client_send_line(client, "250 2.1.5 OK"); + (void)cmd_rcpt_finish(client, rcpt); return 0; } else { const char *query = t_strconcat("LOOKUP\t",