-- v5: bcrypt/tests: Test BCRYPT_PAD_NONE encryption result in test_rsa_encrypt(). bcrypt: Set pubkey from privkey in key_asymmetric_import().
From: Paul Gofman pgofman@codeweavers.com
--- dlls/bcrypt/gnutls.c | 2 ++ dlls/bcrypt/tests/bcrypt.c | 2 +- 2 files changed, 3 insertions(+), 1 deletion(-)
diff --git a/dlls/bcrypt/gnutls.c b/dlls/bcrypt/gnutls.c index bb79e885652..a67030a3ae0 100644 --- a/dlls/bcrypt/gnutls.c +++ b/dlls/bcrypt/gnutls.c @@ -2205,6 +2205,8 @@ static NTSTATUS key_asymmetric_encrypt( void *args ) NTSTATUS status = STATUS_SUCCESS; int ret;
+ if (!key_data(params->key)->a.pubkey) return STATUS_INVALID_HANDLE; + d.data = params->input; d.size = params->input_len; if ((ret = pgnutls_pubkey_encrypt_data(key_data(params->key)->a.pubkey, 0, &d, &e))) diff --git a/dlls/bcrypt/tests/bcrypt.c b/dlls/bcrypt/tests/bcrypt.c index 39cdd015c90..3bcdda0cf47 100644 --- a/dlls/bcrypt/tests/bcrypt.c +++ b/dlls/bcrypt/tests/bcrypt.c @@ -2284,12 +2284,12 @@ static void test_rsa_encrypt(void) ret = BCryptGenerateKeyPair(rsa, &key, 512, 0); ok(ret == STATUS_SUCCESS, "got %lx\n", ret);
- todo_wine { /* Not finalized key */ ret = BCryptEncrypt(key, input, sizeof(input), NULL, NULL, 0, NULL, 0, &encrypted_size, 0); ok(ret == STATUS_INVALID_HANDLE, "got %lx\n", ret); BCryptFinalizeKeyPair(key, 0);
+ todo_wine { /* No padding */ memset(input_no_padding, 0, sizeof(input_no_padding)); strcpy((char *)input_no_padding, "Hello World");
From: Paul Gofman pgofman@codeweavers.com
--- dlls/bcrypt/gnutls.c | 39 ++++++++++++++++++++++++++++++--------- 1 file changed, 30 insertions(+), 9 deletions(-)
diff --git a/dlls/bcrypt/gnutls.c b/dlls/bcrypt/gnutls.c index a67030a3ae0..89e5c91776d 100644 --- a/dlls/bcrypt/gnutls.c +++ b/dlls/bcrypt/gnutls.c @@ -713,8 +713,6 @@ static NTSTATUS key_export_rsa_public( struct key *key, UCHAR *buf, ULONG len, U
if (key_data(key)->a.pubkey) ret = pgnutls_pubkey_export_rsa_raw( key_data(key)->a.pubkey, &m, &e ); - else if (key_data(key)->a.privkey) - ret = pgnutls_privkey_export_rsa_raw( key_data(key)->a.privkey, &m, &e, NULL, NULL, NULL, NULL, NULL, NULL ); else return STATUS_INVALID_PARAMETER;
@@ -781,8 +779,6 @@ static NTSTATUS key_export_ecc_public( struct key *key, UCHAR *buf, ULONG len, U
if (key_data(key)->a.pubkey) ret = pgnutls_pubkey_export_ecc_raw( key_data(key)->a.pubkey, &curve, &x, &y ); - else if (key_data(key)->a.privkey) - ret = pgnutls_privkey_export_ecc_raw( key_data(key)->a.privkey, &curve, &x, &y, NULL ); else return STATUS_INVALID_PARAMETER;
@@ -831,8 +827,6 @@ static NTSTATUS key_export_dsa_public( struct key *key, UCHAR *buf, ULONG len, U
if (key_data(key)->a.pubkey) ret = pgnutls_pubkey_export_dsa_raw( key_data(key)->a.pubkey, &p, &q, &g, &y ); - else if (key_data(key)->a.privkey) - ret = pgnutls_privkey_export_dsa_raw( key_data(key)->a.privkey, &p, &q, &g, &y, NULL ); else return STATUS_INVALID_PARAMETER;
@@ -1574,6 +1568,8 @@ static NTSTATUS key_asymmetric_import( void *args ) const struct key_asymmetric_import_params *params = args; struct key *key = params->key; unsigned flags = params->flags; + gnutls_pubkey_t pubkey; + NTSTATUS ret;
switch (key->alg_id) { @@ -1583,13 +1579,15 @@ static NTSTATUS key_asymmetric_import( void *args ) case ALG_ID_ECDSA_P384: if (flags & KEY_IMPORT_FLAG_PUBLIC) return key_import_ecc_public( key, params->buf, params->len ); - return key_import_ecc( key, params->buf, params->len ); + ret = key_import_ecc( key, params->buf, params->len ); + break;
case ALG_ID_RSA: case ALG_ID_RSA_SIGN: if (flags & KEY_IMPORT_FLAG_PUBLIC) return key_import_rsa_public( key, params->buf, params->len ); - return key_import_rsa( key, params->buf, params->len ); + ret = key_import_rsa( key, params->buf, params->len ); + break;
case ALG_ID_DSA: if (flags & KEY_IMPORT_FLAG_PUBLIC) @@ -1599,7 +1597,10 @@ static NTSTATUS key_asymmetric_import( void *args ) return key_import_dsa_public( key, params->buf, params->len ); } if (key->u.a.flags & KEY_FLAG_LEGACY_DSA_V2) - return key_import_dsa_capi( key, params->buf, params->len ); + { + ret = key_import_dsa_capi( key, params->buf, params->len ); + break; + } FIXME( "DSA private key not supported\n" ); return STATUS_NOT_IMPLEMENTED;
@@ -1607,6 +1608,26 @@ static NTSTATUS key_asymmetric_import( void *args ) FIXME( "algorithm %u not yet supported\n", key->alg_id ); return STATUS_NOT_IMPLEMENTED; } + + if (ret) return ret; + + if ((ret = pgnutls_pubkey_init( &pubkey ))) + { + pgnutls_perror( ret ); + return STATUS_INTERNAL_ERROR; + } + + if (pgnutls_pubkey_import_privkey( pubkey, key_data(params->key)->a.privkey, 0, 0 )) + { + /* Imported private key may be legitimately missing public key, so ignore the failure here. */ + pgnutls_pubkey_deinit( pubkey ); + } + else + { + if (key_data(key)->a.pubkey) pgnutls_pubkey_deinit( key_data(key)->a.pubkey ); + key_data(key)->a.pubkey = pubkey; + } + return STATUS_SUCCESS; }
static NTSTATUS prepare_gnutls_signature_dsa( struct key *key, UCHAR *signature, ULONG signature_len,
From: Paul Gofman pgofman@codeweavers.com
--- dlls/bcrypt/tests/bcrypt.c | 19 ++++++++++++++++++- 1 file changed, 18 insertions(+), 1 deletion(-)
diff --git a/dlls/bcrypt/tests/bcrypt.c b/dlls/bcrypt/tests/bcrypt.c index 3bcdda0cf47..5d1a80f330b 100644 --- a/dlls/bcrypt/tests/bcrypt.c +++ b/dlls/bcrypt/tests/bcrypt.c @@ -2262,6 +2262,14 @@ static UCHAR rsaPublicBlobWithInvalidPublicExpSize[] = 0x87, 0x75, 0x33, 0x15, 0xb8, 0xde, 0x32, 0x30, 0xb4, 0x5e, 0xfd };
+static const UCHAR rsa_encrypted_no_padding[] = +{ + 0x4a, 0xc1, 0xfa, 0x4f, 0xe0, 0x3f, 0x36, 0x9a, 0x64, 0xbf, 0x2e, 0x00, 0xb4, 0xb5, 0x40, 0xbe, + 0x2d, 0x9a, 0x14, 0xf6, 0x8f, 0xa5, 0xc2, 0xe2, 0x20, 0xaf, 0x21, 0x79, 0xc6, 0x32, 0x7e, 0xea, + 0x73, 0x00, 0x01, 0xbb, 0x9a, 0x19, 0x73, 0x41, 0x96, 0xae, 0x88, 0x6e, 0x36, 0x56, 0xe9, 0x9c, + 0xac, 0x04, 0x82, 0xa8, 0x00, 0xdb, 0x4e, 0x29, 0x61, 0x7e, 0xaf, 0x64, 0xdb, 0xa2, 0x70, 0x0f, +}; + static void test_rsa_encrypt(void) { static UCHAR input[] = "Hello World!"; @@ -2287,7 +2295,15 @@ static void test_rsa_encrypt(void) /* Not finalized key */ ret = BCryptEncrypt(key, input, sizeof(input), NULL, NULL, 0, NULL, 0, &encrypted_size, 0); ok(ret == STATUS_INVALID_HANDLE, "got %lx\n", ret); - BCryptFinalizeKeyPair(key, 0); + BCryptDestroyKey(key); + + /* Import a different public key first to make sure a public key from private key improted next + * overrides it. */ + ret = BCryptImportKeyPair(rsa, NULL, BCRYPT_RSAPUBLIC_BLOB, &key, rsaPublicBlob, sizeof(rsaPublicBlob), 0); + ok(ret == STATUS_SUCCESS, "got %#lx\n", ret); + + ret = BCryptImportKeyPair(rsa, NULL, BCRYPT_RSAPRIVATE_BLOB, &key, rsaPrivateBlob, sizeof(rsaPrivateBlob), 0); + ok(ret == STATUS_SUCCESS, "got %#lx\n", ret);
todo_wine { /* No padding */ @@ -2313,6 +2329,7 @@ static void test_rsa_encrypt(void) ret = BCryptEncrypt(key, input_no_padding, sizeof(input_no_padding), NULL, NULL, 0, encrypted_b, encrypted_size, &encrypted_size, BCRYPT_PAD_NONE); ok(ret == STATUS_SUCCESS, "got %lx\n", ret); ok(!memcmp(encrypted_a, encrypted_b, encrypted_size), "Both outputs should be the same\n"); + ok(!memcmp(encrypted_b, rsa_encrypted_no_padding, encrypted_size), "Data mismatch.\n");
BCryptDecrypt(key, encrypted_a, encrypted_size, NULL, NULL, 0, NULL, 0, &decrypted_size, BCRYPT_PAD_NONE); decrypted = malloc(decrypted_size);
Hi,
It looks like your patch introduced the new failures shown below. Please investigate and fix them before resubmitting your patch. If they are not new, fixing them anyway would help a lot. Otherwise please ask for the known failures list to be updated.
The tests also ran into some preexisting test failures. If you know how to fix them that would be helpful. See the TestBot job for the details:
The full results can be found at: https://testbot.winehq.org/JobDetails.pl?Key=127651
Your paranoid android.
=== debian11 (32 bit report) ===
quartz: filtergraph: Timeout
v4: - rename second patch; v5: - remove now unneeded privkey export attempt when exporting pubkeys.
This merge request was approved by Hans Leidekker.