Skip site navigation (1)Skip section navigation (2)
Date:      Sat, 3 Dec 2016 17:40:26 +0000 (UTC)
From:      Oleksandr Tymoshenko <gonzo@FreeBSD.org>
To:        src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-stable@freebsd.org, svn-src-stable-11@freebsd.org
Subject:   svn commit: r309488 - in stable/11/sys: dev/kbdmux modules/kbdmux
Message-ID:  <201612031740.uB3HeQGX020083@repo.freebsd.org>

next in thread | raw e-mail | index | archive | help
Author: gonzo
Date: Sat Dec  3 17:40:26 2016
New Revision: 309488
URL: https://svnweb.freebsd.org/changeset/base/309488

Log:
  MFC r308668:
  
  [evdev] Add evdev support to kbdmux(4) driver
  
  To enable event sourcing from kbdmux(4) kern.evdev.rcpt_mask value
  should have bit 1 set (this is default)
  
  Submitted by:	Vladimir Kondratiev <wulf@cicgroup.ru>
  Differential Revision:	https://reviews.freebsd.org/D8437

Modified:
  stable/11/sys/dev/kbdmux/kbdmux.c
  stable/11/sys/modules/kbdmux/Makefile
Directory Properties:
  stable/11/   (props changed)

Modified: stable/11/sys/dev/kbdmux/kbdmux.c
==============================================================================
--- stable/11/sys/dev/kbdmux/kbdmux.c	Sat Dec  3 17:27:28 2016	(r309487)
+++ stable/11/sys/dev/kbdmux/kbdmux.c	Sat Dec  3 17:40:26 2016	(r309488)
@@ -32,6 +32,7 @@
  */
 
 #include "opt_compat.h"
+#include "opt_evdev.h"
 #include "opt_kbd.h"
 #include "opt_kbdmux.h"
 
@@ -64,6 +65,11 @@
 
 #include <dev/kbd/kbdtables.h>
 
+#ifdef EVDEV_SUPPORT
+#include <dev/evdev/evdev.h>
+#include <dev/evdev/input.h>
+#endif
+
 #define KEYBOARD_NAME	"kbdmux"
 
 MALLOC_DECLARE(M_KBDMUX);
@@ -159,6 +165,11 @@ struct kbdmux_state
 	u_int			 ks_composed_char; /* composed char code */
 	u_char			 ks_prefix;	/* AT scan code prefix */
 
+#ifdef EVDEV_SUPPORT
+	struct evdev_dev *	 ks_evdev;
+	int			 ks_evdev_state;
+#endif
+
 	SLIST_HEAD(, kbdmux_kbd) ks_kbds;	/* keyboards */
 
 	KBDMUX_LOCK_DECL_GLOBAL;
@@ -371,6 +382,12 @@ static keyboard_switch_t kbdmuxsw = {
 	.diag =		genkbd_diag,
 };
 
+#ifdef EVDEV_SUPPORT
+static const struct evdev_methods kbdmux_evdev_methods = {
+	.ev_event = evdev_ev_kbd_event,
+};
+#endif
+
 /*
  * Return the number of found keyboards
  */
@@ -404,6 +421,10 @@ kbdmux_init(int unit, keyboard_t **kbdp,
         accentmap_t	*accmap = NULL;
         fkeytab_t	*fkeymap = NULL;
 	int		 error, needfree, fkeymap_size, delay[2];
+#ifdef EVDEV_SUPPORT
+	struct evdev_dev *evdev;
+	char		 phys_loc[NAMELEN];
+#endif
 
 	if (*kbdp == NULL) {
 		*kbdp = kbd = malloc(sizeof(*kbd), M_KBDMUX, M_NOWAIT | M_ZERO);
@@ -464,6 +485,30 @@ kbdmux_init(int unit, keyboard_t **kbdp,
 		delay[1] = kbd->kb_delay2;
 		kbdmux_ioctl(kbd, KDSETREPEAT, (caddr_t)delay);
 
+#ifdef EVDEV_SUPPORT
+		/* register as evdev provider */
+		evdev = evdev_alloc();
+		evdev_set_name(evdev, "System keyboard multiplexer");
+		snprintf(phys_loc, NAMELEN, KEYBOARD_NAME"%d", unit);
+		evdev_set_phys(evdev, phys_loc);
+		evdev_set_id(evdev, BUS_VIRTUAL, 0, 0, 0);
+		evdev_set_methods(evdev, kbd, &kbdmux_evdev_methods);
+		evdev_support_event(evdev, EV_SYN);
+		evdev_support_event(evdev, EV_KEY);
+		evdev_support_event(evdev, EV_LED);
+		evdev_support_event(evdev, EV_REP);
+		evdev_support_all_known_keys(evdev);
+		evdev_support_led(evdev, LED_NUML);
+		evdev_support_led(evdev, LED_CAPSL);
+		evdev_support_led(evdev, LED_SCROLLL);
+
+		if (evdev_register(evdev))
+			evdev_free(evdev);
+		else
+			state->ks_evdev = evdev;
+		state->ks_evdev_state = 0;
+#endif
+
 		KBD_INIT_DONE(kbd);
 	}
 
@@ -532,6 +577,10 @@ kbdmux_term(keyboard_t *kbd)
 
 	kbd_unregister(kbd);
 
+#ifdef EVDEV_SUPPORT
+	evdev_free(state->ks_evdev);
+#endif
+
 	KBDMUX_LOCK_DESTROY(state);
 	bzero(state, sizeof(*state));
 	free(state, M_KBDMUX);
@@ -694,6 +743,20 @@ next_code:
 
 	kbd->kb_count ++;
 
+#ifdef EVDEV_SUPPORT
+	/* push evdev event */
+	if (evdev_rcpt_mask & EVDEV_RCPT_KBDMUX && state->ks_evdev != NULL) {
+		uint16_t key = evdev_scancode2key(&state->ks_evdev_state,
+		    scancode);
+
+		if (key != KEY_RESERVED) {
+			evdev_push_event(state->ks_evdev, EV_KEY,
+			    key, scancode & 0x80 ? 0 : 1);
+			evdev_sync(state->ks_evdev);
+		}
+	}
+#endif
+
 	/* return the byte as is for the K_RAW mode */
 	if (state->ks_mode == K_RAW) {
 		KBDMUX_UNLOCK(state);
@@ -1120,7 +1183,11 @@ kbdmux_ioctl(keyboard_t *kbd, u_long cmd
 		}
 
 		KBD_LED_VAL(kbd) = *(int *)arg;
-
+#ifdef EVDEV_SUPPORT
+		if (state->ks_evdev != NULL &&
+		    evdev_rcpt_mask & EVDEV_RCPT_KBDMUX)
+			evdev_push_leds(state->ks_evdev, *(int *)arg);
+#endif
 		/* KDSETLED on all slave keyboards */
 		SLIST_FOREACH(k, &state->ks_kbds, next)
 			(void)kbdd_ioctl(k->kbd, KDSETLED, arg);
@@ -1197,7 +1264,11 @@ kbdmux_ioctl(keyboard_t *kbd, u_long cmd
 
 		kbd->kb_delay1 = delays[(mode >> 5) & 3];
 		kbd->kb_delay2 = rates[mode & 0x1f];
-
+#ifdef EVDEV_SUPPORT
+		if (state->ks_evdev != NULL &&
+		    evdev_rcpt_mask & EVDEV_RCPT_KBDMUX)
+			evdev_push_repeats(state->ks_evdev, kbd);
+#endif
 		/* perform command on all slave keyboards */
 		SLIST_FOREACH(k, &state->ks_kbds, next)
 			(void)kbdd_ioctl(k->kbd, cmd, arg);
@@ -1395,4 +1466,6 @@ kbdmux_modevent(module_t mod, int type, 
 }
 
 DEV_MODULE(kbdmux, kbdmux_modevent, NULL);
-
+#ifdef EVDEV_SUPPORT
+MODULE_DEPEND(kbdmux, evdev, 1, 1, 1);
+#endif

Modified: stable/11/sys/modules/kbdmux/Makefile
==============================================================================
--- stable/11/sys/modules/kbdmux/Makefile	Sat Dec  3 17:27:28 2016	(r309487)
+++ stable/11/sys/modules/kbdmux/Makefile	Sat Dec  3 17:40:26 2016	(r309488)
@@ -4,7 +4,8 @@
 .PATH: ${.CURDIR}/../../dev/kbdmux
 
 KMOD=	kbdmux
-SRCS=	kbdmux.c opt_compat.h opt_kbd.h opt_kbdmux.h bus_if.h device_if.h
+SRCS=	kbdmux.c opt_compat.h opt_evdev.h opt_kbd.h opt_kbdmux.h bus_if.h \
+	device_if.h
 
 .if !defined(KERNBUILDDIR)
 opt_compat.h:



Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201612031740.uB3HeQGX020083>