From: Stephan Bosch Date: Tue, 4 Nov 2025 23:04:09 +0000 (+0100) Subject: submission-login: Halt the handling of the AUTH commmand while the auth service is... X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=0dbc990f5018644172325d54ddf0df711b70459b;p=thirdparty%2Fdovecot%2Fcore.git submission-login: Halt the handling of the AUTH commmand while the auth service is not connected --- diff --git a/src/submission-login/client-authenticate.c b/src/submission-login/client-authenticate.c index 39a63f8916..89e7f872b5 100644 --- a/src/submission-login/client-authenticate.c +++ b/src/submission-login/client-authenticate.c @@ -287,6 +287,7 @@ void submission_client_auth_send_challenge(struct client *client, container_of(client, struct submission_client, common); struct smtp_server_cmd_ctx *cmd = subm_client->auth_cmd; + i_assert(!subm_client->auth_cmd_implicit); i_assert(cmd != NULL); smtp_server_cmd_auth_send_challenge(cmd, data); @@ -329,18 +330,49 @@ cmd_auth_set_master_data_prefix(struct submission_client *subm_client, client->master_data_prefix = buffer_free_without_data(&buf); } +void cmd_auth_begin(struct submission_client *subm_client) +{ + subm_client->auth_cmd_deferred = FALSE; + + if (subm_client->auth_cmd == NULL) + return; + + struct client *client = &subm_client->common; + + if (subm_client->auth_cmd_implicit) { + (void)client_auth_begin_implicit(client, + SASL_MECH_NAME_EXTERNAL, "="); + } else { + struct smtp_server_cmd_auth *data = subm_client->auth_cmd_data; + + i_assert(data != NULL); + (void)client_auth_begin(client, data->sasl_mech, + data->initial_response); + } +} + int cmd_auth(void *conn_ctx, struct smtp_server_cmd_ctx *cmd, struct smtp_server_cmd_auth *data) { struct submission_client *subm_client = conn_ctx; struct client *client = &subm_client->common; + i_assert(!client->authenticating); + cmd_auth_set_master_data_prefix(subm_client, NULL); + subm_client->auth_cmd_deferred = FALSE; i_assert(subm_client->auth_cmd == NULL); subm_client->auth_cmd = cmd; + subm_client->auth_cmd_data = data; /* allocated on cmd pool */ + subm_client->auth_cmd_implicit = FALSE; + + if (!auth_client_is_connected(auth_client)) { + subm_client->auth_cmd_deferred = TRUE; + return 0; + } - (void)client_auth_begin(client, data->sasl_mech, data->initial_response); + cmd_auth_begin(subm_client); return 0; } @@ -362,15 +394,24 @@ void cmd_mail(struct smtp_server_cmd_ctx *cmd, const char *params) return; } + i_assert(!client->authenticating); + e_debug(cmd->event, "Performing implicit EXTERNAL authentication"); smtp_server_command_input_lock(cmd); cmd_auth_set_master_data_prefix(subm_client, params); + subm_client->auth_cmd_deferred = FALSE; i_assert(subm_client->auth_cmd == NULL); subm_client->auth_cmd = cmd; + subm_client->auth_cmd_implicit = TRUE; + + if (!auth_client_is_connected(auth_client)) { + subm_client->auth_cmd_deferred = TRUE; + return; + } - (void)client_auth_begin_implicit(client, SASL_MECH_NAME_EXTERNAL, "="); + cmd_auth_begin(subm_client); } diff --git a/src/submission-login/client-authenticate.h b/src/submission-login/client-authenticate.h index 8353b49f31..4f7ea6d077 100644 --- a/src/submission-login/client-authenticate.h +++ b/src/submission-login/client-authenticate.h @@ -13,6 +13,7 @@ int cmd_helo(void *conn_ctx, struct smtp_server_cmd_ctx *cmd, struct smtp_server_cmd_helo *data); int cmd_auth_continue(void *conn_ctx, struct smtp_server_cmd_ctx *cmd, const char *response); +void cmd_auth_begin(struct submission_client *subm_client); int cmd_auth(void *conn_ctx, struct smtp_server_cmd_ctx *cmd, struct smtp_server_cmd_auth *data); diff --git a/src/submission-login/client.c b/src/submission-login/client.c index 1d920d1524..a42ab261ab 100644 --- a/src/submission-login/client.c +++ b/src/submission-login/client.c @@ -168,6 +168,15 @@ static void submission_client_notify_auth_ready(struct client *client) smtp_server_connection_start(subm_client->conn); } +static void submission_client_notify_auth_connected(struct client *client) +{ + struct submission_client *subm_client = + container_of(client, struct submission_client, common); + + if (subm_client->auth_cmd_deferred) + cmd_auth_begin(subm_client); +} + static void submission_client_notify_disconnect(struct client *_client, enum client_disconnect_reason reason, @@ -243,6 +252,7 @@ static void client_connection_disconnect(void *context, const char *reason) struct submission_client *client = context; client->auth_cmd = NULL; + client->auth_cmd_data = NULL; client_disconnect(&client->common, reason); } @@ -323,6 +333,7 @@ static struct client_vfuncs submission_client_vfuncs = { .destroy = submission_client_destroy, .reload_config = submission_client_reload_config, .notify_auth_ready = submission_client_notify_auth_ready, + .notify_auth_connected = submission_client_notify_auth_connected, .notify_disconnect = submission_client_notify_disconnect, .auth_send_challenge = submission_client_auth_send_challenge, .auth_result = submission_client_auth_result, diff --git a/src/submission-login/client.h b/src/submission-login/client.h index 731d912d95..34f948f55f 100644 --- a/src/submission-login/client.h +++ b/src/submission-login/client.h @@ -25,7 +25,9 @@ struct submission_client { enum smtp_capability backend_capabilities; struct smtp_server_connection *conn; + struct smtp_server_cmd_ctx *auth_cmd; + struct smtp_server_cmd_auth *auth_cmd_data; enum submission_proxy_state proxy_state; enum smtp_capability proxy_capability; @@ -34,6 +36,9 @@ struct submission_client { struct smtp_server_reply *proxy_reply; const char **proxy_xclient; unsigned int proxy_xclient_replies_expected; + + bool auth_cmd_implicit:1; + bool auth_cmd_deferred:1; }; #endif