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