Back to Linux

file: uapi/v4l/keytable.c

Documentation/userspace-api/media/rc/keytable.c.rst

7.04.4 KB
Original Source

.. SPDX-License-Identifier: GPL-2.0 OR GFDL-1.1-no-invariants-or-later

file: uapi/v4l/keytable.c

.. code-block:: c

/* keytable.c - This program allows checking/replacing keys at IR

   Copyright (C) 2006-2009 Mauro Carvalho Chehab <[email protected]>

   This program is free software; you can redistribute it and/or modify
   it under the terms of the GNU General Public License as published by
   the Free Software Foundation, version 2 of the License.

   This program is distributed in the hope that it will be useful,
   but WITHOUT ANY WARRANTY; without even the implied warranty of
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   GNU General Public License for more details.
 */

#include <ctype.h>
#include <errno.h>
#include <fcntl.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <linux/input.h>
#include <sys/ioctl.h>

#include "parse.h"

void prtcode (int *codes)
{
    struct parse_key *p;

    for (p=keynames;p->name!=NULL;p++) {
	    if (p->value == (unsigned)codes[1]) {
		    printf("scancode 0x%04x = %s (0x%02x)\\n", codes[0], p->name, codes[1]);
		    return;
	    }
    }

    if (isprint (codes[1]))
	    printf("scancode %d = '%c' (0x%02x)\\n", codes[0], codes[1], codes[1]);
    else
	    printf("scancode %d = 0x%02x\\n", codes[0], codes[1]);
}

int parse_code(char *string)
{
    struct parse_key *p;

    for (p=keynames;p->name!=NULL;p++) {
	    if (!strcasecmp(p->name, string)) {
		    return p->value;
	    }
    }
    return -1;
}

int main (int argc, char *argv[])
{
    int fd;
    unsigned int i, j;
    int codes[2];

    if (argc<2 || argc>4) {
	    printf ("usage: %s <device> to get table; or\\n"
		    "       %s <device> <scancode> <keycode>\\n"
		    "       %s <device> <keycode_file>n",*argv,*argv,*argv);
	    return -1;
    }

    if ((fd = open(argv[1], O_RDONLY)) < 0) {
	    perror("Couldn't open input device");
	    return(-1);
    }

    if (argc==4) {
	    int value;

	    value=parse_code(argv[3]);

	    if (value==-1) {
		    value = strtol(argv[3], NULL, 0);
		    if (errno)
			    perror("value");
	    }

	    codes [0] = (unsigned) strtol(argv[2], NULL, 0);
	    codes [1] = (unsigned) value;

	    if(ioctl(fd, EVIOCSKEYCODE, codes))
		    perror ("EVIOCSKEYCODE");

	    if(ioctl(fd, EVIOCGKEYCODE, codes)==0)
		    prtcode(codes);
	    return 0;
    }

    if (argc==3) {
	    FILE *fin;
	    int value;
	    char *scancode, *keycode, s[2048];

	    fin=fopen(argv[2],"r");
	    if (fin==NULL) {
		    perror ("opening keycode file");
		    return -1;
	    }

	    /* Clears old table */
	    for (j = 0; j < 256; j++) {
		    for (i = 0; i < 256; i++) {
			    codes[0] = (j << 8) | i;
			    codes[1] = KEY_RESERVED;
			    ioctl(fd, EVIOCSKEYCODE, codes);
		    }
	    }

	    while (fgets(s,sizeof(s),fin)) {
		    scancode=strtok(s,"\\n\\t =:");
		    if (!scancode) {
			    perror ("parsing input file scancode");
			    return -1;
		    }
		    if (!strcasecmp(scancode, "scancode")) {
			    scancode = strtok(NULL,"\\n\\t =:");
			    if (!scancode) {
				    perror ("parsing input file scancode");
				    return -1;
			    }
		    }

		    keycode=strtok(NULL,"\\n\\t =:(");
		    if (!keycode) {
			    perror ("parsing input file keycode");
			    return -1;
		    }

		    // printf ("parsing %s=%s:", scancode, keycode);
		    value=parse_code(keycode);
		    // printf ("\\tvalue=%d\\n",value);

		    if (value==-1) {
			    value = strtol(keycode, NULL, 0);
			    if (errno)
				    perror("value");
		    }

		    codes [0] = (unsigned) strtol(scancode, NULL, 0);
		    codes [1] = (unsigned) value;

		    // printf("\\t%04x=%04x\\n",codes[0], codes[1]);
		    if(ioctl(fd, EVIOCSKEYCODE, codes)) {
			    fprintf(stderr, "Setting scancode 0x%04x with 0x%04x via ",codes[0], codes[1]);
			    perror ("EVIOCSKEYCODE");
		    }

		    if(ioctl(fd, EVIOCGKEYCODE, codes)==0)
			    prtcode(codes);
	    }
	    return 0;
    }

    /* Get scancode table */
    for (j = 0; j < 256; j++) {
	    for (i = 0; i < 256; i++) {
		    codes[0] = (j << 8) | i;
		    if (!ioctl(fd, EVIOCGKEYCODE, codes) && codes[1] != KEY_RESERVED)
			    prtcode(codes);
	    }
    }
    return 0;
}