From 4578bbc6a19c763e0a92d1dc17f34afcc58e15ca Mon Sep 17 00:00:00 2001 From: Alexey Gladkov Date: Wed, 30 Mar 2011 02:20:56 +0400 Subject: [PATCH] kbdinfo: Add new utility to obtain information about console Signed-off-by: Alexey Gladkov --- COPYING | 4 ++ src/Makefile.am | 3 +- src/kbdinfo.c | 127 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 3 files changed, 133 insertions(+), 1 deletion(-) create mode 100644 src/kbdinfo.c diff --git a/COPYING b/COPYING index 46f4eba..c8e0497 100644 --- a/COPYING +++ b/COPYING @@ -28,6 +28,10 @@ The files (and changes to earlier mentioned programs) are Copyright (C) 1994-1999 Andries E. Brouwer. +The file + kbdinfo.c +is Copyright (C) 2011 Alexey Gladkov. + All files in this package may be freely copied under the terms of the GNU General Public License (GPL), version 2, or at your option any later version - except possibly for the restrictions diff --git a/src/Makefile.am b/src/Makefile.am index 7e2cadb..fbdfff4 100644 --- a/src/Makefile.am +++ b/src/Makefile.am @@ -9,7 +9,7 @@ OLDPROGS = mapscrn loadunimap PROGS = \ dumpkeys loadkeys showkey setfont showconsolefont \ setleds setmetamode kbd_mode psfxtable fgconsole \ - kbdrate chvt deallocvt openvt + kbdrate chvt deallocvt openvt kbdinfo if KEYCODES_PROGS PROGS += getkeycodes setkeycodes @@ -65,6 +65,7 @@ setpalette_SOURCES = $(ALL_S) setpalette.c $(GETFD_S) setvesablank_SOURCES = $(ALL_S) setvesablank.c $(GETFD_S) showconsolefont_SOURCES = $(ALL_S) showconsolefont.c $(GETFD_S) $(XMAL_S) $(KDMA_S) kdfontop.c kdfontop.h showkey_SOURCES = $(ALL_S) showkey.c $(GETFD_S) +kbdinfo_SOURCES = $(ALL_S) kbdinfo.c $(GETFD_S) mapscrn_CFLAGS = -DMAIN loadunimap_CFLAGS = -DMAIN diff --git a/src/kbdinfo.c b/src/kbdinfo.c new file mode 100644 index 0000000..1df241a --- /dev/null +++ b/src/kbdinfo.c @@ -0,0 +1,127 @@ +#include +#include +#include +#include +#include +#include +#include +#include "getfd.h" +#include "nls.h" +#include "version.h" + +static const char *action = NULL; +static const char *value = NULL; + +static void attr_noreturn +usage(int code) { + fprintf(stderr, _("Usage: %s [-C DEVICE] getmode [text|graphics]\n"), progname); + fprintf(stderr, _(" or: %s [-C DEVICE] gkbmode [raw|xlate|mediumraw|unicode]\n"), progname); + fprintf(stderr, _(" or: %s [-C DEVICE] gkbmeta [metabit|escprefix]\n"), progname); + fprintf(stderr, _(" or: %s [-C DEVICE] gkbled [scrolllock|numlock|capslock]\n"), progname); + exit(code); +} + +static int +answer(const char *ans) { + if (value) + return strcasecmp(value, ans) ? EXIT_FAILURE : EXIT_SUCCESS; + + printf("%s\n", ans); + return EXIT_SUCCESS; +} + +int +main(int argc, char **argv) { + int fd, mode, c; + int rc = EXIT_FAILURE; + char flags; + const char *console = NULL; + + set_progname(argv[0]); + + setlocale(LC_ALL, ""); + bindtextdomain(PACKAGE_NAME, LOCALEDIR); + textdomain(PACKAGE_NAME); + + while ((c = getopt(argc, argv, "C:hV")) != EOF) { + switch (c) { + case 'C': + if (optarg == NULL || optarg[0] == '\0') + usage(EXIT_FAILURE); + console = optarg; + break; + case 'V': + print_version_and_exit(); + break; + case 'h': + usage(EXIT_SUCCESS); + break; + } + } + + if (optind == argc) { + fprintf(stderr, _("Error: Not enough arguments.\n")); + exit(EXIT_FAILURE); + } + + action = argv[optind++]; + + if (optind < argc) + value = argv[optind++]; + + fd = getfd(console); + + if (!strcasecmp("GETMODE", action)) { + if (ioctl(fd, KDGETMODE, &mode) == -1) + error(EXIT_FAILURE, errno, "ioctl"); + + switch (mode) { + case KD_TEXT: rc = answer("text"); break; + case KD_GRAPHICS: rc = answer("graphics"); break; + } + + } else if (!strcasecmp("GKBMODE", action)) { + if (ioctl(fd, KDGKBMODE, &mode) == -1) + error(EXIT_FAILURE, errno, "ioctl"); + + switch (mode) { + case K_RAW: rc = answer("raw"); break; + case K_XLATE: rc = answer("xlate"); break; + case K_MEDIUMRAW: rc = answer("mediumraw"); break; + case K_UNICODE: rc = answer("unicode"); break; + } + + } else if (!strcasecmp("GKBMETA", action)) { + if (ioctl(fd, KDGKBMETA, &mode) == -1) + error(EXIT_FAILURE, errno, "ioctl"); + + switch (mode) { + case K_METABIT: rc = answer("metabit"); break; + case K_ESCPREFIX: rc = answer("escprefix"); break; + } + + } else if (!strcasecmp("GKBLED", action)) { + if (ioctl(fd, KDGKBLED, &flags) == -1) + error(EXIT_FAILURE, errno, "ioctl"); + + mode = (flags & 0x7); + + if (value) { + if (((mode & LED_SCR) && !strcasecmp(value, "scrolllock")) || + ((mode & LED_NUM) && !strcasecmp(value, "numlock")) || + ((mode & LED_CAP) && !strcasecmp(value, "capslock"))) + rc = EXIT_SUCCESS; + } else { + printf("scrolllock:%s ", (mode & LED_SCR) ? "on" : "off"); + printf("numlock:%s ", (mode & LED_NUM) ? "on" : "off"); + printf("capslock:%s\n", (mode & LED_CAP) ? "on" : "off"); + rc = EXIT_SUCCESS; + } + + } else { + fprintf(stderr, _("Error: Unrecognized action: %s\n"), action); + } + + close(fd); + return rc; +} -- 2.7.4