diff options
-rw-r--r-- | net/sctp/input.c | 13 | ||||
-rw-r--r-- | net/sctp/sm_statefuns.c | 2 |
2 files changed, 11 insertions, 4 deletions
diff --git a/net/sctp/input.c b/net/sctp/input.c index 71fd56375641..cb78b50868ee 100644 --- a/net/sctp/input.c +++ b/net/sctp/input.c | |||
@@ -588,10 +588,16 @@ int sctp_rcv_ootb(struct sk_buff *skb) | |||
588 | sctp_errhdr_t *err; | 588 | sctp_errhdr_t *err; |
589 | 589 | ||
590 | ch = (sctp_chunkhdr_t *) skb->data; | 590 | ch = (sctp_chunkhdr_t *) skb->data; |
591 | ch_end = ((__u8 *) ch) + WORD_ROUND(ntohs(ch->length)); | ||
592 | 591 | ||
593 | /* Scan through all the chunks in the packet. */ | 592 | /* Scan through all the chunks in the packet. */ |
594 | while (ch_end > (__u8 *)ch && ch_end < skb->tail) { | 593 | do { |
594 | /* Break out if chunk length is less then minimal. */ | ||
595 | if (ntohs(ch->length) < sizeof(sctp_chunkhdr_t)) | ||
596 | break; | ||
597 | |||
598 | ch_end = ((__u8 *)ch) + WORD_ROUND(ntohs(ch->length)); | ||
599 | if (ch_end > skb->tail) | ||
600 | break; | ||
595 | 601 | ||
596 | /* RFC 8.4, 2) If the OOTB packet contains an ABORT chunk, the | 602 | /* RFC 8.4, 2) If the OOTB packet contains an ABORT chunk, the |
597 | * receiver MUST silently discard the OOTB packet and take no | 603 | * receiver MUST silently discard the OOTB packet and take no |
@@ -622,8 +628,7 @@ int sctp_rcv_ootb(struct sk_buff *skb) | |||
622 | } | 628 | } |
623 | 629 | ||
624 | ch = (sctp_chunkhdr_t *) ch_end; | 630 | ch = (sctp_chunkhdr_t *) ch_end; |
625 | ch_end = ((__u8 *) ch) + WORD_ROUND(ntohs(ch->length)); | 631 | } while (ch_end < skb->tail); |
626 | } | ||
627 | 632 | ||
628 | return 0; | 633 | return 0; |
629 | 634 | ||
diff --git a/net/sctp/sm_statefuns.c b/net/sctp/sm_statefuns.c index 477d7f80dba6..71c9a961c321 100644 --- a/net/sctp/sm_statefuns.c +++ b/net/sctp/sm_statefuns.c | |||
@@ -3090,6 +3090,8 @@ sctp_disposition_t sctp_sf_ootb(const struct sctp_endpoint *ep, | |||
3090 | break; | 3090 | break; |
3091 | 3091 | ||
3092 | ch_end = ((__u8 *)ch) + WORD_ROUND(ntohs(ch->length)); | 3092 | ch_end = ((__u8 *)ch) + WORD_ROUND(ntohs(ch->length)); |
3093 | if (ch_end > skb->tail) | ||
3094 | break; | ||
3093 | 3095 | ||
3094 | if (SCTP_CID_SHUTDOWN_ACK == ch->type) | 3096 | if (SCTP_CID_SHUTDOWN_ACK == ch->type) |
3095 | ootb_shut_ack = 1; | 3097 | ootb_shut_ack = 1; |