summaryrefslogtreecommitdiffstats
path: root/src/lib/hash-method.c
diff options
context:
space:
mode:
authorDaniel Baumann <daniel.baumann@progress-linux.org>2024-04-28 09:51:24 +0000
committerDaniel Baumann <daniel.baumann@progress-linux.org>2024-04-28 09:51:24 +0000
commitf7548d6d28c313cf80e6f3ef89aed16a19815df1 (patch)
treea3f6f2a3f247293bee59ecd28e8cd8ceb6ca064a /src/lib/hash-method.c
parentInitial commit. (diff)
downloaddovecot-f7548d6d28c313cf80e6f3ef89aed16a19815df1.tar.xz
dovecot-f7548d6d28c313cf80e6f3ef89aed16a19815df1.zip
Adding upstream version 1:2.3.19.1+dfsg1.upstream/1%2.3.19.1+dfsg1upstream
Signed-off-by: Daniel Baumann <daniel.baumann@progress-linux.org>
Diffstat (limited to 'src/lib/hash-method.c')
-rw-r--r--src/lib/hash-method.c98
1 files changed, 98 insertions, 0 deletions
diff --git a/src/lib/hash-method.c b/src/lib/hash-method.c
new file mode 100644
index 0000000..d7a6bed
--- /dev/null
+++ b/src/lib/hash-method.c
@@ -0,0 +1,98 @@
+/* Copyright (c) 2010-2018 Dovecot authors, see the included COPYING file */
+
+#include "lib.h"
+#include "md4.h"
+#include "md5.h"
+#include "sha1.h"
+#include "sha2.h"
+#include "sha3.h"
+#include "hash-method.h"
+
+const struct hash_method *hash_method_lookup(const char *name)
+{
+ unsigned int i;
+
+ for (i = 0; hash_methods[i] != NULL; i++) {
+ if (strcmp(hash_methods[i]->name, name) == 0)
+ return hash_methods[i];
+ }
+ return NULL;
+}
+
+static void hash_method_init_size(void *context)
+{
+ uint64_t *ctx = context;
+
+ *ctx = 0;
+}
+
+static void
+hash_method_loop_size(void *context, const void *data ATTR_UNUSED, size_t size)
+{
+ uint64_t *ctx = context;
+
+ *ctx += size;
+}
+
+static void hash_method_result_size(void *context, unsigned char *result_r)
+{
+ uint64_t *ctx = context;
+
+ result_r[0] = (*ctx & 0xff00000000000000ULL) >> 56;
+ result_r[1] = (*ctx & 0x00ff000000000000ULL) >> 48;
+ result_r[2] = (*ctx & 0x0000ff0000000000ULL) >> 40;
+ result_r[3] = (*ctx & 0x000000ff00000000ULL) >> 32;
+ result_r[4] = (*ctx & 0x00000000ff000000ULL) >> 24;
+ result_r[5] = (*ctx & 0x0000000000ff0000ULL) >> 16;
+ result_r[6] = (*ctx & 0x000000000000ff00ULL) >> 8;
+ result_r[7] = (*ctx & 0x00000000000000ffULL);
+}
+
+void hash_method_get_digest(const struct hash_method *meth,
+ const void *data, size_t data_len,
+ unsigned char *result_r)
+{
+ i_assert(meth != NULL);
+ i_assert(data_len == 0 || data != NULL);
+ unsigned char ctx[meth->context_size];
+
+ meth->init(ctx);
+ meth->loop(ctx, data == NULL ? "" : data, data_len);
+ meth->result(ctx, result_r);
+}
+
+buffer_t *t_hash_data(const struct hash_method *meth,
+ const void *data, size_t data_len)
+{
+ i_assert(meth != NULL);
+ buffer_t *result = t_buffer_create(meth->digest_size);
+ unsigned char *resptr = buffer_append_space_unsafe(result,
+ meth->digest_size);
+
+ hash_method_get_digest(meth, data, data_len, resptr);
+ return result;
+}
+
+static const struct hash_method hash_method_size = {
+ .name = "size",
+ .block_size = 1,
+ .context_size = sizeof(uint64_t),
+ .digest_size = sizeof(uint64_t),
+
+ .init = hash_method_init_size,
+ .loop = hash_method_loop_size,
+ .result = hash_method_result_size
+};
+
+const struct hash_method *hash_methods[] = {
+ &hash_method_md4,
+ &hash_method_md5,
+ &hash_method_sha1,
+ &hash_method_sha256,
+ &hash_method_sha384,
+ &hash_method_sha512,
+ &hash_method_sha3_256,
+ &hash_method_sha3_512,
+ &hash_method_size,
+ NULL
+};