]> CyberLeo.Net >> Repos - FreeBSD/FreeBSD.git/blob - sys/dev/evdev/evdev_utils.c
zfs: merge openzfs/zfs@6c8f03232 (master) into main
[FreeBSD/FreeBSD.git] / sys / dev / evdev / evdev_utils.c
1 /*-
2  * Copyright (c) 2014 Jakub Wojciech Klama <jceel@FreeBSD.org>
3  * Copyright (c) 2015-2016 Vladimir Kondratyev <wulf@FreeBSD.org>
4  * All rights reserved.
5  *
6  * Redistribution and use in source and binary forms, with or without
7  * modification, are permitted provided that the following conditions
8  * are met:
9  * 1. Redistributions of source code must retain the above copyright
10  *    notice, this list of conditions and the following disclaimer.
11  * 2. Redistributions in binary form must reproduce the above copyright
12  *    notice, this list of conditions and the following disclaimer in the
13  *    documentation and/or other materials provided with the distribution.
14  *
15  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
16  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
17  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
18  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
19  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
20  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
21  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
22  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
23  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
24  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
25  * SUCH DAMAGE.
26  *
27  * $FreeBSD$
28  */
29
30 #include <sys/param.h>
31 #include <sys/bus.h>
32 #include <sys/conf.h>
33 #include <sys/kbio.h>
34 #include <sys/kernel.h>
35 #include <sys/lock.h>
36 #include <sys/malloc.h>
37 #include <sys/mutex.h>
38 #include <sys/systm.h>
39
40 #include <dev/evdev/evdev.h>
41 #include <dev/evdev/evdev_private.h>
42 #include <dev/evdev/input.h>
43
44 #define NONE    KEY_RESERVED
45
46 static uint16_t evdev_usb_scancodes[256] = {
47         /* 0x00 - 0x27 */
48         NONE,   NONE,   NONE,   NONE,   KEY_A,  KEY_B,  KEY_C,  KEY_D,
49         KEY_E,  KEY_F,  KEY_G,  KEY_H,  KEY_I,  KEY_J,  KEY_K,  KEY_L,
50         KEY_M,  KEY_N,  KEY_O,  KEY_P,  KEY_Q,  KEY_R,  KEY_S,  KEY_T,
51         KEY_U,  KEY_V,  KEY_W,  KEY_X,  KEY_Y,  KEY_Z,  KEY_1,  KEY_2,
52         KEY_3,  KEY_4,  KEY_5,  KEY_6,  KEY_7,  KEY_8,  KEY_9,  KEY_0,
53         /* 0x28 - 0x3f */
54         KEY_ENTER,      KEY_ESC,        KEY_BACKSPACE,  KEY_TAB,
55         KEY_SPACE,      KEY_MINUS,      KEY_EQUAL,      KEY_LEFTBRACE,
56         KEY_RIGHTBRACE, KEY_BACKSLASH,  KEY_BACKSLASH,  KEY_SEMICOLON,
57         KEY_APOSTROPHE, KEY_GRAVE,      KEY_COMMA,      KEY_DOT,
58         KEY_SLASH,      KEY_CAPSLOCK,   KEY_F1,         KEY_F2,
59         KEY_F3,         KEY_F4,         KEY_F5,         KEY_F6,
60         /* 0x40 - 0x5f */
61         KEY_F7,         KEY_F8,         KEY_F9,         KEY_F10,
62         KEY_F11,        KEY_F12,        KEY_SYSRQ,      KEY_SCROLLLOCK,
63         KEY_PAUSE,      KEY_INSERT,     KEY_HOME,       KEY_PAGEUP,
64         KEY_DELETE,     KEY_END,        KEY_PAGEDOWN,   KEY_RIGHT,
65         KEY_LEFT,       KEY_DOWN,       KEY_UP,         KEY_NUMLOCK,
66         KEY_KPSLASH,    KEY_KPASTERISK, KEY_KPMINUS,    KEY_KPPLUS,
67         KEY_KPENTER,    KEY_KP1,        KEY_KP2,        KEY_KP3,
68         KEY_KP4,        KEY_KP5,        KEY_KP6,        KEY_KP7,
69         /* 0x60 - 0x7f */
70         KEY_KP8,        KEY_KP9,        KEY_KP0,        KEY_KPDOT,
71         KEY_102ND,      KEY_COMPOSE,    KEY_POWER,      KEY_KPEQUAL,
72         KEY_F13,        KEY_F14,        KEY_F15,        KEY_F16,
73         KEY_F17,        KEY_F18,        KEY_F19,        KEY_F20,
74         KEY_F21,        KEY_F22,        KEY_F23,        KEY_F24,
75         KEY_OPEN,       KEY_HELP,       KEY_PROPS,      KEY_FRONT,
76         KEY_STOP,       KEY_AGAIN,      KEY_UNDO,       KEY_CUT,
77         KEY_COPY,       KEY_PASTE,      KEY_FIND,       KEY_MUTE,
78         /* 0x80 - 0x9f */
79         KEY_VOLUMEUP,   KEY_VOLUMEDOWN, NONE,           NONE,
80         NONE,           KEY_KPCOMMA,    NONE,           KEY_RO,
81         KEY_KATAKANAHIRAGANA,   KEY_YEN,KEY_HENKAN,     KEY_MUHENKAN,
82         KEY_KPJPCOMMA,  NONE,           NONE,           NONE,
83         KEY_HANGEUL,    KEY_HANJA,      KEY_KATAKANA,   KEY_HIRAGANA,
84         KEY_ZENKAKUHANKAKU,     NONE,   NONE,           NONE,
85         NONE,           NONE,           NONE,           NONE,
86         NONE,           NONE,           NONE,           NONE,
87         /* 0xa0 - 0xbf */
88         NONE,           NONE,           NONE,           NONE,
89         NONE,           NONE,           NONE,           NONE,
90         NONE,           NONE,           NONE,           NONE,
91         NONE,           NONE,           NONE,           NONE,
92         NONE,           NONE,           NONE,           NONE,
93         NONE,           NONE,           NONE,           NONE,
94         NONE,           NONE,           NONE,           NONE,
95         NONE,           NONE,           NONE,           NONE,
96         /* 0xc0 - 0xdf */
97         NONE,           NONE,           NONE,           NONE,
98         NONE,           NONE,           NONE,           NONE,
99         NONE,           NONE,           NONE,           NONE,
100         NONE,           NONE,           NONE,           NONE,
101         NONE,           NONE,           NONE,           NONE,
102         NONE,           NONE,           NONE,           NONE,
103         NONE,           NONE,           NONE,           NONE,
104         NONE,           NONE,           NONE,           NONE,
105         /* 0xe0 - 0xff */
106         KEY_LEFTCTRL,   KEY_LEFTSHIFT,  KEY_LEFTALT,    KEY_LEFTMETA,
107         KEY_RIGHTCTRL,  KEY_RIGHTSHIFT, KEY_RIGHTALT,   KEY_RIGHTMETA,
108         KEY_PLAYPAUSE,  KEY_STOPCD,     KEY_PREVIOUSSONG,KEY_NEXTSONG,
109         KEY_EJECTCD,    KEY_VOLUMEUP,   KEY_VOLUMEDOWN, KEY_MUTE,
110         KEY_WWW,        KEY_BACK,       KEY_FORWARD,    KEY_STOP,
111         KEY_FIND,       KEY_SCROLLUP,   KEY_SCROLLDOWN, KEY_EDIT,
112         KEY_SLEEP,      KEY_COFFEE,     KEY_REFRESH,    KEY_CALC,
113         NONE,           NONE,           NONE,           NONE,
114
115 };
116
117 static uint16_t evdev_at_set1_scancodes[] = {
118         /* 0x00 - 0x1f */
119         NONE,           KEY_ESC,        KEY_1,          KEY_2,
120         KEY_3,          KEY_4,          KEY_5,          KEY_6,
121         KEY_7,          KEY_8,          KEY_9,          KEY_0,
122         KEY_MINUS,      KEY_EQUAL,      KEY_BACKSPACE,  KEY_TAB,
123         KEY_Q,          KEY_W,          KEY_E,          KEY_R,
124         KEY_T,          KEY_Y,          KEY_U,          KEY_I,
125         KEY_O,          KEY_P,          KEY_LEFTBRACE,  KEY_RIGHTBRACE,
126         KEY_ENTER,      KEY_LEFTCTRL,   KEY_A,          KEY_S,
127         /* 0x20 - 0x3f */
128         KEY_D,          KEY_F,          KEY_G,          KEY_H,
129         KEY_J,          KEY_K,          KEY_L,          KEY_SEMICOLON,
130         KEY_APOSTROPHE, KEY_GRAVE,      KEY_LEFTSHIFT,  KEY_BACKSLASH,
131         KEY_Z,          KEY_X,          KEY_C,          KEY_V,
132         KEY_B,          KEY_N,          KEY_M,          KEY_COMMA,
133         KEY_DOT,        KEY_SLASH,      KEY_RIGHTSHIFT, KEY_KPASTERISK,
134         KEY_LEFTALT,    KEY_SPACE,      KEY_CAPSLOCK,   KEY_F1,
135         KEY_F2,         KEY_F3,         KEY_F4,         KEY_F5,
136         /* 0x40 - 0x5f */
137         KEY_F6,         KEY_F7,         KEY_F8,         KEY_F9,
138         KEY_F10,        KEY_NUMLOCK,    KEY_SCROLLLOCK, KEY_KP7,
139         KEY_KP8,        KEY_KP9,        KEY_KPMINUS,    KEY_KP4,
140         KEY_KP5,        KEY_KP6,        KEY_KPPLUS,     KEY_KP1,
141         KEY_KP2,        KEY_KP3,        KEY_KP0,        KEY_KPDOT,
142         NONE,           NONE,           KEY_102ND,      KEY_F11,
143         KEY_F12,        NONE,           NONE,           NONE,
144         NONE,           KEY_F13,        NONE,           NONE,
145         /* 0x60 - 0x7f */
146         NONE,           NONE,           NONE,           NONE,
147         NONE,           NONE,           NONE,           NONE,
148         NONE,           NONE,           NONE,           NONE,
149         NONE,           NONE,           NONE,           NONE,
150         KEY_KATAKANAHIRAGANA,   KEY_HANGEUL,    KEY_HANJA,      KEY_RO,
151         NONE,           NONE,   KEY_ZENKAKUHANKAKU,     KEY_HIRAGANA,
152         KEY_KATAKANA,   KEY_HENKAN,     NONE,           KEY_MUHENKAN,
153         NONE,           KEY_YEN,        KEY_KPCOMMA,    NONE,
154         /* 0x00 - 0x1f. 0xE0 prefixed */
155         NONE,           NONE,           NONE,           NONE,
156         NONE,           NONE,           NONE,           NONE,
157         NONE,           NONE,           NONE,           NONE,
158         NONE,           NONE,           NONE,           NONE,
159         KEY_PREVIOUSSONG,       NONE,   NONE,           NONE,
160         NONE,           NONE,           NONE,           NONE,
161         NONE,           KEY_NEXTSONG,   NONE,           NONE,
162         KEY_KPENTER,    KEY_RIGHTCTRL,  NONE,           NONE,
163         /* 0x20 - 0x3f. 0xE0 prefixed */
164         KEY_MUTE,       KEY_CALC,       KEY_PLAYPAUSE,  NONE,
165         KEY_STOPCD,     NONE,           NONE,           NONE,
166         NONE,           NONE,           NONE,           NONE,
167         NONE,           NONE,           KEY_VOLUMEDOWN, NONE,
168         KEY_VOLUMEUP,   NONE,           KEY_HOMEPAGE,   NONE,
169         NONE,           KEY_KPSLASH,    NONE,           KEY_SYSRQ,
170         KEY_RIGHTALT,   NONE,           NONE,           KEY_F13,
171         KEY_F14,        KEY_F15,        KEY_F16,        KEY_F17,
172         /* 0x40 - 0x5f. 0xE0 prefixed */
173         KEY_F18,        KEY_F19,        KEY_F20,        KEY_F21,
174         KEY_F22,        NONE,           KEY_PAUSE,      KEY_HOME,
175         KEY_UP,         KEY_PAGEUP,     NONE,           KEY_LEFT,
176         NONE,           KEY_RIGHT,      NONE,           KEY_END,
177         KEY_DOWN,       KEY_PAGEDOWN,   KEY_INSERT,     KEY_DELETE,
178         NONE,           NONE,           NONE,           KEY_F23,
179         KEY_F24,        NONE,           NONE,           KEY_LEFTMETA,
180         KEY_RIGHTMETA,  KEY_MENU,       KEY_POWER,      KEY_SLEEP,
181         /* 0x60 - 0x7f. 0xE0 prefixed */
182         NONE,           NONE,           NONE,           KEY_WAKEUP,
183         NONE,           KEY_SEARCH,     KEY_BOOKMARKS,  KEY_REFRESH,
184         KEY_STOP,       KEY_FORWARD,    KEY_BACK,       KEY_COMPUTER,
185         KEY_MAIL,       KEY_MEDIA,      NONE,           NONE,
186         NONE,           NONE,           NONE,           NONE,
187         NONE,           NONE,           NONE,           NONE,
188         NONE,           NONE,           NONE,           NONE,
189         NONE,           NONE,           NONE,           NONE,
190 };
191
192 static uint16_t evdev_mouse_button_codes[] = {
193         BTN_LEFT,
194         BTN_MIDDLE,
195         BTN_RIGHT,
196         BTN_SIDE,
197         BTN_EXTRA,
198         BTN_FORWARD,
199         BTN_BACK,
200         BTN_TASK,
201 };
202
203 static uint16_t evdev_led_codes[] = {
204         LED_CAPSL,      /* CLKED */
205         LED_NUML,       /* NLKED */
206         LED_SCROLLL,    /* SLKED */
207 };
208
209 static uint16_t evdev_nfinger_codes[] = {
210         BTN_TOOL_FINGER,
211         BTN_TOOL_DOUBLETAP,
212         BTN_TOOL_TRIPLETAP,
213         BTN_TOOL_QUADTAP,
214         BTN_TOOL_QUINTTAP,
215 };
216
217 uint16_t
218 evdev_hid2key(int scancode)
219 {
220         return evdev_usb_scancodes[scancode];
221 }
222
223 void
224 evdev_support_all_known_keys(struct evdev_dev *evdev)
225 {
226         size_t i;
227
228         for (i = KEY_RESERVED; i < nitems(evdev_at_set1_scancodes); i++)
229                 if (evdev_at_set1_scancodes[i] != NONE)
230                         evdev_support_key(evdev, evdev_at_set1_scancodes[i]);
231 }
232
233 uint16_t
234 evdev_scancode2key(int *state, int scancode)
235 {
236         uint16_t keycode;
237
238         /* translate the scan code into a keycode */
239         keycode = evdev_at_set1_scancodes[scancode & 0x7f];
240         switch (*state) {
241         case 0x00:      /* normal scancode */
242                 switch(scancode) {
243                 case 0xE0:
244                 case 0xE1:
245                         *state = scancode;
246                         return (NONE);
247                 }
248                 break;
249         case 0xE0:              /* 0xE0 prefix */
250                 *state = 0;
251                 keycode = evdev_at_set1_scancodes[0x80 + (scancode & 0x7f)];
252                 break;
253         case 0xE1:      /* 0xE1 prefix */
254                 /*
255                  * The pause/break key on the 101 keyboard produces:
256                  * E1-1D-45 E1-9D-C5
257                  * Ctrl-pause/break produces:
258                  * E0-46 E0-C6 (See above.)
259                  */
260                 *state = 0;
261                 if ((scancode & 0x7f) == 0x1D)
262                         *state = scancode;
263                 return (NONE);
264                 /* NOT REACHED */
265         case 0x1D:      /* pause / break */
266         case 0x9D:
267                 if ((*state ^ scancode) & 0x80)
268                         return (NONE);
269                 *state = 0;
270                 if ((scancode & 0x7f) != 0x45)
271                         return (NONE);
272                 keycode = KEY_PAUSE;
273                 break;
274         }
275
276         return (keycode);
277 }
278
279 void
280 evdev_push_mouse_btn(struct evdev_dev *evdev, int buttons)
281 {
282         size_t i;
283
284         for (i = 0; i < nitems(evdev_mouse_button_codes); i++)
285                 evdev_push_key(evdev, evdev_mouse_button_codes[i],
286                     buttons & (1 << i));
287 }
288
289 void
290 evdev_push_leds(struct evdev_dev *evdev, int leds)
291 {
292         size_t i;
293
294         /* Some drivers initialize leds before evdev */
295         if (evdev == NULL)
296                 return;
297
298         for (i = 0; i < nitems(evdev_led_codes); i++)
299                 evdev_push_led(evdev, evdev_led_codes[i], leds & (1 << i));
300 }
301
302 void
303 evdev_push_repeats(struct evdev_dev *evdev, keyboard_t *kbd)
304 {
305         /* Some drivers initialize typematics before evdev */
306         if (evdev == NULL)
307                 return;
308
309         evdev_push_event(evdev, EV_REP, REP_DELAY, kbd->kb_delay1);
310         evdev_push_event(evdev, EV_REP, REP_PERIOD, kbd->kb_delay2);
311 }
312
313 void
314 evdev_support_nfingers(struct evdev_dev *evdev, int nfingers)
315 {
316         int i;
317
318         for (i = 0; i < MIN(nitems(evdev_nfinger_codes), nfingers); i++)
319                 evdev_support_key(evdev, evdev_nfinger_codes[i]);
320 }
321
322 void
323 evdev_send_nfingers(struct evdev_dev *evdev, int nfingers)
324 {
325         int i;
326
327         EVDEV_LOCK_ASSERT(evdev);
328
329         if (nfingers > nitems(evdev_nfinger_codes))
330                 nfingers = nitems(evdev_nfinger_codes);
331
332         for (i = 0; i < nitems(evdev_nfinger_codes); i++)
333                 evdev_send_event(evdev, EV_KEY, evdev_nfinger_codes[i],
334                         nfingers == i + 1);
335 }
336
337 void
338 evdev_push_nfingers(struct evdev_dev *evdev, int nfingers)
339 {
340         EVDEV_ENTER(evdev);
341         evdev_send_nfingers(evdev, nfingers);
342         EVDEV_EXIT(evdev);
343 }