[PATCH v4 2/2] bcrypt: Implement BCRYPT_KDF_HASH.
Derek Lesho
dlesho at codeweavers.com
Fri Jan 24 09:30:58 CST 2020
Wine-Bug: https://bugs.winehq.org/show_bug.cgi?id=47699
Signed-off-by: Derek Lesho <dlesho at codeweavers.com>
---
dlls/bcrypt/bcrypt_main.c | 100 +++++++++++++++++++++++++++++++++++++
dlls/bcrypt/tests/bcrypt.c | 2 +-
2 files changed, 101 insertions(+), 1 deletion(-)
diff --git a/dlls/bcrypt/bcrypt_main.c b/dlls/bcrypt/bcrypt_main.c
index ed64cd1965..ed09ffafb3 100644
--- a/dlls/bcrypt/bcrypt_main.c
+++ b/dlls/bcrypt/bcrypt_main.c
@@ -1744,6 +1744,106 @@ NTSTATUS WINAPI BCryptDeriveKey(BCRYPT_SECRET_HANDLE hSecret, LPCWSTR deriv_func
TRACE( "%p, %s, %p, %p, %d, %p, %08x\n", secret, debugstr_w(deriv_func), parameter, derived, derived_size, result, flags );
+ if (flags)
+ {
+ FIXME("flags ignored: %08x\n", flags);
+ }
+
+ if (!(strcmpW(deriv_func, BCRYPT_KDF_HASH)))
+ {
+ unsigned int i;
+ BCryptBuffer *hash_algorithm = NULL;
+ BCryptBuffer *secret_prepend = NULL;
+ BCryptBuffer *secret_append = NULL;
+ enum alg_id hash_alg_id;
+ ULONG hash_length;
+ struct hash_impl hash;
+ NTSTATUS status;
+
+ if (parameter)
+ {
+ for (i = 0; i < parameter->cBuffers; i++)
+ {
+ BCryptBuffer *cur_buffer = ¶meter->pBuffers[i];
+ switch(cur_buffer->BufferType)
+ {
+ case KDF_HASH_ALGORITHM:
+ hash_algorithm = cur_buffer;
+ break;
+ case KDF_SECRET_PREPEND:
+ secret_prepend = cur_buffer;
+ break;
+ case KDF_SECRET_APPEND:
+ secret_append = cur_buffer;
+ break;
+ }
+ }
+ }
+
+ if (!(hash_algorithm))
+ hash_alg_id = ALG_ID_SHA1;
+ else
+ {
+ for (i = 0; i < ARRAY_SIZE( builtin_algorithms ); i++)
+ {
+ if (!strcmpW( hash_algorithm->pvBuffer, builtin_algorithms[i].name))
+ {
+ hash_alg_id = i;
+ break;
+ }
+ }
+ if (i == ARRAY_SIZE(builtin_algorithms))
+ {
+ return STATUS_NOT_SUPPORTED;
+ }
+ if (builtin_algorithms[hash_alg_id].class != BCRYPT_HASH_INTERFACE)
+ {
+ return STATUS_NOT_SUPPORTED;
+ }
+ }
+
+ hash_length = builtin_algorithms[hash_alg_id].hash_length;
+
+ if (!derived)
+ {
+ *result = hash_length;
+ return STATUS_SUCCESS;
+ }
+
+ if ((status = hash_init(&hash, hash_alg_id)))
+ {
+ return status;
+ }
+
+ if (secret_prepend)
+ {
+ hash_update(&hash, hash_alg_id, secret_prepend->pvBuffer, secret_prepend->cbBuffer);
+ }
+
+ hash_update(&hash, hash_alg_id, secret->data, secret->len);
+
+ if (secret_append)
+ {
+ hash_update(&hash, hash_alg_id, secret_append->pvBuffer, secret_append->cbBuffer);
+ }
+
+ if (derived_size >= hash_length)
+ {
+ hash_finish(&hash, hash_alg_id, derived, derived_size);
+ *result = hash_length;
+ }
+ else
+ {
+ UCHAR *output = heap_alloc(hash_length);
+ hash_finish(&hash, hash_alg_id, output, hash_length);
+ memcpy(derived, output, derived_size);
+ heap_free(output);
+ *result = derived_size;
+ }
+
+ return STATUS_SUCCESS;
+ }
+ else
if (!(strcmpW(deriv_func, BCRYPT_KDF_RAW_SECRET)))
{
ULONG n;
diff --git a/dlls/bcrypt/tests/bcrypt.c b/dlls/bcrypt/tests/bcrypt.c
index 985a6f379b..be5561d151 100644
--- a/dlls/bcrypt/tests/bcrypt.c
+++ b/dlls/bcrypt/tests/bcrypt.c
@@ -2087,7 +2087,7 @@ static void test_ECDH(void)
raw_secret_end:
status = pBCryptDeriveKey(secret, BCRYPT_KDF_HASH, &hash_params, NULL, 0, &size, 0);
- todo_wine ok (status == STATUS_SUCCESS, "got %08x\n", status);
+ ok (status == STATUS_SUCCESS, "got %08x\n", status);
if (status != STATUS_SUCCESS)
{
--
2.25.0
More information about the wine-devel
mailing list