mirror of
https://github.com/wolfSSL/wolfssl.git
synced 2025-07-30 10:47:28 +02:00
Merge pull request #6242 from julek-wolfssl/harden-tls
Implement TLS recommendations from RFC 9325
This commit is contained in:
1
.github/workflows/os-check.yml
vendored
1
.github/workflows/os-check.yml
vendored
@ -14,6 +14,7 @@ jobs:
|
|||||||
'',
|
'',
|
||||||
'--enable-all --enable-asn=template',
|
'--enable-all --enable-asn=template',
|
||||||
'--enable-all --enable-asn=original',
|
'--enable-all --enable-asn=original',
|
||||||
|
'--enable-harden-tls',
|
||||||
]
|
]
|
||||||
name: make check
|
name: make check
|
||||||
runs-on: ${{ matrix.os }}
|
runs-on: ${{ matrix.os }}
|
||||||
|
22
configure.ac
22
configure.ac
@ -177,6 +177,26 @@ AS_IF([test "$ax_enable_debug" = "yes"],
|
|||||||
# enabled
|
# enabled
|
||||||
ENABLED_CERTS="no"
|
ENABLED_CERTS="no"
|
||||||
|
|
||||||
|
# Implements requirements from RFC9325
|
||||||
|
AC_ARG_ENABLE([harden-tls],
|
||||||
|
[AS_HELP_STRING([--enable-harden-tls],[Enable requirements from RFC9325. Possible values are <yes>, <112>, or <128>. <yes> is equivalent to <112>. (default: disabled)])],
|
||||||
|
[ ENABLED_HARDEN_TLS=$enableval ],
|
||||||
|
[ ENABLED_HARDEN_TLS=no ]
|
||||||
|
)
|
||||||
|
|
||||||
|
if test "x$ENABLED_HARDEN_TLS" != "xno"
|
||||||
|
then
|
||||||
|
if test "x$ENABLED_HARDEN_TLS" == "xyes" || test "x$ENABLED_HARDEN_TLS" == "x112"
|
||||||
|
then
|
||||||
|
AM_CFLAGS="$AM_CFLAGS -DWOLFSSL_HARDEN_TLS=112"
|
||||||
|
elif test "x$ENABLED_HARDEN_TLS" == "x128"
|
||||||
|
then
|
||||||
|
AM_CFLAGS="$AM_CFLAGS -DWOLFSSL_HARDEN_TLS=128"
|
||||||
|
else
|
||||||
|
AC_MSG_ERROR([Invalid value for --enable-harden-tls])
|
||||||
|
fi
|
||||||
|
AM_CFLAGS="$AM_CFLAGS -DWOLFSSL_EXTRA_ALERTS -DWOLFSSL_CHECK_ALERT_ON_ERR"
|
||||||
|
fi
|
||||||
|
|
||||||
# Support for forcing 32-bit mode
|
# Support for forcing 32-bit mode
|
||||||
# To force 32-bit instructions use:
|
# To force 32-bit instructions use:
|
||||||
@ -3481,7 +3501,7 @@ AC_ARG_ENABLE([oldtls],
|
|||||||
[ ENABLED_OLD_TLS=yes ]
|
[ ENABLED_OLD_TLS=yes ]
|
||||||
)
|
)
|
||||||
|
|
||||||
if test "$ENABLED_CRYPTONLY" = "yes"
|
if test "$ENABLED_CRYPTONLY" = "yes" || test "x$ENABLED_HARDEN_TLS" != "xno"
|
||||||
then
|
then
|
||||||
ENABLED_OLD_TLS=no
|
ENABLED_OLD_TLS=no
|
||||||
fi
|
fi
|
||||||
|
@ -79,6 +79,16 @@
|
|||||||
* by default.
|
* by default.
|
||||||
* https://www.rfc-editor.org/rfc/rfc8446#section-5.5
|
* https://www.rfc-editor.org/rfc/rfc8446#section-5.5
|
||||||
* https://www.rfc-editor.org/rfc/rfc9147.html#name-aead-limits
|
* https://www.rfc-editor.org/rfc/rfc9147.html#name-aead-limits
|
||||||
|
* WOLFSSL_HARDEN_TLS
|
||||||
|
* Implement the recommendations specified in RFC9325. This macro needs to
|
||||||
|
* be defined to the desired number of bits of security. The currently
|
||||||
|
* implemented values are 112 and 128 bits. The following macros disable
|
||||||
|
* certain checks.
|
||||||
|
* - WOLFSSL_HARDEN_TLS_ALLOW_TRUNCATED_HMAC
|
||||||
|
* - WOLFSSL_HARDEN_TLS_ALLOW_OLD_TLS
|
||||||
|
* - WOLFSSL_HARDEN_TLS_NO_SCR_CHECK
|
||||||
|
* - WOLFSSL_HARDEN_TLS_NO_PKEY_CHECK
|
||||||
|
* - WOLFSSL_HARDEN_TLS_ALLOW_ALL_CIPHERSUITES
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
|
||||||
@ -7128,11 +7138,14 @@ int InitSSL(WOLFSSL* ssl, WOLFSSL_CTX* ctx, int writeDup)
|
|||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifdef HAVE_SECURE_RENEGOTIATION
|
#if defined(HAVE_SECURE_RENEGOTIATION) || \
|
||||||
|
defined(HAVE_SERVER_RENEGOTIATION_INFO)
|
||||||
if (ssl->options.side == WOLFSSL_CLIENT_END) {
|
if (ssl->options.side == WOLFSSL_CLIENT_END) {
|
||||||
int useSecureReneg = ssl->ctx->useSecureReneg;
|
int useSecureReneg = ssl->ctx->useSecureReneg;
|
||||||
/* use secure renegotiation by default (not recommend) */
|
/* use secure renegotiation by default (not recommend) */
|
||||||
#ifdef WOLFSSL_SECURE_RENEGOTIATION_ON_BY_DEFAULT
|
#if defined(WOLFSSL_SECURE_RENEGOTIATION_ON_BY_DEFAULT) || \
|
||||||
|
(defined(WOLFSSL_HARDEN_TLS) && !defined(WOLFSSL_NO_TLS12) && \
|
||||||
|
!defined(WOLFSSL_HARDEN_TLS_NO_SCR_CHECK))
|
||||||
useSecureReneg = 1;
|
useSecureReneg = 1;
|
||||||
#endif
|
#endif
|
||||||
if (useSecureReneg) {
|
if (useSecureReneg) {
|
||||||
@ -26985,6 +26998,18 @@ static int HashSkeData(WOLFSSL* ssl, enum wc_HashType hashType,
|
|||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
#if defined(WOLFSSL_HARDEN_TLS) && !defined(WOLFSSL_HARDEN_TLS_NO_SCR_CHECK)
|
||||||
|
if (ssl->secure_renegotiation == NULL ||
|
||||||
|
!ssl->secure_renegotiation->enabled) {
|
||||||
|
/* If the server does not acknowledge the extension, the client
|
||||||
|
* MUST generate a fatal handshake_failure alert prior to
|
||||||
|
* terminating the connection.
|
||||||
|
* https://www.rfc-editor.org/rfc/rfc9325#name-renegotiation-in-tls-12 */
|
||||||
|
WOLFSSL_MSG("ServerHello did not contain SCR extension");
|
||||||
|
return SECURE_RENEGOTIATION_E;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
ssl->options.serverState = SERVER_HELLO_COMPLETE;
|
ssl->options.serverState = SERVER_HELLO_COMPLETE;
|
||||||
|
|
||||||
if (IsEncryptionOn(ssl, 0)) {
|
if (IsEncryptionOn(ssl, 0)) {
|
||||||
|
27
src/ssl.c
27
src/ssl.c
@ -13889,6 +13889,9 @@ int wolfSSL_DTLS_SetCookieSecret(WOLFSSL* ssl,
|
|||||||
|
|
||||||
case ACCEPT_FIRST_REPLY_DONE :
|
case ACCEPT_FIRST_REPLY_DONE :
|
||||||
if ( (ssl->error = SendServerHello(ssl)) != 0) {
|
if ( (ssl->error = SendServerHello(ssl)) != 0) {
|
||||||
|
#ifdef WOLFSSL_CHECK_ALERT_ON_ERR
|
||||||
|
ProcessReplyEx(ssl, 1); /* See if an alert was sent. */
|
||||||
|
#endif
|
||||||
WOLFSSL_ERROR(ssl->error);
|
WOLFSSL_ERROR(ssl->error);
|
||||||
return WOLFSSL_FATAL_ERROR;
|
return WOLFSSL_FATAL_ERROR;
|
||||||
}
|
}
|
||||||
@ -13905,6 +13908,9 @@ int wolfSSL_DTLS_SetCookieSecret(WOLFSSL* ssl,
|
|||||||
#ifndef NO_CERTS
|
#ifndef NO_CERTS
|
||||||
if (!ssl->options.resuming)
|
if (!ssl->options.resuming)
|
||||||
if ( (ssl->error = SendCertificate(ssl)) != 0) {
|
if ( (ssl->error = SendCertificate(ssl)) != 0) {
|
||||||
|
#ifdef WOLFSSL_CHECK_ALERT_ON_ERR
|
||||||
|
ProcessReplyEx(ssl, 1); /* See if an alert was sent. */
|
||||||
|
#endif
|
||||||
WOLFSSL_ERROR(ssl->error);
|
WOLFSSL_ERROR(ssl->error);
|
||||||
return WOLFSSL_FATAL_ERROR;
|
return WOLFSSL_FATAL_ERROR;
|
||||||
}
|
}
|
||||||
@ -13917,6 +13923,9 @@ int wolfSSL_DTLS_SetCookieSecret(WOLFSSL* ssl,
|
|||||||
#ifndef NO_CERTS
|
#ifndef NO_CERTS
|
||||||
if (!ssl->options.resuming)
|
if (!ssl->options.resuming)
|
||||||
if ( (ssl->error = SendCertificateStatus(ssl)) != 0) {
|
if ( (ssl->error = SendCertificateStatus(ssl)) != 0) {
|
||||||
|
#ifdef WOLFSSL_CHECK_ALERT_ON_ERR
|
||||||
|
ProcessReplyEx(ssl, 1); /* See if an alert was sent. */
|
||||||
|
#endif
|
||||||
WOLFSSL_ERROR(ssl->error);
|
WOLFSSL_ERROR(ssl->error);
|
||||||
return WOLFSSL_FATAL_ERROR;
|
return WOLFSSL_FATAL_ERROR;
|
||||||
}
|
}
|
||||||
@ -13933,6 +13942,9 @@ int wolfSSL_DTLS_SetCookieSecret(WOLFSSL* ssl,
|
|||||||
#endif
|
#endif
|
||||||
if (!ssl->options.resuming)
|
if (!ssl->options.resuming)
|
||||||
if ( (ssl->error = SendServerKeyExchange(ssl)) != 0) {
|
if ( (ssl->error = SendServerKeyExchange(ssl)) != 0) {
|
||||||
|
#ifdef WOLFSSL_CHECK_ALERT_ON_ERR
|
||||||
|
ProcessReplyEx(ssl, 1); /* See if an alert was sent. */
|
||||||
|
#endif
|
||||||
WOLFSSL_ERROR(ssl->error);
|
WOLFSSL_ERROR(ssl->error);
|
||||||
return WOLFSSL_FATAL_ERROR;
|
return WOLFSSL_FATAL_ERROR;
|
||||||
}
|
}
|
||||||
@ -13945,6 +13957,9 @@ int wolfSSL_DTLS_SetCookieSecret(WOLFSSL* ssl,
|
|||||||
if (!ssl->options.resuming) {
|
if (!ssl->options.resuming) {
|
||||||
if (ssl->options.verifyPeer) {
|
if (ssl->options.verifyPeer) {
|
||||||
if ( (ssl->error = SendCertificateRequest(ssl)) != 0) {
|
if ( (ssl->error = SendCertificateRequest(ssl)) != 0) {
|
||||||
|
#ifdef WOLFSSL_CHECK_ALERT_ON_ERR
|
||||||
|
ProcessReplyEx(ssl, 1); /* See if an alert was sent. */
|
||||||
|
#endif
|
||||||
WOLFSSL_ERROR(ssl->error);
|
WOLFSSL_ERROR(ssl->error);
|
||||||
return WOLFSSL_FATAL_ERROR;
|
return WOLFSSL_FATAL_ERROR;
|
||||||
}
|
}
|
||||||
@ -13962,6 +13977,9 @@ int wolfSSL_DTLS_SetCookieSecret(WOLFSSL* ssl,
|
|||||||
case CERT_REQ_SENT :
|
case CERT_REQ_SENT :
|
||||||
if (!ssl->options.resuming)
|
if (!ssl->options.resuming)
|
||||||
if ( (ssl->error = SendServerHelloDone(ssl)) != 0) {
|
if ( (ssl->error = SendServerHelloDone(ssl)) != 0) {
|
||||||
|
#ifdef WOLFSSL_CHECK_ALERT_ON_ERR
|
||||||
|
ProcessReplyEx(ssl, 1); /* See if an alert was sent. */
|
||||||
|
#endif
|
||||||
WOLFSSL_ERROR(ssl->error);
|
WOLFSSL_ERROR(ssl->error);
|
||||||
return WOLFSSL_FATAL_ERROR;
|
return WOLFSSL_FATAL_ERROR;
|
||||||
}
|
}
|
||||||
@ -14000,6 +14018,9 @@ int wolfSSL_DTLS_SetCookieSecret(WOLFSSL* ssl,
|
|||||||
#ifdef HAVE_SESSION_TICKET
|
#ifdef HAVE_SESSION_TICKET
|
||||||
if (ssl->options.createTicket && !ssl->options.noTicketTls12) {
|
if (ssl->options.createTicket && !ssl->options.noTicketTls12) {
|
||||||
if ( (ssl->error = SendTicket(ssl)) != 0) {
|
if ( (ssl->error = SendTicket(ssl)) != 0) {
|
||||||
|
#ifdef WOLFSSL_CHECK_ALERT_ON_ERR
|
||||||
|
ProcessReplyEx(ssl, 1); /* See if an alert was sent. */
|
||||||
|
#endif
|
||||||
WOLFSSL_MSG("Thought we need ticket but failed");
|
WOLFSSL_MSG("Thought we need ticket but failed");
|
||||||
WOLFSSL_ERROR(ssl->error);
|
WOLFSSL_ERROR(ssl->error);
|
||||||
return WOLFSSL_FATAL_ERROR;
|
return WOLFSSL_FATAL_ERROR;
|
||||||
@ -14018,6 +14039,9 @@ int wolfSSL_DTLS_SetCookieSecret(WOLFSSL* ssl,
|
|||||||
}
|
}
|
||||||
|
|
||||||
if ( (ssl->error = SendChangeCipher(ssl)) != 0) {
|
if ( (ssl->error = SendChangeCipher(ssl)) != 0) {
|
||||||
|
#ifdef WOLFSSL_CHECK_ALERT_ON_ERR
|
||||||
|
ProcessReplyEx(ssl, 1); /* See if an alert was sent. */
|
||||||
|
#endif
|
||||||
WOLFSSL_ERROR(ssl->error);
|
WOLFSSL_ERROR(ssl->error);
|
||||||
return WOLFSSL_FATAL_ERROR;
|
return WOLFSSL_FATAL_ERROR;
|
||||||
}
|
}
|
||||||
@ -14027,6 +14051,9 @@ int wolfSSL_DTLS_SetCookieSecret(WOLFSSL* ssl,
|
|||||||
|
|
||||||
case CHANGE_CIPHER_SENT :
|
case CHANGE_CIPHER_SENT :
|
||||||
if ( (ssl->error = SendFinished(ssl)) != 0) {
|
if ( (ssl->error = SendFinished(ssl)) != 0) {
|
||||||
|
#ifdef WOLFSSL_CHECK_ALERT_ON_ERR
|
||||||
|
ProcessReplyEx(ssl, 1); /* See if an alert was sent. */
|
||||||
|
#endif
|
||||||
WOLFSSL_ERROR(ssl->error);
|
WOLFSSL_ERROR(ssl->error);
|
||||||
return WOLFSSL_FATAL_ERROR;
|
return WOLFSSL_FATAL_ERROR;
|
||||||
}
|
}
|
||||||
|
72
tests/api.c
72
tests/api.c
@ -64674,6 +64674,77 @@ static int test_extra_alerts_bad_psk(void)
|
|||||||
return TEST_SKIPPED;
|
return TEST_SKIPPED;
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
#if defined(WOLFSSL_HARDEN_TLS) && !defined(WOLFSSL_NO_TLS12) && \
|
||||||
|
defined(HAVE_IO_TESTS_DEPENDENCIES)
|
||||||
|
static int test_harden_no_secure_renegotiation_io_cb(WOLFSSL *ssl, char *buf,
|
||||||
|
int sz, void *ctx)
|
||||||
|
{
|
||||||
|
static int sentServerHello = FALSE;
|
||||||
|
|
||||||
|
if (!sentServerHello) {
|
||||||
|
byte renegExt[] = { 0xFF, 0x01, 0x00, 0x01, 0x00 };
|
||||||
|
size_t i;
|
||||||
|
|
||||||
|
if (sz < (int)sizeof(renegExt))
|
||||||
|
return WOLFSSL_CBIO_ERR_GENERAL;
|
||||||
|
|
||||||
|
/* Remove SCR from ServerHello */
|
||||||
|
for (i = 0; i < sz - sizeof(renegExt); i++) {
|
||||||
|
if (XMEMCMP(buf + i, renegExt, sizeof(renegExt)) == 0) {
|
||||||
|
/* Found the extension. Change it to something unrecognized. */
|
||||||
|
buf[i+1] = 0x11;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
sentServerHello = TRUE;
|
||||||
|
}
|
||||||
|
|
||||||
|
return EmbedSend(ssl, buf, sz, ctx);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void test_harden_no_secure_renegotiation_ssl_ready(WOLFSSL* ssl)
|
||||||
|
{
|
||||||
|
wolfSSL_SSLSetIOSend(ssl, test_harden_no_secure_renegotiation_io_cb);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void test_harden_no_secure_renegotiation_on_cleanup(WOLFSSL* ssl)
|
||||||
|
{
|
||||||
|
WOLFSSL_ALERT_HISTORY h;
|
||||||
|
AssertIntEQ(wolfSSL_get_alert_history(ssl, &h), WOLFSSL_SUCCESS);
|
||||||
|
AssertIntEQ(h.last_rx.code, handshake_failure);
|
||||||
|
AssertIntEQ(h.last_rx.level, alert_fatal);
|
||||||
|
}
|
||||||
|
|
||||||
|
static int test_harden_no_secure_renegotiation(void)
|
||||||
|
{
|
||||||
|
callback_functions client_cbs, server_cbs;
|
||||||
|
|
||||||
|
XMEMSET(&client_cbs, 0, sizeof(client_cbs));
|
||||||
|
XMEMSET(&server_cbs, 0, sizeof(server_cbs));
|
||||||
|
|
||||||
|
client_cbs.method = wolfTLSv1_2_client_method;
|
||||||
|
server_cbs.method = wolfTLSv1_2_server_method;
|
||||||
|
|
||||||
|
server_cbs.ssl_ready = test_harden_no_secure_renegotiation_ssl_ready;
|
||||||
|
server_cbs.on_cleanup = test_harden_no_secure_renegotiation_on_cleanup;
|
||||||
|
test_wolfSSL_client_server_nofail(&client_cbs, &server_cbs);
|
||||||
|
|
||||||
|
AssertIntEQ(client_cbs.return_code, TEST_FAIL);
|
||||||
|
AssertIntEQ(client_cbs.last_err, SECURE_RENEGOTIATION_E);
|
||||||
|
AssertIntEQ(server_cbs.return_code, TEST_FAIL);
|
||||||
|
AssertIntEQ(server_cbs.last_err, SOCKET_ERROR_E);
|
||||||
|
|
||||||
|
return TEST_RES_CHECK(1);
|
||||||
|
}
|
||||||
|
#else
|
||||||
|
static int test_harden_no_secure_renegotiation(void)
|
||||||
|
{
|
||||||
|
return TEST_SKIPPED;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
|
||||||
/*----------------------------------------------------------------------------*
|
/*----------------------------------------------------------------------------*
|
||||||
| Main
|
| Main
|
||||||
*----------------------------------------------------------------------------*/
|
*----------------------------------------------------------------------------*/
|
||||||
@ -65705,6 +65776,7 @@ TEST_CASE testCases[] = {
|
|||||||
TEST_DECL(test_extra_alerts_wrong_cs),
|
TEST_DECL(test_extra_alerts_wrong_cs),
|
||||||
TEST_DECL(test_extra_alerts_skip_hs),
|
TEST_DECL(test_extra_alerts_skip_hs),
|
||||||
TEST_DECL(test_extra_alerts_bad_psk),
|
TEST_DECL(test_extra_alerts_bad_psk),
|
||||||
|
TEST_DECL(test_harden_no_secure_renegotiation),
|
||||||
/* If at some point a stub get implemented this test should fail indicating
|
/* If at some point a stub get implemented this test should fail indicating
|
||||||
* a need to implement a new test case
|
* a need to implement a new test case
|
||||||
*/
|
*/
|
||||||
|
@ -304,8 +304,19 @@
|
|||||||
#undef HAVE_AES_CBC
|
#undef HAVE_AES_CBC
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
/* When adding new ciphersuites, make sure that they have appropriate
|
||||||
|
* guards for WOLFSSL_HARDEN_TLS. */
|
||||||
|
#if defined(WOLFSSL_HARDEN_TLS) && \
|
||||||
|
!defined(WOLFSSL_HARDEN_TLS_ALLOW_ALL_CIPHERSUITES)
|
||||||
|
/* Use a separate define (undef'ed later) to simplify macro logic. */
|
||||||
|
#define WSSL_HARDEN_TLS WOLFSSL_HARDEN_TLS
|
||||||
|
#define NO_TLS_DH
|
||||||
|
#endif
|
||||||
|
|
||||||
#ifndef WOLFSSL_AEAD_ONLY
|
#ifndef WOLFSSL_AEAD_ONLY
|
||||||
#if !defined(NO_RSA) && !defined(NO_RC4)
|
#if !defined(NO_RSA) && !defined(NO_RC4) && !defined(WSSL_HARDEN_TLS)
|
||||||
|
/* MUST NOT negotiate RC4 cipher suites
|
||||||
|
* https://www.rfc-editor.org/rfc/rfc9325#section-4.1 */
|
||||||
#if defined(WOLFSSL_STATIC_RSA)
|
#if defined(WOLFSSL_STATIC_RSA)
|
||||||
#if !defined(NO_SHA)
|
#if !defined(NO_SHA)
|
||||||
#define BUILD_SSL_RSA_WITH_RC4_128_SHA
|
#define BUILD_SSL_RSA_WITH_RC4_128_SHA
|
||||||
@ -376,7 +387,10 @@
|
|||||||
#define BUILD_TLS_RSA_WITH_CAMELLIA_256_CBC_SHA256
|
#define BUILD_TLS_RSA_WITH_CAMELLIA_256_CBC_SHA256
|
||||||
#endif
|
#endif
|
||||||
#endif
|
#endif
|
||||||
#if !defined(NO_DH)
|
#if !defined(NO_DH) && !defined(NO_TLS_DH)
|
||||||
|
/* SHOULD NOT negotiate cipher suites based on ephemeral
|
||||||
|
* finite-field Diffie-Hellman key agreement (i.e., "TLS_DHE_*"
|
||||||
|
* suites). https://www.rfc-editor.org/rfc/rfc9325#section-4.1 */
|
||||||
#if !defined(NO_SHA)
|
#if !defined(NO_SHA)
|
||||||
#define BUILD_TLS_DHE_RSA_WITH_CAMELLIA_128_CBC_SHA
|
#define BUILD_TLS_DHE_RSA_WITH_CAMELLIA_128_CBC_SHA
|
||||||
#define BUILD_TLS_DHE_RSA_WITH_CAMELLIA_256_CBC_SHA
|
#define BUILD_TLS_DHE_RSA_WITH_CAMELLIA_256_CBC_SHA
|
||||||
@ -458,7 +472,10 @@
|
|||||||
#endif
|
#endif
|
||||||
|
|
||||||
#if !defined(NO_DH) && !defined(NO_AES) && !defined(NO_TLS) && \
|
#if !defined(NO_DH) && !defined(NO_AES) && !defined(NO_TLS) && \
|
||||||
!defined(NO_RSA)
|
!defined(NO_RSA) && !defined(NO_TLS_DH)
|
||||||
|
/* SHOULD NOT negotiate cipher suites based on ephemeral
|
||||||
|
* finite-field Diffie-Hellman key agreement (i.e., "TLS_DHE_*"
|
||||||
|
* suites). https://www.rfc-editor.org/rfc/rfc9325#section-4.1 */
|
||||||
|
|
||||||
#if !defined(NO_SHA)
|
#if !defined(NO_SHA)
|
||||||
#if defined(WOLFSSL_AES_128) && defined(HAVE_AES_CBC)
|
#if defined(WOLFSSL_AES_128) && defined(HAVE_AES_CBC)
|
||||||
@ -492,7 +509,11 @@
|
|||||||
#endif
|
#endif
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#if !defined(NO_DH) && !defined(NO_PSK) && !defined(NO_TLS)
|
#if !defined(NO_DH) && !defined(NO_PSK) && !defined(NO_TLS) && \
|
||||||
|
!defined(NO_TLS_DH)
|
||||||
|
/* SHOULD NOT negotiate cipher suites based on ephemeral
|
||||||
|
* finite-field Diffie-Hellman key agreement (i.e., "TLS_DHE_*"
|
||||||
|
* suites). https://www.rfc-editor.org/rfc/rfc9325#section-4.1 */
|
||||||
#ifndef NO_SHA256
|
#ifndef NO_SHA256
|
||||||
#if !defined(NO_AES) && defined(WOLFSSL_AES_128) && \
|
#if !defined(NO_AES) && defined(WOLFSSL_AES_128) && \
|
||||||
defined(HAVE_AES_CBC)
|
defined(HAVE_AES_CBC)
|
||||||
@ -619,7 +640,9 @@
|
|||||||
#endif
|
#endif
|
||||||
#endif
|
#endif
|
||||||
#endif /* NO_AES */
|
#endif /* NO_AES */
|
||||||
#if !defined(NO_RC4)
|
#if !defined(NO_RC4) && !defined(WSSL_HARDEN_TLS)
|
||||||
|
/* MUST NOT negotiate RC4 cipher suites
|
||||||
|
* https://www.rfc-editor.org/rfc/rfc9325#section-4.1 */
|
||||||
#if !defined(NO_SHA)
|
#if !defined(NO_SHA)
|
||||||
#if !defined(NO_RSA)
|
#if !defined(NO_RSA)
|
||||||
#ifndef WOLFSSL_AEAD_ONLY
|
#ifndef WOLFSSL_AEAD_ONLY
|
||||||
@ -642,7 +665,11 @@
|
|||||||
#endif
|
#endif
|
||||||
#endif
|
#endif
|
||||||
#endif
|
#endif
|
||||||
#if !defined(NO_DES3)
|
#if !defined(NO_DES3) && !(defined(WSSL_HARDEN_TLS) && \
|
||||||
|
WSSL_HARDEN_TLS > 112)
|
||||||
|
/* 3DES offers only 112 bits of security.
|
||||||
|
* Using guidance from section 5.6.1
|
||||||
|
* https://nvlpubs.nist.gov/nistpubs/SpecialPublications/NIST.SP.800-57pt1r5.pdf */
|
||||||
#ifndef NO_SHA
|
#ifndef NO_SHA
|
||||||
#if !defined(NO_RSA)
|
#if !defined(NO_RSA)
|
||||||
#define BUILD_TLS_ECDHE_RSA_WITH_3DES_EDE_CBC_SHA
|
#define BUILD_TLS_ECDHE_RSA_WITH_3DES_EDE_CBC_SHA
|
||||||
@ -692,7 +719,10 @@
|
|||||||
#if !defined(NO_RSA) && defined(HAVE_ECC)
|
#if !defined(NO_RSA) && defined(HAVE_ECC)
|
||||||
#define BUILD_TLS_ECDHE_RSA_WITH_CHACHA20_OLD_POLY1305_SHA256
|
#define BUILD_TLS_ECDHE_RSA_WITH_CHACHA20_OLD_POLY1305_SHA256
|
||||||
#endif
|
#endif
|
||||||
#if !defined(NO_DH) && !defined(NO_RSA)
|
#if !defined(NO_DH) && !defined(NO_RSA) && !defined(NO_TLS_DH)
|
||||||
|
/* SHOULD NOT negotiate cipher suites based on ephemeral
|
||||||
|
* finite-field Diffie-Hellman key agreement (i.e., "TLS_DHE_*"
|
||||||
|
* suites). https://www.rfc-editor.org/rfc/rfc9325#section-4.1 */
|
||||||
#define BUILD_TLS_DHE_RSA_WITH_CHACHA20_OLD_POLY1305_SHA256
|
#define BUILD_TLS_DHE_RSA_WITH_CHACHA20_OLD_POLY1305_SHA256
|
||||||
#endif
|
#endif
|
||||||
#endif /* NO_OLD_POLY1305 */
|
#endif /* NO_OLD_POLY1305 */
|
||||||
@ -702,7 +732,10 @@
|
|||||||
defined(HAVE_ED448)
|
defined(HAVE_ED448)
|
||||||
#define BUILD_TLS_ECDHE_PSK_WITH_CHACHA20_POLY1305_SHA256
|
#define BUILD_TLS_ECDHE_PSK_WITH_CHACHA20_POLY1305_SHA256
|
||||||
#endif
|
#endif
|
||||||
#ifndef NO_DH
|
#if !defined(NO_DH) && !defined(NO_TLS_DH)
|
||||||
|
/* SHOULD NOT negotiate cipher suites based on ephemeral
|
||||||
|
* finite-field Diffie-Hellman key agreement (i.e., "TLS_DHE_*"
|
||||||
|
* suites). https://www.rfc-editor.org/rfc/rfc9325#section-4.1 */
|
||||||
#define BUILD_TLS_DHE_PSK_WITH_CHACHA20_POLY1305_SHA256
|
#define BUILD_TLS_DHE_PSK_WITH_CHACHA20_POLY1305_SHA256
|
||||||
#endif
|
#endif
|
||||||
#endif /* !NO_PSK */
|
#endif /* !NO_PSK */
|
||||||
@ -711,7 +744,10 @@
|
|||||||
#endif /* !WOLFSSL_MAX_STRENGTH */
|
#endif /* !WOLFSSL_MAX_STRENGTH */
|
||||||
|
|
||||||
#if !defined(NO_DH) && !defined(NO_AES) && !defined(NO_TLS) && \
|
#if !defined(NO_DH) && !defined(NO_AES) && !defined(NO_TLS) && \
|
||||||
!defined(NO_RSA) && defined(HAVE_AESGCM)
|
!defined(NO_RSA) && defined(HAVE_AESGCM) && !defined(NO_TLS_DH)
|
||||||
|
/* SHOULD NOT negotiate cipher suites based on ephemeral
|
||||||
|
* finite-field Diffie-Hellman key agreement (i.e., "TLS_DHE_*"
|
||||||
|
* suites). https://www.rfc-editor.org/rfc/rfc9325#section-4.1 */
|
||||||
|
|
||||||
#if !defined(NO_SHA256) && defined(WOLFSSL_AES_128)
|
#if !defined(NO_SHA256) && defined(WOLFSSL_AES_128)
|
||||||
#define BUILD_TLS_DHE_RSA_WITH_AES_128_GCM_SHA256
|
#define BUILD_TLS_DHE_RSA_WITH_AES_128_GCM_SHA256
|
||||||
@ -722,7 +758,11 @@
|
|||||||
#endif
|
#endif
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#if !defined(NO_DH) && !defined(NO_PSK) && !defined(NO_TLS)
|
#if !defined(NO_DH) && !defined(NO_PSK) && !defined(NO_TLS) && \
|
||||||
|
!defined(NO_TLS_DH)
|
||||||
|
/* SHOULD NOT negotiate cipher suites based on ephemeral
|
||||||
|
* finite-field Diffie-Hellman key agreement (i.e., "TLS_DHE_*"
|
||||||
|
* suites). https://www.rfc-editor.org/rfc/rfc9325#section-4.1 */
|
||||||
#ifndef NO_SHA256
|
#ifndef NO_SHA256
|
||||||
#if defined(HAVE_AESGCM) && defined(WOLFSSL_AES_128)
|
#if defined(HAVE_AESGCM) && defined(WOLFSSL_AES_128)
|
||||||
#define BUILD_TLS_DHE_PSK_WITH_AES_128_GCM_SHA256
|
#define BUILD_TLS_DHE_PSK_WITH_AES_128_GCM_SHA256
|
||||||
@ -792,7 +832,10 @@
|
|||||||
#define BUILD_TLS_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256
|
#define BUILD_TLS_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256
|
||||||
#endif
|
#endif
|
||||||
#endif
|
#endif
|
||||||
#if !defined(NO_DH) && !defined(NO_RSA)
|
#if !defined(NO_DH) && !defined(NO_RSA) && !defined(NO_TLS_DH)
|
||||||
|
/* SHOULD NOT negotiate cipher suites based on ephemeral
|
||||||
|
* finite-field Diffie-Hellman key agreement (i.e., "TLS_DHE_*"
|
||||||
|
* suites). https://www.rfc-editor.org/rfc/rfc9325#section-4.1 */
|
||||||
#define BUILD_TLS_DHE_RSA_WITH_CHACHA20_POLY1305_SHA256
|
#define BUILD_TLS_DHE_RSA_WITH_CHACHA20_POLY1305_SHA256
|
||||||
#endif
|
#endif
|
||||||
#endif
|
#endif
|
||||||
@ -912,7 +955,9 @@
|
|||||||
#define BUILD_AES
|
#define BUILD_AES
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifndef NO_RC4
|
#if !defined(NO_RC4) && !defined(WSSL_HARDEN_TLS)
|
||||||
|
/* MUST NOT negotiate RC4 cipher suites
|
||||||
|
* https://www.rfc-editor.org/rfc/rfc9325#section-4.1 */
|
||||||
#undef BUILD_ARC4
|
#undef BUILD_ARC4
|
||||||
#define BUILD_ARC4
|
#define BUILD_ARC4
|
||||||
#endif
|
#endif
|
||||||
@ -937,6 +982,23 @@
|
|||||||
#define HAVE_PFS
|
#define HAVE_PFS
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
#ifdef WSSL_HARDEN_TLS
|
||||||
|
#ifdef HAVE_NULL_CIPHER
|
||||||
|
#error "NULL ciphers not allowed https://www.rfc-editor.org/rfc/rfc9325#section-4.1"
|
||||||
|
#endif
|
||||||
|
#ifdef WOLFSSL_STATIC_RSA
|
||||||
|
#error "Static RSA ciphers not allowed https://www.rfc-editor.org/rfc/rfc9325#section-4.1"
|
||||||
|
#endif
|
||||||
|
#ifdef WOLFSSL_STATIC_DH
|
||||||
|
#error "Static DH ciphers not allowed https://www.rfc-editor.org/rfc/rfc9325#section-4.1"
|
||||||
|
#endif
|
||||||
|
#ifdef HAVE_ANON
|
||||||
|
#error "At least the server side has to be authenticated"
|
||||||
|
#endif
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#undef WSSL_HARDEN_TLS
|
||||||
|
|
||||||
/* actual cipher values, 2nd byte */
|
/* actual cipher values, 2nd byte */
|
||||||
enum {
|
enum {
|
||||||
TLS_DHE_RSA_WITH_3DES_EDE_CBC_SHA = 0x16,
|
TLS_DHE_RSA_WITH_3DES_EDE_CBC_SHA = 0x16,
|
||||||
@ -1123,12 +1185,29 @@ enum {
|
|||||||
|
|
||||||
/* set minimum DH key size allowed */
|
/* set minimum DH key size allowed */
|
||||||
#ifndef WOLFSSL_MIN_DHKEY_BITS
|
#ifndef WOLFSSL_MIN_DHKEY_BITS
|
||||||
#ifdef WOLFSSL_MAX_STRENGTH
|
#if defined(WOLFSSL_HARDEN_TLS) && !defined(WOLFSSL_HARDEN_TLS_NO_PKEY_CHECK)
|
||||||
|
/* Using guidance from section 5.6.1
|
||||||
|
* https://nvlpubs.nist.gov/nistpubs/SpecialPublications/NIST.SP.800-57pt1r5.pdf */
|
||||||
|
#if WOLFSSL_HARDEN_TLS >= 128
|
||||||
|
#define WOLFSSL_MIN_DHKEY_BITS 3072
|
||||||
|
#elif WOLFSSL_HARDEN_TLS >= 112
|
||||||
|
#define WOLFSSL_MIN_DHKEY_BITS 2048
|
||||||
|
#endif
|
||||||
|
#elif defined(WOLFSSL_MAX_STRENGTH)
|
||||||
#define WOLFSSL_MIN_DHKEY_BITS 2048
|
#define WOLFSSL_MIN_DHKEY_BITS 2048
|
||||||
#else
|
#else
|
||||||
#define WOLFSSL_MIN_DHKEY_BITS 1024
|
#define WOLFSSL_MIN_DHKEY_BITS 1024
|
||||||
#endif
|
#endif
|
||||||
#endif
|
#endif
|
||||||
|
#if defined(WOLFSSL_HARDEN_TLS) && WOLFSSL_MIN_DHKEY_BITS < 2048 && \
|
||||||
|
!defined(WOLFSSL_HARDEN_TLS_NO_PKEY_CHECK)
|
||||||
|
/* Implementations MUST NOT negotiate cipher suites offering less than
|
||||||
|
* 112 bits of security.
|
||||||
|
* https://www.rfc-editor.org/rfc/rfc9325#section-4.1
|
||||||
|
* Using guidance from section 5.6.1
|
||||||
|
* https://nvlpubs.nist.gov/nistpubs/SpecialPublications/NIST.SP.800-57pt1r5.pdf */
|
||||||
|
#error "For 112 bits of security DH needs at least 2048 bit keys"
|
||||||
|
#endif
|
||||||
#if (WOLFSSL_MIN_DHKEY_BITS % 8)
|
#if (WOLFSSL_MIN_DHKEY_BITS % 8)
|
||||||
#error DH minimum bit size must be multiple of 8
|
#error DH minimum bit size must be multiple of 8
|
||||||
#endif
|
#endif
|
||||||
@ -1156,6 +1235,10 @@ enum {
|
|||||||
#endif
|
#endif
|
||||||
#define MAX_DHKEY_SZ (WOLFSSL_MAX_DHKEY_BITS / 8)
|
#define MAX_DHKEY_SZ (WOLFSSL_MAX_DHKEY_BITS / 8)
|
||||||
|
|
||||||
|
#if WOLFSSL_MAX_DHKEY_BITS < WOLFSSL_MIN_DHKEY_BITS
|
||||||
|
#error "WOLFSSL_MAX_DHKEY_BITS has to be greater than WOLFSSL_MIN_DHKEY_BITS"
|
||||||
|
#endif
|
||||||
|
|
||||||
#ifndef MAX_PSK_ID_LEN
|
#ifndef MAX_PSK_ID_LEN
|
||||||
/* max psk identity/hint supported */
|
/* max psk identity/hint supported */
|
||||||
#if defined(WOLFSSL_TLS13)
|
#if defined(WOLFSSL_TLS13)
|
||||||
@ -1751,12 +1834,29 @@ enum Misc {
|
|||||||
|
|
||||||
/* set minimum RSA key size allowed */
|
/* set minimum RSA key size allowed */
|
||||||
#ifndef WOLFSSL_MIN_RSA_BITS
|
#ifndef WOLFSSL_MIN_RSA_BITS
|
||||||
#ifdef WOLFSSL_MAX_STRENGTH
|
#if defined(WOLFSSL_HARDEN_TLS) && !defined(WOLFSSL_HARDEN_TLS_NO_PKEY_CHECK)
|
||||||
|
/* Using guidance from section 5.6.1
|
||||||
|
* https://nvlpubs.nist.gov/nistpubs/SpecialPublications/NIST.SP.800-57pt1r5.pdf */
|
||||||
|
#if WOLFSSL_HARDEN_TLS >= 128
|
||||||
|
#define WOLFSSL_MIN_RSA_BITS 3072
|
||||||
|
#elif WOLFSSL_HARDEN_TLS >= 112
|
||||||
|
#define WOLFSSL_MIN_RSA_BITS 2048
|
||||||
|
#endif
|
||||||
|
#elif defined(WOLFSSL_MAX_STRENGTH)
|
||||||
#define WOLFSSL_MIN_RSA_BITS 2048
|
#define WOLFSSL_MIN_RSA_BITS 2048
|
||||||
#else
|
#else
|
||||||
#define WOLFSSL_MIN_RSA_BITS 1024
|
#define WOLFSSL_MIN_RSA_BITS 1024
|
||||||
#endif
|
#endif
|
||||||
#endif /* WOLFSSL_MIN_RSA_BITS */
|
#endif /* WOLFSSL_MIN_RSA_BITS */
|
||||||
|
#if defined(WOLFSSL_HARDEN_TLS) && WOLFSSL_MIN_RSA_BITS < 2048 && \
|
||||||
|
!defined(WOLFSSL_HARDEN_TLS_NO_PKEY_CHECK)
|
||||||
|
/* Implementations MUST NOT negotiate cipher suites offering less than
|
||||||
|
* 112 bits of security.
|
||||||
|
* https://www.rfc-editor.org/rfc/rfc9325#section-4.1
|
||||||
|
* Using guidance from section 5.6.1
|
||||||
|
* https://nvlpubs.nist.gov/nistpubs/SpecialPublications/NIST.SP.800-57pt1r5.pdf */
|
||||||
|
#error "For 112 bits of security RSA needs at least 2048 bit keys"
|
||||||
|
#endif
|
||||||
#if (WOLFSSL_MIN_RSA_BITS % 8)
|
#if (WOLFSSL_MIN_RSA_BITS % 8)
|
||||||
/* This is to account for the example case of a min size of 2050 bits but
|
/* This is to account for the example case of a min size of 2050 bits but
|
||||||
still allows 2049 bit key. So we need the measurement to be in bytes. */
|
still allows 2049 bit key. So we need the measurement to be in bytes. */
|
||||||
|
@ -306,6 +306,12 @@
|
|||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
|
||||||
|
#ifdef WOLFSSL_HARDEN_TLS
|
||||||
|
#if WOLFSSL_HARDEN_TLS != 112 && WOLFSSL_HARDEN_TLS != 128
|
||||||
|
#error "WOLFSSL_HARDEN_TLS must be defined either to 112 or 128 bits of security."
|
||||||
|
#endif
|
||||||
|
#endif
|
||||||
|
|
||||||
#if defined(_WIN32) && !defined(_M_X64) && \
|
#if defined(_WIN32) && !defined(_M_X64) && \
|
||||||
defined(HAVE_AESGCM) && defined(WOLFSSL_AESNI)
|
defined(HAVE_AESGCM) && defined(WOLFSSL_AESNI)
|
||||||
|
|
||||||
@ -2007,7 +2013,16 @@ extern void uITRON4_free(void *p) ;
|
|||||||
#ifdef WOLFSSL_MIN_ECC_BITS
|
#ifdef WOLFSSL_MIN_ECC_BITS
|
||||||
#define ECC_MIN_KEY_SZ WOLFSSL_MIN_ECC_BITS
|
#define ECC_MIN_KEY_SZ WOLFSSL_MIN_ECC_BITS
|
||||||
#else
|
#else
|
||||||
#if FIPS_VERSION_GE(2,0)
|
#if defined(WOLFSSL_HARDEN_TLS) && \
|
||||||
|
!defined(WOLFSSL_HARDEN_TLS_NO_PKEY_CHECK)
|
||||||
|
/* Using guidance from section 5.6.1
|
||||||
|
* https://nvlpubs.nist.gov/nistpubs/SpecialPublications/NIST.SP.800-57pt1r5.pdf */
|
||||||
|
#if WOLFSSL_HARDEN_TLS >= 128
|
||||||
|
#define ECC_MIN_KEY_SZ 256
|
||||||
|
#elif WOLFSSL_HARDEN_TLS >= 112
|
||||||
|
#define ECC_MIN_KEY_SZ 224
|
||||||
|
#endif
|
||||||
|
#elif FIPS_VERSION_GE(2,0)
|
||||||
/* FIPSv2 and ready (for now) includes 192-bit support */
|
/* FIPSv2 and ready (for now) includes 192-bit support */
|
||||||
#define ECC_MIN_KEY_SZ 192
|
#define ECC_MIN_KEY_SZ 192
|
||||||
#else
|
#else
|
||||||
@ -2016,6 +2031,16 @@ extern void uITRON4_free(void *p) ;
|
|||||||
#endif
|
#endif
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
#if defined(WOLFSSL_HARDEN_TLS) && ECC_MIN_KEY_SZ < 224 && \
|
||||||
|
!defined(WOLFSSL_HARDEN_TLS_NO_PKEY_CHECK)
|
||||||
|
/* Implementations MUST NOT negotiate cipher suites offering less than
|
||||||
|
* 112 bits of security.
|
||||||
|
* https://www.rfc-editor.org/rfc/rfc9325#section-4.1
|
||||||
|
* Using guidance from section 5.6.1
|
||||||
|
* https://nvlpubs.nist.gov/nistpubs/SpecialPublications/NIST.SP.800-57pt1r5.pdf */
|
||||||
|
#error "For 112 bits of security ECC needs at least 224 bit keys"
|
||||||
|
#endif
|
||||||
|
|
||||||
/* ECC Configs */
|
/* ECC Configs */
|
||||||
#ifdef HAVE_ECC
|
#ifdef HAVE_ECC
|
||||||
/* By default enable Sign, Verify, DHE, Key Import and Key Export unless
|
/* By default enable Sign, Verify, DHE, Key Import and Key Export unless
|
||||||
@ -2967,6 +2992,23 @@ extern void uITRON4_free(void *p) ;
|
|||||||
#error "Dynamic session cache currently does not support persistent session cache."
|
#error "Dynamic session cache currently does not support persistent session cache."
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
#ifdef WOLFSSL_HARDEN_TLS
|
||||||
|
#if defined(HAVE_TRUNCATED_HMAC) && !defined(WOLFSSL_HARDEN_TLS_ALLOW_TRUNCATED_HMAC)
|
||||||
|
#error "Truncated HMAC Extension not allowed https://www.rfc-editor.org/rfc/rfc9325#section-4.6"
|
||||||
|
#endif
|
||||||
|
#if !defined(NO_OLD_TLS) && !defined(WOLFSSL_HARDEN_TLS_ALLOW_OLD_TLS)
|
||||||
|
#error "TLS < 1.2 protocol versions not allowed https://www.rfc-editor.org/rfc/rfc9325#section-3.1.1"
|
||||||
|
#endif
|
||||||
|
#if !defined(WOLFSSL_NO_TLS12) && !defined(HAVE_SECURE_RENEGOTIATION) && \
|
||||||
|
!defined(HAVE_SERVER_RENEGOTIATION_INFO) && !defined(WOLFSSL_HARDEN_TLS_NO_SCR_CHECK)
|
||||||
|
#error "TLS 1.2 requires at least HAVE_SERVER_RENEGOTIATION_INFO to send the secure renegotiation extension https://www.rfc-editor.org/rfc/rfc9325#section-3.5"
|
||||||
|
#endif
|
||||||
|
#if !defined(WOLFSSL_EXTRA_ALERTS) || !defined(WOLFSSL_CHECK_ALERT_ON_ERR)
|
||||||
|
#error "RFC9325 requires some additional alerts to be sent"
|
||||||
|
#endif
|
||||||
|
/* Ciphersuite check done in internal.h */
|
||||||
|
#endif
|
||||||
|
|
||||||
#ifdef __cplusplus
|
#ifdef __cplusplus
|
||||||
} /* extern "C" */
|
} /* extern "C" */
|
||||||
#endif
|
#endif
|
||||||
|
Reference in New Issue
Block a user