dtls handshake improvement

This commit is contained in:
John Safranek 2012-09-14 19:30:50 -07:00
parent 56ee2eaba8
commit 7899252104
3 changed files with 35 additions and 17 deletions

View File

@ -968,6 +968,8 @@ typedef struct Keys {
word32 dtls_peer_sequence_number; word32 dtls_peer_sequence_number;
word32 dtls_expected_peer_sequence_number; word32 dtls_expected_peer_sequence_number;
word16 dtls_handshake_number; word16 dtls_handshake_number;
word16 dtls_peer_handshake_number;
word16 dtls_expected_peer_handshake_number;
word16 dtls_epoch; word16 dtls_epoch;
word16 dtls_peer_epoch; word16 dtls_peer_epoch;
word16 dtls_expected_peer_epoch; word16 dtls_expected_peer_epoch;
@ -1492,6 +1494,7 @@ CYASSL_LOCAL void BuildTlsFinished(CYASSL* ssl, Hashes* hashes,
#ifdef CYASSL_DTLS #ifdef CYASSL_DTLS
CYASSL_LOCAL int DtlsPoolInit(CYASSL*); CYASSL_LOCAL int DtlsPoolInit(CYASSL*);
CYASSL_LOCAL void DtlsPoolSave(CYASSL*, const byte*, int); CYASSL_LOCAL void DtlsPoolSave(CYASSL*, const byte*, int);
CYASSL_LOCAL int DtlsPoolTimeout(CYASSL*);
CYASSL_LOCAL int DtlsPoolSend(CYASSL*); CYASSL_LOCAL int DtlsPoolSend(CYASSL*);
CYASSL_LOCAL void DtlsPoolReset(CYASSL*); CYASSL_LOCAL void DtlsPoolReset(CYASSL*);
#endif /* CYASSL_DTLS */ #endif /* CYASSL_DTLS */

View File

@ -977,6 +977,7 @@ int InitSSL(CYASSL* ssl, CYASSL_CTX* ctx)
ssl->keys.dtls_peer_sequence_number = 0; ssl->keys.dtls_peer_sequence_number = 0;
ssl->keys.dtls_expected_peer_sequence_number = 0; ssl->keys.dtls_expected_peer_sequence_number = 0;
ssl->keys.dtls_handshake_number = 0; ssl->keys.dtls_handshake_number = 0;
ssl->keys.dtls_expected_peer_handshake_number = 0;
ssl->keys.dtls_epoch = 0; ssl->keys.dtls_epoch = 0;
ssl->keys.dtls_peer_epoch = 0; ssl->keys.dtls_peer_epoch = 0;
ssl->keys.dtls_expected_peer_epoch = 0; ssl->keys.dtls_expected_peer_epoch = 0;
@ -1241,6 +1242,17 @@ void DtlsPoolReset(CYASSL* ssl)
} }
int DtlsPoolTimeout(CYASSL* ssl)
{
int result = -1;
if (ssl->dtls_timeout < 64) {
ssl->dtls_timeout *= 2;
result = 0;
}
return result;
}
int DtlsPoolSend(CYASSL* ssl) int DtlsPoolSend(CYASSL* ssl)
{ {
DtlsPool *pool = ssl->dtls_pool; DtlsPool *pool = ssl->dtls_pool;
@ -1532,8 +1544,10 @@ retry:
#ifdef CYASSL_DTLS #ifdef CYASSL_DTLS
case IO_ERR_TIMEOUT: case IO_ERR_TIMEOUT:
DtlsPoolSend(ssl); if (DtlsPoolTimeout(ssl) == 0 && DtlsPoolSend(ssl) == 0)
goto retry; goto retry;
else
return -1;
#endif #endif
default: default:
@ -1803,14 +1817,13 @@ static int GetDtlsHandShakeHeader(CYASSL* ssl, const byte* input,
{ {
word32 idx = *inOutIdx; word32 idx = *inOutIdx;
(void)ssl;
*inOutIdx += HANDSHAKE_HEADER_SZ + DTLS_HANDSHAKE_EXTRA; *inOutIdx += HANDSHAKE_HEADER_SZ + DTLS_HANDSHAKE_EXTRA;
*type = input[idx++]; *type = input[idx++];
c24to32(input + idx, size); c24to32(input + idx, size);
idx += BYTE3_LEN; idx += BYTE3_LEN;
/* skip the sequence number */ ato16(input + idx, &ssl->keys.dtls_peer_handshake_number);
idx += DTLS_HANDSHAKE_SEQ_SZ; idx += DTLS_HANDSHAKE_SEQ_SZ;
c24to32(input + idx, fragOffset); c24to32(input + idx, fragOffset);
@ -2484,6 +2497,15 @@ static int DoDtlsHandShakeMsg(CYASSL* ssl, byte* input, word32* inOutIdx,
if (*inOutIdx + fragSz > totalSz) if (*inOutIdx + fragSz > totalSz)
return INCOMPLETE_DATA; return INCOMPLETE_DATA;
if (ssl->keys.dtls_peer_handshake_number ==
ssl->keys.dtls_expected_peer_handshake_number) {
ssl->keys.dtls_expected_peer_handshake_number++;
}
else {
*inOutIdx += size;
return 0;
}
if (fragSz < size) { if (fragSz < size) {
/* message is fragmented, knit back together */ /* message is fragmented, knit back together */
byte* buf = ssl->buffers.dtlsHandshake.buffer; byte* buf = ssl->buffers.dtlsHandshake.buffer;

View File

@ -2226,23 +2226,16 @@ int CyaSSL_dtls_get_current_timeout(CYASSL* ssl)
int CyaSSL_dtls_got_timeout(CYASSL* ssl) int CyaSSL_dtls_got_timeout(CYASSL* ssl)
{ {
int result = SSL_NOT_IMPLEMENTED;
(void)ssl;
#ifdef CYASSL_DTLS #ifdef CYASSL_DTLS
if (ssl->dtls_timeout < 64) { int result = SSL_SUCCESS;
ssl->dtls_timeout *= 2; if (DtlsPoolTimeout(ssl) < 0 || DtlsPoolSend(ssl) < 0) {
if (DtlsPoolSend(ssl) < 0)
result = SSL_FATAL_ERROR;
else
result = SSL_SUCCESS;
}
else {
result = SSL_FATAL_ERROR; result = SSL_FATAL_ERROR;
} }
#endif
return result; return result;
#else
(void)ssl;
return SSL_NOT_IMPLEMENTED;
#endif
} }