]> git.ipfire.org Git - thirdparty/dovecot/core.git/commitdiff
auth: Refactor auth worker callbacks to use arguments
authorKarl Fleischmann <karl.fleischmann@open-xchange.com>
Tue, 1 Mar 2022 09:35:10 +0000 (10:35 +0100)
committerKarl Fleischmann <karl.fleischmann@open-xchange.com>
Wed, 23 Mar 2022 15:02:04 +0000 (16:02 +0100)
To prepare a refactor of the auth worker input handling to use the
connection API this commit changes the signature of the auth worker
callback to use an arguments array instead of the full line as well as
all relevant callback functions.

src/auth/auth-worker-server.c
src/auth/auth-worker-server.h
src/auth/passdb-blocking.c
src/auth/passdb-blocking.h
src/auth/passdb-cache.c
src/auth/userdb-blocking.c

index 0cc200f0b3a46b980165ad16d45a2984bcbd2254..5b851212ee23007cb3ddc66ac5024f7899529857 100644 (file)
@@ -10,6 +10,7 @@
 #include "ostream.h"
 #include "hex-binary.h"
 #include "str.h"
+#include "strescape.h"
 #include "eacces-error.h"
 #include "auth-request.h"
 #include "auth-worker-client.h"
@@ -94,9 +95,12 @@ static bool auth_worker_request_send(struct auth_worker_connection *worker,
                        "Aborting auth request that was queued for %d secs, "
                        "%d left in queue",
                        age_secs, aqueue_count(worker_request_queue));
-               request->callback(t_strdup_printf(
-                       "FAIL\t%d", PASSDB_RESULT_INTERNAL_FAILURE),
-                       request->context);
+               const char *const args[] = {
+                       "FAIL",
+                       t_strdup_printf("%d", PASSDB_RESULT_INTERNAL_FAILURE),
+                       NULL,
+               };
+               request->callback(args, request->context);
                return FALSE;
        }
        if (age_secs >= AUTH_WORKER_DELAY_WARN_SECS &&
@@ -236,9 +240,12 @@ static void auth_worker_destroy(struct auth_worker_connection **_worker,
                e_error(worker->conn.event, "Aborted %s request for %s: %s",
                        t_strcut(worker->request->data, '\t'),
                        worker->request->username, reason);
-               worker->request->callback(t_strdup_printf(
-                               "FAIL\t%d", PASSDB_RESULT_INTERNAL_FAILURE),
-                               worker->request->context);
+               const char *const args[] = {
+                       "FAIL",
+                       t_strdup_printf("%d", PASSDB_RESULT_INTERNAL_FAILURE),
+                       NULL,
+               };
+               worker->request->callback(args, worker->request->context);
        }
 
        io_remove(&worker->conn.io);
@@ -296,7 +303,13 @@ static bool auth_worker_request_handle(struct auth_worker_connection *worker,
                idle_count++;
        }
 
-       if (!request->callback(line, request->context) &&
+       const char *const *args = t_strsplit_tabescaped(line);
+       if (args[0] == NULL) {
+               const char *empty_args[] = { "", NULL };
+               args = empty_args;
+       }
+
+       if (!request->callback(args, request->context) &&
            worker->conn.io != NULL) {
                worker->timeout_pending_resume = FALSE;
                timeout_remove(&worker->to_lookup);
index a46b332eba04403a72d5c0fb80be88366c0ed2e2..6d166f1f8b3b13de9001f05a98b3532cd7374904 100644 (file)
@@ -4,7 +4,7 @@
 struct auth_request;
 struct auth_stream_reply;
 
-typedef bool auth_worker_callback_t(const char *reply, void *context);
+typedef bool auth_worker_callback_t(const char *const *args, void *context);
 
 struct auth_worker_connection * ATTR_NOWARN_UNUSED_RESULT
 auth_worker_call(pool_t pool, const char *username, const char *data,
index f33a8c2c560659e16f75d09217af4780a288e248..7ba5d10c82adf540aa8aa15c272a15851f498eb4 100644 (file)
@@ -22,12 +22,10 @@ auth_worker_reply_parse_args(struct auth_request *request,
 }
 
 enum passdb_result
-passdb_blocking_auth_worker_reply_parse(struct auth_request *request, const char *reply)
+passdb_blocking_auth_worker_reply_parse(struct auth_request *request,
+                                       const char *const *args)
 {
        enum passdb_result ret;
-       const char *const *args;
-
-       args = t_strsplit_tabescaped(reply);
 
        if (strcmp(*args, "OK") == 0 && args[1] != NULL && args[2] != NULL) {
                /* OK \t user \t password [\t extra] */
@@ -68,18 +66,18 @@ passdb_blocking_auth_worker_reply_parse(struct auth_request *request, const char
                }
        }
 
-       e_error(authdb_event(request),
-               "Received invalid reply from worker: %s", reply);
+       e_error(authdb_event(request), "Received invalid reply from worker: %s",
+               t_strarray_join(args, "\t"));
        return PASSDB_RESULT_INTERNAL_FAILURE;
 }
 
 static bool
-verify_plain_callback(const char *reply, void *context)
+verify_plain_callback(const char *const *args, void *context)
 {
        struct auth_request *request = context;
        enum passdb_result result;
 
-       result = passdb_blocking_auth_worker_reply_parse(request, reply);
+       result = passdb_blocking_auth_worker_reply_parse(request, args);
        auth_request_verify_plain_callback(result, request);
        auth_request_unref(&request);
        return TRUE;
@@ -100,13 +98,13 @@ void passdb_blocking_verify_plain(struct auth_request *request)
                         verify_plain_callback, request);
 }
 
-static bool lookup_credentials_callback(const char *reply, void *context)
+static bool lookup_credentials_callback(const char *const *args, void *context)
 {
        struct auth_request *request = context;
        enum passdb_result result;
        const char *password = NULL, *scheme = NULL;
 
-       result = passdb_blocking_auth_worker_reply_parse(request, reply);
+       result = passdb_blocking_auth_worker_reply_parse(request, args);
        if (result == PASSDB_RESULT_OK && request->passdb_password != NULL) {
                password = request->passdb_password;
                scheme = password_get_scheme(&password);
@@ -141,13 +139,12 @@ void passdb_blocking_lookup_credentials(struct auth_request *request)
 }
 
 static bool
-set_credentials_callback(const char *reply, void *context)
+set_credentials_callback(const char *const *args, void *context)
 {
        struct auth_request *request = context;
        bool success;
 
-       success = strcmp(reply, "OK") == 0 ||
-               str_begins_with(reply, "OK\t");
+       success = strcmp(args[0], "OK") == 0;
        request->private_callback.set_credentials(success, request);
        auth_request_unref(&request);
        return TRUE;
index 396399800e5abe9b8af3b3d6ff0924f477e53432..008a0e4664929c31d9f1ef3eb0dd926bdd9e92fa 100644 (file)
@@ -2,7 +2,8 @@
 #define PASSDB_BLOCKING_H
 
 enum passdb_result
-passdb_blocking_auth_worker_reply_parse(struct auth_request *request, const char *reply);
+passdb_blocking_auth_worker_reply_parse(struct auth_request *request,
+                                       const char *const *args);
 void passdb_blocking_verify_plain(struct auth_request *request);
 void passdb_blocking_lookup_credentials(struct auth_request *request);
 void passdb_blocking_set_credentials(struct auth_request *request,
index 1732f4d693239b50c847f8b5ab71fb86e2d42b18..9bf15c011c889c0084e4f8fbf5eb7131fce5d522 100644 (file)
@@ -52,12 +52,13 @@ passdb_cache_lookup(struct auth_request *request, const char *key,
        return TRUE;
 }
 
-static bool passdb_cache_verify_plain_callback(const char *reply, void *context)
+static bool passdb_cache_verify_plain_callback(const char *const *args,
+                                              void *context)
 {
        struct auth_request *request = context;
        enum passdb_result result;
 
-       result = passdb_blocking_auth_worker_reply_parse(request, reply);
+       result = passdb_blocking_auth_worker_reply_parse(request, args);
        if (result != PASSDB_RESULT_OK)
                auth_fields_rollback(request->fields.extra_fields);
        auth_request_verify_plain_callback_finish(result, request);
index 37952535ad71de80721d66d93d79b3f2973385b7..35e19e70993c88a18f2d52a19d60f5178917e119 100644 (file)
@@ -14,23 +14,28 @@ struct blocking_userdb_iterate_context {
        bool destroyed;
 };
 
-static bool user_callback(const char *reply, void *context)
+static bool user_callback(const char *const *args, void *context)
 {
        struct auth_request *request = context;
        enum userdb_result result;
-       const char *username, *args;
+       const char *username;
 
-       if (str_begins(reply, "FAIL\t", &args)) {
+       if (strcmp(args[0], "FAIL") == 0) {
                result = USERDB_RESULT_INTERNAL_FAILURE;
-       } else if (str_begins(reply, "NOTFOUND\t", &args)) {
+               args++;
+       } else if (strcmp(args[0], "NOTFOUND") == 0) {
                result = USERDB_RESULT_USER_UNKNOWN;
-       } else if (str_begins(reply, "OK\t", &username)) {
+               args++;
+       } else if (strcmp(args[0], "OK") == 0) {
                result = USERDB_RESULT_OK;
-               args = strchr(username, '\t');
-               if (args == NULL)
-                       args = "";
-               else
-                       username = t_strdup_until(username, args++);
+               if (args[1] == NULL) {
+                       username = "";
+                       args++;
+               } else {
+                       username = args[1];
+                       args += 2;
+               }
+
                if (username[0] != '\0' &&
                    strcmp(request->fields.user, username) != 0) {
                        auth_request_set_username_forced(request, username);
@@ -40,11 +45,11 @@ static bool user_callback(const char *reply, void *context)
                result = USERDB_RESULT_INTERNAL_FAILURE;
                e_error(authdb_event(request),
                        "BUG: auth-worker sent invalid user reply");
-               args = "";
+               args = NULL;
        }
 
-       if (*args != '\0') {
-               auth_fields_import(request->fields.userdb_reply, args, 0);
+       if (args != NULL && args[0] != NULL && *args[0] != '\0') {
+               auth_fields_import_args(request->fields.userdb_reply, args, 0);
                if (auth_fields_exists(request->fields.userdb_reply, "tempfail"))
                        request->userdb_lookup_tempfailed = TRUE;
        }
@@ -67,20 +72,19 @@ void userdb_blocking_lookup(struct auth_request *request)
                         str_c(str), user_callback, request);
 }
 
-static bool iter_callback(const char *reply, void *context)
+static bool iter_callback(const char *const *args, void *context)
 {
        struct blocking_userdb_iterate_context *ctx = context;
-       const char *args;
 
-       if (str_begins(reply, "*\t", &args)) {
+       if (strcmp(args[0], "*") == 0 && args[1] != NULL) {
                if (ctx->destroyed)
                        return TRUE;
                ctx->next = FALSE;
-               ctx->ctx.callback(args, ctx->ctx.context);
+               ctx->ctx.callback(args[1], ctx->ctx.context);
                return ctx->next || ctx->destroyed;
        }
 
-       if (strcmp(reply, "OK") != 0)
+       if (strcmp(args[0], "OK") != 0)
                ctx->ctx.failed = TRUE;
        if (!ctx->destroyed)
                ctx->ctx.callback(NULL, ctx->ctx.context);