From owner-svn-src-all@freebsd.org Mon Nov 14 22:33:59 2016 Return-Path: Delivered-To: svn-src-all@mailman.ysv.freebsd.org Received: from mx1.freebsd.org (mx1.freebsd.org [IPv6:2001:1900:2254:206a::19:1]) by mailman.ysv.freebsd.org (Postfix) with ESMTP id 4BE20C41799; Mon, 14 Nov 2016 22:33:59 +0000 (UTC) (envelope-from gonzo@FreeBSD.org) Received: from repo.freebsd.org (repo.freebsd.org [IPv6:2610:1c1:1:6068::e6a:0]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (Client did not present a certificate) by mx1.freebsd.org (Postfix) with ESMTPS id 09319FF; Mon, 14 Nov 2016 22:33:58 +0000 (UTC) (envelope-from gonzo@FreeBSD.org) Received: from repo.freebsd.org ([127.0.1.37]) by repo.freebsd.org (8.15.2/8.15.2) with ESMTP id uAEMXwb5020388; Mon, 14 Nov 2016 22:33:58 GMT (envelope-from gonzo@FreeBSD.org) Received: (from gonzo@localhost) by repo.freebsd.org (8.15.2/8.15.2/Submit) id uAEMXwUN020386; Mon, 14 Nov 2016 22:33:58 GMT (envelope-from gonzo@FreeBSD.org) Message-Id: <201611142233.uAEMXwUN020386@repo.freebsd.org> X-Authentication-Warning: repo.freebsd.org: gonzo set sender to gonzo@FreeBSD.org using -f From: Oleksandr Tymoshenko Date: Mon, 14 Nov 2016 22:33:58 +0000 (UTC) To: src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-stable@freebsd.org, svn-src-stable-11@freebsd.org Subject: svn commit: r308654 - stable/11/sys/dev/atkbdc X-SVN-Group: stable-11 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit X-BeenThere: svn-src-all@freebsd.org X-Mailman-Version: 2.1.23 Precedence: list List-Id: "SVN commit messages for the entire src tree \(except for " user" and " projects" \)" List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Mon, 14 Nov 2016 22:33:59 -0000 Author: gonzo Date: Mon Nov 14 22:33:57 2016 New Revision: 308654 URL: https://svnweb.freebsd.org/changeset/base/308654 Log: MFC r308240: [evdev] Add evdev support to atkbd(4) driver To enable event sourcing from atkbd kern.evdev.rcpt_mask value should have bit 3 set. Submitted by: Vladimir Kondratiev MFC after: 1 week Differential Revision: https://reviews.freebsd.org/D8381 Modified: stable/11/sys/dev/atkbdc/atkbd.c stable/11/sys/dev/atkbdc/atkbd_atkbdc.c Directory Properties: stable/11/ (props changed) Modified: stable/11/sys/dev/atkbdc/atkbd.c ============================================================================== --- stable/11/sys/dev/atkbdc/atkbd.c Mon Nov 14 21:38:36 2016 (r308653) +++ stable/11/sys/dev/atkbdc/atkbd.c Mon Nov 14 22:33:57 2016 (r308654) @@ -31,6 +31,7 @@ __FBSDID("$FreeBSD$"); #include "opt_compat.h" #include "opt_kbd.h" #include "opt_atkbd.h" +#include "opt_evdev.h" #include #include @@ -49,6 +50,11 @@ __FBSDID("$FreeBSD$"); #include #include +#ifdef EVDEV_SUPPORT +#include +#include +#endif + typedef struct atkbd_state { KBDC kbdc; /* keyboard controller */ int ks_mode; /* input mode (K_XLATE,K_RAW,K_CODE) */ @@ -60,6 +66,10 @@ typedef struct atkbd_state { u_int ks_composed_char; /* composed char code (> 0) */ u_char ks_prefix; /* AT scan code prefix */ struct callout ks_timer; +#ifdef EVDEV_SUPPORT + struct evdev_dev *ks_evdev; + int ks_evdev_state; +#endif } atkbd_state_t; static void atkbd_timeout(void *arg); @@ -72,6 +82,11 @@ static int atkbd_reset(KBDC kbdc, int f #define DEFAULT_DELAY 0x1 /* 500ms */ #define DEFAULT_RATE 0x10 /* 14Hz */ +#ifdef EVDEV_SUPPORT +#define PS2_KEYBOARD_VENDOR 1 +#define PS2_KEYBOARD_PRODUCT 1 +#endif + int atkbd_probe_unit(device_t dev, int irq, int flags) { @@ -250,6 +265,12 @@ static int typematic(int delay, int rat static int typematic_delay(int delay); static int typematic_rate(int rate); +#ifdef EVDEV_SUPPORT +static const struct evdev_methods atkbd_evdev_methods = { + .ev_event = evdev_ev_kbd_event, +}; +#endif + /* local variables */ /* the initial key map, accent map and fkey strings */ @@ -352,6 +373,10 @@ atkbd_init(int unit, keyboard_t **kbdp, int delay[2]; int *data = (int *)arg; /* data[0]: controller, data[1]: irq */ int error, needfree; +#ifdef EVDEV_SUPPORT + struct evdev_dev *evdev; + char phys_loc[8]; +#endif /* XXX */ if (unit == ATKBD_DEFAULT) { @@ -436,6 +461,34 @@ atkbd_init(int unit, keyboard_t **kbdp, delay[0] = kbd->kb_delay1; delay[1] = kbd->kb_delay2; atkbd_ioctl(kbd, KDSETREPEAT, (caddr_t)delay); + +#ifdef EVDEV_SUPPORT + /* register as evdev provider on first init */ + if (state->ks_evdev == NULL) { + snprintf(phys_loc, sizeof(phys_loc), "atkbd%d", unit); + evdev = evdev_alloc(); + evdev_set_name(evdev, "AT keyboard"); + evdev_set_phys(evdev, phys_loc); + evdev_set_id(evdev, BUS_I8042, PS2_KEYBOARD_VENDOR, + PS2_KEYBOARD_PRODUCT, 0); + evdev_set_methods(evdev, kbd, &atkbd_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); } if (!KBD_IS_CONFIGURED(kbd)) { @@ -620,6 +673,20 @@ next_code: printf("atkbd_read_char(): scancode:0x%x\n", scancode); #endif +#ifdef EVDEV_SUPPORT + /* push evdev event */ + if (evdev_rcpt_mask & EVDEV_RCPT_HW_KBD && state->ks_evdev != NULL) { + keycode = evdev_scancode2key(&state->ks_evdev_state, + scancode); + + if (keycode != KEY_RESERVED) { + evdev_push_event(state->ks_evdev, EV_KEY, + (uint16_t)keycode, 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) return scancode; @@ -930,6 +997,12 @@ atkbd_ioctl(keyboard_t *kbd, u_long cmd, return error; } } +#ifdef EVDEV_SUPPORT + /* push LED states to evdev */ + if (state->ks_evdev != NULL && + evdev_rcpt_mask & EVDEV_RCPT_HW_KBD) + evdev_push_leds(state->ks_evdev, *(int *)arg); +#endif KBD_LED_VAL(kbd) = *(int *)arg; break; @@ -963,6 +1036,11 @@ atkbd_ioctl(keyboard_t *kbd, u_long cmd, if (error == 0) { kbd->kb_delay1 = typematic_delay(i); kbd->kb_delay2 = typematic_rate(i); +#ifdef EVDEV_SUPPORT + if (state->ks_evdev != NULL && + evdev_rcpt_mask & EVDEV_RCPT_HW_KBD) + evdev_push_repeats(state->ks_evdev, kbd); +#endif } return error; @@ -981,6 +1059,11 @@ atkbd_ioctl(keyboard_t *kbd, u_long cmd, if (error == 0) { kbd->kb_delay1 = typematic_delay(*(int *)arg); kbd->kb_delay2 = typematic_rate(*(int *)arg); +#ifdef EVDEV_SUPPORT + if (state->ks_evdev != NULL && + evdev_rcpt_mask & EVDEV_RCPT_HW_KBD) + evdev_push_repeats(state->ks_evdev, kbd); +#endif } return error; Modified: stable/11/sys/dev/atkbdc/atkbd_atkbdc.c ============================================================================== --- stable/11/sys/dev/atkbdc/atkbd_atkbdc.c Mon Nov 14 21:38:36 2016 (r308653) +++ stable/11/sys/dev/atkbdc/atkbd_atkbdc.c Mon Nov 14 22:33:57 2016 (r308654) @@ -28,6 +28,7 @@ __FBSDID("$FreeBSD$"); #include "opt_kbd.h" +#include "opt_evdev.h" #include #include @@ -169,3 +170,6 @@ atkbdintr(void *arg) } DRIVER_MODULE(atkbd, atkbdc, atkbd_driver, atkbd_devclass, 0, 0); +#ifdef EVDEV_SUPPORT +MODULE_DEPEND(atkbd, evdev, 1, 1, 1); +#endif