Skip to content

Commit cb6676f

Browse files
authored
Merge pull request #7030 from julek-wolfssl/gh/7000
Store ssl->options.dtlsStateful when exporting DTLS session
2 parents 03a8271 + 4ce4dd7 commit cb6676f

3 files changed

Lines changed: 169 additions & 6 deletions

File tree

src/internal.c

Lines changed: 44 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1305,6 +1305,14 @@ static int ExportOptions(WOLFSSL* ssl, byte* exp, word32 len, byte ver,
13051305
#endif
13061306
}
13071307

1308+
if (ver > WOLFSSL_EXPORT_VERSION_4) {
1309+
#ifdef WOLFSSL_DTLS
1310+
exp[idx++] = options->dtlsStateful;
1311+
#else
1312+
exp[idx++] = 0;
1313+
#endif
1314+
}
1315+
13081316
/* version of connection */
13091317
exp[idx++] = ssl->version.major;
13101318
exp[idx++] = ssl->version.minor;
@@ -1320,6 +1328,13 @@ static int ExportOptions(WOLFSSL* ssl, byte* exp, word32 len, byte ver,
13201328
}
13211329
break;
13221330

1331+
case WOLFSSL_EXPORT_VERSION_4:
1332+
if (idx != DTLS_EXPORT_OPT_SZ_4 && type == WOLFSSL_EXPORT_DTLS) {
1333+
WOLFSSL_MSG("Update DTLS_EXPORT_OPT_SZ and version of export");
1334+
return DTLS_EXPORT_VER_E;
1335+
}
1336+
break;
1337+
13231338
case WOLFSSL_EXPORT_VERSION:
13241339
if (idx != DTLS_EXPORT_OPT_SZ && type == WOLFSSL_EXPORT_DTLS) {
13251340
WOLFSSL_MSG("Update DTLS_EXPORT_OPT_SZ and version of export");
@@ -1355,6 +1370,13 @@ static int ImportOptions(WOLFSSL* ssl, const byte* exp, word32 len, byte ver,
13551370
}
13561371
break;
13571372

1373+
case WOLFSSL_EXPORT_VERSION_4:
1374+
if (len < DTLS_EXPORT_OPT_SZ_4) {
1375+
WOLFSSL_MSG("Sanity check on buffer size failed");
1376+
return BAD_FUNC_ARG;
1377+
}
1378+
break;
1379+
13581380
case WOLFSSL_EXPORT_VERSION_3:
13591381
if (len < DTLS_EXPORT_OPT_SZ_3) {
13601382
WOLFSSL_MSG("Sanity check on buffer size failed");
@@ -1488,6 +1510,17 @@ static int ImportOptions(WOLFSSL* ssl, const byte* exp, word32 len, byte ver,
14881510
#endif
14891511
}
14901512

1513+
/* If we had a connection established, let's assume that we can act
1514+
* statefully */
1515+
options->dtlsStateful = 1;
1516+
if (ver > WOLFSSL_EXPORT_VERSION_4) {
1517+
#ifdef WOLFSSL_DTLS
1518+
options->dtlsStateful = exp[idx++];
1519+
#else
1520+
idx++;
1521+
#endif
1522+
}
1523+
14911524
/* version of connection */
14921525
if (ssl->version.major != exp[idx++] || ssl->version.minor != exp[idx++]) {
14931526
WOLFSSL_MSG("Version mismatch ie DTLS v1 vs v1.2");
@@ -1556,7 +1589,8 @@ static int ImportPeerInfo(WOLFSSL* ssl, const byte* buf, word32 len, byte ver)
15561589
word16 port;
15571590
char ip[MAX_EXPORT_IP];
15581591

1559-
if (ver != WOLFSSL_EXPORT_VERSION && ver != WOLFSSL_EXPORT_VERSION_3) {
1592+
if (ver != WOLFSSL_EXPORT_VERSION && ver != WOLFSSL_EXPORT_VERSION_4 &&
1593+
ver != WOLFSSL_EXPORT_VERSION_3) {
15601594
WOLFSSL_MSG("Export version not supported");
15611595
return BAD_FUNC_ARG;
15621596
}
@@ -1814,6 +1848,15 @@ int wolfSSL_session_import_internal(WOLFSSL* ssl, const unsigned char* buf,
18141848
}
18151849
break;
18161850

1851+
case WOLFSSL_EXPORT_VERSION_4:
1852+
if (type == WOLFSSL_EXPORT_DTLS) {
1853+
optSz = DTLS_EXPORT_OPT_SZ_4;
1854+
}
1855+
else {
1856+
optSz = TLS_EXPORT_OPT_SZ;
1857+
}
1858+
break;
1859+
18171860
case WOLFSSL_EXPORT_VERSION_3:
18181861
WOLFSSL_MSG("Importing older version 3");
18191862
optSz = DTLS_EXPORT_OPT_SZ_3;

tests/api.c

Lines changed: 121 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -438,13 +438,15 @@ typedef struct testVector {
438438
typedef int (*ctx_cb)(WOLFSSL_CTX* ctx);
439439
typedef int (*ssl_cb)(WOLFSSL* ssl);
440440
typedef int (*test_cbType)(WOLFSSL_CTX *ctx, WOLFSSL *ssl);
441+
typedef int (*hs_cb)(WOLFSSL_CTX **ctx, WOLFSSL **ssl);
441442

442443
typedef struct test_ssl_cbf {
443444
method_provider method;
444445
ctx_cb ctx_ready;
445446
ssl_cb ssl_ready;
446447
ssl_cb on_result;
447448
ssl_cb on_cleanup;
449+
hs_cb on_handshake;
448450
WOLFSSL_CTX* ctx;
449451
const char* caPemFile;
450452
const char* certPemFile;
@@ -6156,6 +6158,14 @@ int test_wolfSSL_client_server_nofail_memio(test_ssl_cbf* client_cb,
61566158
ExpectIntEQ(client_on_handshake(test_ctx.c_ctx, test_ctx.c_ssl),
61576159
TEST_SUCCESS);
61586160
}
6161+
if (client_cb->on_handshake != NULL) {
6162+
ExpectIntEQ(client_cb->on_handshake(&test_ctx.c_ctx, &test_ctx.c_ssl),
6163+
TEST_SUCCESS);
6164+
}
6165+
if (server_cb->on_handshake != NULL) {
6166+
ExpectIntEQ(server_cb->on_handshake(&test_ctx.s_ctx, &test_ctx.s_ssl),
6167+
TEST_SUCCESS);
6168+
}
61596169
#ifdef WOLFSSL_HAVE_TLS_UNIQUE
61606170
XMEMSET(server_side_msg2, 0, MD_MAX_SIZE);
61616171
msg_len = wolfSSL_get_peer_finished(test_ctx.s_ssl, server_side_msg2,
@@ -8761,8 +8771,8 @@ static int test_wolfSSL_CTX_add_session_ext(
87618771
/* connection 1 - first connection */
87628772
fprintf(stderr, "\tconnect: %s: j=%d\n", param->tls_version, j);
87638773

8764-
XMEMSET(&client_cb, 0, sizeof(callback_functions));
8765-
XMEMSET(&server_cb, 0, sizeof(callback_functions));
8774+
XMEMSET(&client_cb, 0, sizeof(client_cb));
8775+
XMEMSET(&server_cb, 0, sizeof(server_cb));
87668776
client_cb.method = param->client_meth;
87678777
server_cb.method = param->server_meth;
87688778

@@ -9330,7 +9340,6 @@ static int test_wolfSSL_dtls_export(void)
93309340
return EXPECT_RESULT();
93319341
}
93329342

9333-
93349343
#if defined(WOLFSSL_SESSION_EXPORT) && !defined(WOLFSSL_NO_TLS12)
93359344
#ifdef WOLFSSL_TLS13
93369345
static const byte canned_client_tls13_session[] = {
@@ -10214,6 +10223,114 @@ static int test_wolfSSL_SNI_GetFromBuffer(void)
1021410223

1021510224
#endif /* HAVE_IO_TESTS_DEPENDENCIES */
1021610225

10226+
10227+
#if defined(WOLFSSL_DTLS) && defined(WOLFSSL_SESSION_EXPORT) && \
10228+
defined(HAVE_SSL_MEMIO_TESTS_DEPENDENCIES)
10229+
/* Dummy peer functions to satisfy the exporter/importer */
10230+
static int test_wolfSSL_dtls_export_peers_get_peer(WOLFSSL* ssl, char* ip,
10231+
int* ipSz, unsigned short* port, int* fam)
10232+
{
10233+
(void)ssl;
10234+
ip[0] = -1;
10235+
*ipSz = 1;
10236+
*port = 1;
10237+
*fam = 2;
10238+
return 1;
10239+
}
10240+
10241+
static int test_wolfSSL_dtls_export_peers_set_peer(WOLFSSL* ssl, char* ip,
10242+
int ipSz, unsigned short port, int fam)
10243+
{
10244+
(void)ssl;
10245+
if (ip[0] != -1 || ipSz != 1 || port != 1 || fam != 2)
10246+
return 0;
10247+
return 1;
10248+
}
10249+
10250+
static int test_wolfSSL_dtls_export_peers_on_handshake(WOLFSSL_CTX **ctx,
10251+
WOLFSSL **ssl)
10252+
{
10253+
EXPECT_DECLS;
10254+
unsigned char* sessionBuf = NULL;
10255+
unsigned int sessionSz = 0;
10256+
void* ioWriteCtx = wolfSSL_GetIOWriteCtx(*ssl);
10257+
void* ioReadCtx = wolfSSL_GetIOReadCtx(*ssl);
10258+
10259+
wolfSSL_CTX_SetIOGetPeer(*ctx, test_wolfSSL_dtls_export_peers_get_peer);
10260+
wolfSSL_CTX_SetIOSetPeer(*ctx, test_wolfSSL_dtls_export_peers_set_peer);
10261+
ExpectIntGE(wolfSSL_dtls_export(*ssl, NULL, &sessionSz), 0);
10262+
ExpectNotNull(sessionBuf =
10263+
(unsigned char*)XMALLOC(sessionSz, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER));
10264+
ExpectIntGE(wolfSSL_dtls_export(*ssl, sessionBuf, &sessionSz), 0);
10265+
wolfSSL_free(*ssl);
10266+
*ssl = NULL;
10267+
ExpectNotNull(*ssl = wolfSSL_new(*ctx));
10268+
ExpectIntGE(wolfSSL_dtls_import(*ssl, sessionBuf, sessionSz), 0);
10269+
wolfSSL_SetIOWriteCtx(*ssl, ioWriteCtx);
10270+
wolfSSL_SetIOReadCtx(*ssl, ioReadCtx);
10271+
10272+
XFREE(sessionBuf, HEAP_HINT, DYNAMIC_TYPE_TMP_BUFFER);
10273+
return EXPECT_RESULT();
10274+
}
10275+
#endif
10276+
10277+
static int test_wolfSSL_dtls_export_peers(void)
10278+
{
10279+
EXPECT_DECLS;
10280+
#if defined(WOLFSSL_DTLS) && defined(WOLFSSL_SESSION_EXPORT) && \
10281+
defined(HAVE_SSL_MEMIO_TESTS_DEPENDENCIES)
10282+
test_ssl_cbf client_cbf;
10283+
test_ssl_cbf server_cbf;
10284+
size_t i, j;
10285+
struct test_params {
10286+
method_provider client_meth;
10287+
method_provider server_meth;
10288+
const char* dtls_version;
10289+
} params[] = {
10290+
#ifndef NO_OLD_TLS
10291+
{wolfDTLSv1_client_method, wolfDTLSv1_server_method, "1.0"},
10292+
#endif
10293+
{wolfDTLSv1_2_client_method, wolfDTLSv1_2_server_method, "1.2"},
10294+
/* TODO DTLS 1.3 exporting not supported
10295+
#ifdef WOLFSSL_DTLS13
10296+
{wolfDTLSv1_3_client_method, wolfDTLSv1_3_server_method, "1.3"},
10297+
#endif
10298+
*/
10299+
};
10300+
10301+
for (i = 0; i < sizeof(params)/sizeof(*params); i++) {
10302+
for (j = 0; j <= 0b11; j++) {
10303+
XMEMSET(&client_cbf, 0, sizeof(client_cbf));
10304+
XMEMSET(&server_cbf, 0, sizeof(server_cbf));
10305+
10306+
printf("\n\tTesting DTLS %s connection;", params[i].dtls_version);
10307+
10308+
client_cbf.method = params[i].client_meth;
10309+
server_cbf.method = params[i].server_meth;
10310+
10311+
if (j & 0b01) {
10312+
client_cbf.on_handshake =
10313+
test_wolfSSL_dtls_export_peers_on_handshake;
10314+
printf(" With client export;");
10315+
}
10316+
if (j & 0b10) {
10317+
server_cbf.on_handshake =
10318+
test_wolfSSL_dtls_export_peers_on_handshake;
10319+
printf(" With server export;");
10320+
}
10321+
10322+
printf("\n");
10323+
10324+
ExpectIntEQ(test_wolfSSL_client_server_nofail_memio(&client_cbf,
10325+
&server_cbf, NULL), TEST_SUCCESS);
10326+
if (!EXPECT_SUCCESS())
10327+
break;
10328+
}
10329+
}
10330+
#endif
10331+
return EXPECT_RESULT();
10332+
}
10333+
1021710334
static int test_wolfSSL_UseTrustedCA(void)
1021810335
{
1021910336
EXPECT_DECLS;
@@ -69705,6 +69822,7 @@ TEST_CASE testCases[] = {
6970569822
/* Uses Assert in handshake callback. */
6970669823
TEST_DECL(test_wolfSSL_tls_export),
6970769824
#endif
69825+
TEST_DECL(test_wolfSSL_dtls_export_peers),
6970869826
TEST_DECL(test_wolfSSL_SetMinVersion),
6970969827
TEST_DECL(test_wolfSSL_CTX_SetMinVersion),
6971069828

wolfssl/internal.h

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1652,7 +1652,8 @@ enum Misc {
16521652
DTLS_EXPORT_PRO = 165,/* wolfSSL protocol for serialized session */
16531653
DTLS_EXPORT_STATE_PRO = 166,/* wolfSSL protocol for serialized state */
16541654
TLS_EXPORT_PRO = 167,/* wolfSSL protocol for serialized TLS */
1655-
DTLS_EXPORT_OPT_SZ = 61, /* amount of bytes used from Options */
1655+
DTLS_EXPORT_OPT_SZ = 62, /* amount of bytes used from Options */
1656+
DTLS_EXPORT_OPT_SZ_4 = 61, /* amount of bytes used from Options */
16561657
TLS_EXPORT_OPT_SZ = 65, /* amount of bytes used from Options */
16571658
DTLS_EXPORT_OPT_SZ_3 = 60, /* amount of bytes used from Options */
16581659
DTLS_EXPORT_KEY_SZ = 325 + (DTLS_SEQ_SZ * 2),
@@ -1665,8 +1666,9 @@ enum Misc {
16651666
WOLFSSL_EXPORT_SPC_SZ = 16, /* amount of bytes used from CipherSpecs */
16661667
#endif
16671668
WOLFSSL_EXPORT_LEN = 2, /* 2 bytes for length and protocol */
1668-
WOLFSSL_EXPORT_VERSION = 4, /* wolfSSL version for serialized session */
1669+
WOLFSSL_EXPORT_VERSION = 5, /* wolfSSL version for serialized session */
16691670

1671+
WOLFSSL_EXPORT_VERSION_4 = 4, /* 5.6.4 release and before */
16701672
/* older export versions supported */
16711673
WOLFSSL_EXPORT_VERSION_3 = 3, /* wolfSSL version before TLS 1.3 addition */
16721674

0 commit comments

Comments
 (0)