This patch (against 2.4.4) fixes a number of security-related bugs in
ov511's ioctl() function. Please submit it to Linus.

--
Mark McClelland
[EMAIL PROTECTED]

diff -Naur linux-2.4.4-orig/drivers/usb/ov511.c linux/drivers/usb/ov511.c
--- linux-2.4.4-orig/drivers/usb/ov511.c        Sun May 13 15:04:57 2001
+++ linux/drivers/usb/ov511.c   Sun May 13 15:45:44 2001
@@ -2246,6 +2246,7 @@
 
                PDEBUG (4, "VIDIOCGCAP");
 
+               memset(&b, 0, sizeof(b));
                strcpy(b.name, "OV511 USB Camera");
                b.type = VID_TYPE_CAPTURE | VID_TYPE_SUBCAPTURE;
                b.channels = 1;
@@ -2297,9 +2298,11 @@
 
                PDEBUG (4, "VIDIOCGPICT");
 
+               memset(&p, 0, sizeof(p));
+
                if (ov7610_get_picture(ov511, &p))
                        return -EIO;
-                                                       
+
                if (copy_to_user(arg, &p, sizeof(p)))
                        return -EFAULT;
 
@@ -2414,11 +2417,11 @@
        {
                struct video_window vw;
 
+               memset(&vw, 0, sizeof(vw));
                vw.x = 0;               /* FIXME */
                vw.y = 0;
                vw.width = ov511->frame[0].width;
                vw.height = ov511->frame[0].height;
-               vw.chromakey = 0;
                vw.flags = 30;
 
                PDEBUG (4, "VIDIOCGWIN: %dx%d", vw.width, vw.height);
@@ -2431,12 +2434,16 @@
        case VIDIOCGMBUF:
        {
                struct video_mbuf vm;
-
+               int i;
+               
                memset(&vm, 0, sizeof(vm));
                vm.size = OV511_NUMFRAMES * MAX_DATA_SIZE;
                vm.frames = OV511_NUMFRAMES;
                vm.offsets[0] = 0;
-               vm.offsets[1] = MAX_FRAME_SIZE + sizeof (struct timeval);
+               for (i = 1; i < OV511_NUMFRAMES; i++) {
+                       vm.offsets[i] = vm.offsets[i-1] + MAX_FRAME_SIZE
+                               + sizeof (struct timeval);
+               }
 
                if (copy_to_user((void *)arg, (void *)&vm, sizeof(vm)))
                        return -EFAULT;
@@ -2461,7 +2468,7 @@
                        return -EINVAL;
                }
 
-               if ((vm.frame != 0) && (vm.frame != 1)) {
+               if ((unsigned)vm.frame >= OV511_NUMFRAMES) {
                        err("VIDIOCMCAPTURE: invalid frame (%d)", vm.frame);
                        return -EINVAL;
                }
@@ -2510,6 +2517,11 @@
 
                if (copy_from_user((void *)&frame, arg, sizeof(int)))
                        return -EFAULT;
+
+               if ((unsigned)frame >= OV511_NUMFRAMES) {
+                       err("VIDIOCSYNC: invalid frame (%d)", frame);
+                       return -EINVAL;
+               }
 
                PDEBUG(4, "syncing to frame %d, grabstate = %d", frame,
                       ov511->frame[frame].grabstate);

Reply via email to