]> git.ipfire.org Git - thirdparty/dovecot/core.git/commitdiff
lib-auth: password-scheme-scram - Split off auth_scram_generate_key_data() from scram...
authorStephan Bosch <stephan.bosch@open-xchange.com>
Sat, 7 Jan 2023 01:39:09 +0000 (02:39 +0100)
committeraki.tuomi <aki.tuomi@open-xchange.com>
Fri, 27 Jan 2023 09:34:54 +0000 (09:34 +0000)
Moved to auth-scram.

src/lib-auth/auth-scram.c
src/lib-auth/auth-scram.h
src/lib-auth/password-scheme-scram.c

index a1b5460e8dff68b86709ed8f8728aa8f8ec8151e..eeb78c3d2090d67ebb6fee131cc08e676ace8083 100644 (file)
@@ -2,7 +2,10 @@
 
 #include "lib.h"
 #include "safe-memset.h"
+#include "base64.h"
 #include "hmac.h"
+#include "randgen.h"
+#include "str.h"
 
 #include "auth-scram.h"
 
@@ -64,3 +67,49 @@ void auth_scram_hi(const struct hash_method *hmethod,
                        result[k] ^= U[k];
        }
 }
+
+void auth_scram_generate_key_data(const struct hash_method *hmethod,
+                                 const char *plaintext, unsigned int rounds,
+                                 unsigned int *iter_count_r,
+                                 const char **salt_r,
+                                 unsigned char stored_key_r[],
+                                 unsigned char server_key_r[])
+{
+       struct hmac_context ctx;
+       unsigned char salt[16];
+       unsigned char salted_password[hmethod->digest_size];
+       unsigned char client_key[hmethod->digest_size];
+
+       if (rounds == 0)
+               rounds = AUTH_SCRAM_DEFAULT_ITERATE_COUNT;
+       else {
+               rounds = I_MAX(I_MIN(AUTH_SCRAM_MAX_ITERATE_COUNT, rounds),
+                              AUTH_SCRAM_MIN_ITERATE_COUNT);
+       }
+       *iter_count_r = rounds;
+
+       random_fill(salt, sizeof(salt));
+       *salt_r = str_c(t_base64_encode(0, 0, salt, sizeof(salt)));
+
+       /* FIXME: credentials should be SASLprepped UTF8 data here */
+       auth_scram_hi(hmethod,
+                     (const unsigned char *)plaintext, strlen(plaintext),
+                     salt, sizeof(salt), rounds, salted_password);
+
+       /* Calculate ClientKey */
+       hmac_init(&ctx, salted_password, sizeof(salted_password), hmethod);
+       hmac_update(&ctx, "Client Key", 10);
+       hmac_final(&ctx, client_key);
+
+       /* Calculate StoredKey */
+       hash_method_get_digest(hmethod, client_key, sizeof(client_key),
+                              stored_key_r);
+
+       /* Calculate ServerKey */
+       hmac_init(&ctx, salted_password, sizeof(salted_password), hmethod);
+       hmac_update(&ctx, "Server Key", 10);
+       hmac_final(&ctx, server_key_r);
+
+       safe_memset(salted_password, 0, sizeof(salted_password));
+       safe_memset(client_key, 0, sizeof(client_key));
+}
index 91fff2b8dc7dd77f9f332a7295478e1919825736..0a6ba936d98cac81d2a846632d023e9b071e8e06 100644 (file)
@@ -1,6 +1,12 @@
 #ifndef AUTH_SCRAM_H
 #define AUTH_SCRAM_H
 
+/* SCRAM allowed iteration count range. RFC says it SHOULD be at least 4096 */
+#define AUTH_SCRAM_MIN_ITERATE_COUNT 4096
+#define AUTH_SCRAM_MAX_ITERATE_COUNT INT_MAX
+
+#define AUTH_SCRAM_DEFAULT_ITERATE_COUNT 4096
+
 struct auth_scram_key_data {
        pool_t pool;
        const struct hash_method *hmethod;
@@ -18,4 +24,10 @@ void auth_scram_hi(const struct hash_method *hmethod,
                   const unsigned char *salt, size_t salt_size, unsigned int i,
                   unsigned char *result);
 
+void auth_scram_generate_key_data(const struct hash_method *hmethod,
+                                 const char *plaintext, unsigned int rounds,
+                                 unsigned int *iter_count_r,
+                                 const char **salt_r,
+                                 unsigned char stored_key_r[],
+                                 unsigned char server_key_r[]);
 #endif
index e6cdc62e87fff6e11caa171297969fe4bc076078..c70ff2c607c031de40beb25bf9c79a026d389c1b 100644 (file)
@@ -12,7 +12,6 @@
 #include "base64.h"
 #include "buffer.h"
 #include "hmac.h"
-#include "randgen.h"
 #include "hash-method.h"
 #include "sha1.h"
 #include "sha2.h"
 #include "auth-scram.h"
 #include "password-scheme.h"
 
-/* SCRAM allowed iteration count range. RFC says it SHOULD be at least 4096 */
-#define SCRAM_MIN_ITERATE_COUNT 4096
-#define SCRAM_MAX_ITERATE_COUNT INT_MAX
-
-#define SCRAM_DEFAULT_ITERATE_COUNT 4096
-
 int scram_scheme_parse(const struct hash_method *hmethod, const char *name,
                       const unsigned char *credentials, size_t size,
                       unsigned int *iter_count_r, const char **salt_r,
@@ -44,8 +37,8 @@ int scram_scheme_parse(const struct hash_method *hmethod, const char *name,
                return -1;
        }
        if (str_to_uint(fields[0], iter_count_r) < 0 ||
-           *iter_count_r < SCRAM_MIN_ITERATE_COUNT ||
-           *iter_count_r > SCRAM_MAX_ITERATE_COUNT) {
+           *iter_count_r < AUTH_SCRAM_MIN_ITERATE_COUNT ||
+           *iter_count_r > AUTH_SCRAM_MAX_ITERATE_COUNT) {
                *error_r = t_strdup_printf(
                        "Invalid %s iteration count in passdb", name);
                return -1;
@@ -123,50 +116,23 @@ void scram_generate(const struct hash_method *hmethod, const char *plaintext,
                    size_t *size_r)
 {
        string_t *str;
-       struct hmac_context ctx;
-       unsigned char salt[16];
-       unsigned char salted_password[hmethod->digest_size];
-       unsigned char client_key[hmethod->digest_size];
+       unsigned int iter_count;
+       const char *salt;
        unsigned char server_key[hmethod->digest_size];
        unsigned char stored_key[hmethod->digest_size];
 
-       if (rounds == 0)
-               rounds = SCRAM_DEFAULT_ITERATE_COUNT;
-       else {
-               rounds = I_MAX(I_MIN(SCRAM_MAX_ITERATE_COUNT, rounds),
-                              SCRAM_MIN_ITERATE_COUNT);
-       }
-       random_fill(salt, sizeof(salt));
-
-       str = t_str_new(MAX_BASE64_ENCODED_SIZE(sizeof(salt)));
-       str_printfa(str, "%d,", rounds);
-       base64_encode(salt, sizeof(salt), str);
-
-       /* FIXME: credentials should be SASLprepped UTF8 data here */
-       auth_scram_hi(hmethod,
-                     (const unsigned char *)plaintext, strlen(plaintext),
-                     salt, sizeof(salt), rounds, salted_password);
+       auth_scram_generate_key_data(hmethod, plaintext, rounds,
+                                    &iter_count, &salt,
+                                    stored_key, server_key);
 
-       /* Calculate ClientKey */
-       hmac_init(&ctx, salted_password, sizeof(salted_password), hmethod);
-       hmac_update(&ctx, "Client Key", 10);
-       hmac_final(&ctx, client_key);
-
-       /* Calculate StoredKey */
-       hash_method_get_digest(hmethod, client_key, sizeof(client_key),
-                              stored_key);
+       str = t_str_new(strlen(salt) + 256);
+       str_printfa(str, "%d,", iter_count);
+       str_append(str, salt);
        str_append_c(str, ',');
        base64_encode(stored_key, sizeof(stored_key), str);
-
-       /* Calculate ServerKey */
-       hmac_init(&ctx, salted_password, sizeof(salted_password), hmethod);
-       hmac_update(&ctx, "Server Key", 10);
-       hmac_final(&ctx, server_key);
        str_append_c(str, ',');
        base64_encode(server_key, sizeof(server_key), str);
 
-       safe_memset(salted_password, 0, sizeof(salted_password));
-       safe_memset(client_key, 0, sizeof(client_key));
        safe_memset(server_key, 0, sizeof(server_key));
        safe_memset(stored_key, 0, sizeof(stored_key));