at v2.6.13 20 kB view raw
1/* 2 * Event char devices, giving access to raw input device events. 3 * 4 * Copyright (c) 1999-2002 Vojtech Pavlik 5 * 6 * This program is free software; you can redistribute it and/or modify it 7 * under the terms of the GNU General Public License version 2 as published by 8 * the Free Software Foundation. 9 */ 10 11#define EVDEV_MINOR_BASE 64 12#define EVDEV_MINORS 32 13#define EVDEV_BUFFER_SIZE 64 14 15#include <linux/poll.h> 16#include <linux/slab.h> 17#include <linux/module.h> 18#include <linux/init.h> 19#include <linux/input.h> 20#include <linux/major.h> 21#include <linux/smp_lock.h> 22#include <linux/device.h> 23#include <linux/devfs_fs_kernel.h> 24#include <linux/compat.h> 25 26struct evdev { 27 int exist; 28 int open; 29 int minor; 30 char name[16]; 31 struct input_handle handle; 32 wait_queue_head_t wait; 33 struct evdev_list *grab; 34 struct list_head list; 35}; 36 37struct evdev_list { 38 struct input_event buffer[EVDEV_BUFFER_SIZE]; 39 int head; 40 int tail; 41 struct fasync_struct *fasync; 42 struct evdev *evdev; 43 struct list_head node; 44}; 45 46static struct evdev *evdev_table[EVDEV_MINORS]; 47 48static void evdev_event(struct input_handle *handle, unsigned int type, unsigned int code, int value) 49{ 50 struct evdev *evdev = handle->private; 51 struct evdev_list *list; 52 53 if (evdev->grab) { 54 list = evdev->grab; 55 56 do_gettimeofday(&list->buffer[list->head].time); 57 list->buffer[list->head].type = type; 58 list->buffer[list->head].code = code; 59 list->buffer[list->head].value = value; 60 list->head = (list->head + 1) & (EVDEV_BUFFER_SIZE - 1); 61 62 kill_fasync(&list->fasync, SIGIO, POLL_IN); 63 } else 64 list_for_each_entry(list, &evdev->list, node) { 65 66 do_gettimeofday(&list->buffer[list->head].time); 67 list->buffer[list->head].type = type; 68 list->buffer[list->head].code = code; 69 list->buffer[list->head].value = value; 70 list->head = (list->head + 1) & (EVDEV_BUFFER_SIZE - 1); 71 72 kill_fasync(&list->fasync, SIGIO, POLL_IN); 73 } 74 75 wake_up_interruptible(&evdev->wait); 76} 77 78static int evdev_fasync(int fd, struct file *file, int on) 79{ 80 int retval; 81 struct evdev_list *list = file->private_data; 82 retval = fasync_helper(fd, file, on, &list->fasync); 83 return retval < 0 ? retval : 0; 84} 85 86static int evdev_flush(struct file * file) 87{ 88 struct evdev_list *list = file->private_data; 89 if (!list->evdev->exist) return -ENODEV; 90 return input_flush_device(&list->evdev->handle, file); 91} 92 93static void evdev_free(struct evdev *evdev) 94{ 95 evdev_table[evdev->minor] = NULL; 96 kfree(evdev); 97} 98 99static int evdev_release(struct inode * inode, struct file * file) 100{ 101 struct evdev_list *list = file->private_data; 102 103 if (list->evdev->grab == list) { 104 input_release_device(&list->evdev->handle); 105 list->evdev->grab = NULL; 106 } 107 108 evdev_fasync(-1, file, 0); 109 list_del(&list->node); 110 111 if (!--list->evdev->open) { 112 if (list->evdev->exist) 113 input_close_device(&list->evdev->handle); 114 else 115 evdev_free(list->evdev); 116 } 117 118 kfree(list); 119 return 0; 120} 121 122static int evdev_open(struct inode * inode, struct file * file) 123{ 124 struct evdev_list *list; 125 int i = iminor(inode) - EVDEV_MINOR_BASE; 126 int accept_err; 127 128 if (i >= EVDEV_MINORS || !evdev_table[i] || !evdev_table[i]->exist) 129 return -ENODEV; 130 131 if ((accept_err = input_accept_process(&(evdev_table[i]->handle), file))) 132 return accept_err; 133 134 if (!(list = kmalloc(sizeof(struct evdev_list), GFP_KERNEL))) 135 return -ENOMEM; 136 memset(list, 0, sizeof(struct evdev_list)); 137 138 list->evdev = evdev_table[i]; 139 list_add_tail(&list->node, &evdev_table[i]->list); 140 file->private_data = list; 141 142 if (!list->evdev->open++) 143 if (list->evdev->exist) 144 input_open_device(&list->evdev->handle); 145 146 return 0; 147} 148 149#ifdef CONFIG_COMPAT 150struct input_event_compat { 151 struct compat_timeval time; 152 __u16 type; 153 __u16 code; 154 __s32 value; 155}; 156 157#ifdef CONFIG_X86_64 158# define COMPAT_TEST test_thread_flag(TIF_IA32) 159#elif defined(CONFIG_IA64) 160# define COMPAT_TEST IS_IA32_PROCESS(ia64_task_regs(current)) 161#elif defined(CONFIG_ARCH_S390) 162# define COMPAT_TEST test_thread_flag(TIF_31BIT) 163#else 164# define COMPAT_TEST test_thread_flag(TIF_32BIT) 165#endif 166 167static ssize_t evdev_write_compat(struct file * file, const char __user * buffer, size_t count, loff_t *ppos) 168{ 169 struct evdev_list *list = file->private_data; 170 struct input_event_compat event; 171 int retval = 0; 172 173 while (retval < count) { 174 if (copy_from_user(&event, buffer + retval, sizeof(struct input_event_compat))) 175 return -EFAULT; 176 input_event(list->evdev->handle.dev, event.type, event.code, event.value); 177 retval += sizeof(struct input_event_compat); 178 } 179 180 return retval; 181} 182#endif 183 184static ssize_t evdev_write(struct file * file, const char __user * buffer, size_t count, loff_t *ppos) 185{ 186 struct evdev_list *list = file->private_data; 187 struct input_event event; 188 int retval = 0; 189 190 if (!list->evdev->exist) return -ENODEV; 191 192#ifdef CONFIG_COMPAT 193 if (COMPAT_TEST) 194 return evdev_write_compat(file, buffer, count, ppos); 195#endif 196 197 while (retval < count) { 198 199 if (copy_from_user(&event, buffer + retval, sizeof(struct input_event))) 200 return -EFAULT; 201 input_event(list->evdev->handle.dev, event.type, event.code, event.value); 202 retval += sizeof(struct input_event); 203 } 204 205 return retval; 206} 207 208#ifdef CONFIG_COMPAT 209static ssize_t evdev_read_compat(struct file * file, char __user * buffer, size_t count, loff_t *ppos) 210{ 211 struct evdev_list *list = file->private_data; 212 int retval; 213 214 if (count < sizeof(struct input_event_compat)) 215 return -EINVAL; 216 217 if (list->head == list->tail && list->evdev->exist && (file->f_flags & O_NONBLOCK)) 218 return -EAGAIN; 219 220 retval = wait_event_interruptible(list->evdev->wait, 221 list->head != list->tail || (!list->evdev->exist)); 222 223 if (retval) 224 return retval; 225 226 if (!list->evdev->exist) 227 return -ENODEV; 228 229 while (list->head != list->tail && retval + sizeof(struct input_event_compat) <= count) { 230 struct input_event *event = (struct input_event *) list->buffer + list->tail; 231 struct input_event_compat event_compat; 232 event_compat.time.tv_sec = event->time.tv_sec; 233 event_compat.time.tv_usec = event->time.tv_usec; 234 event_compat.type = event->type; 235 event_compat.code = event->code; 236 event_compat.value = event->value; 237 238 if (copy_to_user(buffer + retval, &event_compat, 239 sizeof(struct input_event_compat))) return -EFAULT; 240 list->tail = (list->tail + 1) & (EVDEV_BUFFER_SIZE - 1); 241 retval += sizeof(struct input_event_compat); 242 } 243 244 return retval; 245} 246#endif 247 248static ssize_t evdev_read(struct file * file, char __user * buffer, size_t count, loff_t *ppos) 249{ 250 struct evdev_list *list = file->private_data; 251 int retval; 252 253#ifdef CONFIG_COMPAT 254 if (COMPAT_TEST) 255 return evdev_read_compat(file, buffer, count, ppos); 256#endif 257 258 if (count < sizeof(struct input_event)) 259 return -EINVAL; 260 261 if (list->head == list->tail && list->evdev->exist && (file->f_flags & O_NONBLOCK)) 262 return -EAGAIN; 263 264 retval = wait_event_interruptible(list->evdev->wait, 265 list->head != list->tail || (!list->evdev->exist)); 266 267 if (retval) 268 return retval; 269 270 if (!list->evdev->exist) 271 return -ENODEV; 272 273 while (list->head != list->tail && retval + sizeof(struct input_event) <= count) { 274 if (copy_to_user(buffer + retval, list->buffer + list->tail, 275 sizeof(struct input_event))) return -EFAULT; 276 list->tail = (list->tail + 1) & (EVDEV_BUFFER_SIZE - 1); 277 retval += sizeof(struct input_event); 278 } 279 280 return retval; 281} 282 283/* No kernel lock - fine */ 284static unsigned int evdev_poll(struct file *file, poll_table *wait) 285{ 286 struct evdev_list *list = file->private_data; 287 poll_wait(file, &list->evdev->wait, wait); 288 return ((list->head == list->tail) ? 0 : (POLLIN | POLLRDNORM)) | 289 (list->evdev->exist ? 0 : (POLLHUP | POLLERR)); 290} 291 292static long evdev_ioctl(struct file *file, unsigned int cmd, unsigned long arg) 293{ 294 struct evdev_list *list = file->private_data; 295 struct evdev *evdev = list->evdev; 296 struct input_dev *dev = evdev->handle.dev; 297 struct input_absinfo abs; 298 void __user *p = (void __user *)arg; 299 int __user *ip = (int __user *)arg; 300 int i, t, u, v; 301 302 if (!evdev->exist) return -ENODEV; 303 304 switch (cmd) { 305 306 case EVIOCGVERSION: 307 return put_user(EV_VERSION, ip); 308 309 case EVIOCGID: 310 return copy_to_user(p, &dev->id, sizeof(struct input_id)) ? -EFAULT : 0; 311 312 case EVIOCGKEYCODE: 313 if (get_user(t, ip)) return -EFAULT; 314 if (t < 0 || t >= dev->keycodemax || !dev->keycodesize) return -EINVAL; 315 if (put_user(INPUT_KEYCODE(dev, t), ip + 1)) return -EFAULT; 316 return 0; 317 318 case EVIOCSKEYCODE: 319 if (get_user(t, ip)) return -EFAULT; 320 if (t < 0 || t >= dev->keycodemax || !dev->keycodesize) return -EINVAL; 321 if (get_user(v, ip + 1)) return -EFAULT; 322 if (v < 0 || v > KEY_MAX) return -EINVAL; 323 if (v >> (dev->keycodesize * 8)) return -EINVAL; 324 u = SET_INPUT_KEYCODE(dev, t, v); 325 clear_bit(u, dev->keybit); 326 set_bit(v, dev->keybit); 327 for (i = 0; i < dev->keycodemax; i++) 328 if (INPUT_KEYCODE(dev,i) == u) 329 set_bit(u, dev->keybit); 330 return 0; 331 332 case EVIOCSFF: 333 if (dev->upload_effect) { 334 struct ff_effect effect; 335 int err; 336 337 if (copy_from_user(&effect, p, sizeof(effect))) 338 return -EFAULT; 339 err = dev->upload_effect(dev, &effect); 340 if (put_user(effect.id, &(((struct ff_effect __user *)arg)->id))) 341 return -EFAULT; 342 return err; 343 } 344 else return -ENOSYS; 345 346 case EVIOCRMFF: 347 if (dev->erase_effect) { 348 return dev->erase_effect(dev, (int)arg); 349 } 350 else return -ENOSYS; 351 352 case EVIOCGEFFECTS: 353 if (put_user(dev->ff_effects_max, ip)) 354 return -EFAULT; 355 return 0; 356 357 case EVIOCGRAB: 358 if (arg) { 359 if (evdev->grab) 360 return -EBUSY; 361 if (input_grab_device(&evdev->handle)) 362 return -EBUSY; 363 evdev->grab = list; 364 return 0; 365 } else { 366 if (evdev->grab != list) 367 return -EINVAL; 368 input_release_device(&evdev->handle); 369 evdev->grab = NULL; 370 return 0; 371 } 372 373 default: 374 375 if (_IOC_TYPE(cmd) != 'E') 376 return -EINVAL; 377 378 if (_IOC_DIR(cmd) == _IOC_READ) { 379 380 if ((_IOC_NR(cmd) & ~EV_MAX) == _IOC_NR(EVIOCGBIT(0,0))) { 381 382 long *bits; 383 int len; 384 385 switch (_IOC_NR(cmd) & EV_MAX) { 386 case 0: bits = dev->evbit; len = EV_MAX; break; 387 case EV_KEY: bits = dev->keybit; len = KEY_MAX; break; 388 case EV_REL: bits = dev->relbit; len = REL_MAX; break; 389 case EV_ABS: bits = dev->absbit; len = ABS_MAX; break; 390 case EV_MSC: bits = dev->mscbit; len = MSC_MAX; break; 391 case EV_LED: bits = dev->ledbit; len = LED_MAX; break; 392 case EV_SND: bits = dev->sndbit; len = SND_MAX; break; 393 case EV_FF: bits = dev->ffbit; len = FF_MAX; break; 394 default: return -EINVAL; 395 } 396 len = NBITS(len) * sizeof(long); 397 if (len > _IOC_SIZE(cmd)) len = _IOC_SIZE(cmd); 398 return copy_to_user(p, bits, len) ? -EFAULT : len; 399 } 400 401 if (_IOC_NR(cmd) == _IOC_NR(EVIOCGKEY(0))) { 402 int len; 403 len = NBITS(KEY_MAX) * sizeof(long); 404 if (len > _IOC_SIZE(cmd)) len = _IOC_SIZE(cmd); 405 return copy_to_user(p, dev->key, len) ? -EFAULT : len; 406 } 407 408 if (_IOC_NR(cmd) == _IOC_NR(EVIOCGLED(0))) { 409 int len; 410 len = NBITS(LED_MAX) * sizeof(long); 411 if (len > _IOC_SIZE(cmd)) len = _IOC_SIZE(cmd); 412 return copy_to_user(p, dev->led, len) ? -EFAULT : len; 413 } 414 415 if (_IOC_NR(cmd) == _IOC_NR(EVIOCGSND(0))) { 416 int len; 417 len = NBITS(SND_MAX) * sizeof(long); 418 if (len > _IOC_SIZE(cmd)) len = _IOC_SIZE(cmd); 419 return copy_to_user(p, dev->snd, len) ? -EFAULT : len; 420 } 421 422 if (_IOC_NR(cmd) == _IOC_NR(EVIOCGNAME(0))) { 423 int len; 424 if (!dev->name) return -ENOENT; 425 len = strlen(dev->name) + 1; 426 if (len > _IOC_SIZE(cmd)) len = _IOC_SIZE(cmd); 427 return copy_to_user(p, dev->name, len) ? -EFAULT : len; 428 } 429 430 if (_IOC_NR(cmd) == _IOC_NR(EVIOCGPHYS(0))) { 431 int len; 432 if (!dev->phys) return -ENOENT; 433 len = strlen(dev->phys) + 1; 434 if (len > _IOC_SIZE(cmd)) len = _IOC_SIZE(cmd); 435 return copy_to_user(p, dev->phys, len) ? -EFAULT : len; 436 } 437 438 if (_IOC_NR(cmd) == _IOC_NR(EVIOCGUNIQ(0))) { 439 int len; 440 if (!dev->uniq) return -ENOENT; 441 len = strlen(dev->uniq) + 1; 442 if (len > _IOC_SIZE(cmd)) len = _IOC_SIZE(cmd); 443 return copy_to_user(p, dev->uniq, len) ? -EFAULT : len; 444 } 445 446 if ((_IOC_NR(cmd) & ~ABS_MAX) == _IOC_NR(EVIOCGABS(0))) { 447 448 int t = _IOC_NR(cmd) & ABS_MAX; 449 450 abs.value = dev->abs[t]; 451 abs.minimum = dev->absmin[t]; 452 abs.maximum = dev->absmax[t]; 453 abs.fuzz = dev->absfuzz[t]; 454 abs.flat = dev->absflat[t]; 455 456 if (copy_to_user(p, &abs, sizeof(struct input_absinfo))) 457 return -EFAULT; 458 459 return 0; 460 } 461 462 } 463 464 if (_IOC_DIR(cmd) == _IOC_WRITE) { 465 466 if ((_IOC_NR(cmd) & ~ABS_MAX) == _IOC_NR(EVIOCSABS(0))) { 467 468 int t = _IOC_NR(cmd) & ABS_MAX; 469 470 if (copy_from_user(&abs, p, sizeof(struct input_absinfo))) 471 return -EFAULT; 472 473 dev->abs[t] = abs.value; 474 dev->absmin[t] = abs.minimum; 475 dev->absmax[t] = abs.maximum; 476 dev->absfuzz[t] = abs.fuzz; 477 dev->absflat[t] = abs.flat; 478 479 return 0; 480 } 481 } 482 } 483 return -EINVAL; 484} 485 486#ifdef CONFIG_COMPAT 487 488#define BITS_PER_LONG_COMPAT (sizeof(compat_long_t) * 8) 489#define NBITS_COMPAT(x) ((((x)-1)/BITS_PER_LONG_COMPAT)+1) 490#define OFF_COMPAT(x) ((x)%BITS_PER_LONG_COMPAT) 491#define BIT_COMPAT(x) (1UL<<OFF_COMPAT(x)) 492#define LONG_COMPAT(x) ((x)/BITS_PER_LONG_COMPAT) 493#define test_bit_compat(bit, array) ((array[LONG_COMPAT(bit)] >> OFF_COMPAT(bit)) & 1) 494 495#ifdef __BIG_ENDIAN 496#define bit_to_user(bit, max) \ 497do { \ 498 int i; \ 499 int len = NBITS_COMPAT((max)) * sizeof(compat_long_t); \ 500 if (len > _IOC_SIZE(cmd)) len = _IOC_SIZE(cmd); \ 501 for (i = 0; i < len / sizeof(compat_long_t); i++) \ 502 if (copy_to_user((compat_long_t*) p + i, \ 503 (compat_long_t*) (bit) + i + 1 - ((i % 2) << 1), \ 504 sizeof(compat_long_t))) \ 505 return -EFAULT; \ 506 return len; \ 507} while (0) 508#else 509#define bit_to_user(bit, max) \ 510do { \ 511 int len = NBITS_COMPAT((max)) * sizeof(compat_long_t); \ 512 if (len > _IOC_SIZE(cmd)) len = _IOC_SIZE(cmd); \ 513 return copy_to_user(p, (bit), len) ? -EFAULT : len; \ 514} while (0) 515#endif 516 517static long evdev_ioctl_compat(struct file *file, unsigned int cmd, unsigned long arg) 518{ 519 struct evdev_list *list = file->private_data; 520 struct evdev *evdev = list->evdev; 521 struct input_dev *dev = evdev->handle.dev; 522 struct input_absinfo abs; 523 void __user *p = compat_ptr(arg); 524 525 if (!evdev->exist) return -ENODEV; 526 527 switch (cmd) { 528 529 case EVIOCGVERSION: 530 case EVIOCGID: 531 case EVIOCGKEYCODE: 532 case EVIOCSKEYCODE: 533 case EVIOCSFF: 534 case EVIOCRMFF: 535 case EVIOCGEFFECTS: 536 case EVIOCGRAB: 537 return evdev_ioctl(file, cmd, (unsigned long) p); 538 539 default: 540 541 if (_IOC_TYPE(cmd) != 'E') 542 return -EINVAL; 543 544 if (_IOC_DIR(cmd) == _IOC_READ) { 545 546 if ((_IOC_NR(cmd) & ~EV_MAX) == _IOC_NR(EVIOCGBIT(0,0))) { 547 long *bits; 548 int max; 549 550 switch (_IOC_NR(cmd) & EV_MAX) { 551 case 0: bits = dev->evbit; max = EV_MAX; break; 552 case EV_KEY: bits = dev->keybit; max = KEY_MAX; break; 553 case EV_REL: bits = dev->relbit; max = REL_MAX; break; 554 case EV_ABS: bits = dev->absbit; max = ABS_MAX; break; 555 case EV_MSC: bits = dev->mscbit; max = MSC_MAX; break; 556 case EV_LED: bits = dev->ledbit; max = LED_MAX; break; 557 case EV_SND: bits = dev->sndbit; max = SND_MAX; break; 558 case EV_FF: bits = dev->ffbit; max = FF_MAX; break; 559 default: return -EINVAL; 560 } 561 bit_to_user(bits, max); 562 } 563 564 if (_IOC_NR(cmd) == _IOC_NR(EVIOCGKEY(0))) 565 bit_to_user(dev->key, KEY_MAX); 566 567 if (_IOC_NR(cmd) == _IOC_NR(EVIOCGLED(0))) 568 bit_to_user(dev->led, LED_MAX); 569 570 if (_IOC_NR(cmd) == _IOC_NR(EVIOCGSND(0))) 571 bit_to_user(dev->snd, SND_MAX); 572 573 if (_IOC_NR(cmd) == _IOC_NR(EVIOCGNAME(0))) { 574 int len; 575 if (!dev->name) return -ENOENT; 576 len = strlen(dev->name) + 1; 577 if (len > _IOC_SIZE(cmd)) len = _IOC_SIZE(cmd); 578 return copy_to_user(p, dev->name, len) ? -EFAULT : len; 579 } 580 581 if (_IOC_NR(cmd) == _IOC_NR(EVIOCGPHYS(0))) { 582 int len; 583 if (!dev->phys) return -ENOENT; 584 len = strlen(dev->phys) + 1; 585 if (len > _IOC_SIZE(cmd)) len = _IOC_SIZE(cmd); 586 return copy_to_user(p, dev->phys, len) ? -EFAULT : len; 587 } 588 589 if (_IOC_NR(cmd) == _IOC_NR(EVIOCGUNIQ(0))) { 590 int len; 591 if (!dev->uniq) return -ENOENT; 592 len = strlen(dev->uniq) + 1; 593 if (len > _IOC_SIZE(cmd)) len = _IOC_SIZE(cmd); 594 return copy_to_user(p, dev->uniq, len) ? -EFAULT : len; 595 } 596 597 if ((_IOC_NR(cmd) & ~ABS_MAX) == _IOC_NR(EVIOCGABS(0))) { 598 599 int t = _IOC_NR(cmd) & ABS_MAX; 600 601 abs.value = dev->abs[t]; 602 abs.minimum = dev->absmin[t]; 603 abs.maximum = dev->absmax[t]; 604 abs.fuzz = dev->absfuzz[t]; 605 abs.flat = dev->absflat[t]; 606 607 if (copy_to_user(p, &abs, sizeof(struct input_absinfo))) 608 return -EFAULT; 609 610 return 0; 611 } 612 } 613 614 if (_IOC_DIR(cmd) == _IOC_WRITE) { 615 616 if ((_IOC_NR(cmd) & ~ABS_MAX) == _IOC_NR(EVIOCSABS(0))) { 617 618 int t = _IOC_NR(cmd) & ABS_MAX; 619 620 if (copy_from_user(&abs, p, sizeof(struct input_absinfo))) 621 return -EFAULT; 622 623 dev->abs[t] = abs.value; 624 dev->absmin[t] = abs.minimum; 625 dev->absmax[t] = abs.maximum; 626 dev->absfuzz[t] = abs.fuzz; 627 dev->absflat[t] = abs.flat; 628 629 return 0; 630 } 631 } 632 } 633 return -EINVAL; 634} 635#endif 636 637static struct file_operations evdev_fops = { 638 .owner = THIS_MODULE, 639 .read = evdev_read, 640 .write = evdev_write, 641 .poll = evdev_poll, 642 .open = evdev_open, 643 .release = evdev_release, 644 .unlocked_ioctl = evdev_ioctl, 645#ifdef CONFIG_COMPAT 646 .compat_ioctl = evdev_ioctl_compat, 647#endif 648 .fasync = evdev_fasync, 649 .flush = evdev_flush 650}; 651 652static struct input_handle *evdev_connect(struct input_handler *handler, struct input_dev *dev, struct input_device_id *id) 653{ 654 struct evdev *evdev; 655 int minor; 656 657 for (minor = 0; minor < EVDEV_MINORS && evdev_table[minor]; minor++); 658 if (minor == EVDEV_MINORS) { 659 printk(KERN_ERR "evdev: no more free evdev devices\n"); 660 return NULL; 661 } 662 663 if (!(evdev = kmalloc(sizeof(struct evdev), GFP_KERNEL))) 664 return NULL; 665 memset(evdev, 0, sizeof(struct evdev)); 666 667 INIT_LIST_HEAD(&evdev->list); 668 init_waitqueue_head(&evdev->wait); 669 670 evdev->exist = 1; 671 evdev->minor = minor; 672 evdev->handle.dev = dev; 673 evdev->handle.name = evdev->name; 674 evdev->handle.handler = handler; 675 evdev->handle.private = evdev; 676 sprintf(evdev->name, "event%d", minor); 677 678 evdev_table[minor] = evdev; 679 680 devfs_mk_cdev(MKDEV(INPUT_MAJOR, EVDEV_MINOR_BASE + minor), 681 S_IFCHR|S_IRUGO|S_IWUSR, "input/event%d", minor); 682 class_device_create(input_class, 683 MKDEV(INPUT_MAJOR, EVDEV_MINOR_BASE + minor), 684 dev->dev, "event%d", minor); 685 686 return &evdev->handle; 687} 688 689static void evdev_disconnect(struct input_handle *handle) 690{ 691 struct evdev *evdev = handle->private; 692 struct evdev_list *list; 693 694 class_device_destroy(input_class, 695 MKDEV(INPUT_MAJOR, EVDEV_MINOR_BASE + evdev->minor)); 696 devfs_remove("input/event%d", evdev->minor); 697 evdev->exist = 0; 698 699 if (evdev->open) { 700 input_close_device(handle); 701 wake_up_interruptible(&evdev->wait); 702 list_for_each_entry(list, &evdev->list, node) 703 kill_fasync(&list->fasync, SIGIO, POLL_HUP); 704 } else 705 evdev_free(evdev); 706} 707 708static struct input_device_id evdev_ids[] = { 709 { .driver_info = 1 }, /* Matches all devices */ 710 { }, /* Terminating zero entry */ 711}; 712 713MODULE_DEVICE_TABLE(input, evdev_ids); 714 715static struct input_handler evdev_handler = { 716 .event = evdev_event, 717 .connect = evdev_connect, 718 .disconnect = evdev_disconnect, 719 .fops = &evdev_fops, 720 .minor = EVDEV_MINOR_BASE, 721 .name = "evdev", 722 .id_table = evdev_ids, 723}; 724 725static int __init evdev_init(void) 726{ 727 input_register_handler(&evdev_handler); 728 return 0; 729} 730 731static void __exit evdev_exit(void) 732{ 733 input_unregister_handler(&evdev_handler); 734} 735 736module_init(evdev_init); 737module_exit(evdev_exit); 738 739MODULE_AUTHOR("Vojtech Pavlik <vojtech@ucw.cz>"); 740MODULE_DESCRIPTION("Input driver event char devices"); 741MODULE_LICENSE("GPL");