busybox/console-tools/loadkmap.c
<<
>>
Prefs
   1/* vi: set sw=4 ts=4: */
   2/*
   3 * Mini loadkmap implementation for busybox
   4 *
   5 * Copyright (C) 1998 Enrique Zanardi <ezanardi@ull.es>
   6 *
   7 * Licensed under GPLv2 or later, see file LICENSE in this source tree.
   8 */
   9//config:config LOADKMAP
  10//config:       bool "loadkmap (1.8 kb)"
  11//config:       default y
  12//config:       help
  13//config:       This program loads a keyboard translation table from
  14//config:       standard input.
  15
  16//applet:IF_LOADKMAP(APPLET_NOEXEC(loadkmap, loadkmap, BB_DIR_SBIN, BB_SUID_DROP, loadkmap))
  17
  18//kbuild:lib-$(CONFIG_LOADKMAP) += loadkmap.o
  19
  20//usage:#define loadkmap_trivial_usage
  21//usage:       "< keymap"
  22//usage:#define loadkmap_full_usage "\n\n"
  23//usage:       "Load a binary keyboard translation table from stdin"
  24////usage:       "\n"
  25////usage:       "\n    -C TTY  Affect TTY instead of /dev/tty"
  26//usage:
  27//usage:#define loadkmap_example_usage
  28//usage:       "$ loadkmap < /etc/i18n/lang-keymap\n"
  29
  30#include "libbb.h"
  31
  32#define BINARY_KEYMAP_MAGIC "bkeymap"
  33
  34/* From <linux/kd.h> */
  35struct kbentry {
  36        unsigned char kb_table;
  37        unsigned char kb_index;
  38        unsigned short kb_value;
  39};
  40/* sets one entry in translation table */
  41#define KDSKBENT        0x4B47
  42
  43/* From <linux/keyboard.h> */
  44#define NR_KEYS         128
  45#define MAX_NR_KEYMAPS  256
  46
  47int loadkmap_main(int argc, char **argv) MAIN_EXTERNALLY_VISIBLE;
  48int loadkmap_main(int argc UNUSED_PARAM, char **argv)
  49{
  50        struct kbentry ke;
  51        int i, j, fd;
  52        uint16_t ibuff[NR_KEYS];
  53/*      const char *tty_name = CURRENT_TTY; */
  54        RESERVE_CONFIG_BUFFER(flags, MAX_NR_KEYMAPS);
  55
  56        /* When user accidentally runs "loadkmap FILE"
  57         * instead of "loadkmap <FILE", we end up waiting for input from tty.
  58         * Let's prevent it: */
  59        if (argv[1])
  60                bb_show_usage();
  61/* bb_warn_ignoring_args(argv[1]); */
  62
  63        fd = get_console_fd_or_die();
  64/* or maybe:
  65        opt = getopt32(argv, "C:", &tty_name);
  66        fd = xopen_nonblocking(tty_name);
  67*/
  68
  69        xread(STDIN_FILENO, flags, 7);
  70        if (!is_prefixed_with(flags, BINARY_KEYMAP_MAGIC))
  71                bb_simple_error_msg_and_die("not a valid binary keymap");
  72
  73        xread(STDIN_FILENO, flags, MAX_NR_KEYMAPS);
  74
  75        for (i = 0; i < MAX_NR_KEYMAPS; i++) {
  76                if (flags[i] != 1)
  77                        continue;
  78                xread(STDIN_FILENO, ibuff, NR_KEYS * sizeof(uint16_t));
  79                for (j = 0; j < NR_KEYS; j++) {
  80                        ke.kb_index = j;
  81                        ke.kb_table = i;
  82                        ke.kb_value = ibuff[j];
  83                        /*
  84                         * Note: table[idx:0] can contain special value
  85                         * K_ALLOCATED (marks allocated tables in kernel).
  86                         * dumpkmap saves the value as-is; but attempts
  87                         * to load it here fail, since it isn't a valid
  88                         * key value: it is K(KT_SPEC,126) == 2<<8 + 126,
  89                         * whereas last valid KT_SPEC is
  90                         * K_BARENUMLOCK == K(KT_SPEC,19).
  91                         * So far we just ignore these errors:
  92                         */
  93                        ioctl(fd, KDSKBENT, &ke);
  94                }
  95        }
  96
  97        if (ENABLE_FEATURE_CLEAN_UP) {
  98                close(fd);
  99                RELEASE_CONFIG_BUFFER(flags);
 100        }
 101        return EXIT_SUCCESS;
 102}
 103