]> git.ipfire.org Git - thirdparty/dovecot/core.git/commitdiff
lib-sasl: Support ANONYMOUS mechanism
authorAki Tuomi <aki.tuomi@open-xchange.com>
Mon, 17 Feb 2025 16:09:58 +0000 (18:09 +0200)
committerAki Tuomi <aki.tuomi@open-xchange.com>
Thu, 27 Feb 2025 10:47:44 +0000 (12:47 +0200)
src/lib-sasl/Makefile.am
src/lib-sasl/dsasl-client-private.h
src/lib-sasl/dsasl-client.c
src/lib-sasl/mech-anonymous.c [new file with mode: 0644]

index 22a6f290e71d17c30b2c5c1ec502e417aa013bea..295b8384ef2ba57038f209cb7963a28b312a2fdf 100644 (file)
@@ -9,6 +9,7 @@ AM_CPPFLAGS = \
        -I$(top_srcdir)/src/lib-ssl-iostream
 
 libsasl_la_SOURCES = \
+       mech-anonymous.c \
        mech-external.c \
        mech-login.c \
        mech-plain.c \
index d1a617467868e8bf1d5dc9b5dac7f36f549c2488..8a0cd4f6cb491fb4db5056857bf1a4209bb2c9dc 100644 (file)
@@ -39,6 +39,7 @@ struct dsasl_client_mech {
        void (*free)(struct dsasl_client *client);
 };
 
+extern const struct dsasl_client_mech dsasl_client_mech_anonymous;
 extern const struct dsasl_client_mech dsasl_client_mech_external;
 extern const struct dsasl_client_mech dsasl_client_mech_login;
 extern const struct dsasl_client_mech dsasl_client_mech_oauthbearer;
index d1919505d05ac3cc93b7936da3b61390b83e7eba..d1e38fef3cb983b502df84ffc23af0a1eb0b7aad 100644 (file)
@@ -151,7 +151,8 @@ void dsasl_clients_init(void)
        if (init_refcount++ > 0)
                return;
 
-       i_array_init(&dsasl_mechanisms, 8);
+       i_array_init(&dsasl_mechanisms, 16);
+       dsasl_client_mech_register(&dsasl_client_mech_anonymous);
        dsasl_client_mech_register(&dsasl_client_mech_external);
        dsasl_client_mech_register(&dsasl_client_mech_plain);
        dsasl_client_mech_register(&dsasl_client_mech_login);
diff --git a/src/lib-sasl/mech-anonymous.c b/src/lib-sasl/mech-anonymous.c
new file mode 100644 (file)
index 0000000..1659085
--- /dev/null
@@ -0,0 +1,55 @@
+/* Copyright (c) 2025 Dovecot authors, see the included COPYING file */
+
+#include "lib.h"
+#include "dsasl-client-private.h"
+
+struct anonymous_dsasl_client {
+       struct dsasl_client client;
+       bool output_sent;
+};
+
+static int
+mech_anonymous_input(struct dsasl_client *_client,
+                   const unsigned char *input ATTR_UNUSED, size_t input_len,
+                   const char **error_r)
+{
+       struct anonymous_dsasl_client *client =
+               container_of(_client, struct anonymous_dsasl_client, client);
+
+       if (!client->output_sent) {
+               if (input_len > 0) {
+                       *error_r = "Server sent non-empty initial response";
+                       return -1;
+               }
+       } else if (input_len > 0) {
+               *error_r = "Server sent non-empty response";
+               return -1;
+       }
+       return 0;
+}
+
+static int
+mech_anonymous_output(struct dsasl_client *_client,
+                    const unsigned char **output_r, size_t *output_len_r,
+                    const char **error_r ATTR_UNUSED)
+{
+       struct anonymous_dsasl_client *client =
+               container_of(_client, struct anonymous_dsasl_client, client);
+
+       const char *authid = client->client.set.authid;
+       if (authid == NULL)
+               authid = "";
+       *output_r = (const unsigned char*)authid;
+       *output_len_r = strlen(authid);
+       client->output_sent = TRUE;
+       return 0;
+}
+
+const struct dsasl_client_mech dsasl_client_mech_anonymous = {
+       .name = "ANONYMOUS",
+       .struct_size = sizeof(struct anonymous_dsasl_client),
+       .flags = DSASL_MECH_SEC_NO_PASSWORD,
+
+       .input = mech_anonymous_input,
+       .output = mech_anonymous_output
+};