Skip to content

Commit d09f955

Browse files
Merge pull request #7626 from lealem47/parseServerHello
Improved fix for TLS1.3 to TLS1.2 client downgrade
2 parents c822303 + 5a1ac27 commit d09f955

2 files changed

Lines changed: 71 additions & 11 deletions

File tree

src/tls13.c

Lines changed: 9 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -5298,13 +5298,6 @@ int DoTls13ServerHello(WOLFSSL* ssl, const byte* input, word32* inOutIdx,
52985298
return ret;
52995299
}
53005300
#endif /* WOLFSSL_DTLS13 */
5301-
5302-
#ifndef WOLFSSL_NO_TLS12
5303-
return DoServerHello(ssl, input, inOutIdx, helloSz);
5304-
#else
5305-
SendAlert(ssl, alert_fatal, wolfssl_alert_protocol_version);
5306-
return VERSION_ERROR;
5307-
#endif
53085301
}
53095302
}
53105303

@@ -5330,8 +5323,9 @@ int DoTls13ServerHello(WOLFSSL* ssl, const byte* input, word32* inOutIdx,
53305323
/* restore message type */
53315324
*extMsgType = args->extMsgType;
53325325

5333-
if (args->totalExtSz > 0) {
5334-
/* Parse and handle extensions. */
5326+
/* Parse and handle extensions, unless lower than TLS1.3. In that case,
5327+
* extensions will be parsed in DoServerHello. */
5328+
if (args->totalExtSz > 0 && IsAtLeastTLSv1_3(ssl->version)) {
53355329
ret = TLSX_Parse(ssl, input + args->idx, args->totalExtSz,
53365330
*extMsgType, NULL);
53375331
if (ret != 0) {
@@ -5350,7 +5344,9 @@ int DoTls13ServerHello(WOLFSSL* ssl, const byte* input, word32* inOutIdx,
53505344
ssl->msgsReceived.got_hello_retry_request = 1;
53515345
ssl->msgsReceived.got_server_hello = 0;
53525346
}
5347+
}
53535348

5349+
if (args->totalExtSz > 0) {
53545350
args->idx += args->totalExtSz;
53555351
}
53565352

@@ -5359,7 +5355,9 @@ int DoTls13ServerHello(WOLFSSL* ssl, const byte* input, word32* inOutIdx,
53595355
DtlsCIDOnExtensionsParsed(ssl);
53605356
#endif /* WOLFSSL_DTLS_CID */
53615357

5362-
*inOutIdx = args->idx;
5358+
if (IsAtLeastTLSv1_3(ssl->version)) {
5359+
*inOutIdx = args->idx;
5360+
}
53635361

53645362
ssl->options.serverState = SERVER_HELLO_COMPLETE;
53655363

@@ -5403,7 +5401,7 @@ int DoTls13ServerHello(WOLFSSL* ssl, const byte* input, word32* inOutIdx,
54035401
else
54045402
ssl->chVersion.minor = TLSv1_2_MINOR;
54055403
/* Complete TLS v1.2 processing of ServerHello. */
5406-
ret = CompleteServerHello(ssl);
5404+
ret = DoServerHello(ssl, input, inOutIdx, helloSz);
54075405
#else
54085406
WOLFSSL_MSG("Client using higher version, fatal error");
54095407
WOLFSSL_ERROR_VERBOSE(VERSION_ERROR);

tests/api.c

Lines changed: 62 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -68416,6 +68416,67 @@ static int test_extra_alerts_wrong_cs(void)
6841668416
}
6841768417
#endif
6841868418

68419+
#if defined(WOLFSSL_TLS13) && !defined(WOLFSSL_NO_TLS12) && \
68420+
defined(HAVE_MANUAL_MEMIO_TESTS_DEPENDENCIES)
68421+
68422+
#define TEST_CS_DOWNGRADE_CLIENT "ECDHE-RSA-AES256-GCM-SHA384"
68423+
68424+
byte test_wrong_cs_downgrade_sh[] = {
68425+
0x16, 0x03, 0x03, 0x00, 0x56, 0x02, 0x00, 0x00, 0x52, 0x03, 0x03, 0x10,
68426+
0x2c, 0x88, 0xd9, 0x7a, 0x23, 0xc9, 0xbd, 0x11, 0x3b, 0x64, 0x24, 0xab,
68427+
0x5b, 0x45, 0x33, 0xf6, 0x2c, 0x34, 0xe4, 0xcf, 0xf4, 0x78, 0xc8, 0x62,
68428+
0x06, 0xc7, 0xe5, 0x30, 0x39, 0xbf, 0xa1, 0x20, 0xa3, 0x06, 0x74, 0xc3,
68429+
0xa9, 0x74, 0x52, 0x8a, 0xfb, 0xae, 0xf0, 0xd8, 0x6f, 0xb2, 0x9d, 0xfe,
68430+
0x78, 0xf0, 0x3f, 0x51, 0x8f, 0x9c, 0xcf, 0xbe, 0x61, 0x43, 0x9d, 0xf8,
68431+
0x85, 0xe5, 0x2f, 0x54,
68432+
0xc0, 0x2f, /* ECDHE-RSA-AES128-GCM-SHA256 */
68433+
0x00, 0x00, 0x0a, 0x00, 0x0b, 0x00,
68434+
0x02, 0x01, 0x00, 0x00, 0x17, 0x00, 0x00
68435+
};
68436+
68437+
static int test_wrong_cs_downgrade(void)
68438+
{
68439+
EXPECT_DECLS;
68440+
#ifdef BUILD_TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256
68441+
struct test_memio_ctx test_ctx;
68442+
WOLFSSL_CTX *ctx_c = NULL;
68443+
WOLFSSL *ssl_c = NULL;
68444+
68445+
XMEMSET(&test_ctx, 0, sizeof(test_ctx));
68446+
ExpectIntEQ(test_memio_setup(&test_ctx, &ctx_c, NULL, &ssl_c, NULL,
68447+
wolfSSLv23_client_method, NULL), 0);
68448+
68449+
ExpectIntEQ(wolfSSL_set_cipher_list(ssl_c, TEST_CS_DOWNGRADE_CLIENT),
68450+
WOLFSSL_SUCCESS);
68451+
68452+
/* CH */
68453+
ExpectIntNE(wolfSSL_connect(ssl_c), WOLFSSL_SUCCESS);
68454+
ExpectIntEQ(wolfSSL_get_error(ssl_c, WOLFSSL_FATAL_ERROR),
68455+
WOLFSSL_ERROR_WANT_READ);
68456+
68457+
/* consume CH */
68458+
test_ctx.s_len = 0;
68459+
/* inject SH */
68460+
XMEMCPY(test_ctx.c_buff, test_wrong_cs_downgrade_sh,
68461+
sizeof(test_wrong_cs_downgrade_sh));
68462+
test_ctx.c_len = sizeof(test_wrong_cs_downgrade_sh);
68463+
68464+
ExpectIntNE(wolfSSL_connect(ssl_c), WOLFSSL_SUCCESS);
68465+
ExpectIntNE(wolfSSL_get_error(ssl_c, WOLFSSL_FATAL_ERROR),
68466+
WOLFSSL_ERROR_WANT_READ);
68467+
68468+
wolfSSL_free(ssl_c);
68469+
wolfSSL_CTX_free(ctx_c);
68470+
#endif
68471+
return EXPECT_RESULT();
68472+
}
68473+
#else
68474+
static int test_wrong_cs_downgrade(void)
68475+
{
68476+
return TEST_SKIPPED;
68477+
}
68478+
#endif
68479+
6841968480
#if !defined(WOLFSSL_NO_TLS12) && defined(WOLFSSL_EXTRA_ALERTS) && \
6842068481
defined(HAVE_MANUAL_MEMIO_TESTS_DEPENDENCIES) && !defined(WOLFSSL_SP_MATH)
6842168482

@@ -74020,6 +74081,7 @@ TEST_CASE testCases[] = {
7402074081
TEST_DECL(test_ticket_nonce_malloc),
7402174082
#endif
7402274083
TEST_DECL(test_ticket_ret_create),
74084+
TEST_DECL(test_wrong_cs_downgrade),
7402374085
TEST_DECL(test_extra_alerts_wrong_cs),
7402474086
TEST_DECL(test_extra_alerts_skip_hs),
7402574087
TEST_DECL(test_extra_alerts_bad_psk),

0 commit comments

Comments
 (0)