diff options
Diffstat (limited to 'net/sctp/chunk.c')
| -rw-r--r-- | net/sctp/chunk.c | 20 | 
1 files changed, 14 insertions, 6 deletions
diff --git a/net/sctp/chunk.c b/net/sctp/chunk.c index 7c2df9c33df..69ce21e3716 100644 --- a/net/sctp/chunk.c +++ b/net/sctp/chunk.c @@ -183,7 +183,7 @@ struct sctp_datamsg *sctp_datamsg_from_user(struct sctp_association *asoc,  	msg = sctp_datamsg_new(GFP_KERNEL);  	if (!msg) -		return NULL; +		return ERR_PTR(-ENOMEM);  	/* Note: Calculate this outside of the loop, so that all fragments  	 * have the same expiration. @@ -280,11 +280,14 @@ struct sctp_datamsg *sctp_datamsg_from_user(struct sctp_association *asoc,  		chunk = sctp_make_datafrag_empty(asoc, sinfo, len, frag, 0); -		if (!chunk) +		if (!chunk) { +			err = -ENOMEM;  			goto errout; +		} +  		err = sctp_user_addto_chunk(chunk, offset, len, msgh->msg_iov);  		if (err < 0) -			goto errout; +			goto errout_chunk_free;  		offset += len; @@ -315,8 +318,10 @@ struct sctp_datamsg *sctp_datamsg_from_user(struct sctp_association *asoc,  		chunk = sctp_make_datafrag_empty(asoc, sinfo, over, frag, 0); -		if (!chunk) +		if (!chunk) { +			err = -ENOMEM;  			goto errout; +		}  		err = sctp_user_addto_chunk(chunk, offset, over,msgh->msg_iov); @@ -324,7 +329,7 @@ struct sctp_datamsg *sctp_datamsg_from_user(struct sctp_association *asoc,  		__skb_pull(chunk->skb, (__u8 *)chunk->chunk_hdr  			   - (__u8 *)chunk->skb->data);  		if (err < 0) -			goto errout; +			goto errout_chunk_free;  		sctp_datamsg_assign(msg, chunk);  		list_add_tail(&chunk->frag_list, &msg->chunks); @@ -332,6 +337,9 @@ struct sctp_datamsg *sctp_datamsg_from_user(struct sctp_association *asoc,  	return msg; +errout_chunk_free: +	sctp_chunk_free(chunk); +  errout:  	list_for_each_safe(pos, temp, &msg->chunks) {  		list_del_init(pos); @@ -339,7 +347,7 @@ errout:  		sctp_chunk_free(chunk);  	}  	sctp_datamsg_put(msg); -	return NULL; +	return ERR_PTR(err);  }  /* Check whether this message has expired. */  |