mirror of
https://mirrors.bfsu.edu.cn/git/linux.git
synced 2024-11-11 21:38:32 +08:00
[atm] switch vcc_sendmsg() to copy_from_iter()
... and make it handle multi-segment iovecs - deals with that "fix this later" issue for free. A bit of shame, really - it had been there since 2.3.15pre3 when the whole thing went into the tree, practically a historical artefact by now... Signed-off-by: Al Viro <viro@zeniv.linux.org.uk>
This commit is contained in:
parent
0f7db23a07
commit
7424ce6506
@ -570,15 +570,16 @@ int vcc_recvmsg(struct kiocb *iocb, struct socket *sock, struct msghdr *msg,
|
||||
}
|
||||
|
||||
int vcc_sendmsg(struct kiocb *iocb, struct socket *sock, struct msghdr *m,
|
||||
size_t total_len)
|
||||
size_t size)
|
||||
{
|
||||
struct sock *sk = sock->sk;
|
||||
DEFINE_WAIT(wait);
|
||||
struct atm_vcc *vcc;
|
||||
struct sk_buff *skb;
|
||||
int eff, error;
|
||||
const void __user *buff;
|
||||
int size;
|
||||
struct iov_iter from;
|
||||
|
||||
iov_iter_init(&from, WRITE, m->msg_iov, m->msg_iovlen, size);
|
||||
|
||||
lock_sock(sk);
|
||||
if (sock->state != SS_CONNECTED) {
|
||||
@ -589,12 +590,6 @@ int vcc_sendmsg(struct kiocb *iocb, struct socket *sock, struct msghdr *m,
|
||||
error = -EISCONN;
|
||||
goto out;
|
||||
}
|
||||
if (m->msg_iovlen != 1) {
|
||||
error = -ENOSYS; /* fix this later @@@ */
|
||||
goto out;
|
||||
}
|
||||
buff = m->msg_iov->iov_base;
|
||||
size = m->msg_iov->iov_len;
|
||||
vcc = ATM_SD(sock);
|
||||
if (test_bit(ATM_VF_RELEASED, &vcc->flags) ||
|
||||
test_bit(ATM_VF_CLOSE, &vcc->flags) ||
|
||||
@ -607,7 +602,7 @@ int vcc_sendmsg(struct kiocb *iocb, struct socket *sock, struct msghdr *m,
|
||||
error = 0;
|
||||
goto out;
|
||||
}
|
||||
if (size < 0 || size > vcc->qos.txtp.max_sdu) {
|
||||
if (size > vcc->qos.txtp.max_sdu) {
|
||||
error = -EMSGSIZE;
|
||||
goto out;
|
||||
}
|
||||
@ -639,7 +634,7 @@ int vcc_sendmsg(struct kiocb *iocb, struct socket *sock, struct msghdr *m,
|
||||
goto out;
|
||||
skb->dev = NULL; /* for paths shared with net_device interfaces */
|
||||
ATM_SKB(skb)->atm_options = vcc->atm_options;
|
||||
if (copy_from_user(skb_put(skb, size), buff, size)) {
|
||||
if (copy_from_iter(skb_put(skb, size), size, &from) != size) {
|
||||
kfree_skb(skb);
|
||||
error = -EFAULT;
|
||||
goto out;
|
||||
|
Loading…
Reference in New Issue
Block a user