Package: kbd Version: 1.14.1 The loadkeys program in the kbd package ignores the KDSKBDIACRUC ioctl in current kernels (and so does the console-tools flavor, as far as i can tell). That means even though I can set both my display and my keyboard into UTF-8 mode and I can display all of the Latin2 characters (for example) if I have them in my console font, there's no way to enter them on a plain US keyboard other than with AltGr + keypad, not quite a user-friendly method.
Enclosed find a trivial C program (tested) using this ioctl to load a compose table with circa 200 entries, and a data file I use with it.
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <linux/kd.h>
#include <linux/keyboard.h>
#include <sys/ioctl.h>
#include <fcntl.h>
static int
read_compose_file(struct kbdiacruc kdc[MAX_DIACR], FILE* fp)
{
int num = 0;
while(1) {
char line[256];
int len;
int blanks;
if (fgets(line, sizeof(line), fp) == NULL) {
if (feof(fp)) return num;
else {
perror("fgets");
exit(1);
}
}
len = strlen(line);
if (line[len-1] != '\n') {
fprintf(stderr, "line too long: %s\n", line);
exit(1);
}
blanks = strspn(line, " \t");
if (line[blanks] != '#' || line[blanks] != '\n') {
char accent, base;
unsigned result;
if (num >= MAX_DIACR) {
fprintf(stderr, "too many lines: %s\n", line);
exit(1);
}
if (sscanf(line, " %c %c %x", &accent, &base, &result) != 3) {
fprintf(stderr, "invalid line: %s\n", line);
exit(1);
}
kdc[num].diacr = (unsigned)(unsigned char)accent;
kdc[num].base = (unsigned)(unsigned char)base;
kdc[num].result = result;
num++;
}
}
}
static void
stuff_diacruc(int fd, int num, const struct kbdiacruc kdc[MAX_DIACR])
{
int i;
struct kbdiacrsuc kdcs = {
.kb_cnt = num,
};
for (i = 0; i < num; ++i)
kdcs.kbdiacruc[i] = kdc[i];
if (ioctl(fd, KDSKBDIACRUC, (unsigned long)&kdcs)) {
perror("ioctl");
exit(1);
}
}
static void
usage(void)
{
fprintf(stderr, "usage: load_diacruc [TTY_DEVICE [INPUT_FILE]]\n");
fprintf(stderr, "default tty device: /dev/tty1\n");
fprintf(stderr, "default input file: standard input\n");
}
int
main(int argc, char** argv)
{
FILE* fp = NULL;
const char* tty;
int fd;
int num;
struct kbdiacruc kdc[MAX_DIACR];
switch (argc) {
case 3:
fp = fopen(argv[2], "r");
if (fp == NULL) {
perror(argv[2]);
usage();
exit(2);
}
tty = argv[1];
break;
case 2:
fp = stdin;
tty = argv[1];
break;
case 1:
fp = stdin;
tty = "/dev/tty1";
break;
default:
usage();
exit(2);
}
fd = open(tty, O_RDWR);
if (fd < 0) {
perror(tty);
usage();
exit(2);
}
num = read_compose_file(kdc, fp);
stuff_diacruc(fd, num, kdc);
}
compose-slavic.inc
Description: data file for compose definitions
-- Ian Zimmerman <[email protected]> gpg public key: 1024D/C6FF61AD fingerprint: 66DC D68F 5C1B 4D71 2EE5 BD03 8A00 786C C6FF 61AD Ham is for reading, not for eating.

