Author: dchagin
Date: Thu May 28 04:08:07 2009
New Revision: 192952
URL: http://svn.freebsd.org/changeset/base/192952

Log:
  Merge r192373 from HEAD to stable/7:
  
  Validate user-supplied arguments values.
  Args argument is a pointer to the structure located in user space in
  which the socketcall arguments are packed. The structure must be
  copied to the kernel instead of direct dereferencing.
  
  Approved by:  kib (mentor)

Modified:
  stable/7/sys/   (props changed)
  stable/7/sys/compat/linux/linux_socket.c
  stable/7/sys/contrib/pf/   (props changed)
  stable/7/sys/dev/ath/ath_hal/   (props changed)
  stable/7/sys/dev/cxgb/   (props changed)

Modified: stable/7/sys/compat/linux/linux_socket.c
==============================================================================
--- stable/7/sys/compat/linux/linux_socket.c    Thu May 28 04:03:16 2009        
(r192951)
+++ stable/7/sys/compat/linux/linux_socket.c    Thu May 28 04:08:07 2009        
(r192952)
@@ -1203,11 +1203,38 @@ linux_getsockopt(struct thread *td, stru
        return (error);
 }
 
+/* Argument list sizes for linux_socketcall */
+
+#define LINUX_AL(x) ((x) * sizeof(l_ulong))
+
+static const unsigned char lxs_args[] = {
+       LINUX_AL(0) /* unused*/,        LINUX_AL(3) /* socket */,
+       LINUX_AL(3) /* bind */,         LINUX_AL(3) /* connect */,
+       LINUX_AL(2) /* listen */,       LINUX_AL(3) /* accept */,
+       LINUX_AL(3) /* getsockname */,  LINUX_AL(3) /* getpeername */,
+       LINUX_AL(4) /* socketpair */,   LINUX_AL(4) /* send */,
+       LINUX_AL(4) /* recv */,         LINUX_AL(6) /* sendto */,
+       LINUX_AL(6) /* recvfrom */,     LINUX_AL(2) /* shutdown */,
+       LINUX_AL(5) /* setsockopt */,   LINUX_AL(5) /* getsockopt */,
+       LINUX_AL(3) /* sendmsg */,      LINUX_AL(3) /* recvmsg */
+};
+
+#define        LINUX_AL_SIZE   sizeof(lxs_args) / sizeof(lxs_args[0]) - 1
+
 int
 linux_socketcall(struct thread *td, struct linux_socketcall_args *args)
 {
-       void *arg = (void *)(intptr_t)args->args;
+       l_ulong a[6];
+       void *arg;
+       int error;
+
+       if (args->what < LINUX_SOCKET || args->what > LINUX_AL_SIZE)
+               return (EINVAL);
+       error = copyin(PTRIN(args->args), a, lxs_args[args->what]);
+       if (error)
+               return (error);
 
+       arg = a;
        switch (args->what) {
        case LINUX_SOCKET:
                return (linux_socket(td, arg));
_______________________________________________
svn-src-all@freebsd.org mailing list
http://lists.freebsd.org/mailman/listinfo/svn-src-all
To unsubscribe, send any mail to "svn-src-all-unsubscr...@freebsd.org"

Reply via email to