Fixed bug 2231 - Move src/input/evdev into src/core/linux
authorSam Lantinga <slouken@libsdl.org>
Sat, 16 Nov 2013 12:02:09 -0800
changeset 8000fe9403d0bc9d
parent 7999 2c9aedfba740
child 8001 e3d78fb706fa
Fixed bug 2231 - Move src/input/evdev into src/core/linux

Ryan C. Gordon

To keep the directory layout sane, we should probably move this one piece of source to the linux catch-all directory, instead of making it look like this is part of an SDL "input" subsystem.
src/core/linux/SDL_evdev.c
src/core/linux/SDL_evdev.h
src/input/evdev/SDL_evdev.c
src/input/evdev/SDL_evdev.h
src/video/raspberry/SDL_rpievents.c
src/video/raspberry/SDL_rpivideo.c
     1.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     1.2 +++ b/src/core/linux/SDL_evdev.c	Sat Nov 16 12:02:09 2013 -0800
     1.3 @@ -0,0 +1,805 @@
     1.4 +/*
     1.5 +  Simple DirectMedia Layer
     1.6 +  Copyright (C) 1997-2013 Sam Lantinga <slouken@libsdl.org>
     1.7 +
     1.8 +  This software is provided 'as-is', without any express or implied
     1.9 +  warranty.  In no event will the authors be held liable for any damages
    1.10 +  arising from the use of this software.
    1.11 +
    1.12 +  Permission is granted to anyone to use this software for any purpose,
    1.13 +  including commercial applications, and to alter it and redistribute it
    1.14 +  freely, subject to the following restrictions:
    1.15 +
    1.16 +  1. The origin of this software must not be misrepresented; you must not
    1.17 +     claim that you wrote the original software. If you use this software
    1.18 +     in a product, an acknowledgment in the product documentation would be
    1.19 +     appreciated but is not required.
    1.20 +  2. Altered source versions must be plainly marked as such, and must not be
    1.21 +     misrepresented as being the original software.
    1.22 +  3. This notice may not be removed or altered from any source distribution.
    1.23 +*/
    1.24 +#include "SDL_config.h"
    1.25 +
    1.26 +#ifdef SDL_INPUT_LINUXEV
    1.27 +
    1.28 +/* This is based on the linux joystick driver */
    1.29 +/* References: https://www.kernel.org/doc/Documentation/input/input.txt 
    1.30 + *             https://www.kernel.org/doc/Documentation/input/event-codes.txt
    1.31 + *             /usr/include/linux/input.h
    1.32 + *             The evtest application is also useful to debug the protocol
    1.33 + */
    1.34 +
    1.35 +
    1.36 +#include "SDL_evdev.h"
    1.37 +#define _THIS SDL_EVDEV_PrivateData *_this
    1.38 +static _THIS = NULL;
    1.39 +
    1.40 +#include <sys/stat.h>
    1.41 +#include <unistd.h>
    1.42 +#include <fcntl.h>
    1.43 +#include <sys/ioctl.h>
    1.44 +#include <limits.h>             /* For the definition of PATH_MAX */
    1.45 +#include <linux/input.h>
    1.46 +#ifdef SDL_INPUT_LINUXKD
    1.47 +#include <linux/kd.h>
    1.48 +#include <linux/keyboard.h>
    1.49 +#endif
    1.50 +
    1.51 +
    1.52 +/* We need this to prevent keystrokes from appear in the console */
    1.53 +#ifndef KDSKBMUTE
    1.54 +#define KDSKBMUTE 0x4B51
    1.55 +#endif
    1.56 +#ifndef KDSKBMODE
    1.57 +#define KDSKBMODE 0x4B45
    1.58 +#endif
    1.59 +#ifndef K_OFF
    1.60 +#define K_OFF 0x04
    1.61 +#endif
    1.62 +
    1.63 +#include "SDL.h"
    1.64 +#include "SDL_assert.h"
    1.65 +#include "SDL_endian.h"
    1.66 +#include "../../core/linux/SDL_udev.h"
    1.67 +#include "SDL_scancode.h"
    1.68 +#include "../../events/SDL_events_c.h"
    1.69 +
    1.70 +/* This isn't defined in older Linux kernel headers */
    1.71 +#ifndef SYN_DROPPED
    1.72 +#define SYN_DROPPED 3
    1.73 +#endif
    1.74 +
    1.75 +static SDL_Scancode SDL_EVDEV_translate_keycode(int keycode);
    1.76 +static void SDL_EVDEV_sync_device(SDL_evdevlist_item *item);
    1.77 +static int SDL_EVDEV_device_removed(const char *devpath);
    1.78 +
    1.79 +#if SDL_USE_LIBUDEV
    1.80 +static int SDL_EVDEV_device_added(const char *devpath);
    1.81 +void SDL_EVDEV_udev_callback(SDL_UDEV_deviceevent udev_type, int udev_class, const char *devpath);
    1.82 +#endif /* SDL_USE_LIBUDEV */
    1.83 +
    1.84 +static SDL_Scancode EVDEV_Keycodes[] = {
    1.85 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_RESERVED        0 */
    1.86 +    SDL_SCANCODE_ESCAPE,        /*  KEY_ESC         1 */
    1.87 +    SDL_SCANCODE_1,             /*  KEY_1           2 */
    1.88 +    SDL_SCANCODE_2,             /*  KEY_2           3 */
    1.89 +    SDL_SCANCODE_3,             /*  KEY_3           4 */
    1.90 +    SDL_SCANCODE_4,             /*  KEY_4           5 */
    1.91 +    SDL_SCANCODE_5,             /*  KEY_5           6 */
    1.92 +    SDL_SCANCODE_6,             /*  KEY_6           7 */
    1.93 +    SDL_SCANCODE_7,             /*  KEY_7           8 */
    1.94 +    SDL_SCANCODE_8,             /*  KEY_8           9 */
    1.95 +    SDL_SCANCODE_9,             /*  KEY_9           10 */
    1.96 +    SDL_SCANCODE_0,             /*  KEY_0           11 */
    1.97 +    SDL_SCANCODE_MINUS,         /*  KEY_MINUS       12 */
    1.98 +    SDL_SCANCODE_EQUALS,        /*  KEY_EQUAL       13 */
    1.99 +    SDL_SCANCODE_BACKSPACE,     /*  KEY_BACKSPACE       14 */
   1.100 +    SDL_SCANCODE_TAB,           /*  KEY_TAB         15 */
   1.101 +    SDL_SCANCODE_Q,             /*  KEY_Q           16 */
   1.102 +    SDL_SCANCODE_W,             /*  KEY_W           17 */
   1.103 +    SDL_SCANCODE_E,             /*  KEY_E           18 */
   1.104 +    SDL_SCANCODE_R,             /*  KEY_R           19 */
   1.105 +    SDL_SCANCODE_T,             /*  KEY_T           20 */
   1.106 +    SDL_SCANCODE_Y,             /*  KEY_Y           21 */
   1.107 +    SDL_SCANCODE_U,             /*  KEY_U           22 */
   1.108 +    SDL_SCANCODE_I,             /*  KEY_I           23 */
   1.109 +    SDL_SCANCODE_O,             /*  KEY_O           24 */
   1.110 +    SDL_SCANCODE_P,             /*  KEY_P           25 */
   1.111 +    SDL_SCANCODE_LEFTBRACKET,   /*  KEY_LEFTBRACE       26 */
   1.112 +    SDL_SCANCODE_RIGHTBRACKET,  /*  KEY_RIGHTBRACE      27 */
   1.113 +    SDL_SCANCODE_RETURN,        /*  KEY_ENTER       28 */
   1.114 +    SDL_SCANCODE_LCTRL,         /*  KEY_LEFTCTRL        29 */
   1.115 +    SDL_SCANCODE_A,             /*  KEY_A           30 */
   1.116 +    SDL_SCANCODE_S,             /*  KEY_S           31 */
   1.117 +    SDL_SCANCODE_D,             /*  KEY_D           32 */
   1.118 +    SDL_SCANCODE_F,             /*  KEY_F           33 */
   1.119 +    SDL_SCANCODE_G,             /*  KEY_G           34 */
   1.120 +    SDL_SCANCODE_H,             /*  KEY_H           35 */
   1.121 +    SDL_SCANCODE_J,             /*  KEY_J           36 */
   1.122 +    SDL_SCANCODE_K,             /*  KEY_K           37 */
   1.123 +    SDL_SCANCODE_L,             /*  KEY_L           38 */
   1.124 +    SDL_SCANCODE_SEMICOLON,     /*  KEY_SEMICOLON       39 */
   1.125 +    SDL_SCANCODE_APOSTROPHE,    /*  KEY_APOSTROPHE      40 */
   1.126 +    SDL_SCANCODE_GRAVE,         /*  KEY_GRAVE       41 */
   1.127 +    SDL_SCANCODE_LSHIFT,        /*  KEY_LEFTSHIFT       42 */
   1.128 +    SDL_SCANCODE_BACKSLASH,     /*  KEY_BACKSLASH       43 */
   1.129 +    SDL_SCANCODE_Z,             /*  KEY_Z           44 */
   1.130 +    SDL_SCANCODE_X,             /*  KEY_X           45 */
   1.131 +    SDL_SCANCODE_C,             /*  KEY_C           46 */
   1.132 +    SDL_SCANCODE_V,             /*  KEY_V           47 */
   1.133 +    SDL_SCANCODE_B,             /*  KEY_B           48 */
   1.134 +    SDL_SCANCODE_N,             /*  KEY_N           49 */
   1.135 +    SDL_SCANCODE_M,             /*  KEY_M           50 */
   1.136 +    SDL_SCANCODE_COMMA,         /*  KEY_COMMA       51 */
   1.137 +    SDL_SCANCODE_PERIOD,        /*  KEY_DOT         52 */
   1.138 +    SDL_SCANCODE_SLASH,         /*  KEY_SLASH       53 */
   1.139 +    SDL_SCANCODE_RSHIFT,        /*  KEY_RIGHTSHIFT      54 */
   1.140 +    SDL_SCANCODE_KP_MULTIPLY,   /*  KEY_KPASTERISK      55 */
   1.141 +    SDL_SCANCODE_LALT,          /*  KEY_LEFTALT     56 */
   1.142 +    SDL_SCANCODE_SPACE,         /*  KEY_SPACE       57 */
   1.143 +    SDL_SCANCODE_CAPSLOCK,      /*  KEY_CAPSLOCK        58 */
   1.144 +    SDL_SCANCODE_F1,            /*  KEY_F1          59 */
   1.145 +    SDL_SCANCODE_F2,            /*  KEY_F2          60 */
   1.146 +    SDL_SCANCODE_F3,            /*  KEY_F3          61 */
   1.147 +    SDL_SCANCODE_F4,            /*  KEY_F4          62 */
   1.148 +    SDL_SCANCODE_F5,            /*  KEY_F5          63 */
   1.149 +    SDL_SCANCODE_F6,            /*  KEY_F6          64 */
   1.150 +    SDL_SCANCODE_F7,            /*  KEY_F7          65 */
   1.151 +    SDL_SCANCODE_F8,            /*  KEY_F8          66 */
   1.152 +    SDL_SCANCODE_F9,            /*  KEY_F9          67 */
   1.153 +    SDL_SCANCODE_F10,           /*  KEY_F10         68 */
   1.154 +    SDL_SCANCODE_NUMLOCKCLEAR,  /*  KEY_NUMLOCK     69 */
   1.155 +    SDL_SCANCODE_SCROLLLOCK,    /*  KEY_SCROLLLOCK      70 */
   1.156 +    SDL_SCANCODE_KP_7,          /*  KEY_KP7         71 */
   1.157 +    SDL_SCANCODE_KP_8,          /*  KEY_KP8         72 */
   1.158 +    SDL_SCANCODE_KP_9,          /*  KEY_KP9         73 */
   1.159 +    SDL_SCANCODE_KP_MINUS,      /*  KEY_KPMINUS     74 */
   1.160 +    SDL_SCANCODE_KP_4,          /*  KEY_KP4         75 */
   1.161 +    SDL_SCANCODE_KP_5,          /*  KEY_KP5         76 */
   1.162 +    SDL_SCANCODE_KP_6,          /*  KEY_KP6         77 */
   1.163 +    SDL_SCANCODE_KP_PLUS,       /*  KEY_KPPLUS      78 */
   1.164 +    SDL_SCANCODE_KP_1,          /*  KEY_KP1         79 */
   1.165 +    SDL_SCANCODE_KP_2,          /*  KEY_KP2         80 */
   1.166 +    SDL_SCANCODE_KP_3,          /*  KEY_KP3         81 */
   1.167 +    SDL_SCANCODE_KP_0,          /*  KEY_KP0         82 */
   1.168 +    SDL_SCANCODE_KP_PERIOD,     /*  KEY_KPDOT       83 */
   1.169 +    SDL_SCANCODE_UNKNOWN,       /*  84 */
   1.170 +    SDL_SCANCODE_LANG5,         /*  KEY_ZENKAKUHANKAKU  85 */
   1.171 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_102ND       86 */
   1.172 +    SDL_SCANCODE_F11,           /*  KEY_F11         87 */
   1.173 +    SDL_SCANCODE_F12,           /*  KEY_F12         88 */
   1.174 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_RO          89 */
   1.175 +    SDL_SCANCODE_LANG3,         /*  KEY_KATAKANA        90 */
   1.176 +    SDL_SCANCODE_LANG4,         /*  KEY_HIRAGANA        91 */
   1.177 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_HENKAN      92 */
   1.178 +    SDL_SCANCODE_LANG3,         /*  KEY_KATAKANAHIRAGANA    93 */
   1.179 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_MUHENKAN        94 */
   1.180 +    SDL_SCANCODE_KP_COMMA,      /*  KEY_KPJPCOMMA       95 */
   1.181 +    SDL_SCANCODE_KP_ENTER,      /*  KEY_KPENTER     96 */
   1.182 +    SDL_SCANCODE_RCTRL,         /*  KEY_RIGHTCTRL       97 */
   1.183 +    SDL_SCANCODE_KP_DIVIDE,     /*  KEY_KPSLASH     98 */
   1.184 +    SDL_SCANCODE_SYSREQ,        /*  KEY_SYSRQ       99 */
   1.185 +    SDL_SCANCODE_RALT,          /*  KEY_RIGHTALT        100 */
   1.186 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_LINEFEED        101 */
   1.187 +    SDL_SCANCODE_HOME,          /*  KEY_HOME        102 */
   1.188 +    SDL_SCANCODE_UP,            /*  KEY_UP          103 */
   1.189 +    SDL_SCANCODE_PAGEUP,        /*  KEY_PAGEUP      104 */
   1.190 +    SDL_SCANCODE_LEFT,          /*  KEY_LEFT        105 */
   1.191 +    SDL_SCANCODE_RIGHT,         /*  KEY_RIGHT       106 */
   1.192 +    SDL_SCANCODE_END,           /*  KEY_END         107 */
   1.193 +    SDL_SCANCODE_DOWN,          /*  KEY_DOWN        108 */
   1.194 +    SDL_SCANCODE_PAGEDOWN,      /*  KEY_PAGEDOWN        109 */
   1.195 +    SDL_SCANCODE_INSERT,        /*  KEY_INSERT      110 */
   1.196 +    SDL_SCANCODE_DELETE,        /*  KEY_DELETE      111 */
   1.197 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_MACRO       112 */
   1.198 +    SDL_SCANCODE_MUTE,          /*  KEY_MUTE        113 */
   1.199 +    SDL_SCANCODE_VOLUMEDOWN,    /*  KEY_VOLUMEDOWN      114 */
   1.200 +    SDL_SCANCODE_VOLUMEUP,      /*  KEY_VOLUMEUP        115 */
   1.201 +    SDL_SCANCODE_POWER,         /*  KEY_POWER       116 SC System Power Down */
   1.202 +    SDL_SCANCODE_KP_EQUALS,     /*  KEY_KPEQUAL     117 */
   1.203 +    SDL_SCANCODE_KP_MINUS,      /*  KEY_KPPLUSMINUS     118 */
   1.204 +    SDL_SCANCODE_PAUSE,         /*  KEY_PAUSE       119 */
   1.205 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_SCALE       120 AL Compiz Scale (Expose) */
   1.206 +    SDL_SCANCODE_KP_COMMA,      /*  KEY_KPCOMMA     121 */
   1.207 +    SDL_SCANCODE_LANG1,         /*  KEY_HANGEUL,KEY_HANGUEL 122 */
   1.208 +    SDL_SCANCODE_LANG2,         /*  KEY_HANJA       123 */
   1.209 +    SDL_SCANCODE_INTERNATIONAL3,/*  KEY_YEN         124 */
   1.210 +    SDL_SCANCODE_LGUI,          /*  KEY_LEFTMETA        125 */
   1.211 +    SDL_SCANCODE_RGUI,          /*  KEY_RIGHTMETA       126 */
   1.212 +    SDL_SCANCODE_APPLICATION,   /*  KEY_COMPOSE     127 */
   1.213 +    SDL_SCANCODE_STOP,          /*  KEY_STOP        128 AC Stop */
   1.214 +    SDL_SCANCODE_AGAIN,         /*  KEY_AGAIN       129 */
   1.215 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_PROPS       130 AC Properties */
   1.216 +    SDL_SCANCODE_UNDO,          /*  KEY_UNDO        131 AC Undo */
   1.217 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_FRONT       132 */
   1.218 +    SDL_SCANCODE_COPY,          /*  KEY_COPY        133 AC Copy */
   1.219 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_OPEN        134 AC Open */
   1.220 +    SDL_SCANCODE_PASTE,         /*  KEY_PASTE       135 AC Paste */
   1.221 +    SDL_SCANCODE_FIND,          /*  KEY_FIND        136 AC Search */
   1.222 +    SDL_SCANCODE_CUT,           /*  KEY_CUT         137 AC Cut */
   1.223 +    SDL_SCANCODE_HELP,          /*  KEY_HELP        138 AL Integrated Help Center */
   1.224 +    SDL_SCANCODE_MENU,          /*  KEY_MENU        139 Menu (show menu) */
   1.225 +    SDL_SCANCODE_CALCULATOR,    /*  KEY_CALC        140 AL Calculator */
   1.226 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_SETUP       141 */
   1.227 +    SDL_SCANCODE_SLEEP,         /*  KEY_SLEEP       142 SC System Sleep */
   1.228 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_WAKEUP      143 System Wake Up */
   1.229 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_FILE        144 AL Local Machine Browser */
   1.230 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_SENDFILE        145 */
   1.231 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_DELETEFILE      146 */
   1.232 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_XFER        147 */
   1.233 +    SDL_SCANCODE_APP1,          /*  KEY_PROG1       148 */
   1.234 +    SDL_SCANCODE_APP1,          /*  KEY_PROG2       149 */
   1.235 +    SDL_SCANCODE_WWW,           /*  KEY_WWW         150 AL Internet Browser */
   1.236 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_MSDOS       151 */
   1.237 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_COFFEE,KEY_SCREENLOCK      152 AL Terminal Lock/Screensaver */
   1.238 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_DIRECTION       153 */
   1.239 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_CYCLEWINDOWS    154 */
   1.240 +    SDL_SCANCODE_MAIL,          /*  KEY_MAIL        155 */
   1.241 +    SDL_SCANCODE_AC_BOOKMARKS,  /*  KEY_BOOKMARKS       156 AC Bookmarks */
   1.242 +    SDL_SCANCODE_COMPUTER,      /*  KEY_COMPUTER        157 */
   1.243 +    SDL_SCANCODE_AC_BACK,       /*  KEY_BACK        158 AC Back */
   1.244 +    SDL_SCANCODE_AC_FORWARD,    /*  KEY_FORWARD     159 AC Forward */
   1.245 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_CLOSECD     160 */
   1.246 +    SDL_SCANCODE_EJECT,         /*  KEY_EJECTCD     161 */
   1.247 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_EJECTCLOSECD    162 */
   1.248 +    SDL_SCANCODE_AUDIONEXT,     /*  KEY_NEXTSONG        163 */
   1.249 +    SDL_SCANCODE_AUDIOPLAY,     /*  KEY_PLAYPAUSE       164 */
   1.250 +    SDL_SCANCODE_AUDIOPREV,     /*  KEY_PREVIOUSSONG    165 */
   1.251 +    SDL_SCANCODE_AUDIOSTOP,     /*  KEY_STOPCD      166 */
   1.252 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_RECORD      167 */
   1.253 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_REWIND      168 */
   1.254 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_PHONE       169 Media Select Telephone */
   1.255 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_ISO         170 */
   1.256 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_CONFIG      171 AL Consumer Control Configuration */
   1.257 +    SDL_SCANCODE_AC_HOME,       /*  KEY_HOMEPAGE        172 AC Home */
   1.258 +    SDL_SCANCODE_AC_REFRESH,    /*  KEY_REFRESH     173 AC Refresh */
   1.259 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_EXIT        174 AC Exit */
   1.260 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_MOVE        175 */
   1.261 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_EDIT        176 */
   1.262 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_SCROLLUP        177 */
   1.263 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_SCROLLDOWN      178 */
   1.264 +    SDL_SCANCODE_KP_LEFTPAREN,  /*  KEY_KPLEFTPAREN     179 */
   1.265 +    SDL_SCANCODE_KP_RIGHTPAREN, /*  KEY_KPRIGHTPAREN    180 */
   1.266 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_NEW         181 AC New */
   1.267 +    SDL_SCANCODE_AGAIN,         /*  KEY_REDO        182 AC Redo/Repeat */
   1.268 +    SDL_SCANCODE_F13,           /*  KEY_F13         183 */
   1.269 +    SDL_SCANCODE_F14,           /*  KEY_F14         184 */
   1.270 +    SDL_SCANCODE_F15,           /*  KEY_F15         185 */
   1.271 +    SDL_SCANCODE_F16,           /*  KEY_F16         186 */
   1.272 +    SDL_SCANCODE_F17,           /*  KEY_F17         187 */
   1.273 +    SDL_SCANCODE_F18,           /*  KEY_F18         188 */
   1.274 +    SDL_SCANCODE_F19,           /*  KEY_F19         189 */
   1.275 +    SDL_SCANCODE_F20,           /*  KEY_F20         190 */
   1.276 +    SDL_SCANCODE_F21,           /*  KEY_F21         191 */
   1.277 +    SDL_SCANCODE_F22,           /*  KEY_F22         192 */
   1.278 +    SDL_SCANCODE_F23,           /*  KEY_F23         193 */
   1.279 +    SDL_SCANCODE_F24,           /*  KEY_F24         194 */
   1.280 +    SDL_SCANCODE_UNKNOWN,       /*  195 */
   1.281 +    SDL_SCANCODE_UNKNOWN,       /*  196 */
   1.282 +    SDL_SCANCODE_UNKNOWN,       /*  197 */
   1.283 +    SDL_SCANCODE_UNKNOWN,       /*  198 */
   1.284 +    SDL_SCANCODE_UNKNOWN,       /*  199 */
   1.285 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_PLAYCD      200 */
   1.286 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_PAUSECD     201 */
   1.287 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_PROG3       202 */
   1.288 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_PROG4       203 */
   1.289 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_DASHBOARD       204 AL Dashboard */
   1.290 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_SUSPEND     205 */
   1.291 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_CLOSE       206 AC Close */
   1.292 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_PLAY        207 */
   1.293 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_FASTFORWARD     208 */
   1.294 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_BASSBOOST       209 */
   1.295 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_PRINT       210 AC Print */
   1.296 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_HP          211 */
   1.297 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_CAMERA      212 */
   1.298 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_SOUND       213 */
   1.299 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_QUESTION        214 */
   1.300 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_EMAIL       215 */
   1.301 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_CHAT        216 */
   1.302 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_SEARCH      217 */
   1.303 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_CONNECT     218 */
   1.304 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_FINANCE     219 AL Checkbook/Finance */
   1.305 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_SPORT       220 */
   1.306 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_SHOP        221 */
   1.307 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_ALTERASE        222 */
   1.308 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_CANCEL      223 AC Cancel */
   1.309 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_BRIGHTNESSDOWN  224 */
   1.310 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_BRIGHTNESSUP    225 */
   1.311 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_MEDIA       226 */
   1.312 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_SWITCHVIDEOMODE 227 Cycle between available video outputs (Monitor/LCD/TV-out/etc) */
   1.313 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_KBDILLUMTOGGLE  228 */
   1.314 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_KBDILLUMDOWN    229 */
   1.315 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_KBDILLUMUP      230 */
   1.316 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_SEND        231 AC Send */
   1.317 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_REPLY       232 AC Reply */
   1.318 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_FORWARDMAIL     233 AC Forward Msg */
   1.319 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_SAVE        234 AC Save */
   1.320 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_DOCUMENTS       235 */
   1.321 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_BATTERY     236  */
   1.322 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_BLUETOOTH       237 */
   1.323 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_WLAN        238 */
   1.324 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_UWB         239 */
   1.325 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_UNKNOWN     240 */
   1.326 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_VIDEO_NEXT      241 drive next video source */
   1.327 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_VIDEO_PREV      242 drive previous video source */
   1.328 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_BRIGHTNESS_CYCLE    243 brightness up, after max is min */
   1.329 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_BRIGHTNESS_ZERO 244 brightness off, use ambient */
   1.330 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_DISPLAY_OFF     245 display device to off state */
   1.331 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_WIMAX       246 */
   1.332 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_RFKILL      247 Key that controls all radios */
   1.333 +    SDL_SCANCODE_UNKNOWN,       /*  KEY_MICMUTE     248 Mute / unmute the microphone */
   1.334 +};
   1.335 +
   1.336 +static Uint8 EVDEV_MouseButtons[] = {
   1.337 +    SDL_BUTTON_LEFT,            /*  BTN_LEFT        0x110 */
   1.338 +    SDL_BUTTON_RIGHT,           /*  BTN_RIGHT       0x111 */
   1.339 +    SDL_BUTTON_MIDDLE,          /*  BTN_MIDDLE      0x112 */
   1.340 +    SDL_BUTTON_X1,              /*  BTN_SIDE        0x113 */
   1.341 +    SDL_BUTTON_X2,              /*  BTN_EXTRA       0x114 */
   1.342 +    SDL_BUTTON_X2 + 1,          /*  BTN_FORWARD     0x115 */
   1.343 +    SDL_BUTTON_X2 + 2,          /*  BTN_BACK        0x116 */
   1.344 +    SDL_BUTTON_X2 + 3           /*  BTN_TASK        0x117 */
   1.345 +};
   1.346 +
   1.347 +static char* EVDEV_consoles[] = {
   1.348 +    "/proc/self/fd/0",
   1.349 +    "/dev/tty",
   1.350 +    "/dev/tty0",
   1.351 +    "/dev/tty1",
   1.352 +    "/dev/tty2",
   1.353 +    "/dev/tty3",
   1.354 +    "/dev/tty4",
   1.355 +    "/dev/tty5",
   1.356 +    "/dev/tty6",
   1.357 +    "/dev/vc/0",
   1.358 +    "/dev/console"
   1.359 +};
   1.360 +
   1.361 +#define IS_CONSOLE(fd) isatty (fd) && ioctl(fd, KDGKBTYPE, &arg) == 0 && ((arg == KB_101) || (arg == KB_84))
   1.362 +
   1.363 +static int SDL_EVDEV_get_console_fd(void)
   1.364 +{
   1.365 +    int fd, i;
   1.366 +    char arg = 0;
   1.367 +    
   1.368 +    /* Try a few consoles to see which one we have read access to */
   1.369 +    
   1.370 +    for( i = 0; i < SDL_arraysize(EVDEV_consoles); i++) {
   1.371 +        fd = open(EVDEV_consoles[i], O_RDONLY);
   1.372 +        if (fd >= 0) {
   1.373 +            if (IS_CONSOLE(fd)) return fd;
   1.374 +            close(fd);
   1.375 +        }
   1.376 +    }
   1.377 +    
   1.378 +    /* Try stdin, stdout, stderr */
   1.379 +    
   1.380 +    for( fd = 0; fd < 3; fd++) {
   1.381 +        if (IS_CONSOLE(fd)) return fd;
   1.382 +    }
   1.383 +    
   1.384 +    /* We won't be able to send SDL_TEXTINPUT events */
   1.385 +    return -1;
   1.386 +}
   1.387 +
   1.388 +/* Prevent keystrokes from reaching the tty */
   1.389 +static int SDL_EVDEV_mute_keyboard(int tty, int *kb_mode)
   1.390 +{
   1.391 +    char arg;
   1.392 +    
   1.393 +    *kb_mode = 0; /* FIXME: Is this a sane default in case KDGKBMODE fails? */
   1.394 +    if (!IS_CONSOLE(tty)) {
   1.395 +        return SDL_SetError("Tried to mute an invalid tty");
   1.396 +    }
   1.397 +    ioctl(tty, KDGKBMODE, kb_mode); /* It's not fatal if this fails */
   1.398 +    if (ioctl(tty, KDSKBMUTE, 1) && ioctl(tty, KDSKBMODE, K_OFF)) {
   1.399 +        return SDL_SetError("EVDEV: Failed muting keyboard");
   1.400 +    }
   1.401 +    
   1.402 +    return 0;  
   1.403 +}
   1.404 +
   1.405 +/* Restore the keyboard mode for given tty */
   1.406 +static void SDL_EVDEV_unmute_keyboard(int tty, int kb_mode)
   1.407 +{
   1.408 +    if (ioctl(tty, KDSKBMUTE, 0) && ioctl(tty, KDSKBMODE, kb_mode)) {
   1.409 +        SDL_Log("EVDEV: Failed restoring keyboard mode");
   1.410 +    }
   1.411 +}
   1.412 +
   1.413 +/* Read /sys/class/tty/tty0/active and open the tty */
   1.414 +static int SDL_EVDEV_get_active_tty()
   1.415 +{
   1.416 +    int fd, len;
   1.417 +    char ttyname[NAME_MAX + 1];
   1.418 +    char ttypath[PATH_MAX+1] = "/dev/";
   1.419 +    char arg;
   1.420 +    
   1.421 +    fd = open("/sys/class/tty/tty0/active", O_RDONLY);
   1.422 +    if (fd < 0) {
   1.423 +        return SDL_SetError("Could not determine which tty is active");
   1.424 +    }
   1.425 +    
   1.426 +    len = read(fd, ttyname, NAME_MAX);
   1.427 +    close(fd);
   1.428 +    
   1.429 +    if (len <= 0) {
   1.430 +        return SDL_SetError("Could not read which tty is active");
   1.431 +    }
   1.432 +    
   1.433 +    if (ttyname[len-1] == '\n') {
   1.434 +        ttyname[len-1] = '\0';
   1.435 +    }
   1.436 +    else {
   1.437 +        ttyname[len] = '\0';
   1.438 +    }
   1.439 +    
   1.440 +    SDL_strlcat(ttypath, ttyname, PATH_MAX);
   1.441 +    fd = open(ttypath, O_RDWR | O_NOCTTY);
   1.442 +    if (fd < 0) {
   1.443 +        return SDL_SetError("Could not open tty: %s", ttypath);
   1.444 +    }
   1.445 +    
   1.446 +    if (!IS_CONSOLE(fd)) {
   1.447 +        close(fd);
   1.448 +        return SDL_SetError("Invalid tty obtained: %s", ttypath);
   1.449 +    }
   1.450 +
   1.451 +    return fd;  
   1.452 +}
   1.453 +
   1.454 +int
   1.455 +SDL_EVDEV_Init(void)
   1.456 +{
   1.457 +    int retval = 0;
   1.458 +    
   1.459 +    if (_this == NULL) {
   1.460 +        
   1.461 +        _this = (SDL_EVDEV_PrivateData *) SDL_calloc(1, sizeof(*_this));
   1.462 +        if(_this == NULL) {
   1.463 +            return SDL_OutOfMemory();
   1.464 +        }
   1.465 +
   1.466 +#if SDL_USE_LIBUDEV
   1.467 +        if (SDL_UDEV_Init() < 0) {
   1.468 +            SDL_free(_this);
   1.469 +            _this = NULL;
   1.470 +            return -1;
   1.471 +        }
   1.472 +
   1.473 +        /* Set up the udev callback */
   1.474 +        if ( SDL_UDEV_AddCallback(SDL_EVDEV_udev_callback) < 0) {
   1.475 +            SDL_EVDEV_Quit();
   1.476 +            return -1;
   1.477 +        }
   1.478 +        
   1.479 +        /* Force a scan to build the initial device list */
   1.480 +        SDL_UDEV_Scan();
   1.481 +#else
   1.482 +        /* TODO: Scan the devices manually, like a caveman */
   1.483 +#endif /* SDL_USE_LIBUDEV */
   1.484 +        
   1.485 +        /* We need a physical terminal (not PTS) to be able to translate key code to symbols via the kernel tables */
   1.486 +        _this->console_fd = SDL_EVDEV_get_console_fd();
   1.487 +        
   1.488 +        /* Mute the keyboard so keystrokes only generate evdev events and do not leak through to the console */
   1.489 +        _this->tty = STDIN_FILENO;
   1.490 +        if (SDL_EVDEV_mute_keyboard(_this->tty, &_this->kb_mode) < 0) {
   1.491 +            /* stdin is not a tty, probably we were launched remotely, so we try to disable the active tty */
   1.492 +            _this->tty = SDL_EVDEV_get_active_tty();
   1.493 +            if (_this->tty >= 0) {
   1.494 +                if (SDL_EVDEV_mute_keyboard(_this->tty, &_this->kb_mode) < 0) {
   1.495 +                    close(_this->tty);
   1.496 +                    _this->tty = -1;
   1.497 +                }
   1.498 +            }
   1.499 +        }
   1.500 +    }
   1.501 +    
   1.502 +    _this->ref_count += 1;
   1.503 +    
   1.504 +    return retval;
   1.505 +}
   1.506 +
   1.507 +void
   1.508 +SDL_EVDEV_Quit(void)
   1.509 +{
   1.510 +    if (_this == NULL) {
   1.511 +        return;
   1.512 +    }
   1.513 +    
   1.514 +    _this->ref_count -= 1;
   1.515 +    
   1.516 +    if (_this->ref_count < 1) {
   1.517 +        
   1.518 +#if SDL_USE_LIBUDEV
   1.519 +        SDL_UDEV_DelCallback(SDL_EVDEV_udev_callback);
   1.520 +        SDL_UDEV_Quit();
   1.521 +#endif /* SDL_USE_LIBUDEV */
   1.522 +       
   1.523 +        if (_this->console_fd >= 0) {
   1.524 +            close(_this->console_fd);
   1.525 +        }
   1.526 +        
   1.527 +        if (_this->tty >= 0) {
   1.528 +            SDL_EVDEV_unmute_keyboard(_this->tty, _this->kb_mode);
   1.529 +            close(_this->tty);
   1.530 +        }
   1.531 +        
   1.532 +        /* Remove existing devices */
   1.533 +        while(_this->first != NULL) {
   1.534 +            SDL_EVDEV_device_removed(_this->first->path);
   1.535 +        }
   1.536 +        
   1.537 +        SDL_assert(_this->first == NULL);
   1.538 +        SDL_assert(_this->last == NULL);
   1.539 +        SDL_assert(_this->numdevices == 0);
   1.540 +        
   1.541 +        SDL_free(_this);
   1.542 +        _this = NULL;
   1.543 +    }
   1.544 +}
   1.545 +
   1.546 +#if SDL_USE_LIBUDEV
   1.547 +void SDL_EVDEV_udev_callback(SDL_UDEV_deviceevent udev_type, int udev_class, const char *devpath)
   1.548 +{
   1.549 +    if (devpath == NULL) {
   1.550 +        return;
   1.551 +    }
   1.552 +    
   1.553 +    if (!(udev_class & (SDL_UDEV_DEVICE_MOUSE|SDL_UDEV_DEVICE_KEYBOARD))) {
   1.554 +        return;
   1.555 +    }
   1.556 +
   1.557 +    switch( udev_type ) {
   1.558 +    case SDL_UDEV_DEVICEADDED:
   1.559 +        SDL_EVDEV_device_added(devpath);
   1.560 +        break;
   1.561 +            
   1.562 +    case SDL_UDEV_DEVICEREMOVED:
   1.563 +        SDL_EVDEV_device_removed(devpath);
   1.564 +        break;
   1.565 +            
   1.566 +    default:
   1.567 +        break;
   1.568 +    }
   1.569 +}
   1.570 +
   1.571 +#endif /* SDL_USE_LIBUDEV */
   1.572 +
   1.573 +void 
   1.574 +SDL_EVDEV_Poll(void)
   1.575 +{
   1.576 +    struct input_event events[32];
   1.577 +    int i, len;
   1.578 +    SDL_evdevlist_item *item;
   1.579 +    SDL_Scancode scan_code;
   1.580 +    int mouse_button;
   1.581 +    SDL_Mouse *mouse;
   1.582 +#ifdef SDL_INPUT_LINUXKD
   1.583 +    Uint16 modstate;
   1.584 +    struct kbentry kbe;
   1.585 +    static char keysym[8];
   1.586 +    char *end;
   1.587 +    Uint32 kval;
   1.588 +#endif
   1.589 +
   1.590 +#if SDL_USE_LIBUDEV
   1.591 +    SDL_UDEV_Poll();
   1.592 +#endif
   1.593 +
   1.594 +    mouse = SDL_GetMouse();
   1.595 +
   1.596 +    for (item = _this->first; item != NULL; item = item->next) {
   1.597 +        while ((len = read(item->fd, events, (sizeof events))) > 0) {
   1.598 +            len /= sizeof(events[0]);
   1.599 +            for (i = 0; i < len; ++i) {
   1.600 +                switch (events[i].type) {
   1.601 +                case EV_KEY:
   1.602 +                    if (events[i].code >= BTN_MOUSE && events[i].code < BTN_MOUSE + SDL_arraysize(EVDEV_MouseButtons)) {
   1.603 +                        mouse_button = events[i].code - BTN_MOUSE;
   1.604 +                        if (events[i].value == 0) {
   1.605 +                            SDL_SendMouseButton(mouse->focus, mouse->mouseID, SDL_RELEASED, EVDEV_MouseButtons[mouse_button]);
   1.606 +                        } else if (events[i].value == 1) {
   1.607 +                            SDL_SendMouseButton(mouse->focus, mouse->mouseID, SDL_PRESSED, EVDEV_MouseButtons[mouse_button]);
   1.608 +                        }
   1.609 +                        break;
   1.610 +                    }
   1.611 +
   1.612 +                    /* Probably keyboard */
   1.613 +                    scan_code = SDL_EVDEV_translate_keycode(events[i].code);
   1.614 +                    if (scan_code != SDL_SCANCODE_UNKNOWN) {
   1.615 +                        if (events[i].value == 0) {
   1.616 +                            SDL_SendKeyboardKey(SDL_RELEASED, scan_code);
   1.617 +                        } else if (events[i].value == 1 || events[i].value == 2 /* Key repeated */ ) {
   1.618 +                            SDL_SendKeyboardKey(SDL_PRESSED, scan_code);
   1.619 +#ifdef SDL_INPUT_LINUXKD
   1.620 +                            if (_this->console_fd >= 0) {
   1.621 +                                kbe.kb_index = events[i].code;
   1.622 +                                /* Convert the key to an UTF-8 char */
   1.623 +                                /* Ref: http://www.linuxjournal.com/article/2783 */
   1.624 +                                modstate = SDL_GetModState();
   1.625 +                                kbe.kb_table = 0;
   1.626 +                                
   1.627 +                                /* Ref: http://graphics.stanford.edu/~seander/bithacks.html#ConditionalSetOrClearBitsWithoutBranching */
   1.628 +                                kbe.kb_table |= -( (modstate & KMOD_LCTRL) != 0) & (1 << KG_CTRLL | 1 << KG_CTRL);
   1.629 +                                kbe.kb_table |= -( (modstate & KMOD_RCTRL) != 0) & (1 << KG_CTRLR | 1 << KG_CTRL);
   1.630 +                                kbe.kb_table |= -( (modstate & KMOD_LSHIFT) != 0) & (1 << KG_SHIFTL | 1 << KG_SHIFT);
   1.631 +                                kbe.kb_table |= -( (modstate & KMOD_RSHIFT) != 0) & (1 << KG_SHIFTR | 1 << KG_SHIFT);
   1.632 +                                kbe.kb_table |= -( (modstate & KMOD_LALT) != 0) & (1 << KG_ALT);
   1.633 +                                kbe.kb_table |= -( (modstate & KMOD_RALT) != 0) & (1 << KG_ALTGR);
   1.634 +
   1.635 +                                if (ioctl(_this->console_fd, KDGKBENT, (unsigned long)&kbe) == 0 && 
   1.636 +                                    ((KTYP(kbe.kb_value) == KT_LATIN) || (KTYP(kbe.kb_value) == KT_ASCII) || (KTYP(kbe.kb_value) == KT_LETTER))) 
   1.637 +                                {
   1.638 +                                    kval = KVAL(kbe.kb_value);
   1.639 +                                    
   1.640 +                                    /* While there's a KG_CAPSSHIFT symbol, it's not useful to build the table index with it
   1.641 +                                     * because 1 << KG_CAPSSHIFT overflows the 8 bits of kb_table 
   1.642 +                                     * So, we do the CAPS LOCK logic here. Note that isalpha depends on the locale!
   1.643 +                                     */
   1.644 +                                    if ( modstate & KMOD_CAPS && isalpha(kval) ) {
   1.645 +                                        if ( isupper(kval) ) {
   1.646 +                                            kval = tolower(kval);
   1.647 +                                        } else {
   1.648 +                                            kval = toupper(kval);
   1.649 +                                        }
   1.650 +                                    }
   1.651 +                                     
   1.652 +                                    /* Convert to UTF-8 and send */
   1.653 +                                    end = SDL_UCS4ToUTF8( kval, keysym);
   1.654 +                                    *end = '\0';
   1.655 +                                    SDL_SendKeyboardText(keysym);
   1.656 +                                }
   1.657 +                            }
   1.658 +#endif /* SDL_INPUT_LINUXKD */
   1.659 +                        }
   1.660 +                    }
   1.661 +                    break;
   1.662 +                case EV_ABS:
   1.663 +                    switch(events[i].code) {
   1.664 +                    case ABS_X:
   1.665 +                        SDL_SendMouseMotion(mouse->focus, mouse->mouseID, SDL_FALSE, events[i].value, mouse->y);
   1.666 +                        break;
   1.667 +                    case ABS_Y:
   1.668 +                        SDL_SendMouseMotion(mouse->focus, mouse->mouseID, SDL_FALSE, mouse->x, events[i].value);
   1.669 +                        break;
   1.670 +                    default:
   1.671 +                        break;
   1.672 +                    }
   1.673 +                    break;
   1.674 +                case EV_REL:
   1.675 +                    switch(events[i].code) {
   1.676 +                    case REL_X:
   1.677 +                        SDL_SendMouseMotion(mouse->focus, mouse->mouseID, SDL_TRUE, events[i].value, 0);
   1.678 +                        break;
   1.679 +                    case REL_Y:
   1.680 +                        SDL_SendMouseMotion(mouse->focus, mouse->mouseID, SDL_TRUE, 0, events[i].value);
   1.681 +                        break;
   1.682 +                    case REL_WHEEL:
   1.683 +                        SDL_SendMouseWheel(mouse->focus, mouse->mouseID, 0, events[i].value);
   1.684 +                        break;
   1.685 +                    case REL_HWHEEL:
   1.686 +                        SDL_SendMouseWheel(mouse->focus, mouse->mouseID, events[i].value, 0);
   1.687 +                        break;
   1.688 +                    default:
   1.689 +                        break;
   1.690 +                    }
   1.691 +                    break;
   1.692 +                case EV_SYN:
   1.693 +                    switch (events[i].code) {
   1.694 +                    case SYN_DROPPED:
   1.695 +                        SDL_EVDEV_sync_device(item);
   1.696 +                        break;
   1.697 +                    default:
   1.698 +                        break;
   1.699 +                    }
   1.700 +                    break;
   1.701 +                }
   1.702 +            }
   1.703 +        }    
   1.704 +    }
   1.705 +}
   1.706 +
   1.707 +static SDL_Scancode
   1.708 +SDL_EVDEV_translate_keycode(int keycode)
   1.709 +{
   1.710 +    SDL_Scancode scancode = SDL_SCANCODE_UNKNOWN;
   1.711 +
   1.712 +    if (keycode < SDL_arraysize(EVDEV_Keycodes)) {
   1.713 +        scancode = EVDEV_Keycodes[keycode];
   1.714 +    }
   1.715 +    if (scancode == SDL_SCANCODE_UNKNOWN) {
   1.716 +        SDL_Log("The key you just pressed is not recognized by SDL. To help get this fixed, please report this to the SDL mailing list <sdl@libsdl.org> EVDEV KeyCode %d \n", keycode);
   1.717 +    }
   1.718 +    return scancode;
   1.719 +}
   1.720 +
   1.721 +static void
   1.722 +SDL_EVDEV_sync_device(SDL_evdevlist_item *item) 
   1.723 +{
   1.724 +    /* TODO: get full state of device and report whatever is required */
   1.725 +}
   1.726 +
   1.727 +#if SDL_USE_LIBUDEV
   1.728 +static int
   1.729 +SDL_EVDEV_device_added(const char *devpath)
   1.730 +{
   1.731 +    SDL_evdevlist_item *item;
   1.732 +
   1.733 +    /* Check to make sure it's not already in list. */
   1.734 +    for (item = _this->first; item != NULL; item = item->next) {
   1.735 +        if (strcmp(devpath, item->path) == 0) {
   1.736 +            return -1;  /* already have this one */
   1.737 +        }
   1.738 +    }
   1.739 +    
   1.740 +    item = (SDL_evdevlist_item *) SDL_calloc(1, sizeof (SDL_evdevlist_item));
   1.741 +    if (item == NULL) {
   1.742 +        return SDL_OutOfMemory();
   1.743 +    }
   1.744 +
   1.745 +    item->fd = open(devpath, O_RDONLY, 0);
   1.746 +    if (item->fd < 0) {
   1.747 +        SDL_free(item);
   1.748 +        return SDL_SetError("Unable to open %s", devpath);
   1.749 +    }
   1.750 +    
   1.751 +    item->path = SDL_strdup(devpath);
   1.752 +    if (item->path == NULL) {
   1.753 +        close(item->fd);
   1.754 +        SDL_free(item);
   1.755 +        return SDL_OutOfMemory();
   1.756 +    }
   1.757 +    
   1.758 +    /* Non blocking read mode */
   1.759 +    fcntl(item->fd, F_SETFL, O_NONBLOCK);
   1.760 +    
   1.761 +    if (_this->last == NULL) {
   1.762 +        _this->first = _this->last = item;
   1.763 +    } else {
   1.764 +        _this->last->next = item;
   1.765 +        _this->last = item;
   1.766 +    }
   1.767 +    
   1.768 +    SDL_EVDEV_sync_device(item);
   1.769 +    
   1.770 +    return _this->numdevices++;
   1.771 +}
   1.772 +#endif /* SDL_USE_LIBUDEV */
   1.773 +
   1.774 +static int
   1.775 +SDL_EVDEV_device_removed(const char *devpath)
   1.776 +{
   1.777 +    SDL_evdevlist_item *item;
   1.778 +    SDL_evdevlist_item *prev = NULL;
   1.779 +
   1.780 +    for (item = _this->first; item != NULL; item = item->next) {
   1.781 +        /* found it, remove it. */
   1.782 +        if ( strcmp(devpath, item->path) ==0 ) {
   1.783 +            if (prev != NULL) {
   1.784 +                prev->next = item->next;
   1.785 +            } else {
   1.786 +                SDL_assert(_this->first == item);
   1.787 +                _this->first = item->next;
   1.788 +            }
   1.789 +            if (item == _this->last) {
   1.790 +                _this->last = prev;
   1.791 +            }
   1.792 +            close(item->fd);
   1.793 +            SDL_free(item->path);
   1.794 +            SDL_free(item);
   1.795 +            _this->numdevices--;
   1.796 +            return 0;
   1.797 +        }
   1.798 +        prev = item;
   1.799 +    }
   1.800 +
   1.801 +    return -1;
   1.802 +}
   1.803 +
   1.804 +
   1.805 +#endif /* SDL_INPUT_LINUXEV */
   1.806 +
   1.807 +/* vi: set ts=4 sw=4 expandtab: */
   1.808 +
     2.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     2.2 +++ b/src/core/linux/SDL_evdev.h	Sat Nov 16 12:02:09 2013 -0800
     2.3 @@ -0,0 +1,59 @@
     2.4 +/*
     2.5 +  Simple DirectMedia Layer
     2.6 +  Copyright (C) 1997-2013 Sam Lantinga <slouken@libsdl.org>
     2.7 +
     2.8 +  This software is provided 'as-is', without any express or implied
     2.9 +  warranty.  In no event will the authors be held liable for any damages
    2.10 +  arising from the use of this software.
    2.11 +
    2.12 +  Permission is granted to anyone to use this software for any purpose,
    2.13 +  including commercial applications, and to alter it and redistribute it
    2.14 +  freely, subject to the following restrictions:
    2.15 +
    2.16 +  1. The origin of this software must not be misrepresented; you must not
    2.17 +     claim that you wrote the original software. If you use this software
    2.18 +     in a product, an acknowledgment in the product documentation would be
    2.19 +     appreciated but is not required.
    2.20 +  2. Altered source versions must be plainly marked as such, and must not be
    2.21 +     misrepresented as being the original software.
    2.22 +  3. This notice may not be removed or altered from any source distribution.
    2.23 +*/
    2.24 +
    2.25 +#include "SDL_config.h"
    2.26 +
    2.27 +#ifndef _SDL_evdev_h
    2.28 +#define _SDL_evdev_h
    2.29 +
    2.30 +#ifdef SDL_INPUT_LINUXEV
    2.31 +
    2.32 +#include "SDL_events.h"
    2.33 +#include <sys/stat.h>
    2.34 +
    2.35 +typedef struct SDL_evdevlist_item
    2.36 +{
    2.37 +    char *path;
    2.38 +    int fd;
    2.39 +    struct SDL_evdevlist_item *next;
    2.40 +} SDL_evdevlist_item;
    2.41 +
    2.42 +typedef struct SDL_EVDEV_PrivateData
    2.43 +{
    2.44 +    SDL_evdevlist_item *first;
    2.45 +    SDL_evdevlist_item *last;
    2.46 +    int numdevices;
    2.47 +    int ref_count;
    2.48 +    int console_fd;
    2.49 +    int kb_mode;
    2.50 +    int tty;
    2.51 +} SDL_EVDEV_PrivateData;
    2.52 +
    2.53 +extern int SDL_EVDEV_Init(void);
    2.54 +extern void SDL_EVDEV_Quit(void);
    2.55 +extern void SDL_EVDEV_Poll(void);
    2.56 +
    2.57 +
    2.58 +#endif /* SDL_INPUT_LINUXEV */
    2.59 +
    2.60 +#endif /* _SDL_evdev_h */
    2.61 +
    2.62 +/* vi: set ts=4 sw=4 expandtab: */
     3.1 --- a/src/input/evdev/SDL_evdev.c	Sat Nov 16 11:58:21 2013 -0800
     3.2 +++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
     3.3 @@ -1,805 +0,0 @@
     3.4 -/*
     3.5 -  Simple DirectMedia Layer
     3.6 -  Copyright (C) 1997-2013 Sam Lantinga <slouken@libsdl.org>
     3.7 -
     3.8 -  This software is provided 'as-is', without any express or implied
     3.9 -  warranty.  In no event will the authors be held liable for any damages
    3.10 -  arising from the use of this software.
    3.11 -
    3.12 -  Permission is granted to anyone to use this software for any purpose,
    3.13 -  including commercial applications, and to alter it and redistribute it
    3.14 -  freely, subject to the following restrictions:
    3.15 -
    3.16 -  1. The origin of this software must not be misrepresented; you must not
    3.17 -     claim that you wrote the original software. If you use this software
    3.18 -     in a product, an acknowledgment in the product documentation would be
    3.19 -     appreciated but is not required.
    3.20 -  2. Altered source versions must be plainly marked as such, and must not be
    3.21 -     misrepresented as being the original software.
    3.22 -  3. This notice may not be removed or altered from any source distribution.
    3.23 -*/
    3.24 -#include "SDL_config.h"
    3.25 -
    3.26 -#ifdef SDL_INPUT_LINUXEV
    3.27 -
    3.28 -/* This is based on the linux joystick driver */
    3.29 -/* References: https://www.kernel.org/doc/Documentation/input/input.txt 
    3.30 - *             https://www.kernel.org/doc/Documentation/input/event-codes.txt
    3.31 - *             /usr/include/linux/input.h
    3.32 - *             The evtest application is also useful to debug the protocol
    3.33 - */
    3.34 -
    3.35 -
    3.36 -#include "SDL_evdev.h"
    3.37 -#define _THIS SDL_EVDEV_PrivateData *_this
    3.38 -static _THIS = NULL;
    3.39 -
    3.40 -#include <sys/stat.h>
    3.41 -#include <unistd.h>
    3.42 -#include <fcntl.h>
    3.43 -#include <sys/ioctl.h>
    3.44 -#include <limits.h>             /* For the definition of PATH_MAX */
    3.45 -#include <linux/input.h>
    3.46 -#ifdef SDL_INPUT_LINUXKD
    3.47 -#include <linux/kd.h>
    3.48 -#include <linux/keyboard.h>
    3.49 -#endif
    3.50 -
    3.51 -
    3.52 -/* We need this to prevent keystrokes from appear in the console */
    3.53 -#ifndef KDSKBMUTE
    3.54 -#define KDSKBMUTE 0x4B51
    3.55 -#endif
    3.56 -#ifndef KDSKBMODE
    3.57 -#define KDSKBMODE 0x4B45
    3.58 -#endif
    3.59 -#ifndef K_OFF
    3.60 -#define K_OFF 0x04
    3.61 -#endif
    3.62 -
    3.63 -#include "SDL.h"
    3.64 -#include "SDL_assert.h"
    3.65 -#include "SDL_endian.h"
    3.66 -#include "../../core/linux/SDL_udev.h"
    3.67 -#include "SDL_scancode.h"
    3.68 -#include "../../events/SDL_events_c.h"
    3.69 -
    3.70 -/* This isn't defined in older Linux kernel headers */
    3.71 -#ifndef SYN_DROPPED
    3.72 -#define SYN_DROPPED 3
    3.73 -#endif
    3.74 -
    3.75 -static SDL_Scancode SDL_EVDEV_translate_keycode(int keycode);
    3.76 -static void SDL_EVDEV_sync_device(SDL_evdevlist_item *item);
    3.77 -static int SDL_EVDEV_device_removed(const char *devpath);
    3.78 -
    3.79 -#if SDL_USE_LIBUDEV
    3.80 -static int SDL_EVDEV_device_added(const char *devpath);
    3.81 -void SDL_EVDEV_udev_callback(SDL_UDEV_deviceevent udev_type, int udev_class, const char *devpath);
    3.82 -#endif /* SDL_USE_LIBUDEV */
    3.83 -
    3.84 -static SDL_Scancode EVDEV_Keycodes[] = {
    3.85 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_RESERVED        0 */
    3.86 -    SDL_SCANCODE_ESCAPE,        /*  KEY_ESC         1 */
    3.87 -    SDL_SCANCODE_1,             /*  KEY_1           2 */
    3.88 -    SDL_SCANCODE_2,             /*  KEY_2           3 */
    3.89 -    SDL_SCANCODE_3,             /*  KEY_3           4 */
    3.90 -    SDL_SCANCODE_4,             /*  KEY_4           5 */
    3.91 -    SDL_SCANCODE_5,             /*  KEY_5           6 */
    3.92 -    SDL_SCANCODE_6,             /*  KEY_6           7 */
    3.93 -    SDL_SCANCODE_7,             /*  KEY_7           8 */
    3.94 -    SDL_SCANCODE_8,             /*  KEY_8           9 */
    3.95 -    SDL_SCANCODE_9,             /*  KEY_9           10 */
    3.96 -    SDL_SCANCODE_0,             /*  KEY_0           11 */
    3.97 -    SDL_SCANCODE_MINUS,         /*  KEY_MINUS       12 */
    3.98 -    SDL_SCANCODE_EQUALS,        /*  KEY_EQUAL       13 */
    3.99 -    SDL_SCANCODE_BACKSPACE,     /*  KEY_BACKSPACE       14 */
   3.100 -    SDL_SCANCODE_TAB,           /*  KEY_TAB         15 */
   3.101 -    SDL_SCANCODE_Q,             /*  KEY_Q           16 */
   3.102 -    SDL_SCANCODE_W,             /*  KEY_W           17 */
   3.103 -    SDL_SCANCODE_E,             /*  KEY_E           18 */
   3.104 -    SDL_SCANCODE_R,             /*  KEY_R           19 */
   3.105 -    SDL_SCANCODE_T,             /*  KEY_T           20 */
   3.106 -    SDL_SCANCODE_Y,             /*  KEY_Y           21 */
   3.107 -    SDL_SCANCODE_U,             /*  KEY_U           22 */
   3.108 -    SDL_SCANCODE_I,             /*  KEY_I           23 */
   3.109 -    SDL_SCANCODE_O,             /*  KEY_O           24 */
   3.110 -    SDL_SCANCODE_P,             /*  KEY_P           25 */
   3.111 -    SDL_SCANCODE_LEFTBRACKET,   /*  KEY_LEFTBRACE       26 */
   3.112 -    SDL_SCANCODE_RIGHTBRACKET,  /*  KEY_RIGHTBRACE      27 */
   3.113 -    SDL_SCANCODE_RETURN,        /*  KEY_ENTER       28 */
   3.114 -    SDL_SCANCODE_LCTRL,         /*  KEY_LEFTCTRL        29 */
   3.115 -    SDL_SCANCODE_A,             /*  KEY_A           30 */
   3.116 -    SDL_SCANCODE_S,             /*  KEY_S           31 */
   3.117 -    SDL_SCANCODE_D,             /*  KEY_D           32 */
   3.118 -    SDL_SCANCODE_F,             /*  KEY_F           33 */
   3.119 -    SDL_SCANCODE_G,             /*  KEY_G           34 */
   3.120 -    SDL_SCANCODE_H,             /*  KEY_H           35 */
   3.121 -    SDL_SCANCODE_J,             /*  KEY_J           36 */
   3.122 -    SDL_SCANCODE_K,             /*  KEY_K           37 */
   3.123 -    SDL_SCANCODE_L,             /*  KEY_L           38 */
   3.124 -    SDL_SCANCODE_SEMICOLON,     /*  KEY_SEMICOLON       39 */
   3.125 -    SDL_SCANCODE_APOSTROPHE,    /*  KEY_APOSTROPHE      40 */
   3.126 -    SDL_SCANCODE_GRAVE,         /*  KEY_GRAVE       41 */
   3.127 -    SDL_SCANCODE_LSHIFT,        /*  KEY_LEFTSHIFT       42 */
   3.128 -    SDL_SCANCODE_BACKSLASH,     /*  KEY_BACKSLASH       43 */
   3.129 -    SDL_SCANCODE_Z,             /*  KEY_Z           44 */
   3.130 -    SDL_SCANCODE_X,             /*  KEY_X           45 */
   3.131 -    SDL_SCANCODE_C,             /*  KEY_C           46 */
   3.132 -    SDL_SCANCODE_V,             /*  KEY_V           47 */
   3.133 -    SDL_SCANCODE_B,             /*  KEY_B           48 */
   3.134 -    SDL_SCANCODE_N,             /*  KEY_N           49 */
   3.135 -    SDL_SCANCODE_M,             /*  KEY_M           50 */
   3.136 -    SDL_SCANCODE_COMMA,         /*  KEY_COMMA       51 */
   3.137 -    SDL_SCANCODE_PERIOD,        /*  KEY_DOT         52 */
   3.138 -    SDL_SCANCODE_SLASH,         /*  KEY_SLASH       53 */
   3.139 -    SDL_SCANCODE_RSHIFT,        /*  KEY_RIGHTSHIFT      54 */
   3.140 -    SDL_SCANCODE_KP_MULTIPLY,   /*  KEY_KPASTERISK      55 */
   3.141 -    SDL_SCANCODE_LALT,          /*  KEY_LEFTALT     56 */
   3.142 -    SDL_SCANCODE_SPACE,         /*  KEY_SPACE       57 */
   3.143 -    SDL_SCANCODE_CAPSLOCK,      /*  KEY_CAPSLOCK        58 */
   3.144 -    SDL_SCANCODE_F1,            /*  KEY_F1          59 */
   3.145 -    SDL_SCANCODE_F2,            /*  KEY_F2          60 */
   3.146 -    SDL_SCANCODE_F3,            /*  KEY_F3          61 */
   3.147 -    SDL_SCANCODE_F4,            /*  KEY_F4          62 */
   3.148 -    SDL_SCANCODE_F5,            /*  KEY_F5          63 */
   3.149 -    SDL_SCANCODE_F6,            /*  KEY_F6          64 */
   3.150 -    SDL_SCANCODE_F7,            /*  KEY_F7          65 */
   3.151 -    SDL_SCANCODE_F8,            /*  KEY_F8          66 */
   3.152 -    SDL_SCANCODE_F9,            /*  KEY_F9          67 */
   3.153 -    SDL_SCANCODE_F10,           /*  KEY_F10         68 */
   3.154 -    SDL_SCANCODE_NUMLOCKCLEAR,  /*  KEY_NUMLOCK     69 */
   3.155 -    SDL_SCANCODE_SCROLLLOCK,    /*  KEY_SCROLLLOCK      70 */
   3.156 -    SDL_SCANCODE_KP_7,          /*  KEY_KP7         71 */
   3.157 -    SDL_SCANCODE_KP_8,          /*  KEY_KP8         72 */
   3.158 -    SDL_SCANCODE_KP_9,          /*  KEY_KP9         73 */
   3.159 -    SDL_SCANCODE_KP_MINUS,      /*  KEY_KPMINUS     74 */
   3.160 -    SDL_SCANCODE_KP_4,          /*  KEY_KP4         75 */
   3.161 -    SDL_SCANCODE_KP_5,          /*  KEY_KP5         76 */
   3.162 -    SDL_SCANCODE_KP_6,          /*  KEY_KP6         77 */
   3.163 -    SDL_SCANCODE_KP_PLUS,       /*  KEY_KPPLUS      78 */
   3.164 -    SDL_SCANCODE_KP_1,          /*  KEY_KP1         79 */
   3.165 -    SDL_SCANCODE_KP_2,          /*  KEY_KP2         80 */
   3.166 -    SDL_SCANCODE_KP_3,          /*  KEY_KP3         81 */
   3.167 -    SDL_SCANCODE_KP_0,          /*  KEY_KP0         82 */
   3.168 -    SDL_SCANCODE_KP_PERIOD,     /*  KEY_KPDOT       83 */
   3.169 -    SDL_SCANCODE_UNKNOWN,       /*  84 */
   3.170 -    SDL_SCANCODE_LANG5,         /*  KEY_ZENKAKUHANKAKU  85 */
   3.171 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_102ND       86 */
   3.172 -    SDL_SCANCODE_F11,           /*  KEY_F11         87 */
   3.173 -    SDL_SCANCODE_F12,           /*  KEY_F12         88 */
   3.174 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_RO          89 */
   3.175 -    SDL_SCANCODE_LANG3,         /*  KEY_KATAKANA        90 */
   3.176 -    SDL_SCANCODE_LANG4,         /*  KEY_HIRAGANA        91 */
   3.177 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_HENKAN      92 */
   3.178 -    SDL_SCANCODE_LANG3,         /*  KEY_KATAKANAHIRAGANA    93 */
   3.179 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_MUHENKAN        94 */
   3.180 -    SDL_SCANCODE_KP_COMMA,      /*  KEY_KPJPCOMMA       95 */
   3.181 -    SDL_SCANCODE_KP_ENTER,      /*  KEY_KPENTER     96 */
   3.182 -    SDL_SCANCODE_RCTRL,         /*  KEY_RIGHTCTRL       97 */
   3.183 -    SDL_SCANCODE_KP_DIVIDE,     /*  KEY_KPSLASH     98 */
   3.184 -    SDL_SCANCODE_SYSREQ,        /*  KEY_SYSRQ       99 */
   3.185 -    SDL_SCANCODE_RALT,          /*  KEY_RIGHTALT        100 */
   3.186 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_LINEFEED        101 */
   3.187 -    SDL_SCANCODE_HOME,          /*  KEY_HOME        102 */
   3.188 -    SDL_SCANCODE_UP,            /*  KEY_UP          103 */
   3.189 -    SDL_SCANCODE_PAGEUP,        /*  KEY_PAGEUP      104 */
   3.190 -    SDL_SCANCODE_LEFT,          /*  KEY_LEFT        105 */
   3.191 -    SDL_SCANCODE_RIGHT,         /*  KEY_RIGHT       106 */
   3.192 -    SDL_SCANCODE_END,           /*  KEY_END         107 */
   3.193 -    SDL_SCANCODE_DOWN,          /*  KEY_DOWN        108 */
   3.194 -    SDL_SCANCODE_PAGEDOWN,      /*  KEY_PAGEDOWN        109 */
   3.195 -    SDL_SCANCODE_INSERT,        /*  KEY_INSERT      110 */
   3.196 -    SDL_SCANCODE_DELETE,        /*  KEY_DELETE      111 */
   3.197 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_MACRO       112 */
   3.198 -    SDL_SCANCODE_MUTE,          /*  KEY_MUTE        113 */
   3.199 -    SDL_SCANCODE_VOLUMEDOWN,    /*  KEY_VOLUMEDOWN      114 */
   3.200 -    SDL_SCANCODE_VOLUMEUP,      /*  KEY_VOLUMEUP        115 */
   3.201 -    SDL_SCANCODE_POWER,         /*  KEY_POWER       116 SC System Power Down */
   3.202 -    SDL_SCANCODE_KP_EQUALS,     /*  KEY_KPEQUAL     117 */
   3.203 -    SDL_SCANCODE_KP_MINUS,      /*  KEY_KPPLUSMINUS     118 */
   3.204 -    SDL_SCANCODE_PAUSE,         /*  KEY_PAUSE       119 */
   3.205 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_SCALE       120 AL Compiz Scale (Expose) */
   3.206 -    SDL_SCANCODE_KP_COMMA,      /*  KEY_KPCOMMA     121 */
   3.207 -    SDL_SCANCODE_LANG1,         /*  KEY_HANGEUL,KEY_HANGUEL 122 */
   3.208 -    SDL_SCANCODE_LANG2,         /*  KEY_HANJA       123 */
   3.209 -    SDL_SCANCODE_INTERNATIONAL3,/*  KEY_YEN         124 */
   3.210 -    SDL_SCANCODE_LGUI,          /*  KEY_LEFTMETA        125 */
   3.211 -    SDL_SCANCODE_RGUI,          /*  KEY_RIGHTMETA       126 */
   3.212 -    SDL_SCANCODE_APPLICATION,   /*  KEY_COMPOSE     127 */
   3.213 -    SDL_SCANCODE_STOP,          /*  KEY_STOP        128 AC Stop */
   3.214 -    SDL_SCANCODE_AGAIN,         /*  KEY_AGAIN       129 */
   3.215 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_PROPS       130 AC Properties */
   3.216 -    SDL_SCANCODE_UNDO,          /*  KEY_UNDO        131 AC Undo */
   3.217 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_FRONT       132 */
   3.218 -    SDL_SCANCODE_COPY,          /*  KEY_COPY        133 AC Copy */
   3.219 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_OPEN        134 AC Open */
   3.220 -    SDL_SCANCODE_PASTE,         /*  KEY_PASTE       135 AC Paste */
   3.221 -    SDL_SCANCODE_FIND,          /*  KEY_FIND        136 AC Search */
   3.222 -    SDL_SCANCODE_CUT,           /*  KEY_CUT         137 AC Cut */
   3.223 -    SDL_SCANCODE_HELP,          /*  KEY_HELP        138 AL Integrated Help Center */
   3.224 -    SDL_SCANCODE_MENU,          /*  KEY_MENU        139 Menu (show menu) */
   3.225 -    SDL_SCANCODE_CALCULATOR,    /*  KEY_CALC        140 AL Calculator */
   3.226 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_SETUP       141 */
   3.227 -    SDL_SCANCODE_SLEEP,         /*  KEY_SLEEP       142 SC System Sleep */
   3.228 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_WAKEUP      143 System Wake Up */
   3.229 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_FILE        144 AL Local Machine Browser */
   3.230 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_SENDFILE        145 */
   3.231 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_DELETEFILE      146 */
   3.232 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_XFER        147 */
   3.233 -    SDL_SCANCODE_APP1,          /*  KEY_PROG1       148 */
   3.234 -    SDL_SCANCODE_APP1,          /*  KEY_PROG2       149 */
   3.235 -    SDL_SCANCODE_WWW,           /*  KEY_WWW         150 AL Internet Browser */
   3.236 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_MSDOS       151 */
   3.237 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_COFFEE,KEY_SCREENLOCK      152 AL Terminal Lock/Screensaver */
   3.238 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_DIRECTION       153 */
   3.239 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_CYCLEWINDOWS    154 */
   3.240 -    SDL_SCANCODE_MAIL,          /*  KEY_MAIL        155 */
   3.241 -    SDL_SCANCODE_AC_BOOKMARKS,  /*  KEY_BOOKMARKS       156 AC Bookmarks */
   3.242 -    SDL_SCANCODE_COMPUTER,      /*  KEY_COMPUTER        157 */
   3.243 -    SDL_SCANCODE_AC_BACK,       /*  KEY_BACK        158 AC Back */
   3.244 -    SDL_SCANCODE_AC_FORWARD,    /*  KEY_FORWARD     159 AC Forward */
   3.245 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_CLOSECD     160 */
   3.246 -    SDL_SCANCODE_EJECT,         /*  KEY_EJECTCD     161 */
   3.247 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_EJECTCLOSECD    162 */
   3.248 -    SDL_SCANCODE_AUDIONEXT,     /*  KEY_NEXTSONG        163 */
   3.249 -    SDL_SCANCODE_AUDIOPLAY,     /*  KEY_PLAYPAUSE       164 */
   3.250 -    SDL_SCANCODE_AUDIOPREV,     /*  KEY_PREVIOUSSONG    165 */
   3.251 -    SDL_SCANCODE_AUDIOSTOP,     /*  KEY_STOPCD      166 */
   3.252 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_RECORD      167 */
   3.253 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_REWIND      168 */
   3.254 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_PHONE       169 Media Select Telephone */
   3.255 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_ISO         170 */
   3.256 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_CONFIG      171 AL Consumer Control Configuration */
   3.257 -    SDL_SCANCODE_AC_HOME,       /*  KEY_HOMEPAGE        172 AC Home */
   3.258 -    SDL_SCANCODE_AC_REFRESH,    /*  KEY_REFRESH     173 AC Refresh */
   3.259 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_EXIT        174 AC Exit */
   3.260 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_MOVE        175 */
   3.261 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_EDIT        176 */
   3.262 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_SCROLLUP        177 */
   3.263 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_SCROLLDOWN      178 */
   3.264 -    SDL_SCANCODE_KP_LEFTPAREN,  /*  KEY_KPLEFTPAREN     179 */
   3.265 -    SDL_SCANCODE_KP_RIGHTPAREN, /*  KEY_KPRIGHTPAREN    180 */
   3.266 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_NEW         181 AC New */
   3.267 -    SDL_SCANCODE_AGAIN,         /*  KEY_REDO        182 AC Redo/Repeat */
   3.268 -    SDL_SCANCODE_F13,           /*  KEY_F13         183 */
   3.269 -    SDL_SCANCODE_F14,           /*  KEY_F14         184 */
   3.270 -    SDL_SCANCODE_F15,           /*  KEY_F15         185 */
   3.271 -    SDL_SCANCODE_F16,           /*  KEY_F16         186 */
   3.272 -    SDL_SCANCODE_F17,           /*  KEY_F17         187 */
   3.273 -    SDL_SCANCODE_F18,           /*  KEY_F18         188 */
   3.274 -    SDL_SCANCODE_F19,           /*  KEY_F19         189 */
   3.275 -    SDL_SCANCODE_F20,           /*  KEY_F20         190 */
   3.276 -    SDL_SCANCODE_F21,           /*  KEY_F21         191 */
   3.277 -    SDL_SCANCODE_F22,           /*  KEY_F22         192 */
   3.278 -    SDL_SCANCODE_F23,           /*  KEY_F23         193 */
   3.279 -    SDL_SCANCODE_F24,           /*  KEY_F24         194 */
   3.280 -    SDL_SCANCODE_UNKNOWN,       /*  195 */
   3.281 -    SDL_SCANCODE_UNKNOWN,       /*  196 */
   3.282 -    SDL_SCANCODE_UNKNOWN,       /*  197 */
   3.283 -    SDL_SCANCODE_UNKNOWN,       /*  198 */
   3.284 -    SDL_SCANCODE_UNKNOWN,       /*  199 */
   3.285 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_PLAYCD      200 */
   3.286 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_PAUSECD     201 */
   3.287 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_PROG3       202 */
   3.288 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_PROG4       203 */
   3.289 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_DASHBOARD       204 AL Dashboard */
   3.290 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_SUSPEND     205 */
   3.291 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_CLOSE       206 AC Close */
   3.292 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_PLAY        207 */
   3.293 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_FASTFORWARD     208 */
   3.294 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_BASSBOOST       209 */
   3.295 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_PRINT       210 AC Print */
   3.296 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_HP          211 */
   3.297 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_CAMERA      212 */
   3.298 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_SOUND       213 */
   3.299 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_QUESTION        214 */
   3.300 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_EMAIL       215 */
   3.301 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_CHAT        216 */
   3.302 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_SEARCH      217 */
   3.303 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_CONNECT     218 */
   3.304 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_FINANCE     219 AL Checkbook/Finance */
   3.305 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_SPORT       220 */
   3.306 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_SHOP        221 */
   3.307 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_ALTERASE        222 */
   3.308 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_CANCEL      223 AC Cancel */
   3.309 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_BRIGHTNESSDOWN  224 */
   3.310 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_BRIGHTNESSUP    225 */
   3.311 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_MEDIA       226 */
   3.312 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_SWITCHVIDEOMODE 227 Cycle between available video outputs (Monitor/LCD/TV-out/etc) */
   3.313 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_KBDILLUMTOGGLE  228 */
   3.314 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_KBDILLUMDOWN    229 */
   3.315 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_KBDILLUMUP      230 */
   3.316 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_SEND        231 AC Send */
   3.317 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_REPLY       232 AC Reply */
   3.318 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_FORWARDMAIL     233 AC Forward Msg */
   3.319 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_SAVE        234 AC Save */
   3.320 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_DOCUMENTS       235 */
   3.321 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_BATTERY     236  */
   3.322 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_BLUETOOTH       237 */
   3.323 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_WLAN        238 */
   3.324 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_UWB         239 */
   3.325 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_UNKNOWN     240 */
   3.326 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_VIDEO_NEXT      241 drive next video source */
   3.327 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_VIDEO_PREV      242 drive previous video source */
   3.328 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_BRIGHTNESS_CYCLE    243 brightness up, after max is min */
   3.329 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_BRIGHTNESS_ZERO 244 brightness off, use ambient */
   3.330 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_DISPLAY_OFF     245 display device to off state */
   3.331 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_WIMAX       246 */
   3.332 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_RFKILL      247 Key that controls all radios */
   3.333 -    SDL_SCANCODE_UNKNOWN,       /*  KEY_MICMUTE     248 Mute / unmute the microphone */
   3.334 -};
   3.335 -
   3.336 -static Uint8 EVDEV_MouseButtons[] = {
   3.337 -    SDL_BUTTON_LEFT,            /*  BTN_LEFT        0x110 */
   3.338 -    SDL_BUTTON_RIGHT,           /*  BTN_RIGHT       0x111 */
   3.339 -    SDL_BUTTON_MIDDLE,          /*  BTN_MIDDLE      0x112 */
   3.340 -    SDL_BUTTON_X1,              /*  BTN_SIDE        0x113 */
   3.341 -    SDL_BUTTON_X2,              /*  BTN_EXTRA       0x114 */
   3.342 -    SDL_BUTTON_X2 + 1,          /*  BTN_FORWARD     0x115 */
   3.343 -    SDL_BUTTON_X2 + 2,          /*  BTN_BACK        0x116 */
   3.344 -    SDL_BUTTON_X2 + 3           /*  BTN_TASK        0x117 */
   3.345 -};
   3.346 -
   3.347 -static char* EVDEV_consoles[] = {
   3.348 -    "/proc/self/fd/0",
   3.349 -    "/dev/tty",
   3.350 -    "/dev/tty0",
   3.351 -    "/dev/tty1",
   3.352 -    "/dev/tty2",
   3.353 -    "/dev/tty3",
   3.354 -    "/dev/tty4",
   3.355 -    "/dev/tty5",
   3.356 -    "/dev/tty6",
   3.357 -    "/dev/vc/0",
   3.358 -    "/dev/console"
   3.359 -};
   3.360 -
   3.361 -#define IS_CONSOLE(fd) isatty (fd) && ioctl(fd, KDGKBTYPE, &arg) == 0 && ((arg == KB_101) || (arg == KB_84))
   3.362 -
   3.363 -static int SDL_EVDEV_get_console_fd(void)
   3.364 -{
   3.365 -    int fd, i;
   3.366 -    char arg = 0;
   3.367 -    
   3.368 -    /* Try a few consoles to see which one we have read access to */
   3.369 -    
   3.370 -    for( i = 0; i < SDL_arraysize(EVDEV_consoles); i++) {
   3.371 -        fd = open(EVDEV_consoles[i], O_RDONLY);
   3.372 -        if (fd >= 0) {
   3.373 -            if (IS_CONSOLE(fd)) return fd;
   3.374 -            close(fd);
   3.375 -        }
   3.376 -    }
   3.377 -    
   3.378 -    /* Try stdin, stdout, stderr */
   3.379 -    
   3.380 -    for( fd = 0; fd < 3; fd++) {
   3.381 -        if (IS_CONSOLE(fd)) return fd;
   3.382 -    }
   3.383 -    
   3.384 -    /* We won't be able to send SDL_TEXTINPUT events */
   3.385 -    return -1;
   3.386 -}
   3.387 -
   3.388 -/* Prevent keystrokes from reaching the tty */
   3.389 -static int SDL_EVDEV_mute_keyboard(int tty, int *kb_mode)
   3.390 -{
   3.391 -    char arg;
   3.392 -    
   3.393 -    *kb_mode = 0; /* FIXME: Is this a sane default in case KDGKBMODE fails? */
   3.394 -    if (!IS_CONSOLE(tty)) {
   3.395 -        return SDL_SetError("Tried to mute an invalid tty");
   3.396 -    }
   3.397 -    ioctl(tty, KDGKBMODE, kb_mode); /* It's not fatal if this fails */
   3.398 -    if (ioctl(tty, KDSKBMUTE, 1) && ioctl(tty, KDSKBMODE, K_OFF)) {
   3.399 -        return SDL_SetError("EVDEV: Failed muting keyboard");
   3.400 -    }
   3.401 -    
   3.402 -    return 0;  
   3.403 -}
   3.404 -
   3.405 -/* Restore the keyboard mode for given tty */
   3.406 -static void SDL_EVDEV_unmute_keyboard(int tty, int kb_mode)
   3.407 -{
   3.408 -    if (ioctl(tty, KDSKBMUTE, 0) && ioctl(tty, KDSKBMODE, kb_mode)) {
   3.409 -        SDL_Log("EVDEV: Failed restoring keyboard mode");
   3.410 -    }
   3.411 -}
   3.412 -
   3.413 -/* Read /sys/class/tty/tty0/active and open the tty */
   3.414 -static int SDL_EVDEV_get_active_tty()
   3.415 -{
   3.416 -    int fd, len;
   3.417 -    char ttyname[NAME_MAX + 1];
   3.418 -    char ttypath[PATH_MAX+1] = "/dev/";
   3.419 -    char arg;
   3.420 -    
   3.421 -    fd = open("/sys/class/tty/tty0/active", O_RDONLY);
   3.422 -    if (fd < 0) {
   3.423 -        return SDL_SetError("Could not determine which tty is active");
   3.424 -    }
   3.425 -    
   3.426 -    len = read(fd, ttyname, NAME_MAX);
   3.427 -    close(fd);
   3.428 -    
   3.429 -    if (len <= 0) {
   3.430 -        return SDL_SetError("Could not read which tty is active");
   3.431 -    }
   3.432 -    
   3.433 -    if (ttyname[len-1] == '\n') {
   3.434 -        ttyname[len-1] = '\0';
   3.435 -    }
   3.436 -    else {
   3.437 -        ttyname[len] = '\0';
   3.438 -    }
   3.439 -    
   3.440 -    SDL_strlcat(ttypath, ttyname, PATH_MAX);
   3.441 -    fd = open(ttypath, O_RDWR | O_NOCTTY);
   3.442 -    if (fd < 0) {
   3.443 -        return SDL_SetError("Could not open tty: %s", ttypath);
   3.444 -    }
   3.445 -    
   3.446 -    if (!IS_CONSOLE(fd)) {
   3.447 -        close(fd);
   3.448 -        return SDL_SetError("Invalid tty obtained: %s", ttypath);
   3.449 -    }
   3.450 -
   3.451 -    return fd;  
   3.452 -}
   3.453 -
   3.454 -int
   3.455 -SDL_EVDEV_Init(void)
   3.456 -{
   3.457 -    int retval = 0;
   3.458 -    
   3.459 -    if (_this == NULL) {
   3.460 -        
   3.461 -        _this = (SDL_EVDEV_PrivateData *) SDL_calloc(1, sizeof(*_this));
   3.462 -        if(_this == NULL) {
   3.463 -            return SDL_OutOfMemory();
   3.464 -        }
   3.465 -
   3.466 -#if SDL_USE_LIBUDEV
   3.467 -        if (SDL_UDEV_Init() < 0) {
   3.468 -            SDL_free(_this);
   3.469 -            _this = NULL;
   3.470 -            return -1;
   3.471 -        }
   3.472 -
   3.473 -        /* Set up the udev callback */
   3.474 -        if ( SDL_UDEV_AddCallback(SDL_EVDEV_udev_callback) < 0) {
   3.475 -            SDL_EVDEV_Quit();
   3.476 -            return -1;
   3.477 -        }
   3.478 -        
   3.479 -        /* Force a scan to build the initial device list */
   3.480 -        SDL_UDEV_Scan();
   3.481 -#else
   3.482 -        /* TODO: Scan the devices manually, like a caveman */
   3.483 -#endif /* SDL_USE_LIBUDEV */
   3.484 -        
   3.485 -        /* We need a physical terminal (not PTS) to be able to translate key code to symbols via the kernel tables */
   3.486 -        _this->console_fd = SDL_EVDEV_get_console_fd();
   3.487 -        
   3.488 -        /* Mute the keyboard so keystrokes only generate evdev events and do not leak through to the console */
   3.489 -        _this->tty = STDIN_FILENO;
   3.490 -        if (SDL_EVDEV_mute_keyboard(_this->tty, &_this->kb_mode) < 0) {
   3.491 -            /* stdin is not a tty, probably we were launched remotely, so we try to disable the active tty */
   3.492 -            _this->tty = SDL_EVDEV_get_active_tty();
   3.493 -            if (_this->tty >= 0) {
   3.494 -                if (SDL_EVDEV_mute_keyboard(_this->tty, &_this->kb_mode) < 0) {
   3.495 -                    close(_this->tty);
   3.496 -                    _this->tty = -1;
   3.497 -                }
   3.498 -            }
   3.499 -        }
   3.500 -    }
   3.501 -    
   3.502 -    _this->ref_count += 1;
   3.503 -    
   3.504 -    return retval;
   3.505 -}
   3.506 -
   3.507 -void
   3.508 -SDL_EVDEV_Quit(void)
   3.509 -{
   3.510 -    if (_this == NULL) {
   3.511 -        return;
   3.512 -    }
   3.513 -    
   3.514 -    _this->ref_count -= 1;
   3.515 -    
   3.516 -    if (_this->ref_count < 1) {
   3.517 -        
   3.518 -#if SDL_USE_LIBUDEV
   3.519 -        SDL_UDEV_DelCallback(SDL_EVDEV_udev_callback);
   3.520 -        SDL_UDEV_Quit();
   3.521 -#endif /* SDL_USE_LIBUDEV */
   3.522 -       
   3.523 -        if (_this->console_fd >= 0) {
   3.524 -            close(_this->console_fd);
   3.525 -        }
   3.526 -        
   3.527 -        if (_this->tty >= 0) {
   3.528 -            SDL_EVDEV_unmute_keyboard(_this->tty, _this->kb_mode);
   3.529 -            close(_this->tty);
   3.530 -        }
   3.531 -        
   3.532 -        /* Remove existing devices */
   3.533 -        while(_this->first != NULL) {
   3.534 -            SDL_EVDEV_device_removed(_this->first->path);
   3.535 -        }
   3.536 -        
   3.537 -        SDL_assert(_this->first == NULL);
   3.538 -        SDL_assert(_this->last == NULL);
   3.539 -        SDL_assert(_this->numdevices == 0);
   3.540 -        
   3.541 -        SDL_free(_this);
   3.542 -        _this = NULL;
   3.543 -    }
   3.544 -}
   3.545 -
   3.546 -#if SDL_USE_LIBUDEV
   3.547 -void SDL_EVDEV_udev_callback(SDL_UDEV_deviceevent udev_type, int udev_class, const char *devpath)
   3.548 -{
   3.549 -    if (devpath == NULL) {
   3.550 -        return;
   3.551 -    }
   3.552 -    
   3.553 -    if (!(udev_class & (SDL_UDEV_DEVICE_MOUSE|SDL_UDEV_DEVICE_KEYBOARD))) {
   3.554 -        return;
   3.555 -    }
   3.556 -
   3.557 -    switch( udev_type ) {
   3.558 -    case SDL_UDEV_DEVICEADDED:
   3.559 -        SDL_EVDEV_device_added(devpath);
   3.560 -        break;
   3.561 -            
   3.562 -    case SDL_UDEV_DEVICEREMOVED:
   3.563 -        SDL_EVDEV_device_removed(devpath);
   3.564 -        break;
   3.565 -            
   3.566 -    default:
   3.567 -        break;
   3.568 -    }
   3.569 -}
   3.570 -
   3.571 -#endif /* SDL_USE_LIBUDEV */
   3.572 -
   3.573 -void 
   3.574 -SDL_EVDEV_Poll(void)
   3.575 -{
   3.576 -    struct input_event events[32];
   3.577 -    int i, len;
   3.578 -    SDL_evdevlist_item *item;
   3.579 -    SDL_Scancode scan_code;
   3.580 -    int mouse_button;
   3.581 -    SDL_Mouse *mouse;
   3.582 -#ifdef SDL_INPUT_LINUXKD
   3.583 -    Uint16 modstate;
   3.584 -    struct kbentry kbe;
   3.585 -    static char keysym[8];
   3.586 -    char *end;
   3.587 -    Uint32 kval;
   3.588 -#endif
   3.589 -
   3.590 -#if SDL_USE_LIBUDEV
   3.591 -    SDL_UDEV_Poll();
   3.592 -#endif
   3.593 -
   3.594 -    mouse = SDL_GetMouse();
   3.595 -
   3.596 -    for (item = _this->first; item != NULL; item = item->next) {
   3.597 -        while ((len = read(item->fd, events, (sizeof events))) > 0) {
   3.598 -            len /= sizeof(events[0]);
   3.599 -            for (i = 0; i < len; ++i) {
   3.600 -                switch (events[i].type) {
   3.601 -                case EV_KEY:
   3.602 -                    if (events[i].code >= BTN_MOUSE && events[i].code < BTN_MOUSE + SDL_arraysize(EVDEV_MouseButtons)) {
   3.603 -                        mouse_button = events[i].code - BTN_MOUSE;
   3.604 -                        if (events[i].value == 0) {
   3.605 -                            SDL_SendMouseButton(mouse->focus, mouse->mouseID, SDL_RELEASED, EVDEV_MouseButtons[mouse_button]);
   3.606 -                        } else if (events[i].value == 1) {
   3.607 -                            SDL_SendMouseButton(mouse->focus, mouse->mouseID, SDL_PRESSED, EVDEV_MouseButtons[mouse_button]);
   3.608 -                        }
   3.609 -                        break;
   3.610 -                    }
   3.611 -
   3.612 -                    /* Probably keyboard */
   3.613 -                    scan_code = SDL_EVDEV_translate_keycode(events[i].code);
   3.614 -                    if (scan_code != SDL_SCANCODE_UNKNOWN) {
   3.615 -                        if (events[i].value == 0) {
   3.616 -                            SDL_SendKeyboardKey(SDL_RELEASED, scan_code);
   3.617 -                        } else if (events[i].value == 1 || events[i].value == 2 /* Key repeated */ ) {
   3.618 -                            SDL_SendKeyboardKey(SDL_PRESSED, scan_code);
   3.619 -#ifdef SDL_INPUT_LINUXKD
   3.620 -                            if (_this->console_fd >= 0) {
   3.621 -                                kbe.kb_index = events[i].code;
   3.622 -                                /* Convert the key to an UTF-8 char */
   3.623 -                                /* Ref: http://www.linuxjournal.com/article/2783 */
   3.624 -                                modstate = SDL_GetModState();
   3.625 -                                kbe.kb_table = 0;
   3.626 -                                
   3.627 -                                /* Ref: http://graphics.stanford.edu/~seander/bithacks.html#ConditionalSetOrClearBitsWithoutBranching */
   3.628 -                                kbe.kb_table |= -( (modstate & KMOD_LCTRL) != 0) & (1 << KG_CTRLL | 1 << KG_CTRL);
   3.629 -                                kbe.kb_table |= -( (modstate & KMOD_RCTRL) != 0) & (1 << KG_CTRLR | 1 << KG_CTRL);
   3.630 -                                kbe.kb_table |= -( (modstate & KMOD_LSHIFT) != 0) & (1 << KG_SHIFTL | 1 << KG_SHIFT);
   3.631 -                                kbe.kb_table |= -( (modstate & KMOD_RSHIFT) != 0) & (1 << KG_SHIFTR | 1 << KG_SHIFT);
   3.632 -                                kbe.kb_table |= -( (modstate & KMOD_LALT) != 0) & (1 << KG_ALT);
   3.633 -                                kbe.kb_table |= -( (modstate & KMOD_RALT) != 0) & (1 << KG_ALTGR);
   3.634 -
   3.635 -                                if (ioctl(_this->console_fd, KDGKBENT, (unsigned long)&kbe) == 0 && 
   3.636 -                                    ((KTYP(kbe.kb_value) == KT_LATIN) || (KTYP(kbe.kb_value) == KT_ASCII) || (KTYP(kbe.kb_value) == KT_LETTER))) 
   3.637 -                                {
   3.638 -                                    kval = KVAL(kbe.kb_value);
   3.639 -                                    
   3.640 -                                    /* While there's a KG_CAPSSHIFT symbol, it's not useful to build the table index with it
   3.641 -                                     * because 1 << KG_CAPSSHIFT overflows the 8 bits of kb_table 
   3.642 -                                     * So, we do the CAPS LOCK logic here. Note that isalpha depends on the locale!
   3.643 -                                     */
   3.644 -                                    if ( modstate & KMOD_CAPS && isalpha(kval) ) {
   3.645 -                                        if ( isupper(kval) ) {
   3.646 -                                            kval = tolower(kval);
   3.647 -                                        } else {
   3.648 -                                            kval = toupper(kval);
   3.649 -                                        }
   3.650 -                                    }
   3.651 -                                     
   3.652 -                                    /* Convert to UTF-8 and send */
   3.653 -                                    end = SDL_UCS4ToUTF8( kval, keysym);
   3.654 -                                    *end = '\0';
   3.655 -                                    SDL_SendKeyboardText(keysym);
   3.656 -                                }
   3.657 -                            }
   3.658 -#endif /* SDL_INPUT_LINUXKD */
   3.659 -                        }
   3.660 -                    }
   3.661 -                    break;
   3.662 -                case EV_ABS:
   3.663 -                    switch(events[i].code) {
   3.664 -                    case ABS_X:
   3.665 -                        SDL_SendMouseMotion(mouse->focus, mouse->mouseID, SDL_FALSE, events[i].value, mouse->y);
   3.666 -                        break;
   3.667 -                    case ABS_Y:
   3.668 -                        SDL_SendMouseMotion(mouse->focus, mouse->mouseID, SDL_FALSE, mouse->x, events[i].value);
   3.669 -                        break;
   3.670 -                    default:
   3.671 -                        break;
   3.672 -                    }
   3.673 -                    break;
   3.674 -                case EV_REL:
   3.675 -                    switch(events[i].code) {
   3.676 -                    case REL_X:
   3.677 -                        SDL_SendMouseMotion(mouse->focus, mouse->mouseID, SDL_TRUE, events[i].value, 0);
   3.678 -                        break;
   3.679 -                    case REL_Y:
   3.680 -                        SDL_SendMouseMotion(mouse->focus, mouse->mouseID, SDL_TRUE, 0, events[i].value);
   3.681 -                        break;
   3.682 -                    case REL_WHEEL:
   3.683 -                        SDL_SendMouseWheel(mouse->focus, mouse->mouseID, 0, events[i].value);
   3.684 -                        break;
   3.685 -                    case REL_HWHEEL:
   3.686 -                        SDL_SendMouseWheel(mouse->focus, mouse->mouseID, events[i].value, 0);
   3.687 -                        break;
   3.688 -                    default:
   3.689 -                        break;
   3.690 -                    }
   3.691 -                    break;
   3.692 -                case EV_SYN:
   3.693 -                    switch (events[i].code) {
   3.694 -                    case SYN_DROPPED:
   3.695 -                        SDL_EVDEV_sync_device(item);
   3.696 -                        break;
   3.697 -                    default:
   3.698 -                        break;
   3.699 -                    }
   3.700 -                    break;
   3.701 -                }
   3.702 -            }
   3.703 -        }    
   3.704 -    }
   3.705 -}
   3.706 -
   3.707 -static SDL_Scancode
   3.708 -SDL_EVDEV_translate_keycode(int keycode)
   3.709 -{
   3.710 -    SDL_Scancode scancode = SDL_SCANCODE_UNKNOWN;
   3.711 -
   3.712 -    if (keycode < SDL_arraysize(EVDEV_Keycodes)) {
   3.713 -        scancode = EVDEV_Keycodes[keycode];
   3.714 -    }
   3.715 -    if (scancode == SDL_SCANCODE_UNKNOWN) {
   3.716 -        SDL_Log("The key you just pressed is not recognized by SDL. To help get this fixed, please report this to the SDL mailing list <sdl@libsdl.org> EVDEV KeyCode %d \n", keycode);
   3.717 -    }
   3.718 -    return scancode;
   3.719 -}
   3.720 -
   3.721 -static void
   3.722 -SDL_EVDEV_sync_device(SDL_evdevlist_item *item) 
   3.723 -{
   3.724 -    /* TODO: get full state of device and report whatever is required */
   3.725 -}
   3.726 -
   3.727 -#if SDL_USE_LIBUDEV
   3.728 -static int
   3.729 -SDL_EVDEV_device_added(const char *devpath)
   3.730 -{
   3.731 -    SDL_evdevlist_item *item;
   3.732 -
   3.733 -    /* Check to make sure it's not already in list. */
   3.734 -    for (item = _this->first; item != NULL; item = item->next) {
   3.735 -        if (strcmp(devpath, item->path) == 0) {
   3.736 -            return -1;  /* already have this one */
   3.737 -        }
   3.738 -    }
   3.739 -    
   3.740 -    item = (SDL_evdevlist_item *) SDL_calloc(1, sizeof (SDL_evdevlist_item));
   3.741 -    if (item == NULL) {
   3.742 -        return SDL_OutOfMemory();
   3.743 -    }
   3.744 -
   3.745 -    item->fd = open(devpath, O_RDONLY, 0);
   3.746 -    if (item->fd < 0) {
   3.747 -        SDL_free(item);
   3.748 -        return SDL_SetError("Unable to open %s", devpath);
   3.749 -    }
   3.750 -    
   3.751 -    item->path = SDL_strdup(devpath);
   3.752 -    if (item->path == NULL) {
   3.753 -        close(item->fd);
   3.754 -        SDL_free(item);
   3.755 -        return SDL_OutOfMemory();
   3.756 -    }
   3.757 -    
   3.758 -    /* Non blocking read mode */
   3.759 -    fcntl(item->fd, F_SETFL, O_NONBLOCK);
   3.760 -    
   3.761 -    if (_this->last == NULL) {
   3.762 -        _this->first = _this->last = item;
   3.763 -    } else {
   3.764 -        _this->last->next = item;
   3.765 -        _this->last = item;
   3.766 -    }
   3.767 -    
   3.768 -    SDL_EVDEV_sync_device(item);
   3.769 -    
   3.770 -    return _this->numdevices++;
   3.771 -}
   3.772 -#endif /* SDL_USE_LIBUDEV */
   3.773 -
   3.774 -static int
   3.775 -SDL_EVDEV_device_removed(const char *devpath)
   3.776 -{
   3.777 -    SDL_evdevlist_item *item;
   3.778 -    SDL_evdevlist_item *prev = NULL;
   3.779 -
   3.780 -    for (item = _this->first; item != NULL; item = item->next) {
   3.781 -        /* found it, remove it. */
   3.782 -        if ( strcmp(devpath, item->path) ==0 ) {
   3.783 -            if (prev != NULL) {
   3.784 -                prev->next = item->next;
   3.785 -            } else {
   3.786 -                SDL_assert(_this->first == item);
   3.787 -                _this->first = item->next;
   3.788 -            }
   3.789 -            if (item == _this->last) {
   3.790 -                _this->last = prev;
   3.791 -            }
   3.792 -            close(item->fd);
   3.793 -            SDL_free(item->path);
   3.794 -            SDL_free(item);
   3.795 -            _this->numdevices--;
   3.796 -            return 0;
   3.797 -        }
   3.798 -        prev = item;
   3.799 -    }
   3.800 -
   3.801 -    return -1;
   3.802 -}
   3.803 -
   3.804 -
   3.805 -#endif /* SDL_INPUT_LINUXEV */
   3.806 -
   3.807 -/* vi: set ts=4 sw=4 expandtab: */
   3.808 -
     4.1 --- a/src/input/evdev/SDL_evdev.h	Sat Nov 16 11:58:21 2013 -0800
     4.2 +++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
     4.3 @@ -1,59 +0,0 @@
     4.4 -/*
     4.5 -  Simple DirectMedia Layer
     4.6 -  Copyright (C) 1997-2013 Sam Lantinga <slouken@libsdl.org>
     4.7 -
     4.8 -  This software is provided 'as-is', without any express or implied
     4.9 -  warranty.  In no event will the authors be held liable for any damages
    4.10 -  arising from the use of this software.
    4.11 -
    4.12 -  Permission is granted to anyone to use this software for any purpose,
    4.13 -  including commercial applications, and to alter it and redistribute it
    4.14 -  freely, subject to the following restrictions:
    4.15 -
    4.16 -  1. The origin of this software must not be misrepresented; you must not
    4.17 -     claim that you wrote the original software. If you use this software
    4.18 -     in a product, an acknowledgment in the product documentation would be
    4.19 -     appreciated but is not required.
    4.20 -  2. Altered source versions must be plainly marked as such, and must not be
    4.21 -     misrepresented as being the original software.
    4.22 -  3. This notice may not be removed or altered from any source distribution.
    4.23 -*/
    4.24 -
    4.25 -#include "SDL_config.h"
    4.26 -
    4.27 -#ifndef _SDL_evdev_h
    4.28 -#define _SDL_evdev_h
    4.29 -
    4.30 -#ifdef SDL_INPUT_LINUXEV
    4.31 -
    4.32 -#include "SDL_events.h"
    4.33 -#include <sys/stat.h>
    4.34 -
    4.35 -typedef struct SDL_evdevlist_item
    4.36 -{
    4.37 -    char *path;
    4.38 -    int fd;
    4.39 -    struct SDL_evdevlist_item *next;
    4.40 -} SDL_evdevlist_item;
    4.41 -
    4.42 -typedef struct SDL_EVDEV_PrivateData
    4.43 -{
    4.44 -    SDL_evdevlist_item *first;
    4.45 -    SDL_evdevlist_item *last;
    4.46 -    int numdevices;
    4.47 -    int ref_count;
    4.48 -    int console_fd;
    4.49 -    int kb_mode;
    4.50 -    int tty;
    4.51 -} SDL_EVDEV_PrivateData;
    4.52 -
    4.53 -extern int SDL_EVDEV_Init(void);
    4.54 -extern void SDL_EVDEV_Quit(void);
    4.55 -extern void SDL_EVDEV_Poll(void);
    4.56 -
    4.57 -
    4.58 -#endif /* SDL_INPUT_LINUXEV */
    4.59 -
    4.60 -#endif /* _SDL_evdev_h */
    4.61 -
    4.62 -/* vi: set ts=4 sw=4 expandtab: */
     5.1 --- a/src/video/raspberry/SDL_rpievents.c	Sat Nov 16 11:58:21 2013 -0800
     5.2 +++ b/src/video/raspberry/SDL_rpievents.c	Sat Nov 16 12:02:09 2013 -0800
     5.3 @@ -30,7 +30,7 @@
     5.4  #include "SDL_rpievents_c.h"
     5.5  
     5.6  #ifdef SDL_INPUT_LINUXEV
     5.7 -#include "../../input/evdev/SDL_evdev.h"
     5.8 +#include "../../core/linux/SDL_evdev.h"
     5.9  #endif
    5.10  
    5.11  void RPI_PumpEvents(_THIS)
     6.1 --- a/src/video/raspberry/SDL_rpivideo.c	Sat Nov 16 11:58:21 2013 -0800
     6.2 +++ b/src/video/raspberry/SDL_rpivideo.c	Sat Nov 16 12:02:09 2013 -0800
     6.3 @@ -40,7 +40,7 @@
     6.4  #include "../../events/SDL_keyboard_c.h"
     6.5  
     6.6  #ifdef SDL_INPUT_LINUXEV
     6.7 -#include "../../input/evdev/SDL_evdev.h"
     6.8 +#include "../../core/linux/SDL_evdev.h"
     6.9  #endif
    6.10  
    6.11  /* RPI declarations */