Fixed bug 3469 - Keypresses leak to the console with 2.0.5
authorSam Lantinga <slouken@libsdl.org>
Sat, 07 Jan 2017 10:13:04 -0800
changeset 10778fe9c7d01a093
parent 10777 2883d23b5a28
child 10779 bdc808b931a5
Fixed bug 3469 - Keypresses leak to the console with 2.0.5

tvc

I believe this patch should fix it, instead of looping through all the tty's and seemingly selecting the wrong one and corrupting the console I've just made SDL open /dev/tty which is the console attached to the current process anyway.
src/core/linux/SDL_evdev.c
     1.1 --- a/src/core/linux/SDL_evdev.c	Fri Jan 06 20:43:53 2017 -0800
     1.2 +++ b/src/core/linux/SDL_evdev.c	Sat Jan 07 10:13:04 2017 -0800
     1.3 @@ -107,7 +107,7 @@
     1.4      int num_devices;
     1.5      int ref_count;
     1.6      int console_fd;
     1.7 -    int kb_mode;
     1.8 +    int old_kb_mode;
     1.9  } SDL_EVDEV_PrivateData;
    1.10  
    1.11  #define _THIS SDL_EVDEV_PrivateData *_this
    1.12 @@ -134,21 +134,6 @@
    1.13      SDL_BUTTON_X2 + 3           /*  BTN_TASK        0x117 */
    1.14  };
    1.15  
    1.16 -static const char* EVDEV_consoles[] = {
    1.17 -    /* "/proc/self/fd/0",
    1.18 -    "/dev/tty",
    1.19 -    "/dev/tty0", */ /* the tty ioctl's prohibit these */
    1.20 -    "/dev/tty1",
    1.21 -    "/dev/tty2",
    1.22 -    "/dev/tty3",
    1.23 -    "/dev/tty4",
    1.24 -    "/dev/tty5",
    1.25 -    "/dev/tty6",
    1.26 -    "/dev/tty7", /* usually X is spawned in tty7 */
    1.27 -    "/dev/vc/0",
    1.28 -    "/dev/console"
    1.29 -};
    1.30 -
    1.31  static int SDL_EVDEV_is_console(int fd) {
    1.32      char type;
    1.33      
    1.34 @@ -167,58 +152,19 @@
    1.35          return SDL_SetError("Failed to get keyboard mode during muting");
    1.36      }
    1.37      
    1.38 -    /* FIXME: atm this absolutely ruins the vt, and KDSKBMUTE isn't implemented
    1.39 -       in the kernel */
    1.40 -    /*
    1.41      if (ioctl(tty_fd, KDSKBMODE, K_OFF) < 0) {
    1.42          return SDL_SetError("Failed to set keyboard mode during muting");
    1.43      }
    1.44 -    */
    1.45      
    1.46      return 0;  
    1.47  }
    1.48  
    1.49  /* Restore the keyboard mode for given tty */
    1.50 -static void SDL_EVDEV_unmute_keyboard(int tty_fd, int kb_mode)
    1.51 +static void SDL_EVDEV_unmute_keyboard(int tty_fd, int old_kb_mode)
    1.52  {
    1.53 -    /* read above */
    1.54 -    /*
    1.55 -    if (ioctl(tty_fd, KDSKBMODE, kb_mode) < 0) {
    1.56 -        SDL_Log("Failed to unmute keyboard");
    1.57 +    if (ioctl(tty_fd, KDSKBMODE, old_kb_mode) < 0) {
    1.58 +        SDL_Log("Failed to set keyboard mode");
    1.59      }
    1.60 -    */
    1.61 -}
    1.62 -
    1.63 -static int SDL_EVDEV_get_active_tty()
    1.64 -{  
    1.65 -    int i, fd, ret, tty = 0;
    1.66 -    char tiocl;
    1.67 -    struct vt_stat vt_state;
    1.68 -    char path[PATH_MAX + 1];
    1.69 -    
    1.70 -    for(i = 0; i < SDL_arraysize(EVDEV_consoles); i++) {
    1.71 -        fd = open(EVDEV_consoles[i], O_RDONLY);
    1.72 -        
    1.73 -        if (fd < 0 && !SDL_EVDEV_is_console(fd))
    1.74 -            break;
    1.75 -        
    1.76 -        tiocl = TIOCL_GETFGCONSOLE;
    1.77 -        if ((ret = ioctl(fd, TIOCLINUX, &tiocl)) >= 0)
    1.78 -            tty = ret + 1;
    1.79 -        else if (ioctl(fd, VT_GETSTATE, &vt_state) == 0)
    1.80 -            tty = vt_state.v_active;
    1.81 -        
    1.82 -        close(fd);
    1.83 -        
    1.84 -        if (tty) {
    1.85 -            sprintf(path, "/dev/tty%u", tty);
    1.86 -            fd = open(path, O_RDONLY);
    1.87 -            if (fd >= 0 && SDL_EVDEV_is_console(fd))
    1.88 -                return fd;
    1.89 -        }
    1.90 -    }
    1.91 -    
    1.92 -    return SDL_SetError("Failed to determine active tty");
    1.93  }
    1.94  
    1.95  int
    1.96 @@ -251,13 +197,14 @@
    1.97          /* TODO: Scan the devices manually, like a caveman */
    1.98  #endif /* SDL_USE_LIBUDEV */
    1.99          
   1.100 -        /* We need a physical terminal (not PTS) to be able to translate key
   1.101 -           code to symbols via the kernel tables */
   1.102 -        _this->console_fd = SDL_EVDEV_get_active_tty();
   1.103 +        _this->console_fd = open("/dev/tty", O_RDONLY);
   1.104 +        if( _this->console_fd < 0 ) {
   1.105 +            return SDL_SetError("Failed to open /dev/tty");
   1.106 +        }
   1.107          
   1.108          /* Mute the keyboard so keystrokes only generate evdev events and do not
   1.109             leak through to the console */
   1.110 -        SDL_EVDEV_mute_keyboard(_this->console_fd, &_this->kb_mode);
   1.111 +        SDL_EVDEV_mute_keyboard(_this->console_fd, &_this->old_kb_mode);
   1.112      }
   1.113      
   1.114      _this->ref_count += 1;
   1.115 @@ -281,7 +228,7 @@
   1.116  #endif /* SDL_USE_LIBUDEV */
   1.117         
   1.118          if (_this->console_fd >= 0) {
   1.119 -            SDL_EVDEV_unmute_keyboard(_this->console_fd, _this->kb_mode);
   1.120 +            SDL_EVDEV_unmute_keyboard(_this->console_fd, _this->old_kb_mode);
   1.121              close(_this->console_fd);
   1.122          }
   1.123