aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/input/evdev.c
diff options
context:
space:
mode:
authorGrant Likely <grant.likely@secretlab.ca>2010-12-30 00:20:30 -0500
committerGrant Likely <grant.likely@secretlab.ca>2010-12-30 00:21:47 -0500
commitd392da5207352f09030e95d9ea335a4225667ec0 (patch)
tree7d6cd1932afcad0a5619a5c504a6d93ca318187c /drivers/input/evdev.c
parente39d5ef678045d61812c1401f04fe8edb14d6359 (diff)
parent387c31c7e5c9805b0aef8833d1731a5fe7bdea14 (diff)
Merge v2.6.37-rc8 into powerpc/next
Diffstat (limited to 'drivers/input/evdev.c')
-rw-r--r--drivers/input/evdev.c260
1 files changed, 162 insertions, 98 deletions
diff --git a/drivers/input/evdev.c b/drivers/input/evdev.c
index 054edf346e0b..68f09a868434 100644
--- a/drivers/input/evdev.c
+++ b/drivers/input/evdev.c
@@ -28,7 +28,7 @@ struct evdev {
28 int minor; 28 int minor;
29 struct input_handle handle; 29 struct input_handle handle;
30 wait_queue_head_t wait; 30 wait_queue_head_t wait;
31 struct evdev_client *grab; 31 struct evdev_client __rcu *grab;
32 struct list_head client_list; 32 struct list_head client_list;
33 spinlock_t client_lock; /* protects client_list */ 33 spinlock_t client_lock; /* protects client_list */
34 struct mutex mutex; 34 struct mutex mutex;
@@ -492,13 +492,15 @@ static int str_to_user(const char *str, unsigned int maxlen, void __user *p)
492} 492}
493 493
494#define OLD_KEY_MAX 0x1ff 494#define OLD_KEY_MAX 0x1ff
495static int handle_eviocgbit(struct input_dev *dev, unsigned int cmd, void __user *p, int compat_mode) 495static int handle_eviocgbit(struct input_dev *dev,
496 unsigned int type, unsigned int size,
497 void __user *p, int compat_mode)
496{ 498{
497 static unsigned long keymax_warn_time; 499 static unsigned long keymax_warn_time;
498 unsigned long *bits; 500 unsigned long *bits;
499 int len; 501 int len;
500 502
501 switch (_IOC_NR(cmd) & EV_MAX) { 503 switch (type) {
502 504
503 case 0: bits = dev->evbit; len = EV_MAX; break; 505 case 0: bits = dev->evbit; len = EV_MAX; break;
504 case EV_KEY: bits = dev->keybit; len = KEY_MAX; break; 506 case EV_KEY: bits = dev->keybit; len = KEY_MAX; break;
@@ -517,7 +519,7 @@ static int handle_eviocgbit(struct input_dev *dev, unsigned int cmd, void __user
517 * EVIOCGBIT(EV_KEY, KEY_MAX) and not realize that 'len' 519 * EVIOCGBIT(EV_KEY, KEY_MAX) and not realize that 'len'
518 * should be in bytes, not in bits. 520 * should be in bytes, not in bits.
519 */ 521 */
520 if ((_IOC_NR(cmd) & EV_MAX) == EV_KEY && _IOC_SIZE(cmd) == OLD_KEY_MAX) { 522 if (type == EV_KEY && size == OLD_KEY_MAX) {
521 len = OLD_KEY_MAX; 523 len = OLD_KEY_MAX;
522 if (printk_timed_ratelimit(&keymax_warn_time, 10 * 1000)) 524 if (printk_timed_ratelimit(&keymax_warn_time, 10 * 1000))
523 printk(KERN_WARNING 525 printk(KERN_WARNING
@@ -528,10 +530,81 @@ static int handle_eviocgbit(struct input_dev *dev, unsigned int cmd, void __user
528 BITS_TO_LONGS(OLD_KEY_MAX) * sizeof(long)); 530 BITS_TO_LONGS(OLD_KEY_MAX) * sizeof(long));
529 } 531 }
530 532
531 return bits_to_user(bits, len, _IOC_SIZE(cmd), p, compat_mode); 533 return bits_to_user(bits, len, size, p, compat_mode);
532} 534}
533#undef OLD_KEY_MAX 535#undef OLD_KEY_MAX
534 536
537static int evdev_handle_get_keycode(struct input_dev *dev, void __user *p)
538{
539 struct input_keymap_entry ke = {
540 .len = sizeof(unsigned int),
541 .flags = 0,
542 };
543 int __user *ip = (int __user *)p;
544 int error;
545
546 /* legacy case */
547 if (copy_from_user(ke.scancode, p, sizeof(unsigned int)))
548 return -EFAULT;
549
550 error = input_get_keycode(dev, &ke);
551 if (error)
552 return error;
553
554 if (put_user(ke.keycode, ip + 1))
555 return -EFAULT;
556
557 return 0;
558}
559
560static int evdev_handle_get_keycode_v2(struct input_dev *dev, void __user *p)
561{
562 struct input_keymap_entry ke;
563 int error;
564
565 if (copy_from_user(&ke, p, sizeof(ke)))
566 return -EFAULT;
567
568 error = input_get_keycode(dev, &ke);
569 if (error)
570 return error;
571
572 if (copy_to_user(p, &ke, sizeof(ke)))
573 return -EFAULT;
574
575 return 0;
576}
577
578static int evdev_handle_set_keycode(struct input_dev *dev, void __user *p)
579{
580 struct input_keymap_entry ke = {
581 .len = sizeof(unsigned int),
582 .flags = 0,
583 };
584 int __user *ip = (int __user *)p;
585
586 if (copy_from_user(ke.scancode, p, sizeof(unsigned int)))
587 return -EFAULT;
588
589 if (get_user(ke.keycode, ip + 1))
590 return -EFAULT;
591
592 return input_set_keycode(dev, &ke);
593}
594
595static int evdev_handle_set_keycode_v2(struct input_dev *dev, void __user *p)
596{
597 struct input_keymap_entry ke;
598
599 if (copy_from_user(&ke, p, sizeof(ke)))
600 return -EFAULT;
601
602 if (ke.len > sizeof(ke.scancode))
603 return -EINVAL;
604
605 return input_set_keycode(dev, &ke);
606}
607
535static long evdev_do_ioctl(struct file *file, unsigned int cmd, 608static long evdev_do_ioctl(struct file *file, unsigned int cmd,
536 void __user *p, int compat_mode) 609 void __user *p, int compat_mode)
537{ 610{
@@ -542,8 +615,10 @@ static long evdev_do_ioctl(struct file *file, unsigned int cmd,
542 struct ff_effect effect; 615 struct ff_effect effect;
543 int __user *ip = (int __user *)p; 616 int __user *ip = (int __user *)p;
544 unsigned int i, t, u, v; 617 unsigned int i, t, u, v;
618 unsigned int size;
545 int error; 619 int error;
546 620
621 /* First we check for fixed-length commands */
547 switch (cmd) { 622 switch (cmd) {
548 623
549 case EVIOCGVERSION: 624 case EVIOCGVERSION:
@@ -576,25 +651,6 @@ static long evdev_do_ioctl(struct file *file, unsigned int cmd,
576 651
577 return 0; 652 return 0;
578 653
579 case EVIOCGKEYCODE:
580 if (get_user(t, ip))
581 return -EFAULT;
582
583 error = input_get_keycode(dev, t, &v);
584 if (error)
585 return error;
586
587 if (put_user(v, ip + 1))
588 return -EFAULT;
589
590 return 0;
591
592 case EVIOCSKEYCODE:
593 if (get_user(t, ip) || get_user(v, ip + 1))
594 return -EFAULT;
595
596 return input_set_keycode(dev, t, v);
597
598 case EVIOCRMFF: 654 case EVIOCRMFF:
599 return input_ff_erase(dev, (int)(unsigned long) p, file); 655 return input_ff_erase(dev, (int)(unsigned long) p, file);
600 656
@@ -611,111 +667,118 @@ static long evdev_do_ioctl(struct file *file, unsigned int cmd,
611 else 667 else
612 return evdev_ungrab(evdev, client); 668 return evdev_ungrab(evdev, client);
613 669
614 default: 670 case EVIOCGKEYCODE:
671 return evdev_handle_get_keycode(dev, p);
615 672
616 if (_IOC_TYPE(cmd) != 'E') 673 case EVIOCSKEYCODE:
617 return -EINVAL; 674 return evdev_handle_set_keycode(dev, p);
675
676 case EVIOCGKEYCODE_V2:
677 return evdev_handle_get_keycode_v2(dev, p);
618 678
619 if (_IOC_DIR(cmd) == _IOC_READ) { 679 case EVIOCSKEYCODE_V2:
680 return evdev_handle_set_keycode_v2(dev, p);
681 }
620 682
621 if ((_IOC_NR(cmd) & ~EV_MAX) == _IOC_NR(EVIOCGBIT(0, 0))) 683 size = _IOC_SIZE(cmd);
622 return handle_eviocgbit(dev, cmd, p, compat_mode);
623 684
624 if (_IOC_NR(cmd) == _IOC_NR(EVIOCGKEY(0))) 685 /* Now check variable-length commands */
625 return bits_to_user(dev->key, KEY_MAX, _IOC_SIZE(cmd), 686#define EVIOC_MASK_SIZE(nr) ((nr) & ~(_IOC_SIZEMASK << _IOC_SIZESHIFT))
626 p, compat_mode); 687 switch (EVIOC_MASK_SIZE(cmd)) {
627 688
628 if (_IOC_NR(cmd) == _IOC_NR(EVIOCGLED(0))) 689 case EVIOCGKEY(0):
629 return bits_to_user(dev->led, LED_MAX, _IOC_SIZE(cmd), 690 return bits_to_user(dev->key, KEY_MAX, size, p, compat_mode);
630 p, compat_mode);
631 691
632 if (_IOC_NR(cmd) == _IOC_NR(EVIOCGSND(0))) 692 case EVIOCGLED(0):
633 return bits_to_user(dev->snd, SND_MAX, _IOC_SIZE(cmd), 693 return bits_to_user(dev->led, LED_MAX, size, p, compat_mode);
634 p, compat_mode);
635 694
636 if (_IOC_NR(cmd) == _IOC_NR(EVIOCGSW(0))) 695 case EVIOCGSND(0):
637 return bits_to_user(dev->sw, SW_MAX, _IOC_SIZE(cmd), 696 return bits_to_user(dev->snd, SND_MAX, size, p, compat_mode);
638 p, compat_mode);
639 697
640 if (_IOC_NR(cmd) == _IOC_NR(EVIOCGNAME(0))) 698 case EVIOCGSW(0):
641 return str_to_user(dev->name, _IOC_SIZE(cmd), p); 699 return bits_to_user(dev->sw, SW_MAX, size, p, compat_mode);
642 700
643 if (_IOC_NR(cmd) == _IOC_NR(EVIOCGPHYS(0))) 701 case EVIOCGNAME(0):
644 return str_to_user(dev->phys, _IOC_SIZE(cmd), p); 702 return str_to_user(dev->name, size, p);
645 703
646 if (_IOC_NR(cmd) == _IOC_NR(EVIOCGUNIQ(0))) 704 case EVIOCGPHYS(0):
647 return str_to_user(dev->uniq, _IOC_SIZE(cmd), p); 705 return str_to_user(dev->phys, size, p);
648 706
649 if ((_IOC_NR(cmd) & ~ABS_MAX) == _IOC_NR(EVIOCGABS(0))) { 707 case EVIOCGUNIQ(0):
708 return str_to_user(dev->uniq, size, p);
650 709
651 t = _IOC_NR(cmd) & ABS_MAX; 710 case EVIOC_MASK_SIZE(EVIOCSFF):
711 if (input_ff_effect_from_user(p, size, &effect))
712 return -EFAULT;
652 713
653 abs.value = dev->abs[t]; 714 error = input_ff_upload(dev, &effect, file);
654 abs.minimum = dev->absmin[t];
655 abs.maximum = dev->absmax[t];
656 abs.fuzz = dev->absfuzz[t];
657 abs.flat = dev->absflat[t];
658 abs.resolution = dev->absres[t];
659 715
660 if (copy_to_user(p, &abs, min_t(size_t, 716 if (put_user(effect.id, &(((struct ff_effect __user *)p)->id)))
661 _IOC_SIZE(cmd), 717 return -EFAULT;
662 sizeof(struct input_absinfo))))
663 return -EFAULT;
664 718
665 return 0; 719 return error;
666 } 720 }
667 721
668 } 722 /* Multi-number variable-length handlers */
723 if (_IOC_TYPE(cmd) != 'E')
724 return -EINVAL;
725
726 if (_IOC_DIR(cmd) == _IOC_READ) {
669 727
670 if (_IOC_DIR(cmd) == _IOC_WRITE) { 728 if ((_IOC_NR(cmd) & ~EV_MAX) == _IOC_NR(EVIOCGBIT(0, 0)))
729 return handle_eviocgbit(dev,
730 _IOC_NR(cmd) & EV_MAX, size,
731 p, compat_mode);
671 732
672 if (_IOC_NR(cmd) == _IOC_NR(EVIOCSFF)) { 733 if ((_IOC_NR(cmd) & ~ABS_MAX) == _IOC_NR(EVIOCGABS(0))) {
673 734
674 if (input_ff_effect_from_user(p, _IOC_SIZE(cmd), &effect)) 735 if (!dev->absinfo)
675 return -EFAULT; 736 return -EINVAL;
676 737
677 error = input_ff_upload(dev, &effect, file); 738 t = _IOC_NR(cmd) & ABS_MAX;
739 abs = dev->absinfo[t];
740
741 if (copy_to_user(p, &abs, min_t(size_t,
742 size, sizeof(struct input_absinfo))))
743 return -EFAULT;
678 744
679 if (put_user(effect.id, &(((struct ff_effect __user *)p)->id))) 745 return 0;
680 return -EFAULT; 746 }
747 }
681 748
682 return error; 749 if (_IOC_DIR(cmd) == _IOC_WRITE) {
683 }
684 750
685 if ((_IOC_NR(cmd) & ~ABS_MAX) == _IOC_NR(EVIOCSABS(0))) { 751 if ((_IOC_NR(cmd) & ~ABS_MAX) == _IOC_NR(EVIOCSABS(0))) {
686 752
687 t = _IOC_NR(cmd) & ABS_MAX; 753 if (!dev->absinfo)
754 return -EINVAL;
688 755
689 if (copy_from_user(&abs, p, min_t(size_t, 756 t = _IOC_NR(cmd) & ABS_MAX;
690 _IOC_SIZE(cmd),
691 sizeof(struct input_absinfo))))
692 return -EFAULT;
693 757
694 /* We can't change number of reserved MT slots */ 758 if (copy_from_user(&abs, p, min_t(size_t,
695 if (t == ABS_MT_SLOT) 759 size, sizeof(struct input_absinfo))))
696 return -EINVAL; 760 return -EFAULT;
697 761
698 /* 762 if (size < sizeof(struct input_absinfo))
699 * Take event lock to ensure that we are not 763 abs.resolution = 0;
700 * changing device parameters in the middle
701 * of event.
702 */
703 spin_lock_irq(&dev->event_lock);
704 764
705 dev->abs[t] = abs.value; 765 /* We can't change number of reserved MT slots */
706 dev->absmin[t] = abs.minimum; 766 if (t == ABS_MT_SLOT)
707 dev->absmax[t] = abs.maximum; 767 return -EINVAL;
708 dev->absfuzz[t] = abs.fuzz;
709 dev->absflat[t] = abs.flat;
710 dev->absres[t] = _IOC_SIZE(cmd) < sizeof(struct input_absinfo) ?
711 0 : abs.resolution;
712 768
713 spin_unlock_irq(&dev->event_lock); 769 /*
770 * Take event lock to ensure that we are not
771 * changing device parameters in the middle
772 * of event.
773 */
774 spin_lock_irq(&dev->event_lock);
775 dev->absinfo[t] = abs;
776 spin_unlock_irq(&dev->event_lock);
714 777
715 return 0; 778 return 0;
716 }
717 } 779 }
718 } 780 }
781
719 return -EINVAL; 782 return -EINVAL;
720} 783}
721 784
@@ -767,7 +830,8 @@ static const struct file_operations evdev_fops = {
767 .compat_ioctl = evdev_ioctl_compat, 830 .compat_ioctl = evdev_ioctl_compat,
768#endif 831#endif
769 .fasync = evdev_fasync, 832 .fasync = evdev_fasync,
770 .flush = evdev_flush 833 .flush = evdev_flush,
834 .llseek = no_llseek,
771}; 835};
772 836
773static int evdev_install_chrdev(struct evdev *evdev) 837static int evdev_install_chrdev(struct evdev *evdev)