tipc: Abort excessive send requests as early as possible
authorAllan Stephens <Allan.Stephens@windriver.com>
Tue, 20 Apr 2010 21:58:24 +0000 (17:58 -0400)
committerPaul Gortmaker <paul.gortmaker@windriver.com>
Tue, 10 May 2011 20:03:56 +0000 (16:03 -0400)
Adds checks to TIPC's socket send routines to promptly detect and
abort attempts to send more than 66,000 bytes in a single TIPC
message or more than 2**31-1 bytes in a single TIPC byte stream request.
In addition, this ensures that the number of iovecs in a send request
does not exceed the limits of a standard integer variable.

Signed-off-by: Allan Stephens <Allan.Stephens@windriver.com>
Signed-off-by: Paul Gortmaker <paul.gortmaker@windriver.com>
include/linux/tipc.h
net/tipc/socket.c

index a5b994a204d26f9aff34f3e8058b068eeec3a78f..f2d90091cc2098fd35893132cc45c0b6795c6319 100644 (file)
@@ -101,7 +101,7 @@ static inline unsigned int tipc_node(__u32 addr)
  * Limiting values for messages
  */
 
-#define TIPC_MAX_USER_MSG_SIZE 66000
+#define TIPC_MAX_USER_MSG_SIZE 66000U
 
 /*
  * Message importance levels
index 29d94d53198d748d3ef2432d6dc96833c6868608..e1c791798ba1bac707b1887ab63d5c79ab963d3e 100644 (file)
@@ -535,6 +535,9 @@ static int send_msg(struct kiocb *iocb, struct socket *sock,
        if (unlikely((m->msg_namelen < sizeof(*dest)) ||
                     (dest->family != AF_TIPC)))
                return -EINVAL;
+       if ((total_len > TIPC_MAX_USER_MSG_SIZE) ||
+           (m->msg_iovlen > (unsigned)INT_MAX))
+               return -EMSGSIZE;
 
        if (iocb)
                lock_sock(sk);
@@ -640,6 +643,10 @@ static int send_packet(struct kiocb *iocb, struct socket *sock,
        if (unlikely(dest))
                return send_msg(iocb, sock, m, total_len);
 
+       if ((total_len > TIPC_MAX_USER_MSG_SIZE) ||
+           (m->msg_iovlen > (unsigned)INT_MAX))
+               return -EMSGSIZE;
+
        if (iocb)
                lock_sock(sk);
 
@@ -723,6 +730,12 @@ static int send_stream(struct kiocb *iocb, struct socket *sock,
                goto exit;
        }
 
+       if ((total_len > (unsigned)INT_MAX) ||
+           (m->msg_iovlen > (unsigned)INT_MAX)) {
+               res = -EMSGSIZE;
+               goto exit;
+       }
+
        /*
         * Send each iovec entry using one or more messages
         *