From: Timo Sirainen Date: Fri, 19 Feb 2010 02:20:25 +0000 (+0200) Subject: auth: Don't loop through active requests every 5 seconds, looking for timeouts. X-Git-Tag: 2.0.beta3~41 X-Git-Url: http://git.ipfire.org/gitweb.cgi?a=commitdiff_plain;h=48ac75465ae154b1d705f18de6d95045ab714b65;p=thirdparty%2Fdovecot%2Fcore.git auth: Don't loop through active requests every 5 seconds, looking for timeouts. --HG-- branch : HEAD --- diff --git a/src/auth/auth-client-connection.c b/src/auth/auth-client-connection.c index b42728212f..77a94b7ded 100644 --- a/src/auth/auth-client-connection.c +++ b/src/auth/auth-client-connection.c @@ -24,7 +24,6 @@ #define OUTBUF_THROTTLE_SIZE (1024*50) static ARRAY_DEFINE(auth_client_connections, struct auth_client_connection *); -static struct timeout *to_clients; static void auth_client_connection_unref(struct auth_client_connection **_conn); static void auth_client_input(struct auth_client_connection *conn); @@ -363,24 +362,9 @@ auth_client_connection_lookup(unsigned int pid) return NULL; } -static void request_timeout(void *context ATTR_UNUSED) -{ - struct auth_client_connection *const *clients; - - array_foreach(&auth_client_connections, clients) { - struct auth_client_connection *client = *clients; - - if (client->request_handler != NULL) { - auth_request_handler_check_timeouts( - client->request_handler); - } - } -} - void auth_client_connections_init(void) { i_array_init(&auth_client_connections, 16); - to_clients = timeout_add(5000, request_timeout, NULL); } void auth_client_connections_deinit(void) @@ -388,9 +372,6 @@ void auth_client_connections_deinit(void) struct auth_client_connection **clients; unsigned int i, count; - if (to_clients != NULL) - timeout_remove(&to_clients); - clients = array_get_modifiable(&auth_client_connections, &count); for (i = count; i > 0; i--) auth_client_connection_destroy(&clients[i-1]); diff --git a/src/auth/auth-request-handler.c b/src/auth/auth-request-handler.c index 1c4fa2ef8b..7fc54235b7 100644 --- a/src/auth/auth-request-handler.c +++ b/src/auth/auth-request-handler.c @@ -96,25 +96,12 @@ void auth_request_handler_set(struct auth_request_handler *handler, static void auth_request_handler_remove(struct auth_request_handler *handler, struct auth_request *request) { + i_assert(request->handler == handler); + hash_table_remove(handler->requests, POINTER_CAST(request->id)); auth_request_unref(&request); } -void auth_request_handler_check_timeouts(struct auth_request_handler *handler) -{ - struct hash_iterate_context *iter; - void *key, *value; - - iter = hash_table_iterate_init(handler->requests); - while (hash_table_iterate(iter, &key, &value)) { - struct auth_request *request = value; - - if (request->last_access + AUTH_REQUEST_TIMEOUT < ioloop_time) - auth_request_handler_remove(handler, request); - } - hash_table_iterate_deinit(&iter); -} - static void get_client_extra_fields(struct auth_request *request, struct auth_stream_reply *reply) { @@ -192,7 +179,7 @@ auth_request_handle_failure(struct auth_request *request, auth_penalty_update(request->auth->penalty, request, request->last_penalty + 1); - request->last_access = ioloop_time; + auth_request_refresh_last_access(request); aqueue_append(auth_failures, &request); if (to_auth_failures == NULL) { to_auth_failures = @@ -290,6 +277,11 @@ static void auth_request_handler_auth_fail(struct auth_request_handler *handler, auth_request_handler_remove(handler, request); } +static void auth_request_timeout(struct auth_request *request) +{ + auth_request_handler_remove(request->handler, request); +} + static void auth_request_penalty_finish(struct auth_request *request) { timeout_remove(&request->to_penalty); @@ -343,6 +335,7 @@ bool auth_request_handler_auth_begin(struct auth_request_handler *handler, } request = auth_request_new(handler->auth, mech, auth_callback, handler); + request->handler = handler; request->connect_uid = handler->connect_uid; request->client_pid = handler->client_pid; request->id = id; @@ -383,6 +376,8 @@ bool auth_request_handler_auth_begin(struct auth_request_handler *handler, return FALSE; } + request->to_abort = timeout_add(AUTH_REQUEST_TIMEOUT * 1000, + auth_request_timeout, request); hash_table_insert(handler->requests, POINTER_CAST(id), request); if (request->auth->set->ssl_require_client_cert && diff --git a/src/auth/auth-request-handler.h b/src/auth/auth-request-handler.h index d81abfb8f3..b580677b47 100644 --- a/src/auth/auth-request-handler.h +++ b/src/auth/auth-request-handler.h @@ -30,8 +30,6 @@ void auth_request_handler_set(struct auth_request_handler *handler, unsigned int connect_uid, unsigned int client_pid); -void auth_request_handler_check_timeouts(struct auth_request_handler *handler); - bool auth_request_handler_auth_begin(struct auth_request_handler *handler, const char *args); bool auth_request_handler_auth_continue(struct auth_request_handler *handler, diff --git a/src/auth/auth-request.c b/src/auth/auth-request.c index 7e3432d3e9..d2fef0ce4e 100644 --- a/src/auth/auth-request.c +++ b/src/auth/auth-request.c @@ -62,6 +62,7 @@ struct auth_request *auth_request_new_dummy(struct auth *auth) auth_request->refcount = 1; auth_request->last_access = ioloop_time; + auth_request->auth = auth; auth_request->passdb = auth->passdbs; auth_request->userdb = auth->userdbs; @@ -82,7 +83,7 @@ void auth_request_success(struct auth_request *request, request->state = AUTH_REQUEST_STATE_FINISHED; request->successful = TRUE; - request->last_access = ioloop_time; + auth_request_refresh_last_access(request); request->callback(request, AUTH_CLIENT_RESULT_SUCCESS, data, data_size); } @@ -92,7 +93,7 @@ void auth_request_fail(struct auth_request *request) i_assert(request->state == AUTH_REQUEST_STATE_MECH_CONTINUE); request->state = AUTH_REQUEST_STATE_FINISHED; - request->last_access = ioloop_time; + auth_request_refresh_last_access(request); request->callback(request, AUTH_CLIENT_RESULT_FAILURE, NULL, 0); } @@ -116,6 +117,8 @@ void auth_request_unref(struct auth_request **_request) if (--request->refcount > 0) return; + if (request->to_abort != NULL) + timeout_remove(&request->to_abort); if (request->to_penalty != NULL) timeout_remove(&request->to_penalty); @@ -221,7 +224,7 @@ void auth_request_continue(struct auth_request *request, { i_assert(request->state == AUTH_REQUEST_STATE_MECH_CONTINUE); - request->last_access = ioloop_time; + auth_request_refresh_last_access(request); request->mech->auth_continue(request, data, data_size); } @@ -1561,3 +1564,10 @@ void auth_request_log_error(struct auth_request *auth_request, } T_END; va_end(va); } + +void auth_request_refresh_last_access(struct auth_request *request) +{ + request->last_access = ioloop_time; + if (request->to_abort != NULL) + timeout_reset(request->to_abort); +} diff --git a/src/auth/auth-request.h b/src/auth/auth-request.h index c9e0110091..580939e3ac 100644 --- a/src/auth/auth-request.h +++ b/src/auth/auth-request.h @@ -55,6 +55,7 @@ struct auth_request { struct auth_stream_reply *userdb_reply; const struct mech_module *mech; + struct auth_request_handler *handler; struct auth *auth; struct auth_passdb *passdb; struct auth_userdb *userdb; @@ -68,7 +69,7 @@ struct auth_request { struct ip_addr local_ip, remote_ip; unsigned int local_port, remote_port; - struct timeout *to_penalty; + struct timeout *to_abort, *to_penalty; unsigned int last_penalty; unsigned int initial_response_len; const unsigned char *initial_response; @@ -195,4 +196,6 @@ void auth_request_set_credentials(struct auth_request *request, void auth_request_userdb_callback(enum userdb_result result, struct auth_request *request); +void auth_request_refresh_last_access(struct auth_request *request); + #endif