io_uring: add support for recvmsg()
[linux-2.6-block.git] / net / socket.c
index 472fbefa5d9bbf080f96d6f1b88748fb056733a8..98354cc18840de1b15cffd8b0c597422375ba257 100644 (file)
@@ -645,14 +645,6 @@ void __sock_tx_timestamp(__u16 tsflags, __u8 *tx_flags)
 }
 EXPORT_SYMBOL(__sock_tx_timestamp);
 
-/**
- *     sock_sendmsg - send a message through @sock
- *     @sock: socket
- *     @msg: message to send
- *
- *     Sends @msg through @sock, passing through LSM.
- *     Returns the number of bytes sent, or an error code.
- */
 INDIRECT_CALLABLE_DECLARE(int inet_sendmsg(struct socket *, struct msghdr *,
                                           size_t));
 static inline int sock_sendmsg_nosec(struct socket *sock, struct msghdr *msg)
@@ -663,6 +655,14 @@ static inline int sock_sendmsg_nosec(struct socket *sock, struct msghdr *msg)
        return ret;
 }
 
+/**
+ *     sock_sendmsg - send a message through @sock
+ *     @sock: socket
+ *     @msg: message to send
+ *
+ *     Sends @msg through @sock, passing through LSM.
+ *     Returns the number of bytes sent, or an error code.
+ */
 int sock_sendmsg(struct socket *sock, struct msghdr *msg)
 {
        int err = security_socket_sendmsg(sock, msg,
@@ -875,15 +875,6 @@ void __sock_recv_ts_and_drops(struct msghdr *msg, struct sock *sk,
 }
 EXPORT_SYMBOL_GPL(__sock_recv_ts_and_drops);
 
-/**
- *     sock_recvmsg - receive a message from @sock
- *     @sock: socket
- *     @msg: message to receive
- *     @flags: message flags
- *
- *     Receives @msg from @sock, passing through LSM. Returns the total number
- *     of bytes received, or an error.
- */
 INDIRECT_CALLABLE_DECLARE(int inet_recvmsg(struct socket *, struct msghdr *,
                                           size_t , int ));
 static inline int sock_recvmsg_nosec(struct socket *sock, struct msghdr *msg,
@@ -893,6 +884,15 @@ static inline int sock_recvmsg_nosec(struct socket *sock, struct msghdr *msg,
                                   msg_data_left(msg), flags);
 }
 
+/**
+ *     sock_recvmsg - receive a message from @sock
+ *     @sock: socket
+ *     @msg: message to receive
+ *     @flags: message flags
+ *
+ *     Receives @msg from @sock, passing through LSM. Returns the total number
+ *     of bytes received, or an error.
+ */
 int sock_recvmsg(struct socket *sock, struct msghdr *msg, int flags)
 {
        int err = security_socket_recvmsg(sock, msg, msg_data_left(msg), flags);
@@ -2208,9 +2208,10 @@ static int copy_msghdr_from_user(struct msghdr *kmsg,
 
        kmsg->msg_iocb = NULL;
 
-       return import_iovec(save_addr ? READ : WRITE,
+       err = import_iovec(save_addr ? READ : WRITE,
                            msg.msg_iov, msg.msg_iovlen,
                            UIO_FASTIOV, iov, &kmsg->msg_iter);
+       return err < 0 ? err : 0;
 }
 
 static int ___sys_sendmsg(struct socket *sock, struct user_msghdr __user *msg,
@@ -2312,6 +2313,13 @@ out_freeiov:
 /*
  *     BSD sendmsg interface
  */
+long __sys_sendmsg_sock(struct socket *sock, struct user_msghdr __user *msg,
+                       unsigned int flags)
+{
+       struct msghdr msg_sys;
+
+       return ___sys_sendmsg(sock, msg, &msg_sys, flags, NULL, 0);
+}
 
 long __sys_sendmsg(int fd, struct user_msghdr __user *msg, unsigned int flags,
                   bool forbid_cmsg_compat)
@@ -2486,6 +2494,14 @@ out_freeiov:
  *     BSD recvmsg interface
  */
 
+long __sys_recvmsg_sock(struct socket *sock, struct user_msghdr __user *msg,
+                       unsigned int flags)
+{
+       struct msghdr msg_sys;
+
+       return ___sys_recvmsg(sock, msg, &msg_sys, flags, 0);
+}
+
 long __sys_recvmsg(int fd, struct user_msghdr __user *msg, unsigned int flags,
                   bool forbid_cmsg_compat)
 {