|
|
653b37 |
diff -up openssl-1.0.1e/ssl/d1_pkt.c.dtls1-replay openssl-1.0.1e/ssl/d1_pkt.c
|
|
|
653b37 |
--- openssl-1.0.1e/ssl/d1_pkt.c.dtls1-replay 2016-09-20 16:29:36.767447143 +0200
|
|
|
653b37 |
+++ openssl-1.0.1e/ssl/d1_pkt.c 2016-09-20 16:44:56.654893514 +0200
|
|
|
653b37 |
@@ -178,7 +178,7 @@ static int dtls1_record_needs_buffering(
|
|
|
653b37 |
#endif
|
|
|
653b37 |
static int dtls1_buffer_record(SSL *s, record_pqueue *q,
|
|
|
653b37 |
unsigned char *priority);
|
|
|
653b37 |
-static int dtls1_process_record(SSL *s);
|
|
|
653b37 |
+static int dtls1_process_record(SSL *s, DTLS1_BITMAP *bitmap);
|
|
|
653b37 |
|
|
|
653b37 |
/* copy buffered record into SSL structure */
|
|
|
653b37 |
static int
|
|
|
653b37 |
@@ -304,32 +304,84 @@ static int
|
|
|
653b37 |
dtls1_process_buffered_records(SSL *s)
|
|
|
653b37 |
{
|
|
|
653b37 |
pitem *item;
|
|
|
653b37 |
-
|
|
|
653b37 |
+ SSL3_BUFFER *rb;
|
|
|
653b37 |
+ SSL3_RECORD *rr;
|
|
|
653b37 |
+ DTLS1_BITMAP *bitmap;
|
|
|
653b37 |
+ unsigned int is_next_epoch;
|
|
|
653b37 |
+ int replayok = 1;
|
|
|
653b37 |
+
|
|
|
653b37 |
item = pqueue_peek(s->d1->unprocessed_rcds.q);
|
|
|
653b37 |
if (item)
|
|
|
653b37 |
{
|
|
|
653b37 |
/* Check if epoch is current. */
|
|
|
653b37 |
if (s->d1->unprocessed_rcds.epoch != s->d1->r_epoch)
|
|
|
653b37 |
- return(1); /* Nothing to do. */
|
|
|
653b37 |
-
|
|
|
653b37 |
+ return 1; /* Nothing to do. */
|
|
|
653b37 |
+
|
|
|
653b37 |
+ rr = &s->s3->rrec;
|
|
|
653b37 |
+ rb = &s->s3->rbuf;
|
|
|
653b37 |
+
|
|
|
653b37 |
+ if (rb->left > 0)
|
|
|
653b37 |
+ {
|
|
|
653b37 |
+ /*
|
|
|
653b37 |
+ * We've still got data from the current packet to read. There could
|
|
|
653b37 |
+ * be a record from the new epoch in it - so don't overwrite it
|
|
|
653b37 |
+ * with the unprocessed records yet (we'll do it when we've
|
|
|
653b37 |
+ * finished reading the current packet).
|
|
|
653b37 |
+ */
|
|
|
653b37 |
+ return 1;
|
|
|
653b37 |
+ }
|
|
|
653b37 |
+
|
|
|
653b37 |
+
|
|
|
653b37 |
/* Process all the records. */
|
|
|
653b37 |
while (pqueue_peek(s->d1->unprocessed_rcds.q))
|
|
|
653b37 |
{
|
|
|
653b37 |
dtls1_get_unprocessed_record(s);
|
|
|
653b37 |
- if ( ! dtls1_process_record(s))
|
|
|
653b37 |
- return(0);
|
|
|
653b37 |
- if(dtls1_buffer_record(s, &(s->d1->processed_rcds),
|
|
|
653b37 |
- s->s3->rrec.seq_num)<0)
|
|
|
653b37 |
- return -1;
|
|
|
653b37 |
- }
|
|
|
653b37 |
+ bitmap = dtls1_get_bitmap(s, rr, &is_next_epoch);
|
|
|
653b37 |
+ if (bitmap == NULL)
|
|
|
653b37 |
+ {
|
|
|
653b37 |
+ /*
|
|
|
653b37 |
+ * Should not happen. This will only ever be NULL when the
|
|
|
653b37 |
+ * current record is from a different epoch. But that cannot
|
|
|
653b37 |
+ * be the case because we already checked the epoch above
|
|
|
653b37 |
+ */
|
|
|
653b37 |
+ SSLerr(SSL_F_DTLS1_PROCESS_BUFFERED_RECORDS,
|
|
|
653b37 |
+ ERR_R_INTERNAL_ERROR);
|
|
|
653b37 |
+ return 0;
|
|
|
653b37 |
+ }
|
|
|
653b37 |
+#ifndef OPENSSL_NO_SCTP
|
|
|
653b37 |
+ /* Only do replay check if no SCTP bio */
|
|
|
653b37 |
+ if (!BIO_dgram_is_sctp(SSL_get_rbio(s)))
|
|
|
653b37 |
+#endif
|
|
|
653b37 |
+ {
|
|
|
653b37 |
+ /*
|
|
|
653b37 |
+ * Check whether this is a repeat, or aged record. We did this
|
|
|
653b37 |
+ * check once already when we first received the record - but
|
|
|
653b37 |
+ * we might have updated the window since then due to
|
|
|
653b37 |
+ * records we subsequently processed.
|
|
|
653b37 |
+ */
|
|
|
653b37 |
+ replayok = dtls1_record_replay_check(s, bitmap);
|
|
|
653b37 |
+ }
|
|
|
653b37 |
+
|
|
|
653b37 |
+ if (!replayok || !dtls1_process_record(s, bitmap))
|
|
|
653b37 |
+ {
|
|
|
653b37 |
+ /* dump this record */
|
|
|
653b37 |
+ rr->length = 0;
|
|
|
653b37 |
+ s->packet_length = 0;
|
|
|
653b37 |
+ continue;
|
|
|
653b37 |
+ }
|
|
|
653b37 |
+
|
|
|
653b37 |
+ if (dtls1_buffer_record(s, &(s->d1->processed_rcds),
|
|
|
653b37 |
+ s->s3->rrec.seq_num) < 0)
|
|
|
653b37 |
+ return 0;
|
|
|
653b37 |
}
|
|
|
653b37 |
+ }
|
|
|
653b37 |
|
|
|
653b37 |
/* sync epoch numbers once all the unprocessed records
|
|
|
653b37 |
* have been processed */
|
|
|
653b37 |
s->d1->processed_rcds.epoch = s->d1->r_epoch;
|
|
|
653b37 |
s->d1->unprocessed_rcds.epoch = s->d1->r_epoch + 1;
|
|
|
653b37 |
|
|
|
653b37 |
- return(1);
|
|
|
653b37 |
+ return 1;
|
|
|
653b37 |
}
|
|
|
653b37 |
|
|
|
653b37 |
|
|
|
653b37 |
@@ -379,7 +431,7 @@ dtls1_get_buffered_record(SSL *s)
|
|
|
653b37 |
#endif
|
|
|
653b37 |
|
|
|
653b37 |
static int
|
|
|
653b37 |
-dtls1_process_record(SSL *s)
|
|
|
653b37 |
+dtls1_process_record(SSL *s, DTLS1_BITMAP *bitmap)
|
|
|
653b37 |
{
|
|
|
653b37 |
int i,al;
|
|
|
653b37 |
int enc_err;
|
|
|
653b37 |
@@ -535,6 +587,10 @@ printf("\n");
|
|
|
653b37 |
|
|
|
653b37 |
/* we have pulled in a full packet so zero things */
|
|
|
653b37 |
s->packet_length=0;
|
|
|
653b37 |
+
|
|
|
653b37 |
+ /* Mark receipt of record. */
|
|
|
653b37 |
+ dtls1_record_bitmap_update(s, bitmap);
|
|
|
653b37 |
+
|
|
|
653b37 |
return(1);
|
|
|
653b37 |
|
|
|
653b37 |
f_err:
|
|
|
653b37 |
@@ -565,9 +621,10 @@ int dtls1_get_record(SSL *s)
|
|
|
653b37 |
|
|
|
653b37 |
rr= &(s->s3->rrec);
|
|
|
653b37 |
|
|
|
653b37 |
+again:
|
|
|
653b37 |
/* The epoch may have changed. If so, process all the
|
|
|
653b37 |
* pending records. This is a non-blocking operation. */
|
|
|
653b37 |
- if(dtls1_process_buffered_records(s)<0)
|
|
|
653b37 |
+ if(!dtls1_process_buffered_records(s))
|
|
|
653b37 |
return -1;
|
|
|
653b37 |
|
|
|
653b37 |
/* if we're renegotiating, then there may be buffered records */
|
|
|
653b37 |
@@ -575,7 +632,6 @@ int dtls1_get_record(SSL *s)
|
|
|
653b37 |
return 1;
|
|
|
653b37 |
|
|
|
653b37 |
/* get something from the wire */
|
|
|
653b37 |
-again:
|
|
|
653b37 |
/* check if we have the header */
|
|
|
653b37 |
if ( (s->rstate != SSL_ST_READ_BODY) ||
|
|
|
653b37 |
(s->packet_length < DTLS1_RT_HEADER_LENGTH))
|
|
|
653b37 |
@@ -707,20 +763,18 @@ again:
|
|
|
653b37 |
{
|
|
|
653b37 |
if(dtls1_buffer_record(s, &(s->d1->unprocessed_rcds), rr->seq_num)<0)
|
|
|
653b37 |
return -1;
|
|
|
653b37 |
- dtls1_record_bitmap_update(s, bitmap);/* Mark receipt of record. */
|
|
|
653b37 |
}
|
|
|
653b37 |
rr->length = 0;
|
|
|
653b37 |
s->packet_length = 0;
|
|
|
653b37 |
goto again;
|
|
|
653b37 |
}
|
|
|
653b37 |
|
|
|
653b37 |
- if (!dtls1_process_record(s))
|
|
|
653b37 |
+ if (!dtls1_process_record(s, bitmap))
|
|
|
653b37 |
{
|
|
|
653b37 |
rr->length = 0;
|
|
|
653b37 |
s->packet_length = 0; /* dump this record */
|
|
|
653b37 |
goto again; /* get another record */
|
|
|
653b37 |
}
|
|
|
653b37 |
- dtls1_record_bitmap_update(s, bitmap);/* Mark receipt of record. */
|
|
|
653b37 |
|
|
|
653b37 |
return(1);
|
|
|
653b37 |
|
|
|
653b37 |
@@ -1811,8 +1865,13 @@ dtls1_get_bitmap(SSL *s, SSL3_RECORD *rr
|
|
|
653b37 |
if (rr->epoch == s->d1->r_epoch)
|
|
|
653b37 |
return &s->d1->bitmap;
|
|
|
653b37 |
|
|
|
653b37 |
- /* Only HM and ALERT messages can be from the next epoch */
|
|
|
653b37 |
+ /*
|
|
|
653b37 |
+ * Only HM and ALERT messages can be from the next epoch and only if we
|
|
|
653b37 |
+ * have already processed all of the unprocessed records from the last
|
|
|
653b37 |
+ * epoch
|
|
|
653b37 |
+ */
|
|
|
653b37 |
else if (rr->epoch == (unsigned long)(s->d1->r_epoch + 1) &&
|
|
|
653b37 |
+ s->d1->unprocessed_rcds.epoch != s->d1->r_epoch &&
|
|
|
653b37 |
(rr->type == SSL3_RT_HANDSHAKE ||
|
|
|
653b37 |
rr->type == SSL3_RT_ALERT))
|
|
|
653b37 |
{
|
|
|
653b37 |
diff -up openssl-1.0.1e/ssl/ssl_err.c.dtls1-replay openssl-1.0.1e/ssl/ssl_err.c
|
|
|
653b37 |
--- openssl-1.0.1e/ssl/ssl_err.c.dtls1-replay 2016-09-20 14:55:57.789311197 +0200
|
|
|
653b37 |
+++ openssl-1.0.1e/ssl/ssl_err.c 2016-09-20 16:45:49.827132881 +0200
|
|
|
653b37 |
@@ -1,6 +1,6 @@
|
|
|
653b37 |
/* ssl/ssl_err.c */
|
|
|
653b37 |
/* ====================================================================
|
|
|
653b37 |
- * Copyright (c) 1999-2011 The OpenSSL Project. All rights reserved.
|
|
|
653b37 |
+ * Copyright (c) 1999-2016 The OpenSSL Project. All rights reserved.
|
|
|
653b37 |
*
|
|
|
653b37 |
* Redistribution and use in source and binary forms, with or without
|
|
|
653b37 |
* modification, are permitted provided that the following conditions
|
|
|
653b37 |
@@ -92,6 +92,7 @@ static ERR_STRING_DATA SSL_str_functs[]=
|
|
|
653b37 |
{ERR_FUNC(SSL_F_DTLS1_HEARTBEAT), "DTLS1_HEARTBEAT"},
|
|
|
653b37 |
{ERR_FUNC(SSL_F_DTLS1_OUTPUT_CERT_CHAIN), "DTLS1_OUTPUT_CERT_CHAIN"},
|
|
|
653b37 |
{ERR_FUNC(SSL_F_DTLS1_PREPROCESS_FRAGMENT), "DTLS1_PREPROCESS_FRAGMENT"},
|
|
|
653b37 |
+{ERR_FUNC(SSL_F_DTLS1_PROCESS_BUFFERED_RECORDS), "DTLS1_PROCESS_BUFFERED_RECORDS"},
|
|
|
653b37 |
{ERR_FUNC(SSL_F_DTLS1_PROCESS_OUT_OF_SEQ_MESSAGE), "DTLS1_PROCESS_OUT_OF_SEQ_MESSAGE"},
|
|
|
653b37 |
{ERR_FUNC(SSL_F_DTLS1_PROCESS_RECORD), "DTLS1_PROCESS_RECORD"},
|
|
|
653b37 |
{ERR_FUNC(SSL_F_DTLS1_READ_BYTES), "DTLS1_READ_BYTES"},
|
|
|
653b37 |
diff -up openssl-1.0.1e/ssl/ssl.h.dtls1-replay openssl-1.0.1e/ssl/ssl.h
|
|
|
653b37 |
--- openssl-1.0.1e/ssl/ssl.h.dtls1-replay 2016-09-20 16:29:36.768447167 +0200
|
|
|
653b37 |
+++ openssl-1.0.1e/ssl/ssl.h 2016-09-20 16:30:42.981991082 +0200
|
|
|
653b37 |
@@ -2023,6 +2023,7 @@ void ERR_load_SSL_strings(void);
|
|
|
653b37 |
#define SSL_F_DTLS1_HEARTBEAT 305
|
|
|
653b37 |
#define SSL_F_DTLS1_OUTPUT_CERT_CHAIN 255
|
|
|
653b37 |
#define SSL_F_DTLS1_PREPROCESS_FRAGMENT 288
|
|
|
653b37 |
+#define SSL_F_DTLS1_PROCESS_BUFFERED_RECORDS 424
|
|
|
653b37 |
#define SSL_F_DTLS1_PROCESS_OUT_OF_SEQ_MESSAGE 256
|
|
|
653b37 |
#define SSL_F_DTLS1_PROCESS_RECORD 257
|
|
|
653b37 |
#define SSL_F_DTLS1_READ_BYTES 258
|