Loading drivers/usb/core/devio.c +188 −145 Original line number Diff line number Diff line Loading @@ -75,7 +75,7 @@ struct async { u32 secid; }; static int usbfs_snoop = 0; static int usbfs_snoop; module_param(usbfs_snoop, bool, S_IRUGO | S_IWUSR); MODULE_PARM_DESC(usbfs_snoop, "true to log all usbfs traffic"); Loading Loading @@ -120,7 +120,8 @@ static loff_t usbdev_lseek(struct file *file, loff_t offset, int orig) return ret; } static ssize_t usbdev_read(struct file *file, char __user *buf, size_t nbytes, loff_t *ppos) static ssize_t usbdev_read(struct file *file, char __user *buf, size_t nbytes, loff_t *ppos) { struct dev_state *ps = file->private_data; struct usb_device *dev = ps->dev; Loading @@ -140,7 +141,8 @@ static ssize_t usbdev_read(struct file *file, char __user *buf, size_t nbytes, l } if (pos < sizeof(struct usb_device_descriptor)) { struct usb_device_descriptor temp_desc ; /* 18 bytes - fits on the stack */ /* 18 bytes - fits on the stack */ struct usb_device_descriptor temp_desc; memcpy(&temp_desc, &dev->descriptor, sizeof(dev->descriptor)); le16_to_cpus(&temp_desc.bcdUSB); Loading Loading @@ -259,14 +261,16 @@ static inline struct async *async_getcompleted(struct dev_state *ps) spin_lock_irqsave(&ps->lock, flags); if (!list_empty(&ps->async_completed)) { as = list_entry(ps->async_completed.next, struct async, asynclist); as = list_entry(ps->async_completed.next, struct async, asynclist); list_del_init(&as->asynclist); } spin_unlock_irqrestore(&ps->lock, flags); return as; } static inline struct async *async_getpending(struct dev_state *ps, void __user *userurb) static inline struct async *async_getpending(struct dev_state *ps, void __user *userurb) { unsigned long flags; struct async *as; Loading Loading @@ -348,7 +352,8 @@ static void destroy_async (struct dev_state *ps, struct list_head *list) } } static void destroy_async_on_interface (struct dev_state *ps, unsigned int ifnum) static void destroy_async_on_interface(struct dev_state *ps, unsigned int ifnum) { struct list_head *p, *q, hitlist; unsigned long flags; Loading Loading @@ -474,8 +479,9 @@ static int checkintf(struct dev_state *ps, unsigned int ifnum) if (test_bit(ifnum, &ps->ifclaimed)) return 0; /* if not yet claimed, claim it for the driver */ dev_warn(&ps->dev->dev, "usbfs: process %d (%s) did not claim interface %u before use\n", task_pid_nr(current), current->comm, ifnum); dev_warn(&ps->dev->dev, "usbfs: process %d (%s) did not claim " "interface %u before use\n", task_pid_nr(current), current->comm, ifnum); return claimintf(ps, ifnum); } Loading Loading @@ -504,7 +510,8 @@ static int findintfep(struct usb_device *dev, unsigned int ep) return -ENOENT; } static int check_ctrlrecip(struct dev_state *ps, unsigned int requesttype, unsigned int index) static int check_ctrlrecip(struct dev_state *ps, unsigned int requesttype, unsigned int index) { int ret = 0; Loading @@ -517,7 +524,8 @@ static int check_ctrlrecip(struct dev_state *ps, unsigned int requesttype, unsig index &= 0xff; switch (requesttype & USB_RECIP_MASK) { case USB_RECIP_ENDPOINT: if ((ret = findintfep(ps->dev, index)) >= 0) ret = findintfep(ps->dev, index); if (ret >= 0) ret = checkintf(ps, ret); break; Loading Loading @@ -561,7 +569,8 @@ static int usbdev_open(struct inode *inode, struct file *file) mutex_lock(&usbfs_mutex); ret = -ENOMEM; if (!(ps = kmalloc(sizeof(struct dev_state), GFP_KERNEL))) ps = kmalloc(sizeof(struct dev_state), GFP_KERNEL); if (!ps) goto out; ret = -ENOENT; Loading Loading @@ -642,15 +651,18 @@ static int proc_control(struct dev_state *ps, void __user *arg) if (copy_from_user(&ctrl, arg, sizeof(ctrl))) return -EFAULT; if ((ret = check_ctrlrecip(ps, ctrl.bRequestType, ctrl.wIndex))) ret = check_ctrlrecip(ps, ctrl.bRequestType, ctrl.wIndex); if (ret) return ret; if (ctrl.wLength > PAGE_SIZE) return -EINVAL; if (!(tbuf = (unsigned char *)__get_free_page(GFP_KERNEL))) tbuf = (unsigned char *)__get_free_page(GFP_KERNEL); if (!tbuf) return -ENOMEM; tmo = ctrl.timeout; if (ctrl.bRequestType & 0x80) { if (ctrl.wLength && !access_ok(VERIFY_WRITE, ctrl.data, ctrl.wLength)) { if (ctrl.wLength && !access_ok(VERIFY_WRITE, ctrl.data, ctrl.wLength)) { free_page((unsigned long)tbuf); return -EINVAL; } Loading @@ -661,14 +673,15 @@ static int proc_control(struct dev_state *ps, void __user *arg) ctrl.wIndex, ctrl.wLength); usb_unlock_device(dev); i = usb_control_msg(dev, usb_rcvctrlpipe(dev, 0), ctrl.bRequest, ctrl.bRequestType, ctrl.wValue, ctrl.wIndex, tbuf, ctrl.wLength, tmo); i = usb_control_msg(dev, usb_rcvctrlpipe(dev, 0), ctrl.bRequest, ctrl.bRequestType, ctrl.wValue, ctrl.wIndex, tbuf, ctrl.wLength, tmo); usb_lock_device(dev); if ((i > 0) && ctrl.wLength) { if (usbfs_snoop) { dev_info(&dev->dev, "control read: data "); for (j = 0; j < i; ++j) printk("%02x ", (unsigned char)(tbuf)[j]); printk("%02x ", (u8)(tbuf)[j]); printk("\n"); } if (copy_to_user(ctrl.data, tbuf, i)) { Loading @@ -695,8 +708,9 @@ static int proc_control(struct dev_state *ps, void __user *arg) printk("\n"); } usb_unlock_device(dev); i = usb_control_msg(dev, usb_sndctrlpipe(dev, 0), ctrl.bRequest, ctrl.bRequestType, ctrl.wValue, ctrl.wIndex, tbuf, ctrl.wLength, tmo); i = usb_control_msg(dev, usb_sndctrlpipe(dev, 0), ctrl.bRequest, ctrl.bRequestType, ctrl.wValue, ctrl.wIndex, tbuf, ctrl.wLength, tmo); usb_lock_device(dev); } free_page((unsigned long)tbuf); Loading @@ -720,9 +734,11 @@ static int proc_bulk(struct dev_state *ps, void __user *arg) if (copy_from_user(&bulk, arg, sizeof(bulk))) return -EFAULT; if ((ret = findintfep(ps->dev, bulk.ep)) < 0) ret = findintfep(ps->dev, bulk.ep); if (ret < 0) return ret; if ((ret = checkintf(ps, ret))) ret = checkintf(ps, ret); if (ret) return ret; if (bulk.ep & USB_DIR_IN) pipe = usb_rcvbulkpipe(dev, bulk.ep & 0x7f); Loading Loading @@ -750,7 +766,7 @@ static int proc_bulk(struct dev_state *ps, void __user *arg) if (usbfs_snoop) { dev_info(&dev->dev, "bulk read: data "); for (j = 0; j < len2; ++j) printk("%02x ", (unsigned char)(tbuf)[j]); printk("%02x ", (u8)(tbuf)[j]); printk("\n"); } if (copy_to_user(bulk.data, tbuf, len2)) { Loading Loading @@ -790,9 +806,11 @@ static int proc_resetep(struct dev_state *ps, void __user *arg) if (get_user(ep, (unsigned int __user *)arg)) return -EFAULT; if ((ret = findintfep(ps->dev, ep)) < 0) ret = findintfep(ps->dev, ep); if (ret < 0) return ret; if ((ret = checkintf(ps, ret))) ret = checkintf(ps, ret); if (ret) return ret; usb_settoggle(ps->dev, ep & 0xf, !(ep & USB_DIR_IN), 0); return 0; Loading @@ -806,9 +824,11 @@ static int proc_clearhalt(struct dev_state *ps, void __user *arg) if (get_user(ep, (unsigned int __user *)arg)) return -EFAULT; if ((ret = findintfep(ps->dev, ep)) < 0) ret = findintfep(ps->dev, ep); if (ret < 0) return ret; if ((ret = checkintf(ps, ret))) ret = checkintf(ps, ret); if (ret) return ret; if (ep & USB_DIR_IN) pipe = usb_rcvbulkpipe(ps->dev, ep & 0x7f); Loading @@ -818,7 +838,6 @@ static int proc_clearhalt(struct dev_state *ps, void __user *arg) return usb_clear_halt(ps->dev, pipe); } static int proc_getdriver(struct dev_state *ps, void __user *arg) { struct usbdevfs_getdriver gd; Loading Loading @@ -932,12 +951,16 @@ static int proc_do_submiturb(struct dev_state *ps, struct usbdevfs_urb *uurb, return -EINVAL; if (!uurb->buffer) return -EINVAL; if (uurb->signr != 0 && (uurb->signr < SIGRTMIN || uurb->signr > SIGRTMAX)) if (uurb->signr != 0 && (uurb->signr < SIGRTMIN || uurb->signr > SIGRTMAX)) return -EINVAL; if (!(uurb->type == USBDEVFS_URB_TYPE_CONTROL && (uurb->endpoint & ~USB_ENDPOINT_DIR_MASK) == 0)) { if ((ifnum = findintfep(ps->dev, uurb->endpoint)) < 0) if (!(uurb->type == USBDEVFS_URB_TYPE_CONTROL && (uurb->endpoint & ~USB_ENDPOINT_DIR_MASK) == 0)) { ifnum = findintfep(ps->dev, uurb->endpoint); if (ifnum < 0) return ifnum; if ((ret = checkintf(ps, ifnum))) ret = checkintf(ps, ifnum); if (ret) return ret; } if ((uurb->endpoint & USB_ENDPOINT_DIR_MASK) != 0) { Loading @@ -953,10 +976,13 @@ static int proc_do_submiturb(struct dev_state *ps, struct usbdevfs_urb *uurb, case USBDEVFS_URB_TYPE_CONTROL: if (!usb_endpoint_xfer_control(&ep->desc)) return -EINVAL; /* min 8 byte setup packet, max 8 byte setup plus an arbitrary data stage */ if (uurb->buffer_length < 8 || uurb->buffer_length > (8 + MAX_USBFS_BUFFER_SIZE)) /* min 8 byte setup packet, * max 8 byte setup plus an arbitrary data stage */ if (uurb->buffer_length < 8 || uurb->buffer_length > (8 + MAX_USBFS_BUFFER_SIZE)) return -EINVAL; if (!(dr = kmalloc(sizeof(struct usb_ctrlrequest), GFP_KERNEL))) dr = kmalloc(sizeof(struct usb_ctrlrequest), GFP_KERNEL); if (!dr) return -ENOMEM; if (copy_from_user(dr, uurb->buffer, 8)) { kfree(dr); Loading @@ -966,7 +992,9 @@ static int proc_do_submiturb(struct dev_state *ps, struct usbdevfs_urb *uurb, kfree(dr); return -EINVAL; } if ((ret = check_ctrlrecip(ps, dr->bRequestType, le16_to_cpup(&dr->wIndex)))) { ret = check_ctrlrecip(ps, dr->bRequestType, le16_to_cpup(&dr->wIndex)); if (ret) { kfree(dr); return ret; } Loading Loading @@ -1012,11 +1040,13 @@ static int proc_do_submiturb(struct dev_state *ps, struct usbdevfs_urb *uurb, case USBDEVFS_URB_TYPE_ISO: /* arbitrary limit */ if (uurb->number_of_packets < 1 || uurb->number_of_packets > 128) if (uurb->number_of_packets < 1 || uurb->number_of_packets > 128) return -EINVAL; if (!usb_endpoint_xfer_isoc(&ep->desc)) return -EINVAL; isofrmlen = sizeof(struct usbdevfs_iso_packet_desc) * uurb->number_of_packets; isofrmlen = sizeof(struct usbdevfs_iso_packet_desc) * uurb->number_of_packets; if (!(isopkt = kmalloc(isofrmlen, GFP_KERNEL))) return -ENOMEM; if (copy_from_user(isopkt, iso_frame_desc, isofrmlen)) { Loading @@ -1024,7 +1054,8 @@ static int proc_do_submiturb(struct dev_state *ps, struct usbdevfs_urb *uurb, return -EFAULT; } for (totlen = u = 0; u < uurb->number_of_packets; u++) { /* arbitrary limit, sufficient for USB 2.0 high-bandwidth iso */ /* arbitrary limit, * sufficient for USB 2.0 high-bandwidth iso */ if (isopkt[u].length > 8192) { kfree(isopkt); return -EINVAL; Loading Loading @@ -1054,12 +1085,14 @@ static int proc_do_submiturb(struct dev_state *ps, struct usbdevfs_urb *uurb, default: return -EINVAL; } if (!(as = alloc_async(uurb->number_of_packets))) { as = alloc_async(uurb->number_of_packets); if (!as) { kfree(isopkt); kfree(dr); return -ENOMEM; } if (!(as->urb->transfer_buffer = kmalloc(uurb->buffer_length, GFP_KERNEL))) { as->urb->transfer_buffer = kmalloc(uurb->buffer_length, GFP_KERNEL); if (!as->urb->transfer_buffer) { kfree(isopkt); kfree(dr); free_async(as); Loading Loading @@ -1110,7 +1143,8 @@ static int proc_do_submiturb(struct dev_state *ps, struct usbdevfs_urb *uurb, snoop_urb(as->urb, as->userurb); async_newpending(as); if ((ret = usb_submit_urb(as->urb, GFP_KERNEL))) { dev_printk(KERN_DEBUG, &ps->dev->dev, "usbfs: usb_submit_urb returned %d\n", ret); dev_printk(KERN_DEBUG, &ps->dev->dev, "usbfs: usb_submit_urb returned %d\n", ret); async_removepending(as); free_async(as); return ret; Loading @@ -1125,7 +1159,9 @@ static int proc_submiturb(struct dev_state *ps, void __user *arg) if (copy_from_user(&uurb, arg, sizeof(uurb))) return -EFAULT; return proc_do_submiturb(ps, &uurb, (((struct usbdevfs_urb __user *)arg)->iso_frame_desc), arg); return proc_do_submiturb(ps, &uurb, (((struct usbdevfs_urb __user *)arg)->iso_frame_desc), arg); } static int proc_unlinkurb(struct dev_state *ps, void __user *arg) Loading @@ -1147,7 +1183,8 @@ static int processcompl(struct async *as, void __user * __user *arg) unsigned int i; if (as->userbuffer) if (copy_to_user(as->userbuffer, urb->transfer_buffer, urb->transfer_buffer_length)) if (copy_to_user(as->userbuffer, urb->transfer_buffer, urb->transfer_buffer_length)) return -EFAULT; if (put_user(as->status, &userurb->status)) return -EFAULT; Loading Loading @@ -1183,7 +1220,8 @@ static struct async* reap_as(struct dev_state *ps) add_wait_queue(&ps->wait, &wait); for (;;) { __set_current_state(TASK_INTERRUPTIBLE); if ((as = async_getcompleted(ps))) as = async_getcompleted(ps); if (as) break; if (signal_pending(current)) break; Loading Loading @@ -1250,7 +1288,9 @@ static int proc_submiturb_compat(struct dev_state *ps, void __user *arg) if (get_urb32(&uurb, (struct usbdevfs_urb32 __user *)arg)) return -EFAULT; return proc_do_submiturb(ps, &uurb, ((struct usbdevfs_urb32 __user *)arg)->iso_frame_desc, arg); return proc_do_submiturb(ps, &uurb, ((struct usbdevfs_urb32 __user *)arg)->iso_frame_desc, arg); } static int processcompl_compat(struct async *as, void __user * __user *arg) Loading @@ -1261,7 +1301,8 @@ static int processcompl_compat(struct async *as, void __user * __user *arg) unsigned int i; if (as->userbuffer) if (copy_to_user(as->userbuffer, urb->transfer_buffer, urb->transfer_buffer_length)) if (copy_to_user(as->userbuffer, urb->transfer_buffer, urb->transfer_buffer_length)) return -EFAULT; if (put_user(as->status, &userurb->status)) return -EFAULT; Loading Loading @@ -1450,7 +1491,8 @@ static int proc_ioctl_compat(struct dev_state *ps, compat_uptr_t arg) * are assuming that somehow the configuration has been prevented from * changing. But there's no mechanism to ensure that... */ static int usbdev_ioctl(struct inode *inode, struct file *file, unsigned int cmd, unsigned long arg) static int usbdev_ioctl(struct inode *inode, struct file *file, unsigned int cmd, unsigned long arg) { struct dev_state *ps = file->private_data; struct usb_device *dev = ps->dev; Loading Loading @@ -1593,7 +1635,8 @@ static int usbdev_ioctl(struct inode *inode, struct file *file, unsigned int cmd } /* No kernel lock - fine */ static unsigned int usbdev_poll(struct file *file, struct poll_table_struct *wait) static unsigned int usbdev_poll(struct file *file, struct poll_table_struct *wait) { struct dev_state *ps = file->private_data; unsigned int mask = 0; Loading Loading
drivers/usb/core/devio.c +188 −145 Original line number Diff line number Diff line Loading @@ -75,7 +75,7 @@ struct async { u32 secid; }; static int usbfs_snoop = 0; static int usbfs_snoop; module_param(usbfs_snoop, bool, S_IRUGO | S_IWUSR); MODULE_PARM_DESC(usbfs_snoop, "true to log all usbfs traffic"); Loading Loading @@ -120,7 +120,8 @@ static loff_t usbdev_lseek(struct file *file, loff_t offset, int orig) return ret; } static ssize_t usbdev_read(struct file *file, char __user *buf, size_t nbytes, loff_t *ppos) static ssize_t usbdev_read(struct file *file, char __user *buf, size_t nbytes, loff_t *ppos) { struct dev_state *ps = file->private_data; struct usb_device *dev = ps->dev; Loading @@ -140,7 +141,8 @@ static ssize_t usbdev_read(struct file *file, char __user *buf, size_t nbytes, l } if (pos < sizeof(struct usb_device_descriptor)) { struct usb_device_descriptor temp_desc ; /* 18 bytes - fits on the stack */ /* 18 bytes - fits on the stack */ struct usb_device_descriptor temp_desc; memcpy(&temp_desc, &dev->descriptor, sizeof(dev->descriptor)); le16_to_cpus(&temp_desc.bcdUSB); Loading Loading @@ -259,14 +261,16 @@ static inline struct async *async_getcompleted(struct dev_state *ps) spin_lock_irqsave(&ps->lock, flags); if (!list_empty(&ps->async_completed)) { as = list_entry(ps->async_completed.next, struct async, asynclist); as = list_entry(ps->async_completed.next, struct async, asynclist); list_del_init(&as->asynclist); } spin_unlock_irqrestore(&ps->lock, flags); return as; } static inline struct async *async_getpending(struct dev_state *ps, void __user *userurb) static inline struct async *async_getpending(struct dev_state *ps, void __user *userurb) { unsigned long flags; struct async *as; Loading Loading @@ -348,7 +352,8 @@ static void destroy_async (struct dev_state *ps, struct list_head *list) } } static void destroy_async_on_interface (struct dev_state *ps, unsigned int ifnum) static void destroy_async_on_interface(struct dev_state *ps, unsigned int ifnum) { struct list_head *p, *q, hitlist; unsigned long flags; Loading Loading @@ -474,8 +479,9 @@ static int checkintf(struct dev_state *ps, unsigned int ifnum) if (test_bit(ifnum, &ps->ifclaimed)) return 0; /* if not yet claimed, claim it for the driver */ dev_warn(&ps->dev->dev, "usbfs: process %d (%s) did not claim interface %u before use\n", task_pid_nr(current), current->comm, ifnum); dev_warn(&ps->dev->dev, "usbfs: process %d (%s) did not claim " "interface %u before use\n", task_pid_nr(current), current->comm, ifnum); return claimintf(ps, ifnum); } Loading Loading @@ -504,7 +510,8 @@ static int findintfep(struct usb_device *dev, unsigned int ep) return -ENOENT; } static int check_ctrlrecip(struct dev_state *ps, unsigned int requesttype, unsigned int index) static int check_ctrlrecip(struct dev_state *ps, unsigned int requesttype, unsigned int index) { int ret = 0; Loading @@ -517,7 +524,8 @@ static int check_ctrlrecip(struct dev_state *ps, unsigned int requesttype, unsig index &= 0xff; switch (requesttype & USB_RECIP_MASK) { case USB_RECIP_ENDPOINT: if ((ret = findintfep(ps->dev, index)) >= 0) ret = findintfep(ps->dev, index); if (ret >= 0) ret = checkintf(ps, ret); break; Loading Loading @@ -561,7 +569,8 @@ static int usbdev_open(struct inode *inode, struct file *file) mutex_lock(&usbfs_mutex); ret = -ENOMEM; if (!(ps = kmalloc(sizeof(struct dev_state), GFP_KERNEL))) ps = kmalloc(sizeof(struct dev_state), GFP_KERNEL); if (!ps) goto out; ret = -ENOENT; Loading Loading @@ -642,15 +651,18 @@ static int proc_control(struct dev_state *ps, void __user *arg) if (copy_from_user(&ctrl, arg, sizeof(ctrl))) return -EFAULT; if ((ret = check_ctrlrecip(ps, ctrl.bRequestType, ctrl.wIndex))) ret = check_ctrlrecip(ps, ctrl.bRequestType, ctrl.wIndex); if (ret) return ret; if (ctrl.wLength > PAGE_SIZE) return -EINVAL; if (!(tbuf = (unsigned char *)__get_free_page(GFP_KERNEL))) tbuf = (unsigned char *)__get_free_page(GFP_KERNEL); if (!tbuf) return -ENOMEM; tmo = ctrl.timeout; if (ctrl.bRequestType & 0x80) { if (ctrl.wLength && !access_ok(VERIFY_WRITE, ctrl.data, ctrl.wLength)) { if (ctrl.wLength && !access_ok(VERIFY_WRITE, ctrl.data, ctrl.wLength)) { free_page((unsigned long)tbuf); return -EINVAL; } Loading @@ -661,14 +673,15 @@ static int proc_control(struct dev_state *ps, void __user *arg) ctrl.wIndex, ctrl.wLength); usb_unlock_device(dev); i = usb_control_msg(dev, usb_rcvctrlpipe(dev, 0), ctrl.bRequest, ctrl.bRequestType, ctrl.wValue, ctrl.wIndex, tbuf, ctrl.wLength, tmo); i = usb_control_msg(dev, usb_rcvctrlpipe(dev, 0), ctrl.bRequest, ctrl.bRequestType, ctrl.wValue, ctrl.wIndex, tbuf, ctrl.wLength, tmo); usb_lock_device(dev); if ((i > 0) && ctrl.wLength) { if (usbfs_snoop) { dev_info(&dev->dev, "control read: data "); for (j = 0; j < i; ++j) printk("%02x ", (unsigned char)(tbuf)[j]); printk("%02x ", (u8)(tbuf)[j]); printk("\n"); } if (copy_to_user(ctrl.data, tbuf, i)) { Loading @@ -695,8 +708,9 @@ static int proc_control(struct dev_state *ps, void __user *arg) printk("\n"); } usb_unlock_device(dev); i = usb_control_msg(dev, usb_sndctrlpipe(dev, 0), ctrl.bRequest, ctrl.bRequestType, ctrl.wValue, ctrl.wIndex, tbuf, ctrl.wLength, tmo); i = usb_control_msg(dev, usb_sndctrlpipe(dev, 0), ctrl.bRequest, ctrl.bRequestType, ctrl.wValue, ctrl.wIndex, tbuf, ctrl.wLength, tmo); usb_lock_device(dev); } free_page((unsigned long)tbuf); Loading @@ -720,9 +734,11 @@ static int proc_bulk(struct dev_state *ps, void __user *arg) if (copy_from_user(&bulk, arg, sizeof(bulk))) return -EFAULT; if ((ret = findintfep(ps->dev, bulk.ep)) < 0) ret = findintfep(ps->dev, bulk.ep); if (ret < 0) return ret; if ((ret = checkintf(ps, ret))) ret = checkintf(ps, ret); if (ret) return ret; if (bulk.ep & USB_DIR_IN) pipe = usb_rcvbulkpipe(dev, bulk.ep & 0x7f); Loading Loading @@ -750,7 +766,7 @@ static int proc_bulk(struct dev_state *ps, void __user *arg) if (usbfs_snoop) { dev_info(&dev->dev, "bulk read: data "); for (j = 0; j < len2; ++j) printk("%02x ", (unsigned char)(tbuf)[j]); printk("%02x ", (u8)(tbuf)[j]); printk("\n"); } if (copy_to_user(bulk.data, tbuf, len2)) { Loading Loading @@ -790,9 +806,11 @@ static int proc_resetep(struct dev_state *ps, void __user *arg) if (get_user(ep, (unsigned int __user *)arg)) return -EFAULT; if ((ret = findintfep(ps->dev, ep)) < 0) ret = findintfep(ps->dev, ep); if (ret < 0) return ret; if ((ret = checkintf(ps, ret))) ret = checkintf(ps, ret); if (ret) return ret; usb_settoggle(ps->dev, ep & 0xf, !(ep & USB_DIR_IN), 0); return 0; Loading @@ -806,9 +824,11 @@ static int proc_clearhalt(struct dev_state *ps, void __user *arg) if (get_user(ep, (unsigned int __user *)arg)) return -EFAULT; if ((ret = findintfep(ps->dev, ep)) < 0) ret = findintfep(ps->dev, ep); if (ret < 0) return ret; if ((ret = checkintf(ps, ret))) ret = checkintf(ps, ret); if (ret) return ret; if (ep & USB_DIR_IN) pipe = usb_rcvbulkpipe(ps->dev, ep & 0x7f); Loading @@ -818,7 +838,6 @@ static int proc_clearhalt(struct dev_state *ps, void __user *arg) return usb_clear_halt(ps->dev, pipe); } static int proc_getdriver(struct dev_state *ps, void __user *arg) { struct usbdevfs_getdriver gd; Loading Loading @@ -932,12 +951,16 @@ static int proc_do_submiturb(struct dev_state *ps, struct usbdevfs_urb *uurb, return -EINVAL; if (!uurb->buffer) return -EINVAL; if (uurb->signr != 0 && (uurb->signr < SIGRTMIN || uurb->signr > SIGRTMAX)) if (uurb->signr != 0 && (uurb->signr < SIGRTMIN || uurb->signr > SIGRTMAX)) return -EINVAL; if (!(uurb->type == USBDEVFS_URB_TYPE_CONTROL && (uurb->endpoint & ~USB_ENDPOINT_DIR_MASK) == 0)) { if ((ifnum = findintfep(ps->dev, uurb->endpoint)) < 0) if (!(uurb->type == USBDEVFS_URB_TYPE_CONTROL && (uurb->endpoint & ~USB_ENDPOINT_DIR_MASK) == 0)) { ifnum = findintfep(ps->dev, uurb->endpoint); if (ifnum < 0) return ifnum; if ((ret = checkintf(ps, ifnum))) ret = checkintf(ps, ifnum); if (ret) return ret; } if ((uurb->endpoint & USB_ENDPOINT_DIR_MASK) != 0) { Loading @@ -953,10 +976,13 @@ static int proc_do_submiturb(struct dev_state *ps, struct usbdevfs_urb *uurb, case USBDEVFS_URB_TYPE_CONTROL: if (!usb_endpoint_xfer_control(&ep->desc)) return -EINVAL; /* min 8 byte setup packet, max 8 byte setup plus an arbitrary data stage */ if (uurb->buffer_length < 8 || uurb->buffer_length > (8 + MAX_USBFS_BUFFER_SIZE)) /* min 8 byte setup packet, * max 8 byte setup plus an arbitrary data stage */ if (uurb->buffer_length < 8 || uurb->buffer_length > (8 + MAX_USBFS_BUFFER_SIZE)) return -EINVAL; if (!(dr = kmalloc(sizeof(struct usb_ctrlrequest), GFP_KERNEL))) dr = kmalloc(sizeof(struct usb_ctrlrequest), GFP_KERNEL); if (!dr) return -ENOMEM; if (copy_from_user(dr, uurb->buffer, 8)) { kfree(dr); Loading @@ -966,7 +992,9 @@ static int proc_do_submiturb(struct dev_state *ps, struct usbdevfs_urb *uurb, kfree(dr); return -EINVAL; } if ((ret = check_ctrlrecip(ps, dr->bRequestType, le16_to_cpup(&dr->wIndex)))) { ret = check_ctrlrecip(ps, dr->bRequestType, le16_to_cpup(&dr->wIndex)); if (ret) { kfree(dr); return ret; } Loading Loading @@ -1012,11 +1040,13 @@ static int proc_do_submiturb(struct dev_state *ps, struct usbdevfs_urb *uurb, case USBDEVFS_URB_TYPE_ISO: /* arbitrary limit */ if (uurb->number_of_packets < 1 || uurb->number_of_packets > 128) if (uurb->number_of_packets < 1 || uurb->number_of_packets > 128) return -EINVAL; if (!usb_endpoint_xfer_isoc(&ep->desc)) return -EINVAL; isofrmlen = sizeof(struct usbdevfs_iso_packet_desc) * uurb->number_of_packets; isofrmlen = sizeof(struct usbdevfs_iso_packet_desc) * uurb->number_of_packets; if (!(isopkt = kmalloc(isofrmlen, GFP_KERNEL))) return -ENOMEM; if (copy_from_user(isopkt, iso_frame_desc, isofrmlen)) { Loading @@ -1024,7 +1054,8 @@ static int proc_do_submiturb(struct dev_state *ps, struct usbdevfs_urb *uurb, return -EFAULT; } for (totlen = u = 0; u < uurb->number_of_packets; u++) { /* arbitrary limit, sufficient for USB 2.0 high-bandwidth iso */ /* arbitrary limit, * sufficient for USB 2.0 high-bandwidth iso */ if (isopkt[u].length > 8192) { kfree(isopkt); return -EINVAL; Loading Loading @@ -1054,12 +1085,14 @@ static int proc_do_submiturb(struct dev_state *ps, struct usbdevfs_urb *uurb, default: return -EINVAL; } if (!(as = alloc_async(uurb->number_of_packets))) { as = alloc_async(uurb->number_of_packets); if (!as) { kfree(isopkt); kfree(dr); return -ENOMEM; } if (!(as->urb->transfer_buffer = kmalloc(uurb->buffer_length, GFP_KERNEL))) { as->urb->transfer_buffer = kmalloc(uurb->buffer_length, GFP_KERNEL); if (!as->urb->transfer_buffer) { kfree(isopkt); kfree(dr); free_async(as); Loading Loading @@ -1110,7 +1143,8 @@ static int proc_do_submiturb(struct dev_state *ps, struct usbdevfs_urb *uurb, snoop_urb(as->urb, as->userurb); async_newpending(as); if ((ret = usb_submit_urb(as->urb, GFP_KERNEL))) { dev_printk(KERN_DEBUG, &ps->dev->dev, "usbfs: usb_submit_urb returned %d\n", ret); dev_printk(KERN_DEBUG, &ps->dev->dev, "usbfs: usb_submit_urb returned %d\n", ret); async_removepending(as); free_async(as); return ret; Loading @@ -1125,7 +1159,9 @@ static int proc_submiturb(struct dev_state *ps, void __user *arg) if (copy_from_user(&uurb, arg, sizeof(uurb))) return -EFAULT; return proc_do_submiturb(ps, &uurb, (((struct usbdevfs_urb __user *)arg)->iso_frame_desc), arg); return proc_do_submiturb(ps, &uurb, (((struct usbdevfs_urb __user *)arg)->iso_frame_desc), arg); } static int proc_unlinkurb(struct dev_state *ps, void __user *arg) Loading @@ -1147,7 +1183,8 @@ static int processcompl(struct async *as, void __user * __user *arg) unsigned int i; if (as->userbuffer) if (copy_to_user(as->userbuffer, urb->transfer_buffer, urb->transfer_buffer_length)) if (copy_to_user(as->userbuffer, urb->transfer_buffer, urb->transfer_buffer_length)) return -EFAULT; if (put_user(as->status, &userurb->status)) return -EFAULT; Loading Loading @@ -1183,7 +1220,8 @@ static struct async* reap_as(struct dev_state *ps) add_wait_queue(&ps->wait, &wait); for (;;) { __set_current_state(TASK_INTERRUPTIBLE); if ((as = async_getcompleted(ps))) as = async_getcompleted(ps); if (as) break; if (signal_pending(current)) break; Loading Loading @@ -1250,7 +1288,9 @@ static int proc_submiturb_compat(struct dev_state *ps, void __user *arg) if (get_urb32(&uurb, (struct usbdevfs_urb32 __user *)arg)) return -EFAULT; return proc_do_submiturb(ps, &uurb, ((struct usbdevfs_urb32 __user *)arg)->iso_frame_desc, arg); return proc_do_submiturb(ps, &uurb, ((struct usbdevfs_urb32 __user *)arg)->iso_frame_desc, arg); } static int processcompl_compat(struct async *as, void __user * __user *arg) Loading @@ -1261,7 +1301,8 @@ static int processcompl_compat(struct async *as, void __user * __user *arg) unsigned int i; if (as->userbuffer) if (copy_to_user(as->userbuffer, urb->transfer_buffer, urb->transfer_buffer_length)) if (copy_to_user(as->userbuffer, urb->transfer_buffer, urb->transfer_buffer_length)) return -EFAULT; if (put_user(as->status, &userurb->status)) return -EFAULT; Loading Loading @@ -1450,7 +1491,8 @@ static int proc_ioctl_compat(struct dev_state *ps, compat_uptr_t arg) * are assuming that somehow the configuration has been prevented from * changing. But there's no mechanism to ensure that... */ static int usbdev_ioctl(struct inode *inode, struct file *file, unsigned int cmd, unsigned long arg) static int usbdev_ioctl(struct inode *inode, struct file *file, unsigned int cmd, unsigned long arg) { struct dev_state *ps = file->private_data; struct usb_device *dev = ps->dev; Loading Loading @@ -1593,7 +1635,8 @@ static int usbdev_ioctl(struct inode *inode, struct file *file, unsigned int cmd } /* No kernel lock - fine */ static unsigned int usbdev_poll(struct file *file, struct poll_table_struct *wait) static unsigned int usbdev_poll(struct file *file, struct poll_table_struct *wait) { struct dev_state *ps = file->private_data; unsigned int mask = 0; Loading