sctp: get list_of_streams of strreset outreq earlier
authorXin Long <lucien.xin@gmail.com>
Sat, 15 Apr 2017 13:56:57 +0000 (21:56 +0800)
committerDavid S. Miller <davem@davemloft.net>
Mon, 17 Apr 2017 19:25:35 +0000 (15:25 -0400)
Now when processing strreset out responses, it gets outreq->list_of_streams
only when result is performed. But if result is not performed, str_p will
be NULL. It will cause panic in sctp_ulpevent_make_stream_reset_event if
nums is not 0.

This patch is to fix it by getting outreq->list_of_streams earlier, and
also to improve some codes for the strreset inreq process.

Signed-off-by: Xin Long <lucien.xin@gmail.com>
Signed-off-by: David S. Miller <davem@davemloft.net>
net/sctp/stream.c

index eff6008a32ba5e692957daf31d5f405eff77c3b6..4ec3679a1cefc88dae06bba400348d06aa6cec04 100644 (file)
@@ -732,14 +732,14 @@ struct sctp_chunk *sctp_process_strreset_resp(
 
        if (req->type == SCTP_PARAM_RESET_OUT_REQUEST) {
                struct sctp_strreset_outreq *outreq;
-               __u16 *str_p = NULL;
+               __u16 *str_p;
 
                outreq = (struct sctp_strreset_outreq *)req;
+               str_p = outreq->list_of_streams;
                nums = (ntohs(outreq->param_hdr.length) - sizeof(*outreq)) / 2;
 
                if (result == SCTP_STRRESET_PERFORMED) {
                        if (nums) {
-                               str_p = outreq->list_of_streams;
                                for (i = 0; i < nums; i++)
                                        stream->out[ntohs(str_p[i])].ssn = 0;
                        } else {
@@ -757,16 +757,16 @@ struct sctp_chunk *sctp_process_strreset_resp(
                        nums, str_p, GFP_ATOMIC);
        } else if (req->type == SCTP_PARAM_RESET_IN_REQUEST) {
                struct sctp_strreset_inreq *inreq;
-               __u16 *str_p = NULL;
+               __u16 *str_p;
 
                /* if the result is performed, it's impossible for inreq */
                if (result == SCTP_STRRESET_PERFORMED)
                        return NULL;
 
                inreq = (struct sctp_strreset_inreq *)req;
+               str_p = inreq->list_of_streams;
                nums = (ntohs(inreq->param_hdr.length) - sizeof(*inreq)) / 2;
 
-               str_p = inreq->list_of_streams;
                *evp = sctp_ulpevent_make_stream_reset_event(asoc, flags,
                        nums, str_p, GFP_ATOMIC);
        } else if (req->type == SCTP_PARAM_RESET_TSN_REQUEST) {