aboutsummaryrefslogtreecommitdiffstats
path: root/net/sctp
diff options
context:
space:
mode:
authorAl Viro <viro@zeniv.linux.org.uk>2014-11-15 01:11:23 -0500
committerAl Viro <viro@zeniv.linux.org.uk>2014-11-24 05:16:40 -0500
commite0eb093e794452791b0f932a0120f410f614ad82 (patch)
tree598ab3c7b9f2d179e3b3c318cc0619e304c2bd5f /net/sctp
parent8feb2fb2bb986c533e18037d3c45a5f779421992 (diff)
switch sctp_user_addto_chunk() and sctp_datamsg_from_user() to passing iov_iter
Signed-off-by: Al Viro <viro@zeniv.linux.org.uk>
Diffstat (limited to 'net/sctp')
-rw-r--r--net/sctp/chunk.c9
-rw-r--r--net/sctp/sm_make_chunk.c16
-rw-r--r--net/sctp/socket.c5
3 files changed, 16 insertions, 14 deletions
diff --git a/net/sctp/chunk.c b/net/sctp/chunk.c
index 158701da2d31..a3380917f197 100644
--- a/net/sctp/chunk.c
+++ b/net/sctp/chunk.c
@@ -164,7 +164,7 @@ static void sctp_datamsg_assign(struct sctp_datamsg *msg, struct sctp_chunk *chu
164 */ 164 */
165struct sctp_datamsg *sctp_datamsg_from_user(struct sctp_association *asoc, 165struct sctp_datamsg *sctp_datamsg_from_user(struct sctp_association *asoc,
166 struct sctp_sndrcvinfo *sinfo, 166 struct sctp_sndrcvinfo *sinfo,
167 struct msghdr *msgh, int msg_len) 167 struct iov_iter *from)
168{ 168{
169 int max, whole, i, offset, over, err; 169 int max, whole, i, offset, over, err;
170 int len, first_len; 170 int len, first_len;
@@ -172,6 +172,7 @@ struct sctp_datamsg *sctp_datamsg_from_user(struct sctp_association *asoc,
172 struct sctp_chunk *chunk; 172 struct sctp_chunk *chunk;
173 struct sctp_datamsg *msg; 173 struct sctp_datamsg *msg;
174 struct list_head *pos, *temp; 174 struct list_head *pos, *temp;
175 size_t msg_len = iov_iter_count(from);
175 __u8 frag; 176 __u8 frag;
176 177
177 msg = sctp_datamsg_new(GFP_KERNEL); 178 msg = sctp_datamsg_new(GFP_KERNEL);
@@ -279,12 +280,10 @@ struct sctp_datamsg *sctp_datamsg_from_user(struct sctp_association *asoc,
279 goto errout; 280 goto errout;
280 } 281 }
281 282
282 err = sctp_user_addto_chunk(chunk, offset, len, msgh->msg_iov); 283 err = sctp_user_addto_chunk(chunk, len, from);
283 if (err < 0) 284 if (err < 0)
284 goto errout_chunk_free; 285 goto errout_chunk_free;
285 286
286 offset += len;
287
288 /* Put the chunk->skb back into the form expected by send. */ 287 /* Put the chunk->skb back into the form expected by send. */
289 __skb_pull(chunk->skb, (__u8 *)chunk->chunk_hdr 288 __skb_pull(chunk->skb, (__u8 *)chunk->chunk_hdr
290 - (__u8 *)chunk->skb->data); 289 - (__u8 *)chunk->skb->data);
@@ -317,7 +316,7 @@ struct sctp_datamsg *sctp_datamsg_from_user(struct sctp_association *asoc,
317 goto errout; 316 goto errout;
318 } 317 }
319 318
320 err = sctp_user_addto_chunk(chunk, offset, over, msgh->msg_iov); 319 err = sctp_user_addto_chunk(chunk, over, from);
321 320
322 /* Put the chunk->skb back into the form expected by send. */ 321 /* Put the chunk->skb back into the form expected by send. */
323 __skb_pull(chunk->skb, (__u8 *)chunk->chunk_hdr 322 __skb_pull(chunk->skb, (__u8 *)chunk->chunk_hdr
diff --git a/net/sctp/sm_make_chunk.c b/net/sctp/sm_make_chunk.c
index e49bccebb0cc..e49e231cef52 100644
--- a/net/sctp/sm_make_chunk.c
+++ b/net/sctp/sm_make_chunk.c
@@ -1491,26 +1491,26 @@ static void *sctp_addto_chunk_fixed(struct sctp_chunk *chunk,
1491 * chunk is not big enough. 1491 * chunk is not big enough.
1492 * Returns a kernel err value. 1492 * Returns a kernel err value.
1493 */ 1493 */
1494int sctp_user_addto_chunk(struct sctp_chunk *chunk, int off, int len, 1494int sctp_user_addto_chunk(struct sctp_chunk *chunk, int len,
1495 struct iovec *data) 1495 struct iov_iter *from)
1496{ 1496{
1497 __u8 *target; 1497 void *target;
1498 int err = 0; 1498 ssize_t copied;
1499 1499
1500 /* Make room in chunk for data. */ 1500 /* Make room in chunk for data. */
1501 target = skb_put(chunk->skb, len); 1501 target = skb_put(chunk->skb, len);
1502 1502
1503 /* Copy data (whole iovec) into chunk */ 1503 /* Copy data (whole iovec) into chunk */
1504 if ((err = memcpy_fromiovecend(target, data, off, len))) 1504 copied = copy_from_iter(target, len, from);
1505 goto out; 1505 if (copied != len)
1506 return -EFAULT;
1506 1507
1507 /* Adjust the chunk length field. */ 1508 /* Adjust the chunk length field. */
1508 chunk->chunk_hdr->length = 1509 chunk->chunk_hdr->length =
1509 htons(ntohs(chunk->chunk_hdr->length) + len); 1510 htons(ntohs(chunk->chunk_hdr->length) + len);
1510 chunk->chunk_end = skb_tail_pointer(chunk->skb); 1511 chunk->chunk_end = skb_tail_pointer(chunk->skb);
1511 1512
1512out: 1513 return 0;
1513 return err;
1514} 1514}
1515 1515
1516/* Helper function to assign a TSN if needed. This assumes that both 1516/* Helper function to assign a TSN if needed. This assumes that both
diff --git a/net/sctp/socket.c b/net/sctp/socket.c
index 85e0b653edd7..0397ac9fd98c 100644
--- a/net/sctp/socket.c
+++ b/net/sctp/socket.c
@@ -1609,6 +1609,9 @@ static int sctp_sendmsg(struct kiocb *iocb, struct sock *sk,
1609 __u16 sinfo_flags = 0; 1609 __u16 sinfo_flags = 0;
1610 long timeo; 1610 long timeo;
1611 int err; 1611 int err;
1612 struct iov_iter from;
1613
1614 iov_iter_init(&from, WRITE, msg->msg_iov, msg->msg_iovlen, msg_len);
1612 1615
1613 err = 0; 1616 err = 0;
1614 sp = sctp_sk(sk); 1617 sp = sctp_sk(sk);
@@ -1947,7 +1950,7 @@ static int sctp_sendmsg(struct kiocb *iocb, struct sock *sk,
1947 } 1950 }
1948 1951
1949 /* Break the message into multiple chunks of maximum size. */ 1952 /* Break the message into multiple chunks of maximum size. */
1950 datamsg = sctp_datamsg_from_user(asoc, sinfo, msg, msg_len); 1953 datamsg = sctp_datamsg_from_user(asoc, sinfo, &from);
1951 if (IS_ERR(datamsg)) { 1954 if (IS_ERR(datamsg)) {
1952 err = PTR_ERR(datamsg); 1955 err = PTR_ERR(datamsg);
1953 goto out_free; 1956 goto out_free;