diff --git a/.github/workflows/cryptocb-only.yml b/.github/workflows/cryptocb-only.yml index 52d00a4642a..0bbe6286f17 100644 --- a/.github/workflows/cryptocb-only.yml +++ b/.github/workflows/cryptocb-only.yml @@ -111,9 +111,12 @@ jobs: {"name": "ed25519-no-curve25519", "comment": "Same as ed25519 but with curve25519 off. curve25519 is the only other user of the ge/fe math, so without it the strip is complete and nothing must pull the math back in. The ed25519 entry above keeps curve25519 enabled, which leaves fe_operations.c compiled and would hide such a regression at link time.", "configure": ["--disable-curve25519", "CPPFLAGS=-DWOLF_CRYPTO_CB_ONLY_ED25519"]}, + {"name": "curve25519", + "comment": "WOLF_CRYPTO_CB_ONLY_CURVE25519: strips software X25519 (keygen/shared-secret); swdev provides the software path via cryptocb. Nonblock and async X25519 have no callback path and are left disabled.", + "configure": ["CPPFLAGS=-DWOLF_CRYPTO_CB_ONLY_CURVE25519"]}, {"name": "all", - "comment": "All six ONLY_* macros at once: every supported software primitive is stripped and dispatched through cryptocb. Catches any cross-algorithm call that a single-strip entry would still resolve via the remaining software paths.", - "configure": ["CPPFLAGS=-DWOLF_CRYPTO_CB_ONLY_ECC -DWOLF_CRYPTO_CB_ONLY_RSA -DWOLF_CRYPTO_CB_ONLY_SHA256 -DWOLF_CRYPTO_CB_ONLY_SHA512 -DWOLF_CRYPTO_CB_ONLY_AES -DWOLF_CRYPTO_CB_ONLY_ED25519"]} + "comment": "All seven ONLY_* macros at once: every supported software primitive is stripped and dispatched through cryptocb. Catches any cross-algorithm call that a single-strip entry would still resolve via the remaining software paths.", + "configure": ["CPPFLAGS=-DWOLF_CRYPTO_CB_ONLY_ECC -DWOLF_CRYPTO_CB_ONLY_RSA -DWOLF_CRYPTO_CB_ONLY_SHA256 -DWOLF_CRYPTO_CB_ONLY_SHA512 -DWOLF_CRYPTO_CB_ONLY_AES -DWOLF_CRYPTO_CB_ONLY_ED25519 -DWOLF_CRYPTO_CB_ONLY_CURVE25519"]} ]} EOF .github/scripts/parallel-make-check.py \ diff --git a/tests/api.c b/tests/api.c index f37573e6d5f..9746396d32e 100644 --- a/tests/api.c +++ b/tests/api.c @@ -30160,7 +30160,8 @@ static int test_SSL_CIPHER_get_current_kx(void) (!defined(WOLF_CRYPTO_CB_ONLY_SHA256) && !defined(WOLF_CRYPTO_CB_ONLY_AES) && \ !defined(WOLF_CRYPTO_CB_ONLY_ECC) && !defined(WOLF_CRYPTO_CB_ONLY_RSA) && \ !defined(WOLF_CRYPTO_CB_ONLY_SHA512) && \ - !defined(WOLF_CRYPTO_CB_ONLY_ED25519)) + !defined(WOLF_CRYPTO_CB_ONLY_ED25519) && \ + !defined(WOLF_CRYPTO_CB_ONLY_CURVE25519)) static int load_pem_key_file_as_der(const char* privKeyFile, DerBuffer** pDer, int* keyFormat) @@ -31265,7 +31266,8 @@ static int test_wc_CryptoCb(void) (!defined(WOLF_CRYPTO_CB_ONLY_SHA256) && !defined(WOLF_CRYPTO_CB_ONLY_AES) && \ !defined(WOLF_CRYPTO_CB_ONLY_ECC) && !defined(WOLF_CRYPTO_CB_ONLY_RSA) && \ !defined(WOLF_CRYPTO_CB_ONLY_SHA512) && \ - !defined(WOLF_CRYPTO_CB_ONLY_ED25519)) + !defined(WOLF_CRYPTO_CB_ONLY_ED25519) && \ + !defined(WOLF_CRYPTO_CB_ONLY_CURVE25519)) #if defined(HAVE_IO_TESTS_DEPENDENCIES) && \ (!defined(NO_RSA) || defined(HAVE_ECC) || defined(HAVE_ED25519)) int tlsVer; @@ -37640,15 +37642,13 @@ TEST_CASE testCases[] = { /* Can't memory test as client/server Asserts in thread. */ TEST_DECL(test_prioritize_psk), - /* test_wc_CryptoCb_registry is defined only inside the - * WOLF_CRYPTO_CB + HAVE_IO_TESTS_DEPENDENCIES block below; register it under - * the same condition so it is neither undeclared (when absent) nor - * defined-but-unused. */ + /* Must match the guard on the definition of test_wc_CryptoCb_registry. */ #if defined(WOLF_CRYPTO_CB) && defined(HAVE_IO_TESTS_DEPENDENCIES) && \ (!defined(WOLF_CRYPTO_CB_ONLY_SHA256) && !defined(WOLF_CRYPTO_CB_ONLY_AES) && \ !defined(WOLF_CRYPTO_CB_ONLY_ECC) && !defined(WOLF_CRYPTO_CB_ONLY_RSA) && \ !defined(WOLF_CRYPTO_CB_ONLY_SHA512) && \ - !defined(WOLF_CRYPTO_CB_ONLY_ED25519)) + !defined(WOLF_CRYPTO_CB_ONLY_ED25519) && \ + !defined(WOLF_CRYPTO_CB_ONLY_CURVE25519)) /* Can't memory test as client/server hangs. */ TEST_DECL(test_wc_CryptoCb_registry), #endif diff --git a/tests/swdev/README.md b/tests/swdev/README.md index 0cf5ce2fded..1d62208a57c 100644 --- a/tests/swdev/README.md +++ b/tests/swdev/README.md @@ -16,6 +16,7 @@ The switches it supports are: | `WOLF_CRYPTO_CB_ONLY_SHA512` | software SHA-512 | SHA-512 via CryptoCb | | `WOLF_CRYPTO_CB_ONLY_AES` | software AES | AES via CryptoCb | | `WOLF_CRYPTO_CB_ONLY_ED25519` | software Ed25519 | Ed25519 via CryptoCb | +| `WOLF_CRYPTO_CB_ONLY_CURVE25519` | software X25519 | X25519 via CryptoCb | When a test program calls e.g. `wc_AesCbcEncrypt()` against a libwolfssl built with `-DWOLF_CRYPTO_CB_ONLY_AES`, the software AES path is gone; @@ -57,7 +58,7 @@ internal copy of the AES code, and returns the result. | wc_SwDev_Callback(devId, info, ctx) | | - swdev_ensure_init() lazy wolfCrypt_Init | | - switch (info->algo_type): | - | PK -> RSA / ECC / Ed25519 software impl | + | PK -> RSA/ECC/Ed25519/X25519 software impl | | HASH -> SHA-256 software impl | | CIPHER -> AES (CBC/CTR/ECB/GCM/CCM) software impl | | | @@ -72,7 +73,8 @@ internal copy of the AES code, and returns the result. The whole mechanism rests on compiling the wolfcrypt sources twice: 1. **libwolfssl** is built normally with the user's `_ONLY_*` flags - set, so its software RSA/ECC/SHA-256/SHA-512/AES/Ed25519 paths are gone. + set, so its software RSA/ECC/SHA-256/SHA-512/AES/Ed25519/X25519 paths + are gone. 2. **swdev** recompiles the same source set under `tests/swdev/user_settings.h`, which `#undef`s every `_ONLY_*` macro. swdev therefore contains the full software implementations. diff --git a/tests/swdev/swdev.c b/tests/swdev/swdev.c index 3b69a74cba9..ae612d5456f 100644 --- a/tests/swdev/swdev.c +++ b/tests/swdev/swdev.c @@ -43,6 +43,9 @@ #ifdef HAVE_ED25519 #include #endif +#ifdef HAVE_CURVE25519 +#include +#endif static int swdev_initialized = 0; @@ -318,6 +321,23 @@ static int swdev_ed25519_check_key(wc_CryptoInfo* info) } #endif /* HAVE_ED25519 */ +#ifdef HAVE_CURVE25519 +static int swdev_curve25519_keygen(wc_CryptoInfo* info) +{ + return wc_curve25519_make_key(info->pk.curve25519kg.rng, + info->pk.curve25519kg.size, info->pk.curve25519kg.key); +} + +#ifdef HAVE_CURVE25519_SHARED_SECRET +static int swdev_curve25519(wc_CryptoInfo* info) +{ + return wc_curve25519_shared_secret_ex(info->pk.curve25519.private_key, + info->pk.curve25519.public_key, info->pk.curve25519.out, + info->pk.curve25519.outlen, info->pk.curve25519.endian); +} +#endif /* HAVE_CURVE25519_SHARED_SECRET */ +#endif /* HAVE_CURVE25519 */ + #ifndef NO_SHA256 /* Copy hash state between caller's wc_Sha256 and swdev's shadow, leaving * admin fields (heap, devId, devCtx, W, async, HW ctx) per-side. */ @@ -913,7 +933,8 @@ WC_SWDEV_EXPORT int wc_SwDev_Callback(int devId, wc_CryptoInfo* info, return ret; switch (info->algo_type) { -#if !defined(NO_RSA) || defined(HAVE_ECC) || defined(HAVE_ED25519) +#if !defined(NO_RSA) || defined(HAVE_ECC) || defined(HAVE_ED25519) || \ + defined(HAVE_CURVE25519) case WC_ALGO_TYPE_PK: switch (info->pk.type) { #ifndef NO_RSA @@ -964,6 +985,14 @@ WC_SWDEV_EXPORT int wc_SwDev_Callback(int devId, wc_CryptoInfo* info, case WC_PK_TYPE_ED25519_CHECK_KEY: return swdev_ed25519_check_key(info); #endif /* HAVE_ED25519 */ + #ifdef HAVE_CURVE25519 + case WC_PK_TYPE_CURVE25519_KEYGEN: + return swdev_curve25519_keygen(info); + #ifdef HAVE_CURVE25519_SHARED_SECRET + case WC_PK_TYPE_CURVE25519: + return swdev_curve25519(info); + #endif + #endif /* HAVE_CURVE25519 */ default: return CRYPTOCB_UNAVAILABLE; } diff --git a/tests/swdev/user_settings.h b/tests/swdev/user_settings.h index 46076d50070..ca23306d442 100644 --- a/tests/swdev/user_settings.h +++ b/tests/swdev/user_settings.h @@ -28,6 +28,7 @@ #undef WOLF_CRYPTO_CB_ONLY_SHA512 #undef WOLF_CRYPTO_CB_ONLY_AES #undef WOLF_CRYPTO_CB_ONLY_ED25519 +#undef WOLF_CRYPTO_CB_ONLY_CURVE25519 #ifndef WOLF_CRYPTO_CB #error "wc_swdev requires the main build to define WOLF_CRYPTO_CB" diff --git a/wolfcrypt/src/cryptocb.c b/wolfcrypt/src/cryptocb.c index be5eccb0139..cb155e0c1e9 100644 --- a/wolfcrypt/src/cryptocb.c +++ b/wolfcrypt/src/cryptocb.c @@ -65,6 +65,7 @@ Crypto Callback Build Options: * WOLF_CRYPTO_CB_ONLY_SHA512: Use only callbacks for SHA-512 default: off * WOLF_CRYPTO_CB_ONLY_AES: Use only callbacks for AES default: off * WOLF_CRYPTO_CB_ONLY_ED25519: Use only callbacks for Ed25519 default: off + * WOLF_CRYPTO_CB_ONLY_CURVE25519: Use only callbacks for X25519 default: off */ #include diff --git a/wolfcrypt/src/curve25519.c b/wolfcrypt/src/curve25519.c index 8e7afec5400..8285f31f936 100644 --- a/wolfcrypt/src/curve25519.c +++ b/wolfcrypt/src/curve25519.c @@ -563,7 +563,10 @@ int wc_curve25519_make_key(WC_RNG* rng, int keysize, curve25519_key* key) return BAD_FUNC_ARG; #ifdef WOLF_CRYPTO_CB - if (key->devId != INVALID_DEVID) { + #ifndef WOLF_CRYPTO_CB_FIND + if (key->devId != INVALID_DEVID) + #endif + { ret = wc_CryptoCb_Curve25519Gen(rng, keysize, key); if (ret != WC_NO_ERR_TRACE(CRYPTOCB_UNAVAILABLE)) return ret; @@ -571,6 +574,10 @@ int wc_curve25519_make_key(WC_RNG* rng, int keysize, curve25519_key* key) } #endif +#ifdef WOLF_CRYPTO_CB_ONLY_CURVE25519 + /* software path stripped; callback is the only provider */ + return NO_VALID_DEVID; +#else #if defined(WOLFSSL_ASYNC_CRYPT) && defined(WC_ASYNC_ENABLE_X25519) && \ defined(WOLFSSL_ASYNC_CRYPT_SW) if (key->asyncDev.marker == WOLFSSL_ASYNC_MARKER_X25519) { @@ -614,6 +621,7 @@ int wc_curve25519_make_key(WC_RNG* rng, int keysize, curve25519_key* key) #endif /* !WOLFSSL_SE050 */ return ret; +#endif /* WOLF_CRYPTO_CB_ONLY_CURVE25519 */ } #ifdef HAVE_CURVE25519_SHARED_SECRET @@ -720,7 +728,10 @@ int wc_curve25519_shared_secret_ex(curve25519_key* private_key, #endif #ifdef WOLF_CRYPTO_CB - if (private_key->devId != INVALID_DEVID) { + #ifndef WOLF_CRYPTO_CB_FIND + if (private_key->devId != INVALID_DEVID) + #endif + { ret = wc_CryptoCb_Curve25519(private_key, public_key, out, outlen, endian); if (ret != WC_NO_ERR_TRACE(CRYPTOCB_UNAVAILABLE)) @@ -729,6 +740,10 @@ int wc_curve25519_shared_secret_ex(curve25519_key* private_key, } #endif +#ifdef WOLF_CRYPTO_CB_ONLY_CURVE25519 + /* software path stripped; callback is the only provider */ + return NO_VALID_DEVID; +#else #ifdef WC_X25519_NONBLOCK #if defined(WOLFSSL_ASYNC_CRYPT) && defined(WC_ASYNC_ENABLE_X25519) && \ @@ -814,6 +829,7 @@ int wc_curve25519_shared_secret_ex(curve25519_key* private_key, } return ret; +#endif /* WOLF_CRYPTO_CB_ONLY_CURVE25519 */ } #endif /* HAVE_CURVE25519_SHARED_SECRET */ diff --git a/wolfcrypt/test/test.c b/wolfcrypt/test/test.c index 52a6137c33d..84ee1beb122 100644 --- a/wolfcrypt/test/test.c +++ b/wolfcrypt/test/test.c @@ -3157,7 +3157,8 @@ options: [-s max_relative_stack_bytes] [-m max_relative_heap_memory_bytes]\n\ TEST_PASS("FLATTEN ALT NAMES test passed!\n"); #endif -#ifdef HAVE_CURVE25519 +#if defined(HAVE_CURVE25519) && \ + (!defined(WOLF_CRYPTO_CB_ONLY_CURVE25519) || defined(WOLFSSL_SWDEV)) if ( (ret = curve25519_test()) != 0) TEST_FAIL("CURVE25519 test failed!\n", ret); else @@ -76148,6 +76149,88 @@ static wc_test_ret_t ed25519_onlycb_test(myCryptoDevCtx *ctx) } #endif /* WOLF_CRYPTO_CB_ONLY_ED25519 */ +#ifdef WOLF_CRYPTO_CB_ONLY_CURVE25519 +/* Exercise Curve25519 dispatch under CB_ONLY_CURVE25519: cb-handled then + * cb-delegated. */ +static wc_test_ret_t curve25519_onlycb_test(myCryptoDevCtx *ctx) +{ + wc_test_ret_t ret = 0; + curve25519_key key; +#if defined(HAVE_CURVE25519_SHARED_SECRET) && \ + defined(HAVE_CURVE25519_KEY_IMPORT) + curve25519_key pubKey; + const byte priv[CURVE25519_KEYSIZE] = {1}; + const byte pub[CURVE25519_KEYSIZE] = {9}; + byte out[CURVE25519_KEYSIZE]; + word32 outLen = (word32)sizeof(out); +#endif + WC_RNG rng; + + ret = wc_curve25519_init_ex(&key, HEAP_HINT, devId); + if (ret != 0) + return WC_TEST_RET_ENC_EC(ret); + + ret = wc_InitRng(&rng); + if (ret != 0) { + wc_curve25519_free(&key); + return WC_TEST_RET_ENC_EC(ret); + } + + /* cb handles the op, expects 0(success) */ + ctx->exampleVar = 99; + ret = wc_curve25519_make_key(&rng, CURVE25519_KEYSIZE, &key); + if (ret != 0) + ERROR_OUT(WC_TEST_RET_ENC_EC(ret), exit_onlycb); + + /* cb delegates to software, expects NO_VALID_DEVID(failure) */ + ctx->exampleVar = 1; + ret = wc_curve25519_make_key(&rng, CURVE25519_KEYSIZE, &key); + if (ret != WC_NO_ERR_TRACE(NO_VALID_DEVID)) { + ERROR_OUT(WC_TEST_RET_ENC_EC(ret), exit_onlycb); + } else { + ret = 0; + } + +#if defined(HAVE_CURVE25519_SHARED_SECRET) && \ + defined(HAVE_CURVE25519_KEY_IMPORT) + ret = wc_curve25519_init_ex(&pubKey, HEAP_HINT, devId); + if (ret != 0) + ERROR_OUT(WC_TEST_RET_ENC_EC(ret), exit_onlycb); + + ret = wc_curve25519_import_private(priv, sizeof(priv), &key); + if (ret != 0) + ERROR_OUT(WC_TEST_RET_ENC_EC(ret), exit_onlycb_pub); + ret = wc_curve25519_import_public(pub, sizeof(pub), &pubKey); + if (ret != 0) + ERROR_OUT(WC_TEST_RET_ENC_EC(ret), exit_onlycb_pub); + + /* cb handles the op, expects 0(success) */ + ctx->exampleVar = 99; + ret = wc_curve25519_shared_secret(&key, &pubKey, out, &outLen); + if (ret != 0) + ERROR_OUT(WC_TEST_RET_ENC_EC(ret), exit_onlycb_pub); + + /* cb delegates to software, expects NO_VALID_DEVID(failure) */ + ctx->exampleVar = 1; + ret = wc_curve25519_shared_secret(&key, &pubKey, out, &outLen); + if (ret != WC_NO_ERR_TRACE(NO_VALID_DEVID)) { + ERROR_OUT(WC_TEST_RET_ENC_EC(ret), exit_onlycb_pub); + } else { + ret = 0; + } + +exit_onlycb_pub: + wc_curve25519_free(&pubKey); +#endif /* HAVE_CURVE25519_SHARED_SECRET && HAVE_CURVE25519_KEY_IMPORT */ + +exit_onlycb: + wc_FreeRng(&rng); + wc_curve25519_free(&key); + (void)ctx; + return ret; +} +#endif /* WOLF_CRYPTO_CB_ONLY_CURVE25519 */ + #if defined(HAVE_ECC) && !defined(WOLFSSL_NO_MALLOC) && \ defined(HAVE_ECC_KEY_EXPORT) /* Serialize pub to X9.63 uncompressed (0x04 || X || Y) using the curve size @@ -76543,6 +76626,15 @@ static int myCryptoDevCb(int devIdArg, wc_CryptoInfo* info, void* ctx) if (info->pk.type == WC_PK_TYPE_CURVE25519_KEYGEN) { /* set devId to invalid, so software is used */ info->pk.curve25519kg.key->devId = INVALID_DEVID; + #if defined(WOLF_CRYPTO_CB_ONLY_CURVE25519) + #ifdef DEBUG_WOLFSSL + printf("CryptoDevCb: exampleVar %d\n", myCtx->exampleVar); + #endif + if (myCtx->exampleVar == 99) { + info->pk.curve25519kg.key->devId = devIdArg; + return 0; + } + #endif ret = wc_curve25519_make_key(info->pk.curve25519kg.rng, info->pk.curve25519kg.size, info->pk.curve25519kg.key); @@ -76553,6 +76645,15 @@ static int myCryptoDevCb(int devIdArg, wc_CryptoInfo* info, void* ctx) else if (info->pk.type == WC_PK_TYPE_CURVE25519) { /* set devId to invalid, so software is used */ info->pk.curve25519.private_key->devId = INVALID_DEVID; + #if defined(WOLF_CRYPTO_CB_ONLY_CURVE25519) + #ifdef DEBUG_WOLFSSL + printf("CryptoDevCb: exampleVar %d\n", myCtx->exampleVar); + #endif + if (myCtx->exampleVar == 99) { + info->pk.curve25519.private_key->devId = devIdArg; + return 0; + } + #endif ret = wc_curve25519_shared_secret_ex( info->pk.curve25519.private_key, info->pk.curve25519.public_key, @@ -78860,10 +78961,17 @@ WOLFSSL_TEST_SUBROUTINE wc_test_ret_t cryptocb_test(void) ret = ed25519_onlycb_test(&myCtx); PRIVATE_KEY_LOCK(); #endif -#ifdef HAVE_CURVE25519 +#if defined(HAVE_CURVE25519) && \ + (!defined(WOLF_CRYPTO_CB_ONLY_CURVE25519) || defined(WOLFSSL_SWDEV)) if (ret == 0) ret = curve25519_test(); #endif +#if defined(WOLF_CRYPTO_CB_ONLY_CURVE25519) && !defined(WOLFSSL_SWDEV) + PRIVATE_KEY_UNLOCK(); + if (ret == 0) + ret = curve25519_onlycb_test(&myCtx); + PRIVATE_KEY_LOCK(); +#endif #if !defined(NO_AES) && !defined(WOLF_CRYPTO_CB_ONLY_AES) /* CB_ONLY_AES skips these (aes_onlycb_test covers that path). */ #ifdef HAVE_AESGCM diff --git a/wolfssl/wolfcrypt/fe_operations.h b/wolfssl/wolfcrypt/fe_operations.h index 07ae3bdb8dc..bfac7c04f92 100644 --- a/wolfssl/wolfcrypt/fe_operations.h +++ b/wolfssl/wolfcrypt/fe_operations.h @@ -63,14 +63,15 @@ #define CURVED25519_ASM #endif -/* curve25519 shares the ed25519 field math, and borrows the group math - * on some builds. - * For WOLF_CRYPTO_CB_ONLY_ED25519 to strip the fe/ge modules, ensure that - * curve25519 is disabled. */ +/* curve25519 always uses its own field math, but on some builds it borrows + * ed25519's group math via WOLFSSL_CURVE25519_USE_ED25519 below. Under + * WOLF_CRYPTO_CB_ONLY_ED25519 ed25519's group math is removed. */ #if (defined(CURVED25519_ASM_64BIT) || defined(HAVE_ED25519)) && \ !defined(WOLFSSL_CURVE25519_BLINDING) && \ !defined(WOLFSSL_CURVE25519_NOT_USE_ED25519) && \ - (!defined(WOLF_CRYPTO_CB_ONLY_ED25519) || defined(HAVE_CURVE25519)) + (!defined(WOLF_CRYPTO_CB_ONLY_ED25519) || \ + (defined(HAVE_CURVE25519) && \ + !defined(WOLF_CRYPTO_CB_ONLY_CURVE25519))) #undef WOLFSSL_CURVE25519_USE_ED25519 #define WOLFSSL_CURVE25519_USE_ED25519 #endif diff --git a/wolfssl/wolfcrypt/settings.h b/wolfssl/wolfcrypt/settings.h index da911e6508d..b9a7ace1824 100644 --- a/wolfssl/wolfcrypt/settings.h +++ b/wolfssl/wolfcrypt/settings.h @@ -5736,6 +5736,27 @@ blinding by defining WC_BLINDING_NO_RNG_ACKNOWLEDGE_WEAKNESS." #error "WOLF_CRYPTO_CB_ONLY_ED25519 with " \ "WOLFSSL_ED25519_STREAMING_VERIFY is not supported" #endif +#if defined(WOLF_CRYPTO_CB_ONLY_CURVE25519) && !defined(WOLF_CRYPTO_CB) + #error "WOLF_CRYPTO_CB_ONLY_CURVE25519 requires WOLF_CRYPTO_CB" +#endif +#if defined(WOLF_CRYPTO_CB_ONLY_CURVE25519) && !defined(HAVE_CURVE25519) + #error "WOLF_CRYPTO_CB_ONLY_CURVE25519 requires HAVE_CURVE25519" +#endif +#if defined(WOLF_CRYPTO_CB_ONLY_CURVE25519) && defined(WOLFSSL_SE050) + #error "WOLF_CRYPTO_CB_ONLY_CURVE25519 is incompatible with WOLFSSL_SE050" +#endif +#if defined(WOLF_CRYPTO_CB_ONLY_CURVE25519) && defined(FREESCALE_LTC_ECC) + #error "WOLF_CRYPTO_CB_ONLY_CURVE25519 is incompatible with " \ + "FREESCALE_LTC_ECC" +#endif +#if defined(WOLF_CRYPTO_CB_ONLY_CURVE25519) && defined(WC_X25519_NONBLOCK) + #error "WOLF_CRYPTO_CB_ONLY_CURVE25519 is incompatible with " \ + "WC_X25519_NONBLOCK" +#endif +#if defined(WOLF_CRYPTO_CB_ONLY_CURVE25519) && defined(WOLFSSL_ASYNC_CRYPT) + #error "WOLF_CRYPTO_CB_ONLY_CURVE25519 is incompatible with " \ + "WOLFSSL_ASYNC_CRYPT" +#endif /* Early Data / Session Rules */ #if !defined(WOLFCRYPT_ONLY) && defined(WOLFSSL_EARLY_DATA) && \