]> git.ipfire.org Git - thirdparty/dovecot/core.git/commitdiff
auth: sasl-server-mech - Add facilities for dynamic mechanism passdb need level
authorStephan Bosch <stephan.bosch@open-xchange.com>
Sat, 4 Nov 2023 18:26:37 +0000 (19:26 +0100)
committertimo.sirainen <timo.sirainen@open-xchange.com>
Thu, 9 Oct 2025 08:41:22 +0000 (08:41 +0000)
16 files changed:
src/auth/auth-sasl-mech-apop.c
src/auth/auth-sasl-mech-dovecot-token.c
src/auth/sasl-server-mech-anonymous.c
src/auth/sasl-server-mech-cram-md5.c
src/auth/sasl-server-mech-digest-md5.c
src/auth/sasl-server-mech-external.c
src/auth/sasl-server-mech-gssapi.c
src/auth/sasl-server-mech-login.c
src/auth/sasl-server-mech-oauth2.c
src/auth/sasl-server-mech-otp.c
src/auth/sasl-server-mech-plain.c
src/auth/sasl-server-mech-scram.c
src/auth/sasl-server-mech-winbind.c
src/auth/sasl-server-mech.c
src/auth/sasl-server-private.h
src/auth/sasl-server-protected.h

index 72e9fcc81253241762737a8d0b38b0d54a3e180b..62de4a0a9aeccaf7626e5d64f30bcf31c7a21d5f 100644 (file)
@@ -175,5 +175,5 @@ static const struct sasl_server_mech_def mech_apop = {
 
 void auth_sasl_mech_register_apop(struct sasl_server_instance *sinst)
 {
-       sasl_server_mech_register(sinst, &mech_apop);
+       sasl_server_mech_register(sinst, &mech_apop, NULL);
 }
index f3ecd30c92784dbca2c7097d5bf6b1099070a6e6..1445b0c41f226df49a6b9c5df5c56d99f79b88b3 100644 (file)
@@ -91,5 +91,6 @@ static const struct sasl_server_mech_def mech_dovecot_token = {
 const struct sasl_server_mech *
 auth_sasl_mech_register_dovecot_token(struct sasl_server_instance *sinst)
 {
-       return sasl_server_mech_register_hidden(sinst, &mech_dovecot_token);
+       return sasl_server_mech_register_hidden(sinst, &mech_dovecot_token,
+                                               NULL);
 }
index 24a97ec24e5469560e57f0cda47247b6daae8320..02f9285b87a835c408e9e1af7f75f093f31e0c99 100644 (file)
@@ -34,5 +34,5 @@ static const struct sasl_server_mech_def mech_anonymous = {
 
 void sasl_server_mech_register_anonymous(struct sasl_server_instance *sinst)
 {
-       sasl_server_mech_register(sinst, &mech_anonymous);
+       sasl_server_mech_register(sinst, &mech_anonymous, NULL);
 }
index d271b3524d7ae539d99d6b79336d73d4173063e6..88103dc2fa54cfa669da269e1e0fa9095c8cb277 100644 (file)
@@ -192,5 +192,5 @@ static const struct sasl_server_mech_def mech_cram_md5 = {
 
 void sasl_server_mech_register_cram_md5(struct sasl_server_instance *sinst)
 {
-       sasl_server_mech_register(sinst, &mech_cram_md5);
+       sasl_server_mech_register(sinst, &mech_cram_md5, NULL);
 }
index 305e3d48dc27241a48df7e411f7e629c3a20d055..f486775e37c053ea2a43e953c1884c75307eb7d1 100644 (file)
@@ -624,7 +624,7 @@ static const struct sasl_server_mech_def mech_digest_md5 = {
 
 void sasl_server_mech_register_digest_md5(struct sasl_server_instance *sinst)
 {
-       sasl_server_mech_register(sinst, &mech_digest_md5);
+       sasl_server_mech_register(sinst, &mech_digest_md5, NULL);
 }
 
 void sasl_server_mech_digest_md5_test_set_nonce(
index b4be06a2b4816d2005f4c11a5344bba5d56e40c0..3cc2850038886f643e4c3825dd7cd4d1f6b9045e 100644 (file)
@@ -44,5 +44,5 @@ static const struct sasl_server_mech_def mech_external = {
 
 void sasl_server_mech_register_external(struct sasl_server_instance *sinst)
 {
-       sasl_server_mech_register(sinst, &mech_external);
+       sasl_server_mech_register(sinst, &mech_external, NULL);
 }
index 1eacc42f1b5e170189fbee6a4c2ae427fa80d89a..c0cecd20a2f7beb97e3418f68261489fbbb39359 100644 (file)
@@ -720,7 +720,7 @@ mech_gssapi_register(struct sasl_server_instance *sinst,
        struct sasl_server_mech *mech;
        struct gssapi_auth_mech *gss_mech;
 
-       mech = sasl_server_mech_register(sinst, mech_def);
+       mech = sasl_server_mech_register(sinst, mech_def, NULL);
 
        gss_mech = container_of(mech, struct gssapi_auth_mech, mech);
        gss_mech->hostname = p_strdup(mech->pool, set->hostname);
index 3dcd40d14e4652e5e7adc6063f90621bed5ada0a..7d83764855cb7da723c0e0d27efc1ee41cad0cdd 100644 (file)
@@ -67,5 +67,5 @@ static const struct sasl_server_mech_def mech_login = {
 
 void sasl_server_mech_register_login(struct sasl_server_instance *sinst)
 {
-       sasl_server_mech_register(sinst, &mech_login);
+       sasl_server_mech_register(sinst, &mech_login, NULL);
 }
index 78b42d473846817b280f6cf1e829e6ca6b6ba361..8632ce3681952dedf5a09bc2ec3526175a59b6e9 100644 (file)
@@ -349,10 +349,10 @@ static const struct sasl_server_mech_def mech_xoauth2 = {
 
 void sasl_server_mech_register_oauthbearer(struct sasl_server_instance *sinst)
 {
-       sasl_server_mech_register(sinst, &mech_oauthbearer);
+       sasl_server_mech_register(sinst, &mech_oauthbearer, NULL);
 }
 
 void sasl_server_mech_register_xoauth2(struct sasl_server_instance *sinst)
 {
-       sasl_server_mech_register(sinst, &mech_xoauth2);
+       sasl_server_mech_register(sinst, &mech_xoauth2, NULL);
 }
index 20c0b4bbaf8f2ef118b7f0687ae12f11adaa17d8..b6d9686913ab669fab687ecbb59ead9e6793270f 100644 (file)
@@ -346,5 +346,5 @@ static const struct sasl_server_mech_def mech_otp = {
 
 void sasl_server_mech_register_otp(struct sasl_server_instance *sinst)
 {
-       sasl_server_mech_register(sinst, &mech_otp);
+       sasl_server_mech_register(sinst, &mech_otp, NULL);
 }
index b928b551e5a14b999476f17f1c5c80156db67fc9..dee74bb16bc8cd24b5b9d714a5544b6eb3f677ea 100644 (file)
@@ -78,5 +78,5 @@ static const struct sasl_server_mech_def mech_plain = {
 
 void sasl_server_mech_register_plain(struct sasl_server_instance *sinst)
 {
-       sasl_server_mech_register(sinst, &mech_plain);
+       sasl_server_mech_register(sinst, &mech_plain, NULL);
 }
index 918d362a25fd9ac44e648981fb126c1794223863..327bfd327426e4a115b4258447f3ddf083af6097 100644 (file)
@@ -298,7 +298,7 @@ void sasl_server_mech_register_scram(
 
        i_assert(mech_def->funcs == &sasl_server_mech_scram_funcs);
 
-       mech = sasl_server_mech_register(sinst, mech_def);
+       mech = sasl_server_mech_register(sinst, mech_def, NULL);
 
        scram_mech = container_of(mech, struct scram_auth_mech, mech);
        scram_mech->hash_method = hash_method;
index 01008cab21e2331f39ea803ccdc985c84cf80c24..99d7562e07a542a8a426e3a482570cd60f7af364 100644 (file)
@@ -404,7 +404,7 @@ sasl_server_mech_register_winbind(
 
        i_assert(set->helper_path != NULL);
 
-       mech = sasl_server_mech_register(sinst, mech_def);
+       mech = sasl_server_mech_register(sinst, mech_def, NULL);
 
        wb_mech = container_of(mech, struct winbind_auth_mech, mech);
        wb_mech->helper_path = p_strdup(mech->pool, set->helper_path);
index 90a6decd01ff9efab3edb6c8c184ee011d2594b5..8aab1975de83265a9a6a0c800eb1b1d3edd81680 100644 (file)
@@ -23,7 +23,7 @@ sasl_server_mech_get_security_flags(const struct sasl_server_mech *mech)
 enum sasl_mech_passdb_need
 sasl_server_mech_get_passdb_need(const struct sasl_server_mech *mech)
 {
-       return mech->def->passdb_need;
+       return mech->reg->set.passdb_need;
 }
 
 /*
@@ -119,9 +119,28 @@ sasl_server_mech_find_def_by_name(struct sasl_server *server,
        return mech_dreg;
 }
 
+static void
+sasl_server_mech_def_merge_settings(
+       const struct sasl_server_mech_def *def,
+       struct sasl_server_mech_settings *set,
+       const struct sasl_server_mech_settings *new_set)
+{
+       if (new_set == NULL) {
+               if (def->passdb_need > set->passdb_need)
+                       set->passdb_need = def->passdb_need;
+               return;
+       }
+       if (new_set->passdb_need > set->passdb_need &&
+           new_set->passdb_need > def->passdb_need)
+               set->passdb_need = new_set->passdb_need;
+       else
+               set->passdb_need = def->passdb_need;
+}
+
 static struct sasl_server_mech_def_reg *
 sasl_server_mech_register_def(struct sasl_server *server,
-                             const struct sasl_server_mech_def *def)
+                             const struct sasl_server_mech_def *def,
+                             const struct sasl_server_mech_settings *set)
 {
        struct sasl_server_mech_def_reg *mech_dreg;
 
@@ -132,6 +151,8 @@ sasl_server_mech_register_def(struct sasl_server *server,
        if (mech_dreg != NULL) {
                i_assert(mech_dreg->refcount > 0);
                mech_dreg->refcount++;
+
+               sasl_server_mech_def_merge_settings(def, &mech_dreg->set, set);
                return mech_dreg;
        }
 
@@ -140,6 +161,7 @@ sasl_server_mech_register_def(struct sasl_server *server,
        mech_dreg = p_new(server->pool, struct sasl_server_mech_def_reg, 1);
        mech_dreg->def = def;
        mech_dreg->refcount = 1;
+       sasl_server_mech_def_merge_settings(def, &mech_dreg->set, set);
 
        DLLIST2_APPEND(&server->mechs_head, &server->mechs_tail, mech_dreg);
        return mech_dreg;
@@ -189,7 +211,8 @@ static void sasl_server_mech_free(struct sasl_server_mech *mech)
 
 static struct sasl_server_mech *
 sasl_server_mech_register_common(struct sasl_server_instance *sinst,
-                                const struct sasl_server_mech_def *def)
+                                const struct sasl_server_mech_def *def,
+                                const struct sasl_server_mech_settings *set)
 {
        struct sasl_server_mech_def_reg *mech_dreg;
        struct sasl_server_mech_reg *mech_reg;
@@ -197,10 +220,11 @@ sasl_server_mech_register_common(struct sasl_server_instance *sinst,
 
        i_assert(sasl_server_mech_reg_find(sinst, def->name) == NULL);
 
-       mech_dreg = sasl_server_mech_register_def(sinst->server, def);
+       mech_dreg = sasl_server_mech_register_def(sinst->server, def, set);
 
        mech_reg = p_new(sinst->pool, struct sasl_server_mech_reg, 1);
        mech_reg->def_reg = mech_dreg;
+       sasl_server_mech_def_merge_settings(def, &mech_reg->set, set);
 
        DLLIST_PREPEND_FULL(&mech_dreg->insts, mech_reg, def_prev, def_next);
 
@@ -214,11 +238,12 @@ sasl_server_mech_register_common(struct sasl_server_instance *sinst,
 
 struct sasl_server_mech *
 sasl_server_mech_register(struct sasl_server_instance *sinst,
-                         const struct sasl_server_mech_def *def)
+                         const struct sasl_server_mech_def *def,
+                         const struct sasl_server_mech_settings *set)
 {
        struct sasl_server_mech *mech;
 
-       mech = sasl_server_mech_register_common(sinst, def);
+       mech = sasl_server_mech_register_common(sinst, def, set);
        DLLIST2_APPEND(&sinst->mechs_head, &sinst->mechs_tail, mech->reg);
 
        return mech;
@@ -226,11 +251,12 @@ sasl_server_mech_register(struct sasl_server_instance *sinst,
 
 struct sasl_server_mech *
 sasl_server_mech_register_hidden(struct sasl_server_instance *sinst,
-                                const struct sasl_server_mech_def *def)
+                                const struct sasl_server_mech_def *def,
+                                const struct sasl_server_mech_settings *set)
 {
        struct sasl_server_mech *mech;
 
-       mech = sasl_server_mech_register_common(sinst, def);
+       mech = sasl_server_mech_register_common(sinst, def, set);
        DLLIST_PREPEND(&sinst->mechs_hidden, mech->reg);
 
        return mech;
@@ -381,6 +407,7 @@ bool sasl_server_mech_iter_next(struct sasl_server_mech_iter *iter)
        struct sasl_server_mech_iter_prv *iterp =
                container_of(iter, struct sasl_server_mech_iter_prv, iter);
        const struct sasl_server_mech_def *def;
+       const struct sasl_server_mech_settings *set;
 
        if (!iterp->instance) {
                if (iterp->def_reg == NULL) {
@@ -388,6 +415,7 @@ bool sasl_server_mech_iter_next(struct sasl_server_mech_iter *iter)
                        return FALSE;
                }
                def = iterp->def_reg->def;
+               set = &iterp->def_reg->set;
                iterp->def_reg = iterp->def_reg->next;
        } else {
                if (iterp->reg == NULL) {
@@ -395,12 +423,13 @@ bool sasl_server_mech_iter_next(struct sasl_server_mech_iter *iter)
                        return FALSE;
                }
                def = iterp->reg->mech->def;
+               set = &iterp->reg->set;
                iterp->reg = iterp->reg->next;
        }
 
        iterp->iter.name = def->name;
        iterp->iter.flags = def->flags;
-       iterp->iter.passdb_need = def->passdb_need;
+       iterp->iter.passdb_need = set->passdb_need;
 
        return TRUE;
 }
index 953ce3c9d90909b60d5315f69637102c7c24c77b..9dc2457bbfdccb1e1bc4df7ea82b3f1739c793a2 100644 (file)
@@ -33,6 +33,8 @@ struct sasl_server_mech_reg {
        struct sasl_server_mech *mech;
        struct sasl_server_mech_reg *prev, *next;
 
+       struct sasl_server_mech_settings set;
+
        struct sasl_server_mech_def_reg *def_reg;
        struct sasl_server_mech_reg *def_prev, *def_next;
 };
@@ -42,6 +44,7 @@ struct sasl_server_mech_def_reg {
        unsigned int refcount;
        struct sasl_server_mech_def_reg *prev, *next;
 
+       struct sasl_server_mech_settings set;
        struct sasl_server_mech_data *data;
 
        struct sasl_server_mech_reg *insts;
index 393e179ecd04274618c40d13e4ef90c1333d5a29..25d2b3b04f58b20a06bfcd71f12552f842cb119b 100644 (file)
@@ -41,6 +41,10 @@ struct sasl_server_mech_def {
        const struct sasl_server_mech_funcs *funcs;
 };
 
+struct sasl_server_mech_settings {
+       enum sasl_mech_passdb_need passdb_need;
+};
+
 struct sasl_server_mech_data {
        struct sasl_server *server;
        pool_t pool;
@@ -80,10 +84,12 @@ struct sasl_server_mech_request {
 
 struct sasl_server_mech * ATTR_NOWARN_UNUSED_RESULT
 sasl_server_mech_register(struct sasl_server_instance *sinst,
-                         const struct sasl_server_mech_def *def);
+                         const struct sasl_server_mech_def *def,
+                         const struct sasl_server_mech_settings *set);
 struct sasl_server_mech * ATTR_NOWARN_UNUSED_RESULT
 sasl_server_mech_register_hidden(struct sasl_server_instance *sinst,
-                                const struct sasl_server_mech_def *def);
+                                const struct sasl_server_mech_def *def,
+                                const struct sasl_server_mech_settings *set);
 void sasl_server_mech_unregister(struct sasl_server_instance *sinst,
                                 const struct sasl_server_mech_def *def);