Some installers, like the visual studio installer, also make use of this function, instead of just NCryptVerifySignature.
-- v4: ncrypt: Initial implementation for NCryptEncrypt. bcrypt: Initial RSA encryption implementation. bcrypt/tests: Test for BCryptEncrypt with RSA keys.
From: Santino Mazza mazzasantino1206@gmail.com
Signed-off-by: Santino Mazza mazzasantino1206@gmail.com --- dlls/ncrypt/tests/ncrypt.c | 76 ++++++++++++++++++++++++++++++++++++++ 1 file changed, 76 insertions(+)
diff --git a/dlls/ncrypt/tests/ncrypt.c b/dlls/ncrypt/tests/ncrypt.c index 5808a3bb30a..81b737c9a21 100644 --- a/dlls/ncrypt/tests/ncrypt.c +++ b/dlls/ncrypt/tests/ncrypt.c @@ -539,6 +539,81 @@ static void test_NCryptIsAlgSupported(void) NCryptFreeObject(prov); }
+static UCHAR data_to_encrypt[12] = "Hello world"; + +static void test_NCryptEncrypt(void) +{ + NCRYPT_PROV_HANDLE prov; + NCRYPT_KEY_HANDLE key; + SECURITY_STATUS ret; + BYTE *output_a; + BYTE *output_b; + DWORD output_size; + + todo_wine { + NCryptOpenStorageProvider(&prov, NULL, 0); + NCryptCreatePersistedKey(prov, &key, BCRYPT_RSA_ALGORITHM, NULL, 0, 0); + + /* Test encrypt with invalid key handle */ + ret = NCryptEncrypt(prov, data_to_encrypt, sizeof(data_to_encrypt), NULL, NULL, 0, + &output_size, NCRYPT_PAD_PKCS1_FLAG); + ok(ret == NTE_INVALID_HANDLE, "got %lx\n", ret); + + /* Test encrypt with a non finalized key */ + ret = NCryptEncrypt(key, data_to_encrypt, sizeof(data_to_encrypt), NULL, NULL, 0, + &output_size, NCRYPT_PAD_PKCS1_FLAG); + ok(ret == NTE_BAD_KEY_STATE, "got %lx\n", ret); + + NCryptFinalizeKey(key, 0); + + /* Test encrypt with invalid flags */ + ret = NCryptEncrypt(key, data_to_encrypt, sizeof(data_to_encrypt), NULL, NULL, 0, + &output_size, 51342); + ok(ret == NTE_BAD_FLAGS, "got %lx\n", ret); + + /* Test no padding with RSA */ + ret = NCryptEncrypt(key, data_to_encrypt, sizeof(data_to_encrypt), NULL, NULL, 0, &output_size, + NCRYPT_NO_PADDING_FLAG); + ok(ret == ERROR_SUCCESS, "got %lx\n", ret); + ok(output_size == 128, "got %ld\n", output_size); + + output_a = malloc(output_size); + ret = NCryptEncrypt(key, data_to_encrypt, sizeof(data_to_encrypt), NULL, output_a, output_size, + &output_size, NCRYPT_NO_PADDING_FLAG); + ok(ret == NTE_INVALID_PARAMETER, "got %lx\n", ret); + free(output_a); + + /* Test output RSA with PKCS1. PKCS1 should append a random padding to the data, so the output should be different + * with each call. */ + ret = NCryptEncrypt(key, data_to_encrypt, sizeof(data_to_encrypt), NULL, NULL, 0, + &output_size, NCRYPT_PAD_PKCS1_FLAG); + ok(ret == ERROR_SUCCESS, "got %lx\n", ret); + ok(output_size == 128, "got %ld\n", output_size); + + output_a = malloc(output_size); + output_b = malloc(output_size); + + ret = NCryptEncrypt(key, data_to_encrypt, sizeof(data_to_encrypt), NULL, output_a, 12, + &output_size, NCRYPT_PAD_PKCS1_FLAG); + ok(ret == NTE_BUFFER_TOO_SMALL, "got %lx\n", ret); + + ret = NCryptEncrypt(key, data_to_encrypt, sizeof(data_to_encrypt), NULL, output_a, output_size, + &output_size, NCRYPT_PAD_PKCS1_FLAG); + ok(ret == ERROR_SUCCESS, "got %lx\n", ret); + + ret = NCryptEncrypt(key, data_to_encrypt, sizeof(data_to_encrypt), NULL, output_b, output_size, + &output_size, NCRYPT_PAD_PKCS1_FLAG); + ok(ret == ERROR_SUCCESS, "got %lx\n", ret); + ok(memcmp(output_a, output_b, 128), "expected to have different outputs.\n"); + + NCryptFreeObject(key); + free(output_a); + free(output_b); + + NCryptFreeObject(prov); + } +} + START_TEST(ncrypt) { test_key_import_rsa(); @@ -549,4 +624,5 @@ START_TEST(ncrypt) test_finalize_key(); test_verify_signature(); test_NCryptIsAlgSupported(); + test_NCryptEncrypt(); }
From: Santino Mazza mazzasantino1206@gmail.com
Signed-off-by: Santino Mazza mazzasantino1206@gmail.com --- dlls/bcrypt/tests/bcrypt.c | 111 +++++++++++++++++++++++++++++++++++++ include/bcrypt.h | 6 ++ 2 files changed, 117 insertions(+)
diff --git a/dlls/bcrypt/tests/bcrypt.c b/dlls/bcrypt/tests/bcrypt.c index 08ce360cac0..fca7ae4e1ed 100644 --- a/dlls/bcrypt/tests/bcrypt.c +++ b/dlls/bcrypt/tests/bcrypt.c @@ -2019,6 +2019,114 @@ static UCHAR rsaPublicBlobWithInvalidPublicExpSize[] = 0x87, 0x75, 0x33, 0x15, 0xb8, 0xde, 0x32, 0x30, 0xb4, 0x5e, 0xfd };
+static void test_rsa_encrypt(void) +{ + static UCHAR input[] = "Hello World!"; + static UCHAR input_no_padding[64] = { 0 }; + BCRYPT_ALG_HANDLE rsa = 0; + BCRYPT_KEY_HANDLE key = 0; + NTSTATUS ret = 0; + DWORD encrypted_size = 60; + UCHAR *encrypted_a = NULL; + UCHAR *encrypted_b = NULL; + DWORD decrypted_size = 0; + UCHAR *decrypted = NULL; + BCRYPT_OAEP_PADDING_INFO oaep_pad; + oaep_pad.pszAlgId = BCRYPT_MD5_ALGORITHM; + oaep_pad.pbLabel = (PUCHAR)"test"; + oaep_pad.cbLabel = 5; + + BCryptOpenAlgorithmProvider(&rsa, BCRYPT_RSA_ALGORITHM, NULL, 0); + BCryptGenerateKeyPair(rsa, &key, 512, 0); + + 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); + + /* No padding */ + memset(input_no_padding, 0, sizeof(input_no_padding)); + strcpy((char *)input_no_padding, "Hello World"); + ret = BCryptEncrypt(key, input_no_padding, sizeof(input_no_padding), NULL, NULL, 0, NULL, 0, &encrypted_size, BCRYPT_PAD_NONE); + ok(ret == STATUS_SUCCESS, "got %lx\n", ret); + ok(encrypted_size == 64, "got size of %ld\n", encrypted_size); + + encrypted_a = malloc(encrypted_size); + memset(encrypted_a, 0, encrypted_size); + encrypted_b = malloc(encrypted_size); + memset(encrypted_b, 0xff, encrypted_size); + + ret = BCryptEncrypt(key, input, sizeof(input), NULL, NULL, 0, encrypted_a, encrypted_size, &encrypted_size, BCRYPT_PAD_NONE); + ok(ret == STATUS_INVALID_PARAMETER, "got %lx\n", ret); + + ret = BCryptEncrypt(key, input_no_padding, sizeof(input_no_padding), NULL, NULL, 0, encrypted_a, 12, &encrypted_size, BCRYPT_PAD_NONE); + ok(ret == STATUS_BUFFER_TOO_SMALL, "got %lx\n", ret); + + ret = BCryptEncrypt(key, input_no_padding, sizeof(input_no_padding), NULL, NULL, 0, encrypted_a, encrypted_size, &encrypted_size, BCRYPT_PAD_NONE); + ok(ret == STATUS_SUCCESS, "got %lx\n", ret); + 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"); + + BCryptDecrypt(key, encrypted_a, encrypted_size, NULL, NULL, 0, NULL, 0, &decrypted_size, BCRYPT_PAD_NONE); + decrypted = malloc(decrypted_size); + BCryptDecrypt(key, encrypted_a, encrypted_size, NULL, NULL, 0, decrypted, decrypted_size, &decrypted_size, BCRYPT_PAD_NONE); + ok(!memcmp(decrypted, input_no_padding, sizeof(input_no_padding)), "Decrypted output it's not what expected\n"); + free(decrypted); + + encrypted_size = 60; + /* PKCS1 Padding */ + ret = BCryptEncrypt(key, input, sizeof(input), NULL, NULL, 0, NULL, 0, &encrypted_size, BCRYPT_PAD_PKCS1); + ok(ret == STATUS_SUCCESS, "got %lx\n", ret); + ok(encrypted_size == 64, "got size of %ld\n", encrypted_size); + + encrypted_a = realloc(encrypted_a, encrypted_size); + memset(encrypted_a, 0, encrypted_size); + encrypted_b = realloc(encrypted_b, encrypted_size); + memset(encrypted_b, 0, encrypted_size); + + ret = BCryptEncrypt(key, input, sizeof(input), NULL, NULL, 0, encrypted_a, encrypted_size, &encrypted_size, BCRYPT_PAD_PKCS1); + ok(ret == STATUS_SUCCESS, "got %lx\n", ret); + ret = BCryptEncrypt(key, input, sizeof(input), NULL, NULL, 0, encrypted_b, encrypted_size, &encrypted_size, BCRYPT_PAD_PKCS1); + ok(ret == STATUS_SUCCESS, "got %lx\n", ret); + ok(memcmp(encrypted_a, encrypted_b, encrypted_size), "Both outputs are the same\n"); + + BCryptDecrypt(key, encrypted_a, encrypted_size, NULL, NULL, 0, NULL, 0, &decrypted_size, BCRYPT_PAD_PKCS1); + decrypted = malloc(decrypted_size); + BCryptDecrypt(key, encrypted_a, encrypted_size, NULL, NULL, 0, decrypted, decrypted_size, &decrypted_size, BCRYPT_PAD_PKCS1); + ok(!memcmp(decrypted, input, sizeof(input)), "Decrypted output it's not what expected\n"); + free(decrypted); + + encrypted_size = 60; + /* OAEP Padding */ + ret = BCryptEncrypt(key, input, sizeof(input), &oaep_pad, NULL, 0, NULL, 0, &encrypted_size, BCRYPT_PAD_OAEP); + ok(ret == STATUS_SUCCESS, "got %lx\n", ret); + ok(encrypted_size == 64, "got size of %ld\n", encrypted_size); + + encrypted_a = realloc(encrypted_a, encrypted_size); + memset(encrypted_a, 0, encrypted_size); + encrypted_b = realloc(encrypted_b, encrypted_size); + memset(encrypted_b, 0, encrypted_size); + + ret = BCryptEncrypt(key, input, sizeof(input), &oaep_pad, NULL, 0, encrypted_a, encrypted_size, &encrypted_size, BCRYPT_PAD_OAEP); + ok(ret == STATUS_SUCCESS, "got %lx\n", ret); + ret = BCryptEncrypt(key, input, sizeof(input), &oaep_pad, NULL, 0, encrypted_b, encrypted_size, &encrypted_size, BCRYPT_PAD_OAEP); + ok(ret == STATUS_SUCCESS, "got %lx\n", ret); + ok(memcmp(encrypted_a, encrypted_b, encrypted_size), "Both outputs are the same\n"); + + BCryptDecrypt(key, encrypted_a, encrypted_size, &oaep_pad, NULL, 0, NULL, 0, &decrypted_size, BCRYPT_PAD_OAEP); + decrypted = malloc(decrypted_size); + BCryptDecrypt(key, encrypted_a, encrypted_size, &oaep_pad, NULL, 0, decrypted, decrypted_size, &decrypted_size, BCRYPT_PAD_OAEP); + ok(!memcmp(decrypted, input, sizeof(input)), "Decrypted output it's not what expected\n"); + } + free(decrypted); + + free(encrypted_a); + free(encrypted_b); +} + static void test_RSA(void) { static UCHAR hash[] = @@ -2202,6 +2310,9 @@ static void test_RSA(void)
ret = BCryptCloseAlgorithmProvider(alg, 0); ok(!ret, "got %#lx\n", ret); + + /* RSA encryption */ + test_rsa_encrypt(); }
static void test_RSA_SIGN(void) diff --git a/include/bcrypt.h b/include/bcrypt.h index fbfb5099c09..fd660c1843c 100644 --- a/include/bcrypt.h +++ b/include/bcrypt.h @@ -284,6 +284,12 @@ typedef struct _BCRYPT_PKCS1_PADDING_INFO LPCWSTR pszAlgId; } BCRYPT_PKCS1_PADDING_INFO;
+typedef struct _BCRYPT_OAEP_PADDING_INFO { + LPCWSTR pszAlgId; + PUCHAR pbLabel; + ULONG cbLabel; +} BCRYPT_OAEP_PADDING_INFO; + #define BCRYPT_PAD_NONE 0x00000001 #define BCRYPT_PAD_PKCS1 0x00000002 #define BCRYPT_PAD_OAEP 0x00000004
From: Santino Mazza mazzasantino1206@gmail.com
Signed-off-by: Santino Mazza mazzasantino1206@gmail.com --- dlls/bcrypt/bcrypt_internal.h | 11 ++++++ dlls/bcrypt/bcrypt_main.c | 33 ++++++++++++----- dlls/bcrypt/gnutls.c | 69 ++++++++++++++++++++++++++++++++++- dlls/bcrypt/tests/bcrypt.c | 2 + 4 files changed, 105 insertions(+), 10 deletions(-)
diff --git a/dlls/bcrypt/bcrypt_internal.h b/dlls/bcrypt/bcrypt_internal.h index d57819f2ec6..02461336a57 100644 --- a/dlls/bcrypt/bcrypt_internal.h +++ b/dlls/bcrypt/bcrypt_internal.h @@ -237,6 +237,16 @@ struct key_asymmetric_decrypt_params ULONG *ret_len; };
+struct key_asymmetric_encrypt_params +{ + struct key *key; + UCHAR *input; + unsigned input_len; + UCHAR *output; + ULONG output_len; + ULONG *ret_len; +}; + struct key_asymmetric_duplicate_params { struct key *key_orig; @@ -298,6 +308,7 @@ enum key_funcs unix_key_symmetric_destroy, unix_key_asymmetric_generate, unix_key_asymmetric_decrypt, + unix_key_asymmetric_encrypt, unix_key_asymmetric_duplicate, unix_key_asymmetric_sign, unix_key_asymmetric_verify, diff --git a/dlls/bcrypt/bcrypt_main.c b/dlls/bcrypt/bcrypt_main.c index 2c0d2f8f965..0869fe810a3 100644 --- a/dlls/bcrypt/bcrypt_main.c +++ b/dlls/bcrypt/bcrypt_main.c @@ -1880,26 +1880,41 @@ NTSTATUS WINAPI BCryptEncrypt( BCRYPT_KEY_HANDLE handle, UCHAR *input, ULONG inp ULONG iv_len, UCHAR *output, ULONG output_len, ULONG *ret_len, ULONG flags ) { struct key *key = handle; + struct key_asymmetric_encrypt_params asymmetric_params; NTSTATUS ret;
TRACE( "%p, %p, %lu, %p, %p, %lu, %p, %lu, %p, %#lx\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; - if (!key_is_symmetric( key )) + + if (key_is_symmetric( key )) { - FIXME( "encryption with asymmetric keys not yet supported\n" ); - return STATUS_NOT_IMPLEMENTED; + if (flags & ~BCRYPT_BLOCK_PADDING) + { + FIXME( "flags %#lx not implemented\n", flags ); + return STATUS_NOT_IMPLEMENTED; + } + EnterCriticalSection( &key->u.s.cs ); + ret = key_symmetric_encrypt( key, input, input_len, padding, iv, iv_len, output, output_len, ret_len, flags ); + LeaveCriticalSection( &key->u.s.cs ); } - if (flags & ~BCRYPT_BLOCK_PADDING) + else { - FIXME( "flags %#lx not implemented\n", flags ); - return STATUS_NOT_IMPLEMENTED; + if (flags & BCRYPT_PAD_NONE || flags & BCRYPT_PAD_OAEP) + { + FIXME( "flags %#lx not implemented\n", flags ); + return STATUS_NOT_IMPLEMENTED; + } + asymmetric_params.input = input; + asymmetric_params.input_len = input_len; + asymmetric_params.key = key; + asymmetric_params.output = output; + asymmetric_params.output_len = output_len; + asymmetric_params.ret_len = ret_len; + ret = UNIX_CALL(key_asymmetric_encrypt, &asymmetric_params); }
- EnterCriticalSection( &key->u.s.cs ); - ret = key_symmetric_encrypt( key, input, input_len, padding, iv, iv_len, output, output_len, ret_len, flags ); - LeaveCriticalSection( &key->u.s.cs ); return ret; }
diff --git a/dlls/bcrypt/gnutls.c b/dlls/bcrypt/gnutls.c index b38bf4ba8ff..70ad62a0b0d 100644 --- a/dlls/bcrypt/gnutls.c +++ b/dlls/bcrypt/gnutls.c @@ -97,6 +97,8 @@ static int (*pgnutls_privkey_import_ecc_raw)(gnutls_privkey_t, gnutls_ecc_curve_ const gnutls_datum_t *, const gnutls_datum_t *); static int (*pgnutls_pubkey_verify_hash2)(gnutls_pubkey_t, gnutls_sign_algorithm_t, unsigned int, const gnutls_datum_t *, const gnutls_datum_t *); +static int (*pgnutls_pubkey_encrypt_data)(gnutls_pubkey_t, unsigned int flags, const gnutls_datum_t *, + gnutls_datum_t *);
/* Not present in gnutls version < 2.11.0 */ static int (*pgnutls_pubkey_import_rsa_raw)(gnutls_pubkey_t, const gnutls_datum_t *, const gnutls_datum_t *); @@ -105,6 +107,8 @@ static int (*pgnutls_pubkey_import_rsa_raw)(gnutls_pubkey_t, const gnutls_datum_ static int (*pgnutls_pubkey_import_dsa_raw)(gnutls_pubkey_t, const gnutls_datum_t *, const gnutls_datum_t *, const gnutls_datum_t *, const gnutls_datum_t *); static int (*pgnutls_pubkey_import_privkey)(gnutls_pubkey_t, gnutls_privkey_t, unsigned int, unsigned int); +static int (*pgnutls_privkey_decrypt_data)(gnutls_privkey_t, unsigned int flags, const gnutls_datum_t *, + gnutls_datum_t *);
/* Not present in gnutls version < 3.3.0 */ static int (*pgnutls_pubkey_export_dsa_raw)(gnutls_pubkey_t, gnutls_datum_t *, gnutls_datum_t *, gnutls_datum_t *, @@ -121,7 +125,6 @@ static int (*pgnutls_privkey_generate)(gnutls_privkey_t, gnutls_pk_algorithm_t, static int (*pgnutls_privkey_import_rsa_raw)(gnutls_privkey_t, const gnutls_datum_t *, const gnutls_datum_t *, const gnutls_datum_t *, const gnutls_datum_t *, const gnutls_datum_t *, const gnutls_datum_t *, const gnutls_datum_t *, const gnutls_datum_t *); -static int (*pgnutls_privkey_decrypt_data)(gnutls_privkey_t, unsigned int flags, const gnutls_datum_t *, gnutls_datum_t *);
/* Not present in gnutls version < 3.6.0 */ static int (*pgnutls_decode_rs_value)(const gnutls_datum_t *, gnutls_datum_t *, gnutls_datum_t *); @@ -143,6 +146,7 @@ MAKE_FUNCPTR(gnutls_privkey_import_dsa_raw); MAKE_FUNCPTR(gnutls_privkey_init); MAKE_FUNCPTR(gnutls_privkey_sign_hash); MAKE_FUNCPTR(gnutls_pubkey_deinit); +MAKE_FUNCPTR(gnutls_pubkey_encrypt_data); MAKE_FUNCPTR(gnutls_pubkey_import_privkey); MAKE_FUNCPTR(gnutls_pubkey_init); #undef MAKE_FUNCPTR @@ -253,6 +257,12 @@ static int compat_gnutls_privkey_decrypt_data(gnutls_privkey_t key, unsigned int return GNUTLS_E_UNKNOWN_PK_ALGORITHM; }
+static int compat_gnutls_pubkey_encrypt_data(gnutls_pubkey_t key, unsigned int flags, const gnutls_datum_t *cipher_text, + gnutls_datum_t *plain_text) +{ + return GNUTLS_E_UNKNOWN_PK_ALGORITHM; +} + static void gnutls_log( int level, const char *msg ) { TRACE( "<%d> %s", level, msg ); @@ -329,6 +339,7 @@ static NTSTATUS gnutls_process_attach( void *args ) LOAD_FUNCPTR_OPT(gnutls_decode_rs_value) LOAD_FUNCPTR_OPT(gnutls_privkey_import_rsa_raw) LOAD_FUNCPTR_OPT(gnutls_privkey_decrypt_data) + LOAD_FUNCPTR_OPT(gnutls_pubkey_encrypt_data) #undef LOAD_FUNCPTR_OPT
if ((ret = pgnutls_global_init()) != GNUTLS_E_SUCCESS) @@ -1927,6 +1938,30 @@ static NTSTATUS key_asymmetric_decrypt( void *args ) return status; }
+static NTSTATUS key_asymmetric_encrypt( void *args ) +{ + const struct key_asymmetric_encrypt_params *params = args; + gnutls_datum_t d, e = { 0 }; + NTSTATUS status = STATUS_SUCCESS; + int ret; + + d.data = params->input; + d.size = params->input_len; + if ((ret = pgnutls_pubkey_encrypt_data(key_data(params->key)->a.pubkey, 0, &d, &e))) + { + pgnutls_perror( ret ); + return STATUS_INTERNAL_ERROR; + } + + *params->ret_len = e.size; + if (params->output_len >= e.size) memcpy( params->output, e.data, *params->ret_len ); + else if (params->output_len == 0) status = STATUS_SUCCESS; + else status = STATUS_BUFFER_TOO_SMALL; + + free( e.data ); + return status; +} + const unixlib_entry_t __wine_unix_call_funcs[] = { gnutls_process_attach, @@ -1939,6 +1974,7 @@ const unixlib_entry_t __wine_unix_call_funcs[] = key_symmetric_destroy, key_asymmetric_generate, key_asymmetric_decrypt, + key_asymmetric_encrypt, key_asymmetric_duplicate, key_asymmetric_sign, key_asymmetric_verify, @@ -2188,6 +2224,36 @@ static NTSTATUS wow64_key_asymmetric_decrypt( void *args ) return ret; }
+static NTSTATUS wow64_key_asymmetric_encrypt( void *args ) +{ + struct + { + PTR32 key; + PTR32 input; + ULONG input_len; + PTR32 output; + ULONG output_len; + PTR32 ret_len; + } const *params32 = args; + + NTSTATUS ret; + struct key key; + struct key32 *key32 = ULongToPtr( params32->key ); + struct key_asymmetric_encrypt_params params = + { + get_asymmetric_key( key32, &key ), + ULongToPtr(params32->input), + params32->input_len, + ULongToPtr(params32->output), + params32->output_len, + ULongToPtr(params32->ret_len) + }; + + ret = key_asymmetric_encrypt( ¶ms ); + put_asymmetric_key32( &key, key32 ); + return ret; +} + static NTSTATUS wow64_key_asymmetric_duplicate( void *args ) { struct @@ -2369,6 +2435,7 @@ const unixlib_entry_t __wine_unix_call_wow64_funcs[] = wow64_key_symmetric_destroy, wow64_key_asymmetric_generate, wow64_key_asymmetric_decrypt, + wow64_key_asymmetric_encrypt, wow64_key_asymmetric_duplicate, wow64_key_asymmetric_sign, wow64_key_asymmetric_verify, diff --git a/dlls/bcrypt/tests/bcrypt.c b/dlls/bcrypt/tests/bcrypt.c index fca7ae4e1ed..5d7ad5d3e0a 100644 --- a/dlls/bcrypt/tests/bcrypt.c +++ b/dlls/bcrypt/tests/bcrypt.c @@ -2075,6 +2075,7 @@ static void test_rsa_encrypt(void) BCryptDecrypt(key, encrypted_a, encrypted_size, NULL, NULL, 0, decrypted, decrypted_size, &decrypted_size, BCRYPT_PAD_NONE); ok(!memcmp(decrypted, input_no_padding, sizeof(input_no_padding)), "Decrypted output it's not what expected\n"); free(decrypted); + }
encrypted_size = 60; /* PKCS1 Padding */ @@ -2093,6 +2094,7 @@ static void test_rsa_encrypt(void) ok(ret == STATUS_SUCCESS, "got %lx\n", ret); ok(memcmp(encrypted_a, encrypted_b, encrypted_size), "Both outputs are the same\n");
+ todo_wine { BCryptDecrypt(key, encrypted_a, encrypted_size, NULL, NULL, 0, NULL, 0, &decrypted_size, BCRYPT_PAD_PKCS1); decrypted = malloc(decrypted_size); BCryptDecrypt(key, encrypted_a, encrypted_size, NULL, NULL, 0, decrypted, decrypted_size, &decrypted_size, BCRYPT_PAD_PKCS1);
From: Santino Mazza mazzasantino1206@gmail.com
Signed-off-by: Santino Mazza mazzasantino1206@gmail.com --- dlls/ncrypt/main.c | 24 ++++++++++++++++++++++-- dlls/ncrypt/tests/ncrypt.c | 6 ++++-- 2 files changed, 26 insertions(+), 4 deletions(-)
diff --git a/dlls/ncrypt/main.c b/dlls/ncrypt/main.c index 58503338d6e..9f859acfdf9 100644 --- a/dlls/ncrypt/main.c +++ b/dlls/ncrypt/main.c @@ -43,6 +43,7 @@ static SECURITY_STATUS map_ntstatus(NTSTATUS status) case STATUS_NO_MEMORY: return NTE_NO_MEMORY; case STATUS_NOT_SUPPORTED: return NTE_NOT_SUPPORTED; case NTE_BAD_DATA: return NTE_BAD_DATA; + case STATUS_BUFFER_TOO_SMALL: return NTE_BUFFER_TOO_SMALL; default: FIXME("unhandled status %#lx\n", status); return NTE_INTERNAL_ERROR; @@ -227,9 +228,28 @@ SECURITY_STATUS WINAPI NCryptDeleteKey(NCRYPT_KEY_HANDLE key, DWORD flags) SECURITY_STATUS WINAPI NCryptEncrypt(NCRYPT_KEY_HANDLE key, BYTE *input, DWORD insize, void *padding, BYTE *output, DWORD outsize, DWORD *result, DWORD flags) { - FIXME("(%#Ix, %p, %lu, %p, %p, %lu, %p, %#lx): stub\n", key, input, insize, padding, + struct object *key_object = (struct object *)key; + + TRACE("(%#Ix, %p, %lu, %p, %p, %lu, %p, %#lx)\n", key, input, insize, padding, output, outsize, result, flags); - return NTE_NOT_SUPPORTED; + + if (flags & ~(NCRYPT_NO_PADDING_FLAG | NCRYPT_PAD_OAEP_FLAG + | NCRYPT_PAD_PKCS1_FLAG | NCRYPT_SILENT_FLAG)) + { + FIXME("Flags %lx not supported\n", flags); + return NTE_BAD_FLAGS; + } + + if (flags & NCRYPT_NO_PADDING_FLAG || flags & NCRYPT_PAD_OAEP_FLAG) + { + FIXME("No padding and oaep padding not supported\n"); + return NTE_NOT_SUPPORTED; + } + + if (key_object->type != KEY) return NTE_INVALID_HANDLE; + + return map_ntstatus(BCryptEncrypt(key_object->key.bcrypt_key, input, insize, padding, + NULL, 0, output, outsize, result, flags)); }
SECURITY_STATUS WINAPI NCryptEnumAlgorithms(NCRYPT_PROV_HANDLE provider, DWORD alg_ops, diff --git a/dlls/ncrypt/tests/ncrypt.c b/dlls/ncrypt/tests/ncrypt.c index 81b737c9a21..bd2f63bea87 100644 --- a/dlls/ncrypt/tests/ncrypt.c +++ b/dlls/ncrypt/tests/ncrypt.c @@ -550,7 +550,6 @@ static void test_NCryptEncrypt(void) BYTE *output_b; DWORD output_size;
- todo_wine { NCryptOpenStorageProvider(&prov, NULL, 0); NCryptCreatePersistedKey(prov, &key, BCRYPT_RSA_ALGORITHM, NULL, 0, 0);
@@ -562,6 +561,7 @@ static void test_NCryptEncrypt(void) /* Test encrypt with a non finalized key */ ret = NCryptEncrypt(key, data_to_encrypt, sizeof(data_to_encrypt), NULL, NULL, 0, &output_size, NCRYPT_PAD_PKCS1_FLAG); + todo_wine ok(ret == NTE_BAD_KEY_STATE, "got %lx\n", ret);
NCryptFinalizeKey(key, 0); @@ -572,6 +572,8 @@ static void test_NCryptEncrypt(void) ok(ret == NTE_BAD_FLAGS, "got %lx\n", ret);
/* Test no padding with RSA */ + todo_wine + { ret = NCryptEncrypt(key, data_to_encrypt, sizeof(data_to_encrypt), NULL, NULL, 0, &output_size, NCRYPT_NO_PADDING_FLAG); ok(ret == ERROR_SUCCESS, "got %lx\n", ret); @@ -582,6 +584,7 @@ static void test_NCryptEncrypt(void) &output_size, NCRYPT_NO_PADDING_FLAG); ok(ret == NTE_INVALID_PARAMETER, "got %lx\n", ret); free(output_a); + }
/* Test output RSA with PKCS1. PKCS1 should append a random padding to the data, so the output should be different * with each call. */ @@ -611,7 +614,6 @@ static void test_NCryptEncrypt(void) free(output_b);
NCryptFreeObject(prov); - } }
START_TEST(ncrypt)
This merge request was approved by Hans Leidekker.