mirror of
https://gitlab.winehq.org/wine/wine-staging.git
synced 2024-11-21 16:46:54 -08:00
bcrypt-Improvements: Update patchset and implement support for AES GCM.
This commit is contained in:
parent
84b08ebde9
commit
8db21bfce6
@ -469,7 +469,7 @@ index 6023c94..937bdf7 100644
|
||||
+ struct key *key = handle;
|
||||
+ NTSTATUS status;
|
||||
+
|
||||
+ FIXME( "%p, %p, %u, %p, %p, %u, %p, %u, %p, %08x\n", handle, input, input_len,
|
||||
+ TRACE( "%p, %p, %u, %p, %p, %u, %p, %u, %p, %08x\n", handle, input, input_len,
|
||||
+ padding, iv, iv_len, output, output_len, ret_len, flags );
|
||||
+
|
||||
+ if (!key || key->hdr.magic != MAGIC_KEY) return STATUS_INVALID_HANDLE;
|
||||
|
@ -1,16 +1,16 @@
|
||||
From 8554c6eea279baa21e10d3b742e1c62a732bbe69 Mon Sep 17 00:00:00 2001
|
||||
From 026aff5aa7c66fdc8e8c724dc73217585e8edf91 Mon Sep 17 00:00:00 2001
|
||||
From: =?UTF-8?q?Michael=20M=C3=BCller?= <michael@fds-team.de>
|
||||
Date: Wed, 21 Dec 2016 04:09:03 +0100
|
||||
Subject: bcrypt: Fix handling of padding when input size equals block size for
|
||||
AES.
|
||||
|
||||
---
|
||||
dlls/bcrypt/bcrypt_main.c | 13 +++++++------
|
||||
dlls/bcrypt/bcrypt_main.c | 14 ++++++++------
|
||||
dlls/bcrypt/tests/bcrypt.c | 33 ++++++++++++++++++++++++++++++++-
|
||||
2 files changed, 39 insertions(+), 7 deletions(-)
|
||||
2 files changed, 40 insertions(+), 7 deletions(-)
|
||||
|
||||
diff --git a/dlls/bcrypt/bcrypt_main.c b/dlls/bcrypt/bcrypt_main.c
|
||||
index 944a9ea..f97638f 100644
|
||||
index 944a9ea..f53ea1c 100644
|
||||
--- a/dlls/bcrypt/bcrypt_main.c
|
||||
+++ b/dlls/bcrypt/bcrypt_main.c
|
||||
@@ -997,11 +997,12 @@ NTSTATUS WINAPI BCryptEncrypt( BCRYPT_KEY_HANDLE handle, UCHAR *input, ULONG inp
|
||||
@ -31,12 +31,13 @@ index 944a9ea..f97638f 100644
|
||||
if (!output) return STATUS_SUCCESS;
|
||||
if (output_len < *ret_len) return STATUS_BUFFER_TOO_SMALL;
|
||||
|
||||
@@ -1014,7 +1015,7 @@ NTSTATUS WINAPI BCryptEncrypt( BCRYPT_KEY_HANDLE handle, UCHAR *input, ULONG inp
|
||||
@@ -1014,7 +1015,8 @@ NTSTATUS WINAPI BCryptEncrypt( BCRYPT_KEY_HANDLE handle, UCHAR *input, ULONG inp
|
||||
src += key->block_size;
|
||||
dst += key->block_size;
|
||||
}
|
||||
- if (bytes_left)
|
||||
+ if (bytes_left || (flags & BCRYPT_BLOCK_PADDING))
|
||||
+
|
||||
+ if (flags & BCRYPT_BLOCK_PADDING)
|
||||
{
|
||||
if (!(buf = HeapAlloc( GetProcessHeap(), 0, key->block_size ))) return STATUS_NO_MEMORY;
|
||||
memcpy( buf, src, bytes_left );
|
||||
|
@ -20,7 +20,7 @@ index f97638f..653301b 100644
|
||||
+ UCHAR *buf, *src, *dst;
|
||||
NTSTATUS status;
|
||||
|
||||
FIXME( "%p, %p, %u, %p, %p, %u, %p, %u, %p, %08x\n", handle, input, input_len,
|
||||
TRACE( "%p, %p, %u, %p, %p, %u, %p, %u, %p, %08x\n", handle, input, input_len,
|
||||
@@ -1052,11 +1054,44 @@ NTSTATUS WINAPI BCryptDecrypt( BCRYPT_KEY_HANDLE handle, UCHAR *input, ULONG inp
|
||||
if ((status = key_set_params( key, iv, iv_len ))) return status;
|
||||
|
||||
|
@ -0,0 +1,39 @@
|
||||
From f7dc69131cc016917b31c5deedf97da31b11c597 Mon Sep 17 00:00:00 2001
|
||||
From: =?UTF-8?q?Michael=20M=C3=BCller?= <michael@fds-team.de>
|
||||
Date: Mon, 26 Dec 2016 02:43:39 +0100
|
||||
Subject: bcrypt: Fix use-after-free in key_init.
|
||||
|
||||
---
|
||||
dlls/bcrypt/bcrypt_main.c | 6 +++++-
|
||||
1 file changed, 5 insertions(+), 1 deletion(-)
|
||||
|
||||
diff --git a/dlls/bcrypt/bcrypt_main.c b/dlls/bcrypt/bcrypt_main.c
|
||||
index 09bf6c30..a9006a4 100644
|
||||
--- a/dlls/bcrypt/bcrypt_main.c
|
||||
+++ b/dlls/bcrypt/bcrypt_main.c
|
||||
@@ -791,6 +791,8 @@ static ULONG get_block_size( enum alg_id alg )
|
||||
|
||||
static NTSTATUS key_init( struct key *key, enum alg_id id, UCHAR *secret, ULONG secret_len )
|
||||
{
|
||||
+ UCHAR *buffer;
|
||||
+
|
||||
if (!libgnutls_handle) return STATUS_INTERNAL_ERROR;
|
||||
|
||||
switch (id)
|
||||
@@ -804,10 +806,12 @@ static NTSTATUS key_init( struct key *key, enum alg_id id, UCHAR *secret, ULONG
|
||||
}
|
||||
|
||||
if (!(key->block_size = get_block_size( id ))) return STATUS_INVALID_PARAMETER;
|
||||
+ if (!(buffer = HeapAlloc( GetProcessHeap(), 0, secret_len ))) return STATUS_NO_MEMORY;
|
||||
+ memcpy( buffer, secret, secret_len );
|
||||
|
||||
key->alg_id = id;
|
||||
key->handle = 0; /* initialized on first use */
|
||||
- key->secret = secret;
|
||||
+ key->secret = buffer;
|
||||
key->secret_len = secret_len;
|
||||
|
||||
return STATUS_SUCCESS;
|
||||
--
|
||||
2.9.0
|
||||
|
@ -0,0 +1,83 @@
|
||||
From 873d431347aa25effc70e47566e562c122a5edc8 Mon Sep 17 00:00:00 2001
|
||||
From: Sebastian Lackner <sebastian@fds-team.de>
|
||||
Date: Mon, 26 Dec 2016 04:23:31 +0100
|
||||
Subject: bcrypt: Handle NULL pointers in BCryptDuplicateHash and add tests.
|
||||
|
||||
---
|
||||
dlls/bcrypt/bcrypt_main.c | 1 +
|
||||
dlls/bcrypt/tests/bcrypt.c | 26 +++++++++++++++++++++++++-
|
||||
2 files changed, 26 insertions(+), 1 deletion(-)
|
||||
|
||||
diff --git a/dlls/bcrypt/bcrypt_main.c b/dlls/bcrypt/bcrypt_main.c
|
||||
index a9006a4..d1516cc 100644
|
||||
--- a/dlls/bcrypt/bcrypt_main.c
|
||||
+++ b/dlls/bcrypt/bcrypt_main.c
|
||||
@@ -681,6 +681,7 @@ NTSTATUS WINAPI BCryptDuplicateHash( BCRYPT_HASH_HANDLE handle, BCRYPT_HASH_HAND
|
||||
TRACE( "%p, %p, %p, %u, %u\n", handle, handle_copy, object, object_count, flags );
|
||||
|
||||
if (!hash_orig || hash_orig->hdr.magic != MAGIC_HASH) return STATUS_INVALID_HANDLE;
|
||||
+ if (!handle_copy) return STATUS_INVALID_PARAMETER;
|
||||
if (!(hash_copy = HeapAlloc( GetProcessHeap(), 0, sizeof(*hash_copy) )))
|
||||
return STATUS_NO_MEMORY;
|
||||
|
||||
diff --git a/dlls/bcrypt/tests/bcrypt.c b/dlls/bcrypt/tests/bcrypt.c
|
||||
index 997b298..bfe3a7e 100644
|
||||
--- a/dlls/bcrypt/tests/bcrypt.c
|
||||
+++ b/dlls/bcrypt/tests/bcrypt.c
|
||||
@@ -33,6 +33,7 @@ static NTSTATUS (WINAPI *pBCryptCreateHash)(BCRYPT_ALG_HANDLE, BCRYPT_HASH_HANDL
|
||||
ULONG, ULONG);
|
||||
static NTSTATUS (WINAPI *pBCryptHash)(BCRYPT_ALG_HANDLE, UCHAR *, ULONG, UCHAR *, ULONG, UCHAR *, ULONG);
|
||||
static NTSTATUS (WINAPI *pBCryptHashData)(BCRYPT_HASH_HANDLE, PUCHAR, ULONG, ULONG);
|
||||
+static NTSTATUS (WINAPI *pBCryptDuplicateHash)(BCRYPT_HASH_HANDLE, BCRYPT_HASH_HANDLE *, UCHAR *, ULONG, ULONG);
|
||||
static NTSTATUS (WINAPI *pBCryptFinishHash)(BCRYPT_HASH_HANDLE, PUCHAR, ULONG, ULONG);
|
||||
static NTSTATUS (WINAPI *pBCryptDestroyHash)(BCRYPT_HASH_HANDLE);
|
||||
static NTSTATUS (WINAPI *pBCryptGenRandom)(BCRYPT_ALG_HANDLE, PUCHAR, ULONG, ULONG);
|
||||
@@ -173,7 +174,7 @@ static void test_sha1(void)
|
||||
static const char expected[] = "961fa64958818f767707072755d7018dcd278e94";
|
||||
static const char expected_hmac[] = "2472cf65d0e090618d769d3e46f0d9446cf212da";
|
||||
BCRYPT_ALG_HANDLE alg;
|
||||
- BCRYPT_HASH_HANDLE hash;
|
||||
+ BCRYPT_HASH_HANDLE hash, hash2;
|
||||
UCHAR buf[512], buf_hmac[1024], sha1[20], sha1_hmac[20];
|
||||
ULONG size, len;
|
||||
char str[41];
|
||||
@@ -260,6 +261,28 @@ static void test_sha1(void)
|
||||
test_hash_length(hash, 20);
|
||||
test_alg_name(hash, "SHA1");
|
||||
|
||||
+ ret = pBCryptDuplicateHash(NULL, &hash2, NULL, 0, 0);
|
||||
+ ok(ret == STATUS_INVALID_HANDLE, "got %08x\n", ret);
|
||||
+
|
||||
+ ret = pBCryptDuplicateHash(hash, NULL, NULL, 0, 0);
|
||||
+ ok(ret == STATUS_INVALID_PARAMETER, "got %08x\n", ret);
|
||||
+
|
||||
+ hash2 = (void *)0xdeadbeef;
|
||||
+ ret = pBCryptDuplicateHash(hash, &hash2, NULL, 0, 0);
|
||||
+ ok(ret == STATUS_SUCCESS || broken(ret == STATUS_INVALID_PARAMETER) /* < Win 7 */, "got %08x\n", ret);
|
||||
+
|
||||
+ if (ret == STATUS_SUCCESS)
|
||||
+ {
|
||||
+ memset(sha1_hmac, 0, sizeof(sha1_hmac));
|
||||
+ ret = pBCryptFinishHash(hash2, sha1_hmac, sizeof(sha1_hmac), 0);
|
||||
+ ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
+ format_hash( sha1_hmac, sizeof(sha1_hmac), str );
|
||||
+ ok(!strcmp(str, expected_hmac), "got %s\n", str);
|
||||
+
|
||||
+ ret = pBCryptDestroyHash(hash2);
|
||||
+ ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
+ }
|
||||
+
|
||||
memset(sha1_hmac, 0, sizeof(sha1_hmac));
|
||||
ret = pBCryptFinishHash(hash, sha1_hmac, sizeof(sha1_hmac), 0);
|
||||
ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
@@ -1179,6 +1202,7 @@ START_TEST(bcrypt)
|
||||
pBCryptCreateHash = (void *)GetProcAddress(module, "BCryptCreateHash");
|
||||
pBCryptHash = (void *)GetProcAddress(module, "BCryptHash");
|
||||
pBCryptHashData = (void *)GetProcAddress(module, "BCryptHashData");
|
||||
+ pBCryptDuplicateHash = (void *)GetProcAddress(module, "BCryptDuplicateHash");
|
||||
pBCryptFinishHash = (void *)GetProcAddress(module, "BCryptFinishHash");
|
||||
pBCryptDestroyHash = (void *)GetProcAddress(module, "BCryptDestroyHash");
|
||||
pBCryptGenRandom = (void *)GetProcAddress(module, "BCryptGenRandom");
|
||||
--
|
||||
2.9.0
|
||||
|
@ -0,0 +1,29 @@
|
||||
From 83b15bed14a0999bacd2a5959297bff842a125e0 Mon Sep 17 00:00:00 2001
|
||||
From: Sebastian Lackner <sebastian@fds-team.de>
|
||||
Date: Mon, 26 Dec 2016 04:38:15 +0100
|
||||
Subject: bcrypt/tests: Add test for bugs in BCryptGetProperty.
|
||||
|
||||
---
|
||||
dlls/bcrypt/tests/bcrypt.c | 6 ++++++
|
||||
1 file changed, 6 insertions(+)
|
||||
|
||||
diff --git a/dlls/bcrypt/tests/bcrypt.c b/dlls/bcrypt/tests/bcrypt.c
|
||||
index bfe3a7e..23e150e 100644
|
||||
--- a/dlls/bcrypt/tests/bcrypt.c
|
||||
+++ b/dlls/bcrypt/tests/bcrypt.c
|
||||
@@ -841,6 +841,12 @@ static void test_aes(void)
|
||||
ok(size == 64, "got %u\n", size);
|
||||
|
||||
size = 0;
|
||||
+ ret = pBCryptGetProperty(alg, BCRYPT_CHAINING_MODE, mode, sizeof(mode) - 1, &size, 0);
|
||||
+ todo_wine ok(ret == STATUS_BUFFER_TOO_SMALL, "got %08x\n", ret);
|
||||
+ ok(size == 64, "got %u\n", size);
|
||||
+
|
||||
+ size = 0;
|
||||
+ memset(mode, 0, sizeof(mode));
|
||||
ret = pBCryptGetProperty(alg, BCRYPT_CHAINING_MODE, mode, sizeof(mode), &size, 0);
|
||||
ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
ok(!lstrcmpW((const WCHAR *)mode, BCRYPT_CHAIN_MODE_CBC), "got %s\n", mode);
|
||||
--
|
||||
2.9.0
|
||||
|
@ -0,0 +1,282 @@
|
||||
From 9e70e218c8a5c497ece71e17034ccae2e0baa218 Mon Sep 17 00:00:00 2001
|
||||
From: =?UTF-8?q?Michael=20M=C3=BCller?= <michael@fds-team.de>
|
||||
Date: Mon, 26 Dec 2016 05:37:02 +0100
|
||||
Subject: bcrypt/tests: Add tests for AES GCM mode.
|
||||
|
||||
---
|
||||
dlls/bcrypt/tests/bcrypt.c | 155 ++++++++++++++++++++++++++++++++++++++++++++-
|
||||
include/bcrypt.h | 29 +++++++++
|
||||
include/ntstatus.h | 2 +
|
||||
3 files changed, 185 insertions(+), 1 deletion(-)
|
||||
|
||||
diff --git a/dlls/bcrypt/tests/bcrypt.c b/dlls/bcrypt/tests/bcrypt.c
|
||||
index 23e150e..699a995 100644
|
||||
--- a/dlls/bcrypt/tests/bcrypt.c
|
||||
+++ b/dlls/bcrypt/tests/bcrypt.c
|
||||
@@ -941,6 +941,8 @@ static void test_BCryptGenerateSymmetricKey(void)
|
||||
|
||||
static void test_BCryptEncrypt(void)
|
||||
{
|
||||
+ static UCHAR nonce[] =
|
||||
+ {0x10, 0x20, 0x30, 0x40, 0x50, 0x60, 0x10, 0x20, 0x30, 0x40, 0x50, 0x60};
|
||||
static UCHAR secret[] =
|
||||
{0x00,0x01,0x02,0x03,0x04,0x05,0x06,0x07,0x08,0x09,0x0a,0x0b,0x0c,0x0d,0x0e,0x0f};
|
||||
static UCHAR iv[] =
|
||||
@@ -959,15 +961,28 @@ static void test_BCryptEncrypt(void)
|
||||
{0xc6,0xa1,0x3b,0x37,0x87,0x8f,0x5b,0x82,0x6f,0x4f,0x81,0x62,0xa1,0xc8,0xd8,0x79,
|
||||
0xb1,0xa2,0x92,0x73,0xbe,0x2c,0x42,0x07,0xa5,0xac,0xe3,0x93,0x39,0x8c,0xb6,0xfb,
|
||||
0x87,0x5d,0xea,0xa3,0x7e,0x0f,0xde,0xfa,0xd9,0xec,0x6c,0x4e,0x3c,0x76,0x86,0xe4};
|
||||
+ static UCHAR expected4[] =
|
||||
+ {0xe1,0x82,0xc3,0xc0,0x24,0xfb,0x86,0x85,0xf3,0xf1,0x2b,0x7d,0x09,0xb4,0x73,0x67,
|
||||
+ 0x86,0x64,0xc3,0xfe,0xa3,0x07,0x61,0xf8,0x16,0xc9,0x78,0x7f,0xe7,0xb1,0xc4,0x94};
|
||||
+ static UCHAR expected_tag[] =
|
||||
+ {0x89,0xb3,0x92,0x00,0x39,0x20,0x09,0xb4,0x6a,0xd6,0xaf,0xca,0x4b,0x5b,0xfd,0xd0};
|
||||
+ static UCHAR expected_tag2[] =
|
||||
+ {0x9a,0x92,0x32,0x2c,0x61,0x2a,0xae,0xef,0x66,0x2a,0xfb,0x55,0xe9,0x48,0xdf,0xbd};
|
||||
+ BCRYPT_AUTHENTICATED_CIPHER_MODE_INFO auth_info;
|
||||
+ UCHAR *buf, ciphertext[48], ivbuf[16], tag[16];
|
||||
+ BCRYPT_AUTH_TAG_LENGTHS_STRUCT tag_length;
|
||||
BCRYPT_ALG_HANDLE aes;
|
||||
BCRYPT_KEY_HANDLE key;
|
||||
- UCHAR *buf, ciphertext[48], ivbuf[16];
|
||||
ULONG size, len, i;
|
||||
NTSTATUS ret;
|
||||
|
||||
ret = pBCryptOpenAlgorithmProvider(&aes, BCRYPT_AES_ALGORITHM, NULL, 0);
|
||||
ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
|
||||
+ /******************
|
||||
+ * AES - CBC mode *
|
||||
+ ******************/
|
||||
+
|
||||
len = 0xdeadbeef;
|
||||
size = sizeof(len);
|
||||
ret = pBCryptGetProperty(aes, BCRYPT_OBJECT_LENGTH, (UCHAR *)&len, sizeof(len), &size, 0);
|
||||
@@ -1054,12 +1069,101 @@ static void test_BCryptEncrypt(void)
|
||||
ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
HeapFree(GetProcessHeap(), 0, buf);
|
||||
|
||||
+ /******************
|
||||
+ * AES - GCM mode *
|
||||
+ ******************/
|
||||
+
|
||||
+ size = 0;
|
||||
+ ret = BCryptGetProperty(aes, BCRYPT_AUTH_TAG_LENGTH, NULL, 0, &size, 0);
|
||||
+ todo_wine ok(ret == STATUS_NOT_SUPPORTED, "got %08x\n", ret);
|
||||
+
|
||||
+ ret = BCryptSetProperty(aes, BCRYPT_CHAINING_MODE, (UCHAR*)BCRYPT_CHAIN_MODE_GCM, sizeof(BCRYPT_CHAIN_MODE_GCM), 0);
|
||||
+ todo_wine ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
+
|
||||
+ size = 0;
|
||||
+ ret = BCryptGetProperty(aes, BCRYPT_AUTH_TAG_LENGTH, NULL, 0, &size, 0);
|
||||
+ todo_wine ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
+ todo_wine ok(size == sizeof(tag_length), "got %u\n", size);
|
||||
+
|
||||
+ size = 0;
|
||||
+ memset(&tag_length, 0, sizeof(tag_length));
|
||||
+ ret = BCryptGetProperty(aes, BCRYPT_AUTH_TAG_LENGTH, (UCHAR*)&tag_length, sizeof(tag_length), &size, 0);
|
||||
+ todo_wine ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
+ todo_wine ok(size == sizeof(tag_length), "got %u\n", size);
|
||||
+ todo_wine ok(tag_length.dwMinLength == 12, "Expected 12, got %d\n", tag_length.dwMinLength);
|
||||
+ todo_wine ok(tag_length.dwMaxLength == 16, "Expected 16, got %d\n", tag_length.dwMaxLength);
|
||||
+ todo_wine ok(tag_length.dwIncrement == 1, "Expected 1, got %d\n", tag_length.dwIncrement);
|
||||
+
|
||||
+ len = 0xdeadbeef;
|
||||
+ size = sizeof(len);
|
||||
+ ret = pBCryptGetProperty(aes, BCRYPT_OBJECT_LENGTH, (UCHAR *)&len, sizeof(len), &size, 0);
|
||||
+ ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
+
|
||||
+ buf = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, len);
|
||||
+ ret = pBCryptGenerateSymmetricKey(aes, &key, buf, len, secret, sizeof(secret), 0);
|
||||
+ ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
+
|
||||
+ memset(&auth_info, 0, sizeof(auth_info));
|
||||
+ auth_info.cbSize = sizeof(auth_info);
|
||||
+ auth_info.dwInfoVersion = 1;
|
||||
+ auth_info.pbNonce = nonce;
|
||||
+ auth_info.cbNonce = sizeof(nonce);
|
||||
+ auth_info.pbTag = tag;
|
||||
+ auth_info.cbTag = sizeof(tag);
|
||||
+
|
||||
+ /* input size is a multiple of block size */
|
||||
+ size = 0;
|
||||
+ memcpy(ivbuf, iv, sizeof(iv));
|
||||
+ memset(ciphertext, 0xff, sizeof(ciphertext));
|
||||
+ memset(tag, 0xff, sizeof(tag));
|
||||
+ ret = pBCryptEncrypt(key, data2, 32, &auth_info, ivbuf, 16, ciphertext, 32, &size, 0);
|
||||
+ todo_wine ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
+ todo_wine ok(size == 32, "got %u\n", size);
|
||||
+ todo_wine ok(!memcmp(ciphertext, expected4, sizeof(expected4)), "wrong data\n");
|
||||
+ todo_wine ok(!memcmp(tag, expected_tag, sizeof(expected_tag)), "wrong tag\n");
|
||||
+ for (i = 0; i < 32; i++)
|
||||
+ todo_wine ok(ciphertext[i] == expected4[i], "%u: %02x != %02x\n", i, ciphertext[i], expected4[i]);
|
||||
+ for (i = 0; i < 16; i++)
|
||||
+ todo_wine ok(tag[i] == expected_tag[i], "%u: %02x != %02x\n", i, tag[i], expected_tag[i]);
|
||||
+
|
||||
+ /* input size is not multiple of block size */
|
||||
+ size = 0;
|
||||
+ memcpy(ivbuf, iv, sizeof(iv));
|
||||
+ memset(ciphertext, 0xff, sizeof(ciphertext));
|
||||
+ memset(tag, 0xff, sizeof(tag));
|
||||
+ ret = pBCryptEncrypt(key, data2, 24, &auth_info, ivbuf, 16, ciphertext, 24, &size, 0);
|
||||
+ todo_wine ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
+ todo_wine ok(size == 24, "got %u\n", size);
|
||||
+ todo_wine ok(!memcmp(ciphertext, expected4, 24), "wrong data\n");
|
||||
+ todo_wine ok(!memcmp(tag, expected_tag2, sizeof(expected_tag2)), "wrong tag\n");
|
||||
+ for (i = 0; i < 24; i++)
|
||||
+ todo_wine ok(ciphertext[i] == expected4[i], "%u: %02x != %02x\n", i, ciphertext[i], expected4[i]);
|
||||
+ for (i = 0; i < 16; i++)
|
||||
+ todo_wine ok(tag[i] == expected_tag2[i], "%u: %02x != %02x\n", i, tag[i], expected_tag2[i]);
|
||||
+
|
||||
+ /* test with padding */
|
||||
+ memcpy(ivbuf, iv, sizeof(iv));
|
||||
+ memset(ciphertext, 0, sizeof(ciphertext));
|
||||
+ ret = pBCryptEncrypt(key, data2, 32, &auth_info, ivbuf, 16, ciphertext, 32, &size, BCRYPT_BLOCK_PADDING);
|
||||
+ todo_wine ok(ret == STATUS_BUFFER_TOO_SMALL, "got %08x\n", ret);
|
||||
+
|
||||
+ memcpy(ivbuf, iv, sizeof(iv));
|
||||
+ memset(ciphertext, 0, sizeof(ciphertext));
|
||||
+ ret = pBCryptEncrypt(key, data2, 32, &auth_info, ivbuf, 16, ciphertext, 48, &size, BCRYPT_BLOCK_PADDING);
|
||||
+ todo_wine ok(ret == STATUS_INVALID_PARAMETER, "got %08x\n", ret);
|
||||
+
|
||||
+ ret = pBCryptDestroyKey(key);
|
||||
+ ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
+ HeapFree(GetProcessHeap(), 0, buf);
|
||||
+
|
||||
ret = pBCryptCloseAlgorithmProvider(aes, 0);
|
||||
ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
}
|
||||
|
||||
static void test_BCryptDecrypt(void)
|
||||
{
|
||||
+ static UCHAR nonce[] =
|
||||
+ {0x10, 0x20, 0x30, 0x40, 0x50, 0x60, 0x10, 0x20, 0x30, 0x40, 0x50, 0x60};
|
||||
static UCHAR secret[] =
|
||||
{0x00,0x01,0x02,0x03,0x04,0x05,0x06,0x07,0x08,0x09,0x0a,0x0b,0x0c,0x0d,0x0e,0x0f};
|
||||
static UCHAR iv[] =
|
||||
@@ -1081,6 +1185,12 @@ static void test_BCryptDecrypt(void)
|
||||
{0xc6,0xa1,0x3b,0x37,0x87,0x8f,0x5b,0x82,0x6f,0x4f,0x81,0x62,0xa1,0xc8,0xd8,0x79,
|
||||
0xb1,0xa2,0x92,0x73,0xbe,0x2c,0x42,0x07,0xa5,0xac,0xe3,0x93,0x39,0x8c,0xb6,0xfb,
|
||||
0x87,0x5d,0xea,0xa3,0x7e,0x0f,0xde,0xfa,0xd9,0xec,0x6c,0x4e,0x3c,0x76,0x86,0xe4};
|
||||
+ static UCHAR ciphertext4[] =
|
||||
+ {0xe1,0x82,0xc3,0xc0,0x24,0xfb,0x86,0x85,0xf3,0xf1,0x2b,0x7d,0x09,0xb4,0x73,0x67,
|
||||
+ 0x86,0x64,0xc3,0xfe,0xa3,0x07,0x61,0xf8,0x16,0xc9,0x78,0x7f,0xe7,0xb1,0xc4,0x94};
|
||||
+ static UCHAR tag[] =
|
||||
+ {0x89,0xb3,0x92,0x00,0x39,0x20,0x09,0xb4,0x6a,0xd6,0xaf,0xca,0x4b,0x5b,0xfd,0xd0};
|
||||
+ BCRYPT_AUTHENTICATED_CIPHER_MODE_INFO auth_info;
|
||||
BCRYPT_ALG_HANDLE aes;
|
||||
BCRYPT_KEY_HANDLE key;
|
||||
UCHAR *buf, plaintext[48], ivbuf[16];
|
||||
@@ -1090,6 +1200,10 @@ static void test_BCryptDecrypt(void)
|
||||
ret = pBCryptOpenAlgorithmProvider(&aes, BCRYPT_AES_ALGORITHM, NULL, 0);
|
||||
ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
|
||||
+ /******************
|
||||
+ * AES - CBC mode *
|
||||
+ ******************/
|
||||
+
|
||||
len = 0xdeadbeef;
|
||||
size = sizeof(len);
|
||||
ret = pBCryptGetProperty(aes, BCRYPT_OBJECT_LENGTH, (UCHAR *)&len, sizeof(len), &size, 0);
|
||||
@@ -1187,6 +1301,45 @@ static void test_BCryptDecrypt(void)
|
||||
ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
HeapFree(GetProcessHeap(), 0, buf);
|
||||
|
||||
+ /******************
|
||||
+ * AES - GCM mode *
|
||||
+ ******************/
|
||||
+
|
||||
+ ret = BCryptSetProperty(aes, BCRYPT_CHAINING_MODE, (UCHAR*)BCRYPT_CHAIN_MODE_GCM, sizeof(BCRYPT_CHAIN_MODE_GCM), 0);
|
||||
+ todo_wine ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
+
|
||||
+ buf = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, len);
|
||||
+ ret = pBCryptGenerateSymmetricKey(aes, &key, buf, len, secret, sizeof(secret), 0);
|
||||
+ ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
+
|
||||
+ memset(&auth_info, 0, sizeof(auth_info));
|
||||
+ auth_info.cbSize = sizeof(auth_info);
|
||||
+ auth_info.dwInfoVersion = 1;
|
||||
+ auth_info.pbNonce = nonce;
|
||||
+ auth_info.cbNonce = sizeof(nonce);
|
||||
+ auth_info.pbTag = tag;
|
||||
+ auth_info.cbTag = sizeof(tag);
|
||||
+
|
||||
+ /* input size is a multiple of block size */
|
||||
+ size = 0;
|
||||
+ memcpy(ivbuf, iv, sizeof(iv));
|
||||
+ memset(plaintext, 0, sizeof(plaintext));
|
||||
+ ret = pBCryptDecrypt(key, ciphertext4, 32, &auth_info, ivbuf, 16, plaintext, 32, &size, 0);
|
||||
+ todo_wine ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
+ todo_wine ok(size == 32, "got %u\n", size);
|
||||
+ todo_wine ok(!memcmp(plaintext, expected3, sizeof(expected3)), "wrong data\n");
|
||||
+
|
||||
+ /* test with wrong tag */
|
||||
+ memcpy(ivbuf, iv, sizeof(iv));
|
||||
+ auth_info.pbTag = iv; /* wrong tag */
|
||||
+ ret = pBCryptDecrypt(key, ciphertext4, 32, &auth_info, ivbuf, 16, plaintext, 32, &size, 0);
|
||||
+ todo_wine ok(ret == STATUS_AUTH_TAG_MISMATCH, "got %08x\n", ret);
|
||||
+ todo_wine ok(size == 32, "got %u\n", size);
|
||||
+
|
||||
+ ret = pBCryptDestroyKey(key);
|
||||
+ ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
+ HeapFree(GetProcessHeap(), 0, buf);
|
||||
+
|
||||
ret = pBCryptCloseAlgorithmProvider(aes, 0);
|
||||
ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
}
|
||||
diff --git a/include/bcrypt.h b/include/bcrypt.h
|
||||
index 6af85e3..b8ff624 100644
|
||||
--- a/include/bcrypt.h
|
||||
+++ b/include/bcrypt.h
|
||||
@@ -85,6 +85,35 @@ typedef struct _BCRYPT_ALGORITHM_IDENTIFIER
|
||||
ULONG dwFlags;
|
||||
} BCRYPT_ALGORITHM_IDENTIFIER;
|
||||
|
||||
+typedef struct __BCRYPT_KEY_LENGTHS_STRUCT
|
||||
+{
|
||||
+ ULONG dwMinLength;
|
||||
+ ULONG dwMaxLength;
|
||||
+ ULONG dwIncrement;
|
||||
+} BCRYPT_KEY_LENGTHS_STRUCT, BCRYPT_AUTH_TAG_LENGTHS_STRUCT;
|
||||
+
|
||||
+typedef struct _BCRYPT_AUTHENTICATED_CIPHER_MODE_INFO
|
||||
+{
|
||||
+ ULONG cbSize;
|
||||
+ ULONG dwInfoVersion;
|
||||
+ UCHAR *pbNonce;
|
||||
+ ULONG cbNonce;
|
||||
+ UCHAR *pbAuthData;
|
||||
+ ULONG cbAuthData;
|
||||
+ UCHAR *pbTag;
|
||||
+ ULONG cbTag;
|
||||
+ UCHAR *pbMacContext;
|
||||
+ ULONG cbMacContext;
|
||||
+ ULONG cbAAD;
|
||||
+ ULONGLONG cbData;
|
||||
+ ULONG dwFlags;
|
||||
+} BCRYPT_AUTHENTICATED_CIPHER_MODE_INFO, *PBCRYPT_AUTHENTICATED_CIPHER_MODE_INFO;
|
||||
+
|
||||
+#define BCRYPT_AUTHENTICATED_CIPHER_MODE_INFO_VERSION 1
|
||||
+
|
||||
+#define BCRYPT_AUTH_MODE_CHAIN_CALLS_FLAG 0x00000001
|
||||
+#define BCRYPT_AUTH_MODE_IN_PROGRESS_FLAG 0x00000002
|
||||
+
|
||||
typedef PVOID BCRYPT_ALG_HANDLE;
|
||||
typedef PVOID BCRYPT_KEY_HANDLE;
|
||||
typedef PVOID BCRYPT_HANDLE;
|
||||
diff --git a/include/ntstatus.h b/include/ntstatus.h
|
||||
index 86dad85..7026de7 100644
|
||||
--- a/include/ntstatus.h
|
||||
+++ b/include/ntstatus.h
|
||||
@@ -990,6 +990,8 @@
|
||||
|
||||
#define STATUS_WOW_ASSERTION ((NTSTATUS) 0xC0009898)
|
||||
|
||||
+#define STATUS_AUTH_TAG_MISMATCH ((NTSTATUS) 0xC000A002)
|
||||
+
|
||||
#define RPC_NT_INVALID_STRING_BINDING ((NTSTATUS) 0xC0020001)
|
||||
#define RPC_NT_WRONG_KIND_OF_BINDING ((NTSTATUS) 0xC0020002)
|
||||
#define RPC_NT_INVALID_BINDING ((NTSTATUS) 0xC0020003)
|
||||
--
|
||||
2.9.0
|
||||
|
@ -0,0 +1,133 @@
|
||||
From 9f68ea60cf840c9366aefe1ab486e9d1ee192843 Mon Sep 17 00:00:00 2001
|
||||
From: Sebastian Lackner <sebastian@fds-team.de>
|
||||
Date: Mon, 26 Dec 2016 06:18:01 +0100
|
||||
Subject: bcrypt: Pass object to get_{alg,hash}_property instead of alg_id.
|
||||
|
||||
---
|
||||
dlls/bcrypt/bcrypt_main.c | 32 ++++++++++++++++----------------
|
||||
1 file changed, 16 insertions(+), 16 deletions(-)
|
||||
|
||||
diff --git a/dlls/bcrypt/bcrypt_main.c b/dlls/bcrypt/bcrypt_main.c
|
||||
index d1516cc..8a5161b 100644
|
||||
--- a/dlls/bcrypt/bcrypt_main.c
|
||||
+++ b/dlls/bcrypt/bcrypt_main.c
|
||||
@@ -450,16 +450,16 @@ static NTSTATUS generic_alg_property( enum alg_id id, const WCHAR *prop, UCHAR *
|
||||
return STATUS_NOT_IMPLEMENTED;
|
||||
}
|
||||
|
||||
-static NTSTATUS get_alg_property( enum alg_id id, const WCHAR *prop, UCHAR *buf, ULONG size, ULONG *ret_size )
|
||||
+static NTSTATUS get_alg_property( const struct algorithm *alg, const WCHAR *prop, UCHAR *buf, ULONG size, ULONG *ret_size )
|
||||
{
|
||||
NTSTATUS status;
|
||||
ULONG value;
|
||||
|
||||
- status = generic_alg_property( id, prop, buf, size, ret_size );
|
||||
+ status = generic_alg_property( alg->id, prop, buf, size, ret_size );
|
||||
if (status != STATUS_NOT_IMPLEMENTED)
|
||||
return status;
|
||||
|
||||
- switch (id)
|
||||
+ switch (alg->id)
|
||||
{
|
||||
case ALG_ID_AES:
|
||||
if (!strcmpW( prop, BCRYPT_BLOCK_LENGTH ))
|
||||
@@ -540,7 +540,7 @@ static NTSTATUS get_alg_property( enum alg_id id, const WCHAR *prop, UCHAR *buf,
|
||||
return STATUS_NOT_IMPLEMENTED;
|
||||
|
||||
default:
|
||||
- FIXME( "unsupported algorithm %u\n", id );
|
||||
+ FIXME( "unsupported algorithm %u\n", alg->id );
|
||||
return STATUS_NOT_IMPLEMENTED;
|
||||
}
|
||||
|
||||
@@ -555,11 +555,11 @@ static NTSTATUS get_alg_property( enum alg_id id, const WCHAR *prop, UCHAR *buf,
|
||||
return STATUS_SUCCESS;
|
||||
}
|
||||
|
||||
-static NTSTATUS get_hash_property( enum alg_id id, const WCHAR *prop, UCHAR *buf, ULONG size, ULONG *ret_size )
|
||||
+static NTSTATUS get_hash_property( const struct hash *hash, const WCHAR *prop, UCHAR *buf, ULONG size, ULONG *ret_size )
|
||||
{
|
||||
NTSTATUS status;
|
||||
|
||||
- status = generic_alg_property( id, prop, buf, size, ret_size );
|
||||
+ status = generic_alg_property( hash->alg_id, prop, buf, size, ret_size );
|
||||
if (status == STATUS_NOT_IMPLEMENTED)
|
||||
FIXME( "unsupported property %s\n", debugstr_w(prop) );
|
||||
return status;
|
||||
@@ -579,12 +579,12 @@ NTSTATUS WINAPI BCryptGetProperty( BCRYPT_HANDLE handle, LPCWSTR prop, UCHAR *bu
|
||||
case MAGIC_ALG:
|
||||
{
|
||||
const struct algorithm *alg = (const struct algorithm *)object;
|
||||
- return get_alg_property( alg->id, prop, buffer, count, res );
|
||||
+ return get_alg_property( alg, prop, buffer, count, res );
|
||||
}
|
||||
case MAGIC_HASH:
|
||||
{
|
||||
const struct hash *hash = (const struct hash *)object;
|
||||
- return get_hash_property( hash->alg_id, prop, buffer, count, res );
|
||||
+ return get_hash_property( hash, prop, buffer, count, res );
|
||||
}
|
||||
default:
|
||||
WARN( "unknown magic %08x\n", object->magic );
|
||||
@@ -783,34 +783,34 @@ struct key
|
||||
ULONG secret_len;
|
||||
};
|
||||
|
||||
-static ULONG get_block_size( enum alg_id alg )
|
||||
+static ULONG get_block_size( struct algorithm *alg )
|
||||
{
|
||||
ULONG ret = 0, size = sizeof(ret);
|
||||
get_alg_property( alg, BCRYPT_BLOCK_LENGTH, (UCHAR *)&ret, sizeof(ret), &size );
|
||||
return ret;
|
||||
}
|
||||
|
||||
-static NTSTATUS key_init( struct key *key, enum alg_id id, UCHAR *secret, ULONG secret_len )
|
||||
+static NTSTATUS key_init( struct key *key, struct algorithm *alg, UCHAR *secret, ULONG secret_len )
|
||||
{
|
||||
UCHAR *buffer;
|
||||
|
||||
if (!libgnutls_handle) return STATUS_INTERNAL_ERROR;
|
||||
|
||||
- switch (id)
|
||||
+ switch (alg->id)
|
||||
{
|
||||
case ALG_ID_AES:
|
||||
break;
|
||||
|
||||
default:
|
||||
- FIXME( "algorithm %u not supported\n", id );
|
||||
+ FIXME( "algorithm %u not supported\n", alg->id );
|
||||
return STATUS_NOT_SUPPORTED;
|
||||
}
|
||||
|
||||
- if (!(key->block_size = get_block_size( id ))) return STATUS_INVALID_PARAMETER;
|
||||
+ if (!(key->block_size = get_block_size( alg ))) return STATUS_INVALID_PARAMETER;
|
||||
if (!(buffer = HeapAlloc( GetProcessHeap(), 0, secret_len ))) return STATUS_NO_MEMORY;
|
||||
memcpy( buffer, secret, secret_len );
|
||||
|
||||
- key->alg_id = id;
|
||||
+ key->alg_id = alg->id;
|
||||
key->handle = 0; /* initialized on first use */
|
||||
key->secret = buffer;
|
||||
key->secret_len = secret_len;
|
||||
@@ -906,7 +906,7 @@ struct key
|
||||
ULONG block_size;
|
||||
};
|
||||
|
||||
-static NTSTATUS key_init( struct key *key, enum alg_id id, const UCHAR *secret, ULONG secret_len )
|
||||
+static NTSTATUS key_init( struct key *key, struct algorithm *alg, UCHAR *secret, ULONG secret_len )
|
||||
{
|
||||
ERR( "support for keys not available at build time\n" );
|
||||
return STATUS_NOT_IMPLEMENTED;
|
||||
@@ -955,7 +955,7 @@ NTSTATUS WINAPI BCryptGenerateSymmetricKey( BCRYPT_ALG_HANDLE algorithm, BCRYPT_
|
||||
if (!(key = HeapAlloc( GetProcessHeap(), 0, sizeof(*key) ))) return STATUS_NO_MEMORY;
|
||||
key->hdr.magic = MAGIC_KEY;
|
||||
|
||||
- if ((status = key_init( key, alg->id, secret, secret_len )))
|
||||
+ if ((status = key_init( key, alg, secret, secret_len )))
|
||||
{
|
||||
HeapFree( GetProcessHeap(), 0, key );
|
||||
return status;
|
||||
--
|
||||
2.9.0
|
||||
|
@ -0,0 +1,149 @@
|
||||
From 5313398cdabe97a17b21e2d9f25a191da7bd9434 Mon Sep 17 00:00:00 2001
|
||||
From: =?UTF-8?q?Michael=20M=C3=BCller?= <michael@fds-team.de>
|
||||
Date: Mon, 26 Dec 2016 06:08:33 +0100
|
||||
Subject: bcrypt: Implement BCryptSetProperty for algorithms.
|
||||
|
||||
---
|
||||
dlls/bcrypt/bcrypt_main.c | 66 ++++++++++++++++++++++++++++++++++++++++++++--
|
||||
dlls/bcrypt/tests/bcrypt.c | 6 ++---
|
||||
2 files changed, 67 insertions(+), 5 deletions(-)
|
||||
|
||||
diff --git a/dlls/bcrypt/bcrypt_main.c b/dlls/bcrypt/bcrypt_main.c
|
||||
index 8a5161b..4757878 100644
|
||||
--- a/dlls/bcrypt/bcrypt_main.c
|
||||
+++ b/dlls/bcrypt/bcrypt_main.c
|
||||
@@ -153,6 +153,12 @@ enum alg_id
|
||||
ALG_ID_SHA512
|
||||
};
|
||||
|
||||
+enum mode_id
|
||||
+{
|
||||
+ MODE_ID_CBC,
|
||||
+ MODE_ID_GCM
|
||||
+};
|
||||
+
|
||||
#define MAX_HASH_OUTPUT_BYTES 64
|
||||
|
||||
static const struct {
|
||||
@@ -172,6 +178,7 @@ struct algorithm
|
||||
{
|
||||
struct object hdr;
|
||||
enum alg_id id;
|
||||
+ enum mode_id mode;
|
||||
BOOL hmac;
|
||||
};
|
||||
|
||||
@@ -265,6 +272,7 @@ NTSTATUS WINAPI BCryptOpenAlgorithmProvider( BCRYPT_ALG_HANDLE *handle, LPCWSTR
|
||||
if (!(alg = HeapAlloc( GetProcessHeap(), 0, sizeof(*alg) ))) return STATUS_NO_MEMORY;
|
||||
alg->hdr.magic = MAGIC_ALG;
|
||||
alg->id = alg_id;
|
||||
+ alg->mode = MODE_ID_CBC;
|
||||
alg->hmac = flags & BCRYPT_ALG_HANDLE_HMAC_FLAG;
|
||||
|
||||
*handle = alg;
|
||||
@@ -555,6 +563,40 @@ static NTSTATUS get_alg_property( const struct algorithm *alg, const WCHAR *prop
|
||||
return STATUS_SUCCESS;
|
||||
}
|
||||
|
||||
+static NTSTATUS set_alg_property( struct algorithm *alg, const WCHAR *prop, UCHAR *value, ULONG size, ULONG flags )
|
||||
+{
|
||||
+ switch (alg->id)
|
||||
+ {
|
||||
+ case ALG_ID_AES:
|
||||
+ if (!strcmpW( prop, BCRYPT_CHAINING_MODE ))
|
||||
+ {
|
||||
+ if (size == sizeof(BCRYPT_CHAIN_MODE_CBC) &&
|
||||
+ !strncmpW( (WCHAR *)value, BCRYPT_CHAIN_MODE_CBC, size ))
|
||||
+ {
|
||||
+ alg->mode = MODE_ID_CBC;
|
||||
+ return STATUS_SUCCESS;
|
||||
+ }
|
||||
+ else if (size == sizeof(BCRYPT_CHAIN_MODE_GCM) &&
|
||||
+ !strncmpW( (WCHAR *)value, BCRYPT_CHAIN_MODE_GCM, size ))
|
||||
+ {
|
||||
+ alg->mode = MODE_ID_GCM;
|
||||
+ return STATUS_SUCCESS;
|
||||
+ }
|
||||
+ else
|
||||
+ {
|
||||
+ FIXME( "unsupported mode %s\n", debugstr_wn( (WCHAR *)value, size ) );
|
||||
+ return STATUS_NOT_IMPLEMENTED;
|
||||
+ }
|
||||
+ }
|
||||
+ FIXME( "unsupported aes algorithm property %s\n", debugstr_w(prop) );
|
||||
+ return STATUS_NOT_IMPLEMENTED;
|
||||
+
|
||||
+ default:
|
||||
+ FIXME( "unsupported algorithm %u\n", alg->id );
|
||||
+ return STATUS_NOT_IMPLEMENTED;
|
||||
+ }
|
||||
+}
|
||||
+
|
||||
static NTSTATUS get_hash_property( const struct hash *hash, const WCHAR *prop, UCHAR *buf, ULONG size, ULONG *ret_size )
|
||||
{
|
||||
NTSTATUS status;
|
||||
@@ -595,8 +637,28 @@ NTSTATUS WINAPI BCryptGetProperty( BCRYPT_HANDLE handle, LPCWSTR prop, UCHAR *bu
|
||||
NTSTATUS WINAPI BCryptSetProperty( BCRYPT_HANDLE handle, const WCHAR *prop, UCHAR *value,
|
||||
ULONG size, ULONG flags )
|
||||
{
|
||||
- FIXME( "%p, %s, %p, %u, %08x\n", handle, debugstr_w(prop), value, size, flags );
|
||||
- return STATUS_NOT_IMPLEMENTED;
|
||||
+ struct object *object = handle;
|
||||
+
|
||||
+ TRACE( "%p, %s, %p, %u, %08x\n", handle, debugstr_w(prop), value, size, flags );
|
||||
+
|
||||
+ if (!object) return STATUS_INVALID_HANDLE;
|
||||
+
|
||||
+ switch (object->magic)
|
||||
+ {
|
||||
+ case MAGIC_ALG:
|
||||
+ {
|
||||
+ struct algorithm *alg = (struct algorithm *)object;
|
||||
+ return set_alg_property( alg, prop, value, size, flags );
|
||||
+ }
|
||||
+ case MAGIC_KEY:
|
||||
+ {
|
||||
+ FIXME( "keys not implemented yet\n" );
|
||||
+ return STATUS_NOT_IMPLEMENTED;
|
||||
+ }
|
||||
+ default:
|
||||
+ WARN( "unknown magic %08x\n", object->magic );
|
||||
+ return STATUS_INVALID_HANDLE;
|
||||
+ }
|
||||
}
|
||||
|
||||
NTSTATUS WINAPI BCryptCreateHash( BCRYPT_ALG_HANDLE algorithm, BCRYPT_HASH_HANDLE *handle, UCHAR *object, ULONG objectlen,
|
||||
diff --git a/dlls/bcrypt/tests/bcrypt.c b/dlls/bcrypt/tests/bcrypt.c
|
||||
index 699a995..d850738 100644
|
||||
--- a/dlls/bcrypt/tests/bcrypt.c
|
||||
+++ b/dlls/bcrypt/tests/bcrypt.c
|
||||
@@ -889,7 +889,7 @@ static void test_BCryptGenerateSymmetricKey(void)
|
||||
|
||||
ret = pBCryptSetProperty(aes, BCRYPT_CHAINING_MODE, (UCHAR *)BCRYPT_CHAIN_MODE_CBC,
|
||||
sizeof(BCRYPT_CHAIN_MODE_CBC), 0);
|
||||
- todo_wine ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
+ ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
|
||||
size = 0xdeadbeef;
|
||||
ret = pBCryptEncrypt(key, NULL, 0, NULL, NULL, 0, NULL, 0, &size, 0);
|
||||
@@ -1078,7 +1078,7 @@ static void test_BCryptEncrypt(void)
|
||||
todo_wine ok(ret == STATUS_NOT_SUPPORTED, "got %08x\n", ret);
|
||||
|
||||
ret = BCryptSetProperty(aes, BCRYPT_CHAINING_MODE, (UCHAR*)BCRYPT_CHAIN_MODE_GCM, sizeof(BCRYPT_CHAIN_MODE_GCM), 0);
|
||||
- todo_wine ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
+ ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
|
||||
size = 0;
|
||||
ret = BCryptGetProperty(aes, BCRYPT_AUTH_TAG_LENGTH, NULL, 0, &size, 0);
|
||||
@@ -1306,7 +1306,7 @@ static void test_BCryptDecrypt(void)
|
||||
******************/
|
||||
|
||||
ret = BCryptSetProperty(aes, BCRYPT_CHAINING_MODE, (UCHAR*)BCRYPT_CHAIN_MODE_GCM, sizeof(BCRYPT_CHAIN_MODE_GCM), 0);
|
||||
- todo_wine ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
+ ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
|
||||
buf = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, len);
|
||||
ret = pBCryptGenerateSymmetricKey(aes, &key, buf, len, secret, sizeof(secret), 0);
|
||||
--
|
||||
2.9.0
|
||||
|
@ -0,0 +1,58 @@
|
||||
From f7749755c11e54d1e75cd05b6656d2c474ade8ae Mon Sep 17 00:00:00 2001
|
||||
From: =?UTF-8?q?Michael=20M=C3=BCller?= <michael@fds-team.de>
|
||||
Date: Mon, 26 Dec 2016 06:46:11 +0100
|
||||
Subject: bcrypt: Implement BCryptGetProperty for BCRYPT_CHAINING_MODE.
|
||||
|
||||
---
|
||||
dlls/bcrypt/bcrypt_main.c | 19 ++++++++++---------
|
||||
dlls/bcrypt/tests/bcrypt.c | 2 +-
|
||||
2 files changed, 11 insertions(+), 10 deletions(-)
|
||||
|
||||
diff --git a/dlls/bcrypt/bcrypt_main.c b/dlls/bcrypt/bcrypt_main.c
|
||||
index 4757878..24dee8b 100644
|
||||
--- a/dlls/bcrypt/bcrypt_main.c
|
||||
+++ b/dlls/bcrypt/bcrypt_main.c
|
||||
@@ -482,17 +482,18 @@ static NTSTATUS get_alg_property( const struct algorithm *alg, const WCHAR *prop
|
||||
}
|
||||
if (!strcmpW( prop, BCRYPT_CHAINING_MODE ))
|
||||
{
|
||||
- if (size >= sizeof(BCRYPT_CHAIN_MODE_CBC))
|
||||
+ const WCHAR *mode;
|
||||
+ switch (alg->mode)
|
||||
{
|
||||
- memcpy(buf, BCRYPT_CHAIN_MODE_CBC, sizeof(BCRYPT_CHAIN_MODE_CBC));
|
||||
- *ret_size = sizeof(BCRYPT_CHAIN_MODE_CBC) * sizeof(WCHAR);
|
||||
- return STATUS_SUCCESS;
|
||||
- }
|
||||
- else
|
||||
- {
|
||||
- *ret_size = sizeof(BCRYPT_CHAIN_MODE_CBC) * sizeof(WCHAR);
|
||||
- return STATUS_BUFFER_TOO_SMALL;
|
||||
+ case MODE_ID_GCM: mode = BCRYPT_CHAIN_MODE_GCM; break;
|
||||
+ case MODE_ID_CBC: mode = BCRYPT_CHAIN_MODE_CBC; break;
|
||||
+ default: return STATUS_NOT_IMPLEMENTED;
|
||||
}
|
||||
+
|
||||
+ *ret_size = 64;
|
||||
+ if (size < *ret_size) return STATUS_BUFFER_TOO_SMALL;
|
||||
+ memcpy( buf, mode, (strlenW(mode) + 1) * sizeof(WCHAR) );
|
||||
+ return STATUS_SUCCESS;
|
||||
}
|
||||
FIXME( "unsupported aes algorithm property %s\n", debugstr_w(prop) );
|
||||
return STATUS_NOT_IMPLEMENTED;
|
||||
diff --git a/dlls/bcrypt/tests/bcrypt.c b/dlls/bcrypt/tests/bcrypt.c
|
||||
index d850738..bbf18c4 100644
|
||||
--- a/dlls/bcrypt/tests/bcrypt.c
|
||||
+++ b/dlls/bcrypt/tests/bcrypt.c
|
||||
@@ -842,7 +842,7 @@ static void test_aes(void)
|
||||
|
||||
size = 0;
|
||||
ret = pBCryptGetProperty(alg, BCRYPT_CHAINING_MODE, mode, sizeof(mode) - 1, &size, 0);
|
||||
- todo_wine ok(ret == STATUS_BUFFER_TOO_SMALL, "got %08x\n", ret);
|
||||
+ ok(ret == STATUS_BUFFER_TOO_SMALL, "got %08x\n", ret);
|
||||
ok(size == 64, "got %u\n", size);
|
||||
|
||||
size = 0;
|
||||
--
|
||||
2.9.0
|
||||
|
@ -0,0 +1,75 @@
|
||||
From 017f5d467e537e5159f9c14f703df97661a1453e Mon Sep 17 00:00:00 2001
|
||||
From: =?UTF-8?q?Michael=20M=C3=BCller?= <michael@fds-team.de>
|
||||
Date: Mon, 26 Dec 2016 06:50:28 +0100
|
||||
Subject: bcrypt: Implement BCryptGetProperty for BCRYPT_AUTH_TAG_LENGTH.
|
||||
|
||||
---
|
||||
dlls/bcrypt/bcrypt_main.c | 14 ++++++++++++++
|
||||
dlls/bcrypt/tests/bcrypt.c | 16 ++++++++--------
|
||||
2 files changed, 22 insertions(+), 8 deletions(-)
|
||||
|
||||
diff --git a/dlls/bcrypt/bcrypt_main.c b/dlls/bcrypt/bcrypt_main.c
|
||||
index 24dee8b..dc5c798 100644
|
||||
--- a/dlls/bcrypt/bcrypt_main.c
|
||||
+++ b/dlls/bcrypt/bcrypt_main.c
|
||||
@@ -495,6 +495,20 @@ static NTSTATUS get_alg_property( const struct algorithm *alg, const WCHAR *prop
|
||||
memcpy( buf, mode, (strlenW(mode) + 1) * sizeof(WCHAR) );
|
||||
return STATUS_SUCCESS;
|
||||
}
|
||||
+ if (!strcmpW( prop, BCRYPT_AUTH_TAG_LENGTH ))
|
||||
+ {
|
||||
+ BCRYPT_AUTH_TAG_LENGTHS_STRUCT *tag_length = (void *)buf;
|
||||
+ if (alg->mode != MODE_ID_GCM) return STATUS_NOT_SUPPORTED;
|
||||
+ *ret_size = sizeof(*tag_length);
|
||||
+ if (tag_length && size < *ret_size) return STATUS_BUFFER_TOO_SMALL;
|
||||
+ if (tag_length)
|
||||
+ {
|
||||
+ tag_length->dwMinLength = 12;
|
||||
+ tag_length->dwMaxLength = 16;
|
||||
+ tag_length->dwIncrement = 1;
|
||||
+ }
|
||||
+ return STATUS_SUCCESS;
|
||||
+ }
|
||||
FIXME( "unsupported aes algorithm property %s\n", debugstr_w(prop) );
|
||||
return STATUS_NOT_IMPLEMENTED;
|
||||
|
||||
diff --git a/dlls/bcrypt/tests/bcrypt.c b/dlls/bcrypt/tests/bcrypt.c
|
||||
index bbf18c4..513d11f 100644
|
||||
--- a/dlls/bcrypt/tests/bcrypt.c
|
||||
+++ b/dlls/bcrypt/tests/bcrypt.c
|
||||
@@ -1075,24 +1075,24 @@ static void test_BCryptEncrypt(void)
|
||||
|
||||
size = 0;
|
||||
ret = BCryptGetProperty(aes, BCRYPT_AUTH_TAG_LENGTH, NULL, 0, &size, 0);
|
||||
- todo_wine ok(ret == STATUS_NOT_SUPPORTED, "got %08x\n", ret);
|
||||
+ ok(ret == STATUS_NOT_SUPPORTED, "got %08x\n", ret);
|
||||
|
||||
ret = BCryptSetProperty(aes, BCRYPT_CHAINING_MODE, (UCHAR*)BCRYPT_CHAIN_MODE_GCM, sizeof(BCRYPT_CHAIN_MODE_GCM), 0);
|
||||
ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
|
||||
size = 0;
|
||||
ret = BCryptGetProperty(aes, BCRYPT_AUTH_TAG_LENGTH, NULL, 0, &size, 0);
|
||||
- todo_wine ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
- todo_wine ok(size == sizeof(tag_length), "got %u\n", size);
|
||||
+ ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
+ ok(size == sizeof(tag_length), "got %u\n", size);
|
||||
|
||||
size = 0;
|
||||
memset(&tag_length, 0, sizeof(tag_length));
|
||||
ret = BCryptGetProperty(aes, BCRYPT_AUTH_TAG_LENGTH, (UCHAR*)&tag_length, sizeof(tag_length), &size, 0);
|
||||
- todo_wine ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
- todo_wine ok(size == sizeof(tag_length), "got %u\n", size);
|
||||
- todo_wine ok(tag_length.dwMinLength == 12, "Expected 12, got %d\n", tag_length.dwMinLength);
|
||||
- todo_wine ok(tag_length.dwMaxLength == 16, "Expected 16, got %d\n", tag_length.dwMaxLength);
|
||||
- todo_wine ok(tag_length.dwIncrement == 1, "Expected 1, got %d\n", tag_length.dwIncrement);
|
||||
+ ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
+ ok(size == sizeof(tag_length), "got %u\n", size);
|
||||
+ ok(tag_length.dwMinLength == 12, "Expected 12, got %d\n", tag_length.dwMinLength);
|
||||
+ ok(tag_length.dwMaxLength == 16, "Expected 16, got %d\n", tag_length.dwMaxLength);
|
||||
+ ok(tag_length.dwIncrement == 1, "Expected 1, got %d\n", tag_length.dwIncrement);
|
||||
|
||||
len = 0xdeadbeef;
|
||||
size = sizeof(len);
|
||||
--
|
||||
2.9.0
|
||||
|
@ -0,0 +1,56 @@
|
||||
From 698dc9ea948f98eba154453e6cdc79919373d007 Mon Sep 17 00:00:00 2001
|
||||
From: Sebastian Lackner <sebastian@fds-team.de>
|
||||
Date: Mon, 26 Dec 2016 07:21:27 +0100
|
||||
Subject: bcrypt: Fix string comparison in set_alg_property.
|
||||
|
||||
---
|
||||
dlls/bcrypt/bcrypt_main.c | 6 ++----
|
||||
dlls/bcrypt/tests/bcrypt.c | 11 +++++++++++
|
||||
2 files changed, 13 insertions(+), 4 deletions(-)
|
||||
|
||||
diff --git a/dlls/bcrypt/bcrypt_main.c b/dlls/bcrypt/bcrypt_main.c
|
||||
index dc5c798..7eea550 100644
|
||||
--- a/dlls/bcrypt/bcrypt_main.c
|
||||
+++ b/dlls/bcrypt/bcrypt_main.c
|
||||
@@ -585,14 +585,12 @@ static NTSTATUS set_alg_property( struct algorithm *alg, const WCHAR *prop, UCHA
|
||||
case ALG_ID_AES:
|
||||
if (!strcmpW( prop, BCRYPT_CHAINING_MODE ))
|
||||
{
|
||||
- if (size == sizeof(BCRYPT_CHAIN_MODE_CBC) &&
|
||||
- !strncmpW( (WCHAR *)value, BCRYPT_CHAIN_MODE_CBC, size ))
|
||||
+ if (!strncmpW( (WCHAR *)value, BCRYPT_CHAIN_MODE_CBC, size ))
|
||||
{
|
||||
alg->mode = MODE_ID_CBC;
|
||||
return STATUS_SUCCESS;
|
||||
}
|
||||
- else if (size == sizeof(BCRYPT_CHAIN_MODE_GCM) &&
|
||||
- !strncmpW( (WCHAR *)value, BCRYPT_CHAIN_MODE_GCM, size ))
|
||||
+ else if (!strncmpW( (WCHAR *)value, BCRYPT_CHAIN_MODE_GCM, size ))
|
||||
{
|
||||
alg->mode = MODE_ID_GCM;
|
||||
return STATUS_SUCCESS;
|
||||
diff --git a/dlls/bcrypt/tests/bcrypt.c b/dlls/bcrypt/tests/bcrypt.c
|
||||
index 513d11f..77aacdc 100644
|
||||
--- a/dlls/bcrypt/tests/bcrypt.c
|
||||
+++ b/dlls/bcrypt/tests/bcrypt.c
|
||||
@@ -852,6 +852,17 @@ static void test_aes(void)
|
||||
ok(!lstrcmpW((const WCHAR *)mode, BCRYPT_CHAIN_MODE_CBC), "got %s\n", mode);
|
||||
ok(size == 64, "got %u\n", size);
|
||||
|
||||
+ memcpy(mode, BCRYPT_CHAIN_MODE_GCM, sizeof(BCRYPT_CHAIN_MODE_GCM));
|
||||
+ ret = pBCryptSetProperty(alg, BCRYPT_CHAINING_MODE, mode, sizeof(mode), 0);
|
||||
+ ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
+
|
||||
+ size = 0;
|
||||
+ memset(mode, 0, sizeof(mode));
|
||||
+ ret = pBCryptGetProperty(alg, BCRYPT_CHAINING_MODE, mode, sizeof(mode), &size, 0);
|
||||
+ ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
+ ok(!lstrcmpW((const WCHAR *)mode, BCRYPT_CHAIN_MODE_GCM), "got %s\n", mode);
|
||||
+ ok(size == 64, "got %u\n", size);
|
||||
+
|
||||
test_alg_name(alg, "AES");
|
||||
|
||||
ret = pBCryptCloseAlgorithmProvider(alg, 0);
|
||||
--
|
||||
2.9.0
|
||||
|
@ -0,0 +1,168 @@
|
||||
From ad15e50c53901317847236410be7b1d005e1a502 Mon Sep 17 00:00:00 2001
|
||||
From: =?UTF-8?q?Michael=20M=C3=BCller?= <michael@fds-team.de>
|
||||
Date: Mon, 26 Dec 2016 07:46:57 +0100
|
||||
Subject: bcrypt: Implement BCryptEncrypt for AES GCM mode.
|
||||
|
||||
---
|
||||
dlls/bcrypt/bcrypt_main.c | 50 ++++++++++++++++++++++++++++++++++++++--------
|
||||
dlls/bcrypt/tests/bcrypt.c | 18 ++++++++---------
|
||||
2 files changed, 51 insertions(+), 17 deletions(-)
|
||||
|
||||
diff --git a/dlls/bcrypt/bcrypt_main.c b/dlls/bcrypt/bcrypt_main.c
|
||||
index 774f29a..a143580 100644
|
||||
--- a/dlls/bcrypt/bcrypt_main.c
|
||||
+++ b/dlls/bcrypt/bcrypt_main.c
|
||||
@@ -62,6 +62,12 @@ MAKE_FUNCPTR(gnutls_global_set_log_level);
|
||||
MAKE_FUNCPTR(gnutls_perror);
|
||||
#undef MAKE_FUNCPTR
|
||||
|
||||
+#if GNUTLS_VERSION_MAJOR < 3
|
||||
+#define GNUTLS_CIPHER_AES_192_CBC 92
|
||||
+#define GNUTLS_CIPHER_AES_128_GCM 93
|
||||
+#define GNUTLS_CIPHER_AES_256_GCM 94
|
||||
+#endif
|
||||
+
|
||||
static void gnutls_log( int level, const char *msg )
|
||||
{
|
||||
TRACE( "<%d> %s", level, msg );
|
||||
@@ -852,6 +858,7 @@ struct key
|
||||
{
|
||||
struct object hdr;
|
||||
enum alg_id alg_id;
|
||||
+ enum mode_id mode;
|
||||
ULONG block_size;
|
||||
gnutls_cipher_hd_t handle;
|
||||
UCHAR *secret;
|
||||
@@ -886,6 +893,7 @@ static NTSTATUS key_init( struct key *key, struct algorithm *alg, UCHAR *secret,
|
||||
memcpy( buffer, secret, secret_len );
|
||||
|
||||
key->alg_id = alg->id;
|
||||
+ key->mode = alg->mode;
|
||||
key->handle = 0; /* initialized on first use */
|
||||
key->secret = buffer;
|
||||
key->secret_len = secret_len;
|
||||
@@ -898,9 +906,13 @@ static gnutls_cipher_algorithm_t get_gnutls_cipher( const struct key *key )
|
||||
switch (key->alg_id)
|
||||
{
|
||||
case ALG_ID_AES:
|
||||
- FIXME( "handle block size and chaining mode\n" );
|
||||
- return GNUTLS_CIPHER_AES_128_CBC;
|
||||
-
|
||||
+ WARN( "handle block size\n" );
|
||||
+ switch (key->mode)
|
||||
+ {
|
||||
+ case MODE_ID_GCM: return GNUTLS_CIPHER_AES_128_GCM;
|
||||
+ case MODE_ID_CBC:
|
||||
+ default: return GNUTLS_CIPHER_AES_128_CBC;
|
||||
+ }
|
||||
default:
|
||||
FIXME( "algorithm %u not supported\n", key->alg_id );
|
||||
return GNUTLS_CIPHER_UNKNOWN;
|
||||
@@ -978,12 +990,14 @@ static NTSTATUS key_destroy( struct key *key )
|
||||
struct key
|
||||
{
|
||||
struct object hdr;
|
||||
+ enum mode_id mode;
|
||||
ULONG block_size;
|
||||
};
|
||||
|
||||
static NTSTATUS key_init( struct key *key, struct algorithm *alg, UCHAR *secret, ULONG secret_len )
|
||||
{
|
||||
ERR( "support for keys not available at build time\n" );
|
||||
+ key->mode = MODE_ID_CBC;
|
||||
return STATUS_NOT_IMPLEMENTED;
|
||||
}
|
||||
|
||||
@@ -1063,17 +1077,37 @@ NTSTATUS WINAPI BCryptEncrypt( BCRYPT_KEY_HANDLE handle, UCHAR *input, ULONG inp
|
||||
padding, iv, iv_len, output, output_len, ret_len, flags );
|
||||
|
||||
if (!key || key->hdr.magic != MAGIC_KEY) return STATUS_INVALID_HANDLE;
|
||||
- if (padding)
|
||||
- {
|
||||
- FIXME( "padding info not implemented\n" );
|
||||
- return STATUS_NOT_IMPLEMENTED;
|
||||
- }
|
||||
if (flags & ~BCRYPT_BLOCK_PADDING)
|
||||
{
|
||||
FIXME( "flags %08x not implemented\n", flags );
|
||||
return STATUS_NOT_IMPLEMENTED;
|
||||
}
|
||||
|
||||
+ if (key->mode == MODE_ID_GCM)
|
||||
+ {
|
||||
+ BCRYPT_AUTHENTICATED_CIPHER_MODE_INFO *auth_info = padding;
|
||||
+
|
||||
+ if (!auth_info) return STATUS_INVALID_PARAMETER;
|
||||
+ if (!auth_info->pbNonce) return STATUS_INVALID_PARAMETER;
|
||||
+ if (!auth_info->pbTag) return STATUS_INVALID_PARAMETER;
|
||||
+ if (auth_info->cbTag < 12 || auth_info->cbTag > 16) return STATUS_INVALID_PARAMETER;
|
||||
+ if (auth_info->dwFlags & BCRYPT_AUTH_MODE_CHAIN_CALLS_FLAG)
|
||||
+ FIXME( "call chaining not implemented\n" );
|
||||
+
|
||||
+ if ((status = key_set_params( key, auth_info->pbNonce, auth_info->cbNonce )))
|
||||
+ return status;
|
||||
+
|
||||
+ *ret_len = input_len;
|
||||
+ if (flags & BCRYPT_BLOCK_PADDING) return STATUS_INVALID_PARAMETER;
|
||||
+ if (!output) return STATUS_SUCCESS;
|
||||
+ if (output_len < *ret_len) return STATUS_BUFFER_TOO_SMALL;
|
||||
+
|
||||
+ if ((status = key_encrypt( key, input, input_len, output, output_len )))
|
||||
+ return status;
|
||||
+
|
||||
+ return STATUS_SUCCESS;
|
||||
+ }
|
||||
+
|
||||
if ((status = key_set_params( key, iv, iv_len ))) return status;
|
||||
|
||||
*ret_len = input_len;
|
||||
diff --git a/dlls/bcrypt/tests/bcrypt.c b/dlls/bcrypt/tests/bcrypt.c
|
||||
index 77aacdc..d2a74ce 100644
|
||||
--- a/dlls/bcrypt/tests/bcrypt.c
|
||||
+++ b/dlls/bcrypt/tests/bcrypt.c
|
||||
@@ -1128,12 +1128,12 @@ static void test_BCryptEncrypt(void)
|
||||
memset(ciphertext, 0xff, sizeof(ciphertext));
|
||||
memset(tag, 0xff, sizeof(tag));
|
||||
ret = pBCryptEncrypt(key, data2, 32, &auth_info, ivbuf, 16, ciphertext, 32, &size, 0);
|
||||
- todo_wine ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
- todo_wine ok(size == 32, "got %u\n", size);
|
||||
- todo_wine ok(!memcmp(ciphertext, expected4, sizeof(expected4)), "wrong data\n");
|
||||
+ ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
+ ok(size == 32, "got %u\n", size);
|
||||
+ ok(!memcmp(ciphertext, expected4, sizeof(expected4)), "wrong data\n");
|
||||
todo_wine ok(!memcmp(tag, expected_tag, sizeof(expected_tag)), "wrong tag\n");
|
||||
for (i = 0; i < 32; i++)
|
||||
- todo_wine ok(ciphertext[i] == expected4[i], "%u: %02x != %02x\n", i, ciphertext[i], expected4[i]);
|
||||
+ ok(ciphertext[i] == expected4[i], "%u: %02x != %02x\n", i, ciphertext[i], expected4[i]);
|
||||
for (i = 0; i < 16; i++)
|
||||
todo_wine ok(tag[i] == expected_tag[i], "%u: %02x != %02x\n", i, tag[i], expected_tag[i]);
|
||||
|
||||
@@ -1143,12 +1143,12 @@ static void test_BCryptEncrypt(void)
|
||||
memset(ciphertext, 0xff, sizeof(ciphertext));
|
||||
memset(tag, 0xff, sizeof(tag));
|
||||
ret = pBCryptEncrypt(key, data2, 24, &auth_info, ivbuf, 16, ciphertext, 24, &size, 0);
|
||||
- todo_wine ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
- todo_wine ok(size == 24, "got %u\n", size);
|
||||
- todo_wine ok(!memcmp(ciphertext, expected4, 24), "wrong data\n");
|
||||
+ ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
+ ok(size == 24, "got %u\n", size);
|
||||
+ ok(!memcmp(ciphertext, expected4, 24), "wrong data\n");
|
||||
todo_wine ok(!memcmp(tag, expected_tag2, sizeof(expected_tag2)), "wrong tag\n");
|
||||
for (i = 0; i < 24; i++)
|
||||
- todo_wine ok(ciphertext[i] == expected4[i], "%u: %02x != %02x\n", i, ciphertext[i], expected4[i]);
|
||||
+ ok(ciphertext[i] == expected4[i], "%u: %02x != %02x\n", i, ciphertext[i], expected4[i]);
|
||||
for (i = 0; i < 16; i++)
|
||||
todo_wine ok(tag[i] == expected_tag2[i], "%u: %02x != %02x\n", i, tag[i], expected_tag2[i]);
|
||||
|
||||
@@ -1161,7 +1161,7 @@ static void test_BCryptEncrypt(void)
|
||||
memcpy(ivbuf, iv, sizeof(iv));
|
||||
memset(ciphertext, 0, sizeof(ciphertext));
|
||||
ret = pBCryptEncrypt(key, data2, 32, &auth_info, ivbuf, 16, ciphertext, 48, &size, BCRYPT_BLOCK_PADDING);
|
||||
- todo_wine ok(ret == STATUS_INVALID_PARAMETER, "got %08x\n", ret);
|
||||
+ ok(ret == STATUS_INVALID_PARAMETER, "got %08x\n", ret);
|
||||
|
||||
ret = pBCryptDestroyKey(key);
|
||||
ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
--
|
||||
2.9.0
|
||||
|
@ -0,0 +1,83 @@
|
||||
From ebe7443d7e83bd4ba3143b52010ca97eaf767a9e Mon Sep 17 00:00:00 2001
|
||||
From: =?UTF-8?q?Michael=20M=C3=BCller?= <michael@fds-team.de>
|
||||
Date: Mon, 26 Dec 2016 07:53:10 +0100
|
||||
Subject: bcrypt: Implement BCryptDecrypt for AES GCM mode.
|
||||
|
||||
---
|
||||
dlls/bcrypt/bcrypt_main.c | 28 +++++++++++++++++++++++-----
|
||||
dlls/bcrypt/tests/bcrypt.c | 8 ++++----
|
||||
2 files changed, 27 insertions(+), 9 deletions(-)
|
||||
|
||||
diff --git a/dlls/bcrypt/bcrypt_main.c b/dlls/bcrypt/bcrypt_main.c
|
||||
index 77db0b1..c41524d 100644
|
||||
--- a/dlls/bcrypt/bcrypt_main.c
|
||||
+++ b/dlls/bcrypt/bcrypt_main.c
|
||||
@@ -1153,17 +1153,35 @@ NTSTATUS WINAPI BCryptDecrypt( BCRYPT_KEY_HANDLE handle, UCHAR *input, ULONG inp
|
||||
padding, iv, iv_len, output, output_len, ret_len, flags );
|
||||
|
||||
if (!key || key->hdr.magic != MAGIC_KEY) return STATUS_INVALID_HANDLE;
|
||||
- if (padding)
|
||||
- {
|
||||
- FIXME( "padding info not implemented\n" );
|
||||
- return STATUS_NOT_IMPLEMENTED;
|
||||
- }
|
||||
if (flags & ~BCRYPT_BLOCK_PADDING)
|
||||
{
|
||||
FIXME( "flags %08x not supported\n", flags );
|
||||
return STATUS_NOT_IMPLEMENTED;
|
||||
}
|
||||
|
||||
+ if (key->mode == MODE_ID_GCM)
|
||||
+ {
|
||||
+ BCRYPT_AUTHENTICATED_CIPHER_MODE_INFO *auth_info = padding;
|
||||
+
|
||||
+ if (!auth_info) return STATUS_INVALID_PARAMETER;
|
||||
+ if (!auth_info->pbNonce) return STATUS_INVALID_PARAMETER;
|
||||
+ if (!auth_info->pbTag) return STATUS_INVALID_PARAMETER;
|
||||
+ if (auth_info->cbTag < 12 || auth_info->cbTag > 16) return STATUS_INVALID_PARAMETER;
|
||||
+
|
||||
+ if ((status = key_set_params( key, auth_info->pbNonce, auth_info->cbNonce )))
|
||||
+ return status;
|
||||
+
|
||||
+ *ret_len = input_len;
|
||||
+ if (flags & BCRYPT_BLOCK_PADDING) return STATUS_INVALID_PARAMETER;
|
||||
+ if (!output) return STATUS_SUCCESS;
|
||||
+ if (output_len < *ret_len) return STATUS_BUFFER_TOO_SMALL;
|
||||
+
|
||||
+ if ((status = key_decrypt( key, input, input_len, output, output_len )))
|
||||
+ return status;
|
||||
+
|
||||
+ return STATUS_SUCCESS;
|
||||
+ }
|
||||
+
|
||||
if ((status = key_set_params( key, iv, iv_len ))) return status;
|
||||
|
||||
*ret_len = input_len;
|
||||
diff --git a/dlls/bcrypt/tests/bcrypt.c b/dlls/bcrypt/tests/bcrypt.c
|
||||
index d2a74ce..3a1bc00 100644
|
||||
--- a/dlls/bcrypt/tests/bcrypt.c
|
||||
+++ b/dlls/bcrypt/tests/bcrypt.c
|
||||
@@ -1336,16 +1336,16 @@ static void test_BCryptDecrypt(void)
|
||||
memcpy(ivbuf, iv, sizeof(iv));
|
||||
memset(plaintext, 0, sizeof(plaintext));
|
||||
ret = pBCryptDecrypt(key, ciphertext4, 32, &auth_info, ivbuf, 16, plaintext, 32, &size, 0);
|
||||
- todo_wine ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
- todo_wine ok(size == 32, "got %u\n", size);
|
||||
- todo_wine ok(!memcmp(plaintext, expected3, sizeof(expected3)), "wrong data\n");
|
||||
+ ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
+ ok(size == 32, "got %u\n", size);
|
||||
+ ok(!memcmp(plaintext, expected3, sizeof(expected3)), "wrong data\n");
|
||||
|
||||
/* test with wrong tag */
|
||||
memcpy(ivbuf, iv, sizeof(iv));
|
||||
auth_info.pbTag = iv; /* wrong tag */
|
||||
ret = pBCryptDecrypt(key, ciphertext4, 32, &auth_info, ivbuf, 16, plaintext, 32, &size, 0);
|
||||
todo_wine ok(ret == STATUS_AUTH_TAG_MISMATCH, "got %08x\n", ret);
|
||||
- todo_wine ok(size == 32, "got %u\n", size);
|
||||
+ ok(size == 32, "got %u\n", size);
|
||||
|
||||
ret = pBCryptDestroyKey(key);
|
||||
ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
--
|
||||
2.9.0
|
||||
|
@ -0,0 +1,155 @@
|
||||
From ec780b6b895ed5d9cd7bad5a2f24a822c3ae0e33 Mon Sep 17 00:00:00 2001
|
||||
From: =?UTF-8?q?Michael=20M=C3=BCller?= <michael@fds-team.de>
|
||||
Date: Mon, 26 Dec 2016 08:02:36 +0100
|
||||
Subject: bcrypt: Add support for computing/comparing cipher tag.
|
||||
|
||||
---
|
||||
dlls/bcrypt/bcrypt_main.c | 41 ++++++++++++++++++++++++++++++++++++++++-
|
||||
dlls/bcrypt/tests/bcrypt.c | 10 +++++-----
|
||||
2 files changed, 45 insertions(+), 6 deletions(-)
|
||||
|
||||
diff --git a/dlls/bcrypt/bcrypt_main.c b/dlls/bcrypt/bcrypt_main.c
|
||||
index c41524d..8a2df46 100644
|
||||
--- a/dlls/bcrypt/bcrypt_main.c
|
||||
+++ b/dlls/bcrypt/bcrypt_main.c
|
||||
@@ -49,6 +49,9 @@ static HINSTANCE instance;
|
||||
#if defined(HAVE_GNUTLS_HASH) && !defined(HAVE_COMMONCRYPTO_COMMONDIGEST_H)
|
||||
WINE_DECLARE_DEBUG_CHANNEL(winediag);
|
||||
|
||||
+/* Not present in gnutls version < 3.0 */
|
||||
+static int (*pgnutls_cipher_tag)(gnutls_cipher_hd_t handle, void * tag, size_t tag_size);
|
||||
+
|
||||
static void *libgnutls_handle;
|
||||
#define MAKE_FUNCPTR(f) static typeof(f) * p##f
|
||||
MAKE_FUNCPTR(gnutls_cipher_init);
|
||||
@@ -68,6 +71,11 @@ MAKE_FUNCPTR(gnutls_perror);
|
||||
#define GNUTLS_CIPHER_AES_256_GCM 94
|
||||
#endif
|
||||
|
||||
+static int compat_gnutls_cipher_tag(gnutls_cipher_hd_t handle, void * tag, size_t tag_size)
|
||||
+{
|
||||
+ return GNUTLS_E_UNKNOWN_CIPHER_TYPE;
|
||||
+}
|
||||
+
|
||||
static void gnutls_log( int level, const char *msg )
|
||||
{
|
||||
TRACE( "<%d> %s", level, msg );
|
||||
@@ -101,6 +109,12 @@ static BOOL gnutls_initialize(void)
|
||||
LOAD_FUNCPTR(gnutls_perror)
|
||||
#undef LOAD_FUNCPTR
|
||||
|
||||
+ if (!(pgnutls_cipher_tag = wine_dlsym( libgnutls_handle, "gnutls_cipher_tag", NULL, 0 )))
|
||||
+ {
|
||||
+ WARN("gnutls_cipher_tag not found\n");
|
||||
+ pgnutls_cipher_tag = compat_gnutls_cipher_tag;
|
||||
+ }
|
||||
+
|
||||
if ((ret = pgnutls_global_init()) != GNUTLS_E_SUCCESS)
|
||||
{
|
||||
pgnutls_perror( ret );
|
||||
@@ -979,6 +993,19 @@ static NTSTATUS key_decrypt( struct key *key, const UCHAR *input, ULONG input_le
|
||||
return STATUS_SUCCESS;
|
||||
}
|
||||
|
||||
+static NTSTATUS key_get_tag( struct key *key, UCHAR *tag, ULONG len )
|
||||
+{
|
||||
+ int ret;
|
||||
+
|
||||
+ if ((ret = pgnutls_cipher_tag( key->handle, tag, len )))
|
||||
+ {
|
||||
+ pgnutls_perror( ret );
|
||||
+ return STATUS_INTERNAL_ERROR;
|
||||
+ }
|
||||
+
|
||||
+ return STATUS_SUCCESS;
|
||||
+}
|
||||
+
|
||||
static NTSTATUS key_destroy( struct key *key )
|
||||
{
|
||||
if (key->handle) pgnutls_cipher_deinit( key->handle );
|
||||
@@ -1019,6 +1046,12 @@ static NTSTATUS key_decrypt( struct key *key, const UCHAR *input, ULONG input_le
|
||||
return STATUS_NOT_IMPLEMENTED;
|
||||
}
|
||||
|
||||
+static NTSTATUS key_get_tag( struct key *key, UCHAR *tag, ULONG len )
|
||||
+{
|
||||
+ ERR( "support for keys not available at build time\n" );
|
||||
+ return STATUS_NOT_IMPLEMENTED;
|
||||
+}
|
||||
+
|
||||
static NTSTATUS key_destroy( struct key *key )
|
||||
{
|
||||
ERR( "support for keys not available at build time\n" );
|
||||
@@ -1103,7 +1136,7 @@ NTSTATUS WINAPI BCryptEncrypt( BCRYPT_KEY_HANDLE handle, UCHAR *input, ULONG inp
|
||||
if ((status = key_encrypt( key, input, input_len, output, output_len )))
|
||||
return status;
|
||||
|
||||
- return STATUS_SUCCESS;
|
||||
+ return key_get_tag( key, auth_info->pbTag, auth_info->cbTag );
|
||||
}
|
||||
|
||||
if ((status = key_set_params( key, iv, iv_len ))) return status;
|
||||
@@ -1162,6 +1195,7 @@ NTSTATUS WINAPI BCryptDecrypt( BCRYPT_KEY_HANDLE handle, UCHAR *input, ULONG inp
|
||||
if (key->mode == MODE_ID_GCM)
|
||||
{
|
||||
BCRYPT_AUTHENTICATED_CIPHER_MODE_INFO *auth_info = padding;
|
||||
+ UCHAR tag[16];
|
||||
|
||||
if (!auth_info) return STATUS_INVALID_PARAMETER;
|
||||
if (!auth_info->pbNonce) return STATUS_INVALID_PARAMETER;
|
||||
@@ -1179,6 +1213,11 @@ NTSTATUS WINAPI BCryptDecrypt( BCRYPT_KEY_HANDLE handle, UCHAR *input, ULONG inp
|
||||
if ((status = key_decrypt( key, input, input_len, output, output_len )))
|
||||
return status;
|
||||
|
||||
+ if ((status = key_get_tag( key, tag, sizeof(tag) )))
|
||||
+ return status;
|
||||
+ if (memcmp( tag, auth_info->pbTag, auth_info->cbTag ))
|
||||
+ return STATUS_AUTH_TAG_MISMATCH;
|
||||
+
|
||||
return STATUS_SUCCESS;
|
||||
}
|
||||
|
||||
diff --git a/dlls/bcrypt/tests/bcrypt.c b/dlls/bcrypt/tests/bcrypt.c
|
||||
index 3a1bc00..5d8447c 100644
|
||||
--- a/dlls/bcrypt/tests/bcrypt.c
|
||||
+++ b/dlls/bcrypt/tests/bcrypt.c
|
||||
@@ -1131,11 +1131,11 @@ static void test_BCryptEncrypt(void)
|
||||
ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
ok(size == 32, "got %u\n", size);
|
||||
ok(!memcmp(ciphertext, expected4, sizeof(expected4)), "wrong data\n");
|
||||
- todo_wine ok(!memcmp(tag, expected_tag, sizeof(expected_tag)), "wrong tag\n");
|
||||
+ ok(!memcmp(tag, expected_tag, sizeof(expected_tag)), "wrong tag\n");
|
||||
for (i = 0; i < 32; i++)
|
||||
ok(ciphertext[i] == expected4[i], "%u: %02x != %02x\n", i, ciphertext[i], expected4[i]);
|
||||
for (i = 0; i < 16; i++)
|
||||
- todo_wine ok(tag[i] == expected_tag[i], "%u: %02x != %02x\n", i, tag[i], expected_tag[i]);
|
||||
+ ok(tag[i] == expected_tag[i], "%u: %02x != %02x\n", i, tag[i], expected_tag[i]);
|
||||
|
||||
/* input size is not multiple of block size */
|
||||
size = 0;
|
||||
@@ -1146,11 +1146,11 @@ static void test_BCryptEncrypt(void)
|
||||
ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
ok(size == 24, "got %u\n", size);
|
||||
ok(!memcmp(ciphertext, expected4, 24), "wrong data\n");
|
||||
- todo_wine ok(!memcmp(tag, expected_tag2, sizeof(expected_tag2)), "wrong tag\n");
|
||||
+ ok(!memcmp(tag, expected_tag2, sizeof(expected_tag2)), "wrong tag\n");
|
||||
for (i = 0; i < 24; i++)
|
||||
ok(ciphertext[i] == expected4[i], "%u: %02x != %02x\n", i, ciphertext[i], expected4[i]);
|
||||
for (i = 0; i < 16; i++)
|
||||
- todo_wine ok(tag[i] == expected_tag2[i], "%u: %02x != %02x\n", i, tag[i], expected_tag2[i]);
|
||||
+ ok(tag[i] == expected_tag2[i], "%u: %02x != %02x\n", i, tag[i], expected_tag2[i]);
|
||||
|
||||
/* test with padding */
|
||||
memcpy(ivbuf, iv, sizeof(iv));
|
||||
@@ -1344,7 +1344,7 @@ static void test_BCryptDecrypt(void)
|
||||
memcpy(ivbuf, iv, sizeof(iv));
|
||||
auth_info.pbTag = iv; /* wrong tag */
|
||||
ret = pBCryptDecrypt(key, ciphertext4, 32, &auth_info, ivbuf, 16, plaintext, 32, &size, 0);
|
||||
- todo_wine ok(ret == STATUS_AUTH_TAG_MISMATCH, "got %08x\n", ret);
|
||||
+ ok(ret == STATUS_AUTH_TAG_MISMATCH, "got %08x\n", ret);
|
||||
ok(size == 32, "got %u\n", size);
|
||||
|
||||
ret = pBCryptDestroyKey(key);
|
||||
--
|
||||
2.9.0
|
||||
|
@ -0,0 +1,100 @@
|
||||
From e930551dfa4e0bb97db71d056a4ed59f9e459e01 Mon Sep 17 00:00:00 2001
|
||||
From: =?UTF-8?q?Michael=20M=C3=BCller?= <michael@fds-team.de>
|
||||
Date: Mon, 26 Dec 2016 08:28:24 +0100
|
||||
Subject: bcrypt: Implement BCryptDuplicateKey.
|
||||
|
||||
---
|
||||
dlls/bcrypt/bcrypt.spec | 2 +-
|
||||
dlls/bcrypt/bcrypt_main.c | 49 +++++++++++++++++++++++++++++++++++++++++++++++
|
||||
2 files changed, 50 insertions(+), 1 deletion(-)
|
||||
|
||||
diff --git a/dlls/bcrypt/bcrypt.spec b/dlls/bcrypt/bcrypt.spec
|
||||
index 9ecd21d..f5911d2 100644
|
||||
--- a/dlls/bcrypt/bcrypt.spec
|
||||
+++ b/dlls/bcrypt/bcrypt.spec
|
||||
@@ -12,7 +12,7 @@
|
||||
@ stdcall BCryptDestroyKey(ptr)
|
||||
@ stub BCryptDestroySecret
|
||||
@ stdcall BCryptDuplicateHash(ptr ptr ptr long long)
|
||||
-@ stub BCryptDuplicateKey
|
||||
+@ stdcall BCryptDuplicateKey(ptr ptr ptr long long)
|
||||
@ stdcall BCryptEncrypt(ptr ptr long ptr ptr long ptr long ptr long)
|
||||
@ stdcall BCryptEnumAlgorithms(long ptr ptr long)
|
||||
@ stub BCryptEnumContextFunctionProviders
|
||||
diff --git a/dlls/bcrypt/bcrypt_main.c b/dlls/bcrypt/bcrypt_main.c
|
||||
index 198b010..37d6909 100644
|
||||
--- a/dlls/bcrypt/bcrypt_main.c
|
||||
+++ b/dlls/bcrypt/bcrypt_main.c
|
||||
@@ -915,6 +915,24 @@ static NTSTATUS key_init( struct key *key, struct algorithm *alg, UCHAR *secret,
|
||||
return STATUS_SUCCESS;
|
||||
}
|
||||
|
||||
+static NTSTATUS key_duplicate( struct key *key_orig, struct key *key_copy )
|
||||
+{
|
||||
+ UCHAR *buffer;
|
||||
+
|
||||
+ if (!(buffer = HeapAlloc( GetProcessHeap(), 0, key_orig->secret_len ))) return STATUS_NO_MEMORY;
|
||||
+ memcpy( buffer, key_orig->secret, key_orig->secret_len );
|
||||
+
|
||||
+ key_copy->hdr = key_orig->hdr;
|
||||
+ key_copy->alg_id = key_orig->alg_id;
|
||||
+ key_copy->mode = key_orig->mode;
|
||||
+ key_copy->block_size = key_orig->block_size;
|
||||
+ key_copy->handle = NULL;
|
||||
+ key_copy->secret = buffer;
|
||||
+ key_copy->secret_len = key_orig->secret_len;
|
||||
+
|
||||
+ return STATUS_SUCCESS;
|
||||
+}
|
||||
+
|
||||
static gnutls_cipher_algorithm_t get_gnutls_cipher( const struct key *key )
|
||||
{
|
||||
switch (key->alg_id)
|
||||
@@ -1028,6 +1046,13 @@ static NTSTATUS key_init( struct key *key, struct algorithm *alg, UCHAR *secret,
|
||||
return STATUS_NOT_IMPLEMENTED;
|
||||
}
|
||||
|
||||
+static NTSTATUS key_duplicate( struct key *key_orig, struct key *key_copy )
|
||||
+{
|
||||
+ ERR( "support for keys not available at build time\n" );
|
||||
+ key_copy->mode = MODE_ID_CBC;
|
||||
+ return STATUS_NOT_IMPLEMENTED;
|
||||
+}
|
||||
+
|
||||
static NTSTATUS key_set_params( struct key *key, UCHAR *iv, ULONG iv_len )
|
||||
{
|
||||
ERR( "support for keys not available at build time\n" );
|
||||
@@ -1087,6 +1112,30 @@ NTSTATUS WINAPI BCryptGenerateSymmetricKey( BCRYPT_ALG_HANDLE algorithm, BCRYPT_
|
||||
return STATUS_SUCCESS;
|
||||
}
|
||||
|
||||
+NTSTATUS WINAPI BCryptDuplicateKey( BCRYPT_KEY_HANDLE handle, BCRYPT_KEY_HANDLE *handle_copy,
|
||||
+ UCHAR *object, ULONG object_len, ULONG flags )
|
||||
+{
|
||||
+ struct key *key_orig = handle;
|
||||
+ struct key *key_copy;
|
||||
+ NTSTATUS status;
|
||||
+
|
||||
+ TRACE( "%p, %p, %p, %u, %08x\n", handle, handle_copy, object, object_len, flags );
|
||||
+
|
||||
+ if (!key_orig || key_orig->hdr.magic != MAGIC_KEY) return STATUS_INVALID_HANDLE;
|
||||
+ if (!handle_copy) return STATUS_INVALID_PARAMETER;
|
||||
+ if (!(key_copy = HeapAlloc( GetProcessHeap(), 0, sizeof(*key_copy) )))
|
||||
+ return STATUS_NO_MEMORY;
|
||||
+
|
||||
+ if ((status = key_duplicate( key_orig, key_copy )))
|
||||
+ {
|
||||
+ HeapFree( GetProcessHeap(), 0, key_copy );
|
||||
+ return status;
|
||||
+ }
|
||||
+
|
||||
+ *handle_copy = key_copy;
|
||||
+ return STATUS_SUCCESS;
|
||||
+}
|
||||
+
|
||||
NTSTATUS WINAPI BCryptDestroyKey( BCRYPT_KEY_HANDLE handle )
|
||||
{
|
||||
struct key *key = handle;
|
||||
--
|
||||
2.9.0
|
||||
|
@ -0,0 +1,77 @@
|
||||
From ec32e3345f5293704d8165c8428325e536986716 Mon Sep 17 00:00:00 2001
|
||||
From: Sebastian Lackner <sebastian@fds-team.de>
|
||||
Date: Mon, 26 Dec 2016 08:30:43 +0100
|
||||
Subject: bcrypt/tests: Add tests for BCryptDuplicateKey.
|
||||
|
||||
---
|
||||
dlls/bcrypt/tests/bcrypt.c | 33 ++++++++++++++++++++++++++++++++-
|
||||
1 file changed, 32 insertions(+), 1 deletion(-)
|
||||
|
||||
diff --git a/dlls/bcrypt/tests/bcrypt.c b/dlls/bcrypt/tests/bcrypt.c
|
||||
index 5d8447c..a55d9a9 100644
|
||||
--- a/dlls/bcrypt/tests/bcrypt.c
|
||||
+++ b/dlls/bcrypt/tests/bcrypt.c
|
||||
@@ -45,6 +45,7 @@ static NTSTATUS (WINAPI *pBCryptEncrypt)(BCRYPT_KEY_HANDLE, PUCHAR, ULONG, VOID
|
||||
ULONG *, ULONG);
|
||||
static NTSTATUS (WINAPI *pBCryptDecrypt)(BCRYPT_KEY_HANDLE, PUCHAR, ULONG, VOID *, PUCHAR, ULONG, PUCHAR, ULONG,
|
||||
ULONG *, ULONG);
|
||||
+static NTSTATUS (WINAPI *pBCryptDuplicateKey)(BCRYPT_KEY_HANDLE, BCRYPT_KEY_HANDLE *, UCHAR *, ULONG, ULONG);
|
||||
static NTSTATUS (WINAPI *pBCryptDestroyKey)(BCRYPT_KEY_HANDLE);
|
||||
|
||||
static void test_BCryptGenRandom(void)
|
||||
@@ -880,7 +881,7 @@ static void test_BCryptGenerateSymmetricKey(void)
|
||||
static UCHAR expected[] =
|
||||
{0xc6,0xa1,0x3b,0x37,0x87,0x8f,0x5b,0x82,0x6f,0x4f,0x81,0x62,0xa1,0xc8,0xd8,0x79};
|
||||
BCRYPT_ALG_HANDLE aes;
|
||||
- BCRYPT_KEY_HANDLE key;
|
||||
+ BCRYPT_KEY_HANDLE key, key2;
|
||||
UCHAR *buf, ciphertext[16], plaintext[16], ivbuf[16];
|
||||
ULONG size, len, i;
|
||||
NTSTATUS ret;
|
||||
@@ -923,6 +924,35 @@ static void test_BCryptGenerateSymmetricKey(void)
|
||||
for (i = 0; i < 16; i++)
|
||||
ok(ciphertext[i] == expected[i], "%u: %02x != %02x\n", i, ciphertext[i], expected[i]);
|
||||
|
||||
+ ret = pBCryptDuplicateKey(NULL, &key2, NULL, 0, 0);
|
||||
+ ok(ret == STATUS_INVALID_HANDLE, "got %08x\n", ret);
|
||||
+
|
||||
+ if (0) /* crashes on some Windows versions */
|
||||
+ {
|
||||
+ ret = pBCryptDuplicateKey(key, NULL, NULL, 0, 0);
|
||||
+ ok(ret == STATUS_INVALID_PARAMETER, "got %08x\n", ret);
|
||||
+ }
|
||||
+
|
||||
+ key2 = (void *)0xdeadbeef;
|
||||
+ ret = pBCryptDuplicateKey(key, &key2, NULL, 0, 0);
|
||||
+ ok(ret == STATUS_SUCCESS || broken(ret == STATUS_INVALID_PARAMETER), "got %08x\n", ret);
|
||||
+
|
||||
+ if (ret == STATUS_SUCCESS)
|
||||
+ {
|
||||
+ size = 0;
|
||||
+ memcpy(ivbuf, iv, sizeof(iv));
|
||||
+ memset(ciphertext, 0, sizeof(ciphertext));
|
||||
+ ret = pBCryptEncrypt(key2, data, 16, NULL, ivbuf, 16, ciphertext, 16, &size, 0);
|
||||
+ ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
+ ok(size == 16, "got %u\n", size);
|
||||
+ ok(!memcmp(ciphertext, expected, sizeof(expected)), "wrong data\n");
|
||||
+ for (i = 0; i < 16; i++)
|
||||
+ ok(ciphertext[i] == expected[i], "%u: %02x != %02x\n", i, ciphertext[i], expected[i]);
|
||||
+
|
||||
+ ret = pBCryptDestroyKey(key2);
|
||||
+ ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
+ }
|
||||
+
|
||||
size = 0xdeadbeef;
|
||||
ret = pBCryptDecrypt(key, NULL, 0, NULL, NULL, 0, NULL, 0, &size, 0);
|
||||
ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
@@ -1381,6 +1411,7 @@ START_TEST(bcrypt)
|
||||
pBCryptGenerateSymmetricKey = (void *)GetProcAddress(module, "BCryptGenerateSymmetricKey");
|
||||
pBCryptEncrypt = (void *)GetProcAddress(module, "BCryptEncrypt");
|
||||
pBCryptDecrypt = (void *)GetProcAddress(module, "BCryptDecrypt");
|
||||
+ pBCryptDuplicateKey = (void *)GetProcAddress(module, "BCryptDuplicateKey");
|
||||
pBCryptDestroyKey = (void *)GetProcAddress(module, "BCryptDestroyKey");
|
||||
|
||||
test_BCryptGenRandom();
|
||||
--
|
||||
2.9.0
|
||||
|
@ -0,0 +1,98 @@
|
||||
From 85c7ad0c67aa6cc57e93f2160922305f80d49b4c Mon Sep 17 00:00:00 2001
|
||||
From: =?UTF-8?q?Michael=20M=C3=BCller?= <michael@fds-team.de>
|
||||
Date: Mon, 26 Dec 2016 08:41:31 +0100
|
||||
Subject: bcrypt: Allow to call BCryptSetProperty on key objects.
|
||||
|
||||
---
|
||||
dlls/bcrypt/bcrypt_main.c | 38 ++++++++++++++++++++++++++++++++++++--
|
||||
dlls/bcrypt/tests/bcrypt.c | 4 ++++
|
||||
2 files changed, 40 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/dlls/bcrypt/bcrypt_main.c b/dlls/bcrypt/bcrypt_main.c
|
||||
index a07250e..3638c77 100644
|
||||
--- a/dlls/bcrypt/bcrypt_main.c
|
||||
+++ b/dlls/bcrypt/bcrypt_main.c
|
||||
@@ -215,6 +215,9 @@ int alg_block_bits[] =
|
||||
/* ALG_ID_SHA512 */ 1024
|
||||
};
|
||||
|
||||
+struct key;
|
||||
+static NTSTATUS set_key_property( struct key *key, const WCHAR *prop, UCHAR *value, ULONG size, ULONG flags );
|
||||
+
|
||||
NTSTATUS WINAPI BCryptGenRandom(BCRYPT_ALG_HANDLE handle, UCHAR *buffer, ULONG count, ULONG flags)
|
||||
{
|
||||
const DWORD supported_flags = BCRYPT_USE_SYSTEM_PREFERRED_RNG;
|
||||
@@ -685,8 +688,8 @@ NTSTATUS WINAPI BCryptSetProperty( BCRYPT_HANDLE handle, const WCHAR *prop, UCHA
|
||||
}
|
||||
case MAGIC_KEY:
|
||||
{
|
||||
- FIXME( "keys not implemented yet\n" );
|
||||
- return STATUS_NOT_IMPLEMENTED;
|
||||
+ struct key *key = (struct key *)object;
|
||||
+ return set_key_property( key, prop, value, size, flags );
|
||||
}
|
||||
default:
|
||||
WARN( "unknown magic %08x\n", object->magic );
|
||||
@@ -933,6 +936,31 @@ static NTSTATUS key_duplicate( struct key *key_orig, struct key *key_copy )
|
||||
return STATUS_SUCCESS;
|
||||
}
|
||||
|
||||
+static NTSTATUS set_key_property( struct key *key, const WCHAR *prop, UCHAR *value, ULONG size, ULONG flags )
|
||||
+{
|
||||
+ if (!strcmpW( prop, BCRYPT_CHAINING_MODE ))
|
||||
+ {
|
||||
+ if (!strncmpW( (WCHAR *)value, BCRYPT_CHAIN_MODE_CBC, size ))
|
||||
+ {
|
||||
+ key->mode = MODE_ID_CBC;
|
||||
+ return STATUS_SUCCESS;
|
||||
+ }
|
||||
+ else if (!strncmpW( (WCHAR *)value, BCRYPT_CHAIN_MODE_GCM, size ))
|
||||
+ {
|
||||
+ key->mode = MODE_ID_GCM;
|
||||
+ return STATUS_SUCCESS;
|
||||
+ }
|
||||
+ else
|
||||
+ {
|
||||
+ FIXME( "unsupported mode %s\n", debugstr_wn( (WCHAR *)value, size ) );
|
||||
+ return STATUS_NOT_IMPLEMENTED;
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
+ FIXME( "unsupported key property %s\n", debugstr_w(prop) );
|
||||
+ return STATUS_NOT_IMPLEMENTED;
|
||||
+}
|
||||
+
|
||||
static gnutls_cipher_algorithm_t get_gnutls_cipher( const struct key *key )
|
||||
{
|
||||
switch (key->alg_id)
|
||||
@@ -1050,6 +1078,12 @@ static NTSTATUS key_duplicate( struct key *key_orig, struct key *key_copy )
|
||||
return STATUS_NOT_IMPLEMENTED;
|
||||
}
|
||||
|
||||
+static NTSTATUS set_key_property( struct key *key, const WCHAR *prop, UCHAR *value, ULONG size, ULONG flags )
|
||||
+{
|
||||
+ ERR( "support for keys not available at build time\n" );
|
||||
+ return STATUS_NOT_IMPLEMENTED;
|
||||
+}
|
||||
+
|
||||
static NTSTATUS key_set_params( struct key *key, UCHAR *iv, ULONG iv_len )
|
||||
{
|
||||
ERR( "support for keys not available at build time\n" );
|
||||
diff --git a/dlls/bcrypt/tests/bcrypt.c b/dlls/bcrypt/tests/bcrypt.c
|
||||
index a55d9a9..62f0ca7 100644
|
||||
--- a/dlls/bcrypt/tests/bcrypt.c
|
||||
+++ b/dlls/bcrypt/tests/bcrypt.c
|
||||
@@ -903,6 +903,10 @@ static void test_BCryptGenerateSymmetricKey(void)
|
||||
sizeof(BCRYPT_CHAIN_MODE_CBC), 0);
|
||||
ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
|
||||
+ ret = pBCryptSetProperty(key, BCRYPT_CHAINING_MODE, (UCHAR *)BCRYPT_CHAIN_MODE_CBC,
|
||||
+ sizeof(BCRYPT_CHAIN_MODE_CBC), 0);
|
||||
+ ok(ret == STATUS_SUCCESS || broken(ret == STATUS_NOT_SUPPORTED) /* < Win 8 */, "got %08x\n", ret);
|
||||
+
|
||||
size = 0xdeadbeef;
|
||||
ret = pBCryptEncrypt(key, NULL, 0, NULL, NULL, 0, NULL, 0, &size, 0);
|
||||
ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
--
|
||||
2.9.0
|
||||
|
@ -0,0 +1,103 @@
|
||||
From 89b061b83343ad1b0c16f936be3bcad78829d9e8 Mon Sep 17 00:00:00 2001
|
||||
From: =?UTF-8?q?Michael=20M=C3=BCller?= <michael@fds-team.de>
|
||||
Date: Mon, 26 Dec 2016 15:01:19 +0100
|
||||
Subject: bcrypt: Add support for auth data in AES GCM mode.
|
||||
|
||||
---
|
||||
dlls/bcrypt/bcrypt_main.c | 38 ++++++++++++++++++++++++++++++++++++--
|
||||
1 file changed, 36 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/dlls/bcrypt/bcrypt_main.c b/dlls/bcrypt/bcrypt_main.c
|
||||
index 3638c77..34b6497 100644
|
||||
--- a/dlls/bcrypt/bcrypt_main.c
|
||||
+++ b/dlls/bcrypt/bcrypt_main.c
|
||||
@@ -50,7 +50,8 @@ static HINSTANCE instance;
|
||||
WINE_DECLARE_DEBUG_CHANNEL(winediag);
|
||||
|
||||
/* Not present in gnutls version < 3.0 */
|
||||
-static int (*pgnutls_cipher_tag)(gnutls_cipher_hd_t handle, void * tag, size_t tag_size);
|
||||
+static int (*pgnutls_cipher_tag)(gnutls_cipher_hd_t handle, void *tag, size_t tag_size);
|
||||
+static int (*pgnutls_cipher_add_auth)(gnutls_cipher_hd_t handle, const void *ptext, size_t ptext_size);
|
||||
|
||||
static void *libgnutls_handle;
|
||||
#define MAKE_FUNCPTR(f) static typeof(f) * p##f
|
||||
@@ -71,7 +72,12 @@ MAKE_FUNCPTR(gnutls_perror);
|
||||
#define GNUTLS_CIPHER_AES_256_GCM 94
|
||||
#endif
|
||||
|
||||
-static int compat_gnutls_cipher_tag(gnutls_cipher_hd_t handle, void * tag, size_t tag_size)
|
||||
+static int compat_gnutls_cipher_tag(gnutls_cipher_hd_t handle, void *tag, size_t tag_size)
|
||||
+{
|
||||
+ return GNUTLS_E_UNKNOWN_CIPHER_TYPE;
|
||||
+}
|
||||
+
|
||||
+static int compat_gnutls_cipher_add_auth(gnutls_cipher_hd_t handle, const void *ptext, size_t ptext_size)
|
||||
{
|
||||
return GNUTLS_E_UNKNOWN_CIPHER_TYPE;
|
||||
}
|
||||
@@ -114,6 +120,11 @@ static BOOL gnutls_initialize(void)
|
||||
WARN("gnutls_cipher_tag not found\n");
|
||||
pgnutls_cipher_tag = compat_gnutls_cipher_tag;
|
||||
}
|
||||
+ if (!(pgnutls_cipher_add_auth = wine_dlsym( libgnutls_handle, "gnutls_cipher_add_auth", NULL, 0 )))
|
||||
+ {
|
||||
+ WARN("gnutls_cipher_add_auth not found\n");
|
||||
+ pgnutls_cipher_add_auth = compat_gnutls_cipher_add_auth;
|
||||
+ }
|
||||
|
||||
if ((ret = pgnutls_global_init()) != GNUTLS_E_SUCCESS)
|
||||
{
|
||||
@@ -1011,6 +1022,19 @@ static NTSTATUS key_set_params( struct key *key, UCHAR *iv, ULONG iv_len )
|
||||
return STATUS_SUCCESS;
|
||||
}
|
||||
|
||||
+static NTSTATUS key_set_auth_data( struct key *key, UCHAR *auth_data, ULONG len )
|
||||
+{
|
||||
+ int ret;
|
||||
+
|
||||
+ if ((ret = pgnutls_cipher_add_auth( key->handle, auth_data, len )))
|
||||
+ {
|
||||
+ pgnutls_perror( ret );
|
||||
+ return STATUS_INTERNAL_ERROR;
|
||||
+ }
|
||||
+
|
||||
+ return STATUS_SUCCESS;
|
||||
+}
|
||||
+
|
||||
static NTSTATUS key_encrypt( struct key *key, const UCHAR *input, ULONG input_len, UCHAR *output,
|
||||
ULONG output_len )
|
||||
{
|
||||
@@ -1090,6 +1114,12 @@ static NTSTATUS key_set_params( struct key *key, UCHAR *iv, ULONG iv_len )
|
||||
return STATUS_NOT_IMPLEMENTED;
|
||||
}
|
||||
|
||||
+static NTSTATUS key_set_auth_data( struct key *key, UCHAR *auth_data, ULONG len )
|
||||
+{
|
||||
+ ERR( "support for keys not available at build time\n" );
|
||||
+ return STATUS_NOT_IMPLEMENTED;
|
||||
+}
|
||||
+
|
||||
static NTSTATUS key_encrypt( struct key *key, const UCHAR *input, ULONG input_len, UCHAR *output,
|
||||
ULONG output_len )
|
||||
{
|
||||
@@ -1215,6 +1245,8 @@ NTSTATUS WINAPI BCryptEncrypt( BCRYPT_KEY_HANDLE handle, UCHAR *input, ULONG inp
|
||||
if (!output) return STATUS_SUCCESS;
|
||||
if (output_len < *ret_len) return STATUS_BUFFER_TOO_SMALL;
|
||||
|
||||
+ if (auth_info->pbAuthData && (status = key_set_auth_data( key, auth_info->pbAuthData, auth_info->cbAuthData )))
|
||||
+ return status;
|
||||
if ((status = key_encrypt( key, input, input_len, output, output_len )))
|
||||
return status;
|
||||
|
||||
@@ -1292,6 +1324,8 @@ NTSTATUS WINAPI BCryptDecrypt( BCRYPT_KEY_HANDLE handle, UCHAR *input, ULONG inp
|
||||
if (!output) return STATUS_SUCCESS;
|
||||
if (output_len < *ret_len) return STATUS_BUFFER_TOO_SMALL;
|
||||
|
||||
+ if (auth_info->pbAuthData && (status = key_set_auth_data( key, auth_info->pbAuthData, auth_info->cbAuthData )))
|
||||
+ return status;
|
||||
if ((status = key_decrypt( key, input, input_len, output, output_len )))
|
||||
return status;
|
||||
|
||||
--
|
||||
2.9.0
|
||||
|
@ -0,0 +1,102 @@
|
||||
From 930962bf986a469b956e3a5e17d8c026098fadfb Mon Sep 17 00:00:00 2001
|
||||
From: Sebastian Lackner <sebastian@fds-team.de>
|
||||
Date: Mon, 26 Dec 2016 15:01:38 +0100
|
||||
Subject: bcrypt/tests: Add tests for auth data in AES GCM mode.
|
||||
|
||||
---
|
||||
dlls/bcrypt/tests/bcrypt.c | 44 ++++++++++++++++++++++++++++++++++++++++++--
|
||||
1 file changed, 42 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/dlls/bcrypt/tests/bcrypt.c b/dlls/bcrypt/tests/bcrypt.c
|
||||
index 62f0ca7..a18e495 100644
|
||||
--- a/dlls/bcrypt/tests/bcrypt.c
|
||||
+++ b/dlls/bcrypt/tests/bcrypt.c
|
||||
@@ -987,7 +987,9 @@ static void test_BCryptGenerateSymmetricKey(void)
|
||||
static void test_BCryptEncrypt(void)
|
||||
{
|
||||
static UCHAR nonce[] =
|
||||
- {0x10, 0x20, 0x30, 0x40, 0x50, 0x60, 0x10, 0x20, 0x30, 0x40, 0x50, 0x60};
|
||||
+ {0x10,0x20,0x30,0x40,0x50,0x60,0x10,0x20,0x30,0x40,0x50,0x60};
|
||||
+ static UCHAR auth_data[] =
|
||||
+ {0x60,0x50,0x40,0x30,0x20,0x10,0x60,0x50,0x40,0x30,0x20,0x10};
|
||||
static UCHAR secret[] =
|
||||
{0x00,0x01,0x02,0x03,0x04,0x05,0x06,0x07,0x08,0x09,0x0a,0x0b,0x0c,0x0d,0x0e,0x0f};
|
||||
static UCHAR iv[] =
|
||||
@@ -1013,6 +1015,8 @@ static void test_BCryptEncrypt(void)
|
||||
{0x89,0xb3,0x92,0x00,0x39,0x20,0x09,0xb4,0x6a,0xd6,0xaf,0xca,0x4b,0x5b,0xfd,0xd0};
|
||||
static UCHAR expected_tag2[] =
|
||||
{0x9a,0x92,0x32,0x2c,0x61,0x2a,0xae,0xef,0x66,0x2a,0xfb,0x55,0xe9,0x48,0xdf,0xbd};
|
||||
+ static UCHAR expected_tag3[] =
|
||||
+ {0x17,0x9d,0xc0,0x7a,0xf0,0xcf,0xaa,0xd5,0x1c,0x11,0xc4,0x4b,0xd6,0xa3,0x3e,0x77};
|
||||
BCRYPT_AUTHENTICATED_CIPHER_MODE_INFO auth_info;
|
||||
UCHAR *buf, ciphertext[48], ivbuf[16], tag[16];
|
||||
BCRYPT_AUTH_TAG_LENGTHS_STRUCT tag_length;
|
||||
@@ -1186,6 +1190,24 @@ static void test_BCryptEncrypt(void)
|
||||
for (i = 0; i < 16; i++)
|
||||
ok(tag[i] == expected_tag2[i], "%u: %02x != %02x\n", i, tag[i], expected_tag2[i]);
|
||||
|
||||
+ /* test with auth data */
|
||||
+ auth_info.pbAuthData = auth_data;
|
||||
+ auth_info.cbAuthData = sizeof(auth_data);
|
||||
+
|
||||
+ size = 0;
|
||||
+ memcpy(ivbuf, iv, sizeof(iv));
|
||||
+ memset(ciphertext, 0xff, sizeof(ciphertext));
|
||||
+ memset(tag, 0xff, sizeof(tag));
|
||||
+ ret = pBCryptEncrypt(key, data2, 32, &auth_info, ivbuf, 16, ciphertext, 32, &size, 0);
|
||||
+ ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
+ ok(size == 32, "got %u\n", size);
|
||||
+ ok(!memcmp(ciphertext, expected4, sizeof(expected4)), "wrong data\n");
|
||||
+ ok(!memcmp(tag, expected_tag3, sizeof(expected_tag3)), "wrong tag\n");
|
||||
+ for (i = 0; i < 32; i++)
|
||||
+ ok(ciphertext[i] == expected4[i], "%u: %02x != %02x\n", i, ciphertext[i], expected4[i]);
|
||||
+ for (i = 0; i < 16; i++)
|
||||
+ ok(tag[i] == expected_tag3[i], "%u: %02x != %02x\n", i, tag[i], expected_tag3[i]);
|
||||
+
|
||||
/* test with padding */
|
||||
memcpy(ivbuf, iv, sizeof(iv));
|
||||
memset(ciphertext, 0, sizeof(ciphertext));
|
||||
@@ -1208,7 +1230,9 @@ static void test_BCryptEncrypt(void)
|
||||
static void test_BCryptDecrypt(void)
|
||||
{
|
||||
static UCHAR nonce[] =
|
||||
- {0x10, 0x20, 0x30, 0x40, 0x50, 0x60, 0x10, 0x20, 0x30, 0x40, 0x50, 0x60};
|
||||
+ {0x10,0x20,0x30,0x40,0x50,0x60,0x10,0x20,0x30,0x40,0x50,0x60};
|
||||
+ static UCHAR auth_data[] =
|
||||
+ {0x60,0x50,0x40,0x30,0x20,0x10,0x60,0x50,0x40,0x30,0x20,0x10};
|
||||
static UCHAR secret[] =
|
||||
{0x00,0x01,0x02,0x03,0x04,0x05,0x06,0x07,0x08,0x09,0x0a,0x0b,0x0c,0x0d,0x0e,0x0f};
|
||||
static UCHAR iv[] =
|
||||
@@ -1235,6 +1259,8 @@ static void test_BCryptDecrypt(void)
|
||||
0x86,0x64,0xc3,0xfe,0xa3,0x07,0x61,0xf8,0x16,0xc9,0x78,0x7f,0xe7,0xb1,0xc4,0x94};
|
||||
static UCHAR tag[] =
|
||||
{0x89,0xb3,0x92,0x00,0x39,0x20,0x09,0xb4,0x6a,0xd6,0xaf,0xca,0x4b,0x5b,0xfd,0xd0};
|
||||
+ static UCHAR tag2[] =
|
||||
+ {0x17,0x9d,0xc0,0x7a,0xf0,0xcf,0xaa,0xd5,0x1c,0x11,0xc4,0x4b,0xd6,0xa3,0x3e,0x77};
|
||||
BCRYPT_AUTHENTICATED_CIPHER_MODE_INFO auth_info;
|
||||
BCRYPT_ALG_HANDLE aes;
|
||||
BCRYPT_KEY_HANDLE key;
|
||||
@@ -1374,6 +1400,20 @@ static void test_BCryptDecrypt(void)
|
||||
ok(size == 32, "got %u\n", size);
|
||||
ok(!memcmp(plaintext, expected3, sizeof(expected3)), "wrong data\n");
|
||||
|
||||
+ /* test with auuth data */
|
||||
+ auth_info.pbAuthData = auth_data;
|
||||
+ auth_info.cbAuthData = sizeof(auth_data);
|
||||
+ auth_info.pbTag = tag2;
|
||||
+ auth_info.cbTag = sizeof(tag2);
|
||||
+
|
||||
+ size = 0;
|
||||
+ memcpy(ivbuf, iv, sizeof(iv));
|
||||
+ memset(plaintext, 0, sizeof(plaintext));
|
||||
+ ret = pBCryptDecrypt(key, ciphertext4, 32, &auth_info, ivbuf, 16, plaintext, 32, &size, 0);
|
||||
+ ok(ret == STATUS_SUCCESS, "got %08x\n", ret);
|
||||
+ ok(size == 32, "got %u\n", size);
|
||||
+ ok(!memcmp(plaintext, expected3, sizeof(expected3)), "wrong data\n");
|
||||
+
|
||||
/* test with wrong tag */
|
||||
memcpy(ivbuf, iv, sizeof(iv));
|
||||
auth_info.pbTag = iv; /* wrong tag */
|
||||
--
|
||||
2.9.0
|
||||
|
@ -0,0 +1,51 @@
|
||||
From b7aa5302f9f16e906968b0a4483988f4e99a44b2 Mon Sep 17 00:00:00 2001
|
||||
From: Sebastian Lackner <sebastian@fds-team.de>
|
||||
Date: Mon, 26 Dec 2016 16:20:57 +0100
|
||||
Subject: bcrypt: Avoid crash in tests when compiling without gnutls support.
|
||||
|
||||
---
|
||||
dlls/bcrypt/bcrypt_main.c | 11 ++++++++++-
|
||||
1 file changed, 10 insertions(+), 1 deletion(-)
|
||||
|
||||
diff --git a/dlls/bcrypt/bcrypt_main.c b/dlls/bcrypt/bcrypt_main.c
|
||||
index 75eaf46..564b2a5 100644
|
||||
--- a/dlls/bcrypt/bcrypt_main.c
|
||||
+++ b/dlls/bcrypt/bcrypt_main.c
|
||||
@@ -1163,12 +1163,17 @@ NTSTATUS WINAPI BCryptGenerateSymmetricKey( BCRYPT_ALG_HANDLE algorithm, BCRYPT_
|
||||
if (!alg || alg->hdr.magic != MAGIC_ALG) return STATUS_INVALID_HANDLE;
|
||||
if (object) FIXME( "ignoring object buffer\n" );
|
||||
|
||||
- if (!(key = HeapAlloc( GetProcessHeap(), 0, sizeof(*key) ))) return STATUS_NO_MEMORY;
|
||||
+ if (!(key = HeapAlloc( GetProcessHeap(), 0, sizeof(*key) )))
|
||||
+ {
|
||||
+ *handle = NULL;
|
||||
+ return STATUS_NO_MEMORY;
|
||||
+ }
|
||||
key->hdr.magic = MAGIC_KEY;
|
||||
|
||||
if ((status = key_init( key, alg, secret, secret_len )))
|
||||
{
|
||||
HeapFree( GetProcessHeap(), 0, key );
|
||||
+ *handle = NULL;
|
||||
return status;
|
||||
}
|
||||
|
||||
@@ -1188,11 +1193,15 @@ NTSTATUS WINAPI BCryptDuplicateKey( BCRYPT_KEY_HANDLE handle, BCRYPT_KEY_HANDLE
|
||||
if (!key_orig || key_orig->hdr.magic != MAGIC_KEY) return STATUS_INVALID_HANDLE;
|
||||
if (!handle_copy) return STATUS_INVALID_PARAMETER;
|
||||
if (!(key_copy = HeapAlloc( GetProcessHeap(), 0, sizeof(*key_copy) )))
|
||||
+ {
|
||||
+ *handle_copy = NULL;
|
||||
return STATUS_NO_MEMORY;
|
||||
+ }
|
||||
|
||||
if ((status = key_duplicate( key_orig, key_copy )))
|
||||
{
|
||||
HeapFree( GetProcessHeap(), 0, key_copy );
|
||||
+ *handle_copy = NULL;
|
||||
return status;
|
||||
}
|
||||
|
||||
--
|
||||
2.9.0
|
||||
|
@ -52,7 +52,7 @@ usage()
|
||||
# Get the upstream commit sha
|
||||
upstream_commit()
|
||||
{
|
||||
echo "1bcd38f788bb5165cc65a830ea912ff4eda50b84"
|
||||
echo "80d2edd5845c09b98cb5b6b7779b4455dfbc1095"
|
||||
}
|
||||
|
||||
# Show version information
|
||||
@ -2862,7 +2862,8 @@ fi
|
||||
# |
|
||||
# | Modified files:
|
||||
# | * dlls/bcrypt/Makefile.in, dlls/bcrypt/bcrypt.spec, dlls/bcrypt/bcrypt_internal.h, dlls/bcrypt/bcrypt_main.c,
|
||||
# | dlls/bcrypt/sha256.c, dlls/bcrypt/sha384.c, dlls/bcrypt/sha512.c, dlls/bcrypt/tests/bcrypt.c, include/bcrypt.h
|
||||
# | dlls/bcrypt/sha256.c, dlls/bcrypt/sha384.c, dlls/bcrypt/sha512.c, dlls/bcrypt/tests/bcrypt.c, include/bcrypt.h,
|
||||
# | include/ntstatus.h
|
||||
# |
|
||||
if test "$enable_bcrypt_Improvements" -eq 1; then
|
||||
patch_apply bcrypt-Improvements/0001-bcrypt-Add-AES-provider.patch
|
||||
@ -2872,6 +2873,24 @@ if test "$enable_bcrypt_Improvements" -eq 1; then
|
||||
patch_apply bcrypt-Improvements/0005-bcrypt-Implement-BCryptDuplicateHash.patch
|
||||
patch_apply bcrypt-Improvements/0006-bcrypt-Fix-handling-of-padding-when-input-size-equal.patch
|
||||
patch_apply bcrypt-Improvements/0007-bcrypt-Properly-handle-padding-in-AES-decryption.patch
|
||||
patch_apply bcrypt-Improvements/0008-bcrypt-Fix-use-after-free-in-key_init.patch
|
||||
patch_apply bcrypt-Improvements/0009-bcrypt-Handle-NULL-pointers-in-BCryptDuplicateHash-a.patch
|
||||
patch_apply bcrypt-Improvements/0010-bcrypt-tests-Add-test-for-bugs-in-BCryptGetProperty.patch
|
||||
patch_apply bcrypt-Improvements/0011-bcrypt-tests-Add-tests-for-AES-GCM-mode.patch
|
||||
patch_apply bcrypt-Improvements/0012-bcrypt-Pass-object-to-get_-alg-hash-_property-instea.patch
|
||||
patch_apply bcrypt-Improvements/0013-bcrypt-Implement-BCryptSetProperty-for-algorithms.patch
|
||||
patch_apply bcrypt-Improvements/0014-bcrypt-Implement-BCryptGetProperty-for-BCRYPT_CHAINI.patch
|
||||
patch_apply bcrypt-Improvements/0015-bcrypt-Implement-BCryptGetProperty-for-BCRYPT_AUTH_T.patch
|
||||
patch_apply bcrypt-Improvements/0016-bcrypt-Fix-string-comparison-in-set_alg_property.patch
|
||||
patch_apply bcrypt-Improvements/0017-bcrypt-Implement-BCryptEncrypt-for-AES-GCM-mode.patch
|
||||
patch_apply bcrypt-Improvements/0018-bcrypt-Implement-BCryptDecrypt-for-AES-GCM-mode.patch
|
||||
patch_apply bcrypt-Improvements/0019-bcrypt-Add-support-for-computing-comparing-cipher-ta.patch
|
||||
patch_apply bcrypt-Improvements/0020-bcrypt-Implement-BCryptDuplicateKey.patch
|
||||
patch_apply bcrypt-Improvements/0021-bcrypt-tests-Add-tests-for-BCryptDuplicateKey.patch
|
||||
patch_apply bcrypt-Improvements/0022-bcrypt-Allow-to-call-BCryptSetProperty-on-key-object.patch
|
||||
patch_apply bcrypt-Improvements/0023-bcrypt-Add-support-for-auth-data-in-AES-GCM-mode.patch
|
||||
patch_apply bcrypt-Improvements/0024-bcrypt-tests-Add-tests-for-auth-data-in-AES-GCM-mode.patch
|
||||
patch_apply bcrypt-Improvements/0025-bcrypt-Avoid-crash-in-tests-when-compiling-without-g.patch
|
||||
(
|
||||
echo '+ { "Hans Leidekker", "bcrypt: Add AES provider.", 1 },';
|
||||
echo '+ { "Michael Müller", "bcrypt: Directly implement hmac computation.", 1 },';
|
||||
@ -2880,6 +2899,24 @@ if test "$enable_bcrypt_Improvements" -eq 1; then
|
||||
echo '+ { "Michael Müller", "bcrypt: Implement BCryptDuplicateHash.", 1 },';
|
||||
echo '+ { "Michael Müller", "bcrypt: Fix handling of padding when input size equals block size for AES.", 1 },';
|
||||
echo '+ { "Michael Müller", "bcrypt: Properly handle padding in AES decryption.", 1 },';
|
||||
echo '+ { "Michael Müller", "bcrypt: Fix use-after-free in key_init.", 1 },';
|
||||
echo '+ { "Sebastian Lackner", "bcrypt: Handle NULL pointers in BCryptDuplicateHash and add tests.", 1 },';
|
||||
echo '+ { "Sebastian Lackner", "bcrypt/tests: Add test for bugs in BCryptGetProperty.", 1 },';
|
||||
echo '+ { "Michael Müller", "bcrypt/tests: Add tests for AES GCM mode.", 1 },';
|
||||
echo '+ { "Sebastian Lackner", "bcrypt: Pass object to get_{alg,hash}_property instead of alg_id.", 1 },';
|
||||
echo '+ { "Michael Müller", "bcrypt: Implement BCryptSetProperty for algorithms.", 1 },';
|
||||
echo '+ { "Michael Müller", "bcrypt: Implement BCryptGetProperty for BCRYPT_CHAINING_MODE.", 1 },';
|
||||
echo '+ { "Michael Müller", "bcrypt: Implement BCryptGetProperty for BCRYPT_AUTH_TAG_LENGTH.", 1 },';
|
||||
echo '+ { "Sebastian Lackner", "bcrypt: Fix string comparison in set_alg_property.", 1 },';
|
||||
echo '+ { "Michael Müller", "bcrypt: Implement BCryptEncrypt for AES GCM mode.", 1 },';
|
||||
echo '+ { "Michael Müller", "bcrypt: Implement BCryptDecrypt for AES GCM mode.", 1 },';
|
||||
echo '+ { "Michael Müller", "bcrypt: Add support for computing/comparing cipher tag.", 1 },';
|
||||
echo '+ { "Michael Müller", "bcrypt: Implement BCryptDuplicateKey.", 1 },';
|
||||
echo '+ { "Sebastian Lackner", "bcrypt/tests: Add tests for BCryptDuplicateKey.", 1 },';
|
||||
echo '+ { "Michael Müller", "bcrypt: Allow to call BCryptSetProperty on key objects.", 1 },';
|
||||
echo '+ { "Michael Müller", "bcrypt: Add support for auth data in AES GCM mode.", 1 },';
|
||||
echo '+ { "Sebastian Lackner", "bcrypt/tests: Add tests for auth data in AES GCM mode.", 1 },';
|
||||
echo '+ { "Sebastian Lackner", "bcrypt: Avoid crash in tests when compiling without gnutls support.", 1 },';
|
||||
) >> "$patchlist"
|
||||
fi
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user