如果我在应用程序中工作并且我从键盘按下键,如何在用户区中的GNU / LINUX下的C中捕获该键(或字符串),包括源应用程序的名称,而不是X11:)< / p>
感谢。
答案 0 :(得分:20)
嗯,没有X11这个问题就更难了 对于击键部分,您可以使用与此类似的代码,但您必须将您正在阅读的设备作为参数传递(键盘,通常是/ dev / input / event0)
#include <linux/input.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <stdio.h>
#include <unistd.h>
int main(int argc, char **argv)
{
int fd;
if(argc < 2) {
printf("usage: %s <device>\n", argv[0]);
return 1;
}
fd = open(argv[1], O_RDONLY);
struct input_event ev;
while (1)
{
read(fd, &ev, sizeof(struct input_event));
if(ev.type == 1)
printf("key %i state %i\n", ev.code, ev.value);
}
}
积分不给我,这段代码取自Ventriloctrl hack来获取击键。 http://public.callutheran.edu/~abarker/ventriloctrl-0.4.tar.gz
希望我有所帮助。
答案 1 :(得分:3)
您可以从/ dev / input中的某个文件中读取数据。哪一个取决于您的系统。它可能是/ dev / input / event0或/ dev / input / by-path / platform-i8042-serio-0-event-kbd或其他。格式在内核头input.h中指定。它是
struct input_event {
struct timeval time;
__u16 type;
__u16 code;
__s32 value;
};
你可以运行
od -tx2 FILENAME
并输入内容以查看会发生什么。
至于找出哪个应用程序收到了关键事件,我不确定。您可以尝试检查哪一个正在读取主tty。
答案 2 :(得分:1)
一种可能性:查找并查看“sudosh”的来源,“sudo shell”(或者其中一个替代品,因为它已经有一段时间未被修改; Google是您的朋友)。
它与伪ttys混淆并通过将信息记录到文件来跟踪所有输入和输出。
这对你来说是否足够精确可能更值得商榷;它会记录所有应用程序的所有击键。我也不确定它如何与X11一起使用 - 如果它适用于X11。
答案 3 :(得分:1)
有一个很好的例子,请看一下showkey的代码。
特别是,这是主循环。所有这一切都是获取终端,复制它,将复制的一个转换为原始模式,直到给出“退出”或“中断”键序列,它只打印出给终端的密钥。
/*
* showkey.c -- display cooked key sequences
*
* Invoke this (no arguments needed) to see keycap-to-keystrokes mappings.
*
* by Eric S. Raymond <esr@snark.thyrsus.com>, 1 Nov 88
* - fix for little-endian machines (version 1.1), 21 Oct 1996.
* - cleanup and modern packaging (version 1.2), 1 Aug 2002.
* - changed to use termios (version 1.3), 26 Aug 2002.
* See the RPM spec file changelog for more recent stuff.
*/
#include <stdio.h>
#include <termios.h>
#include <signal.h>
#include <string.h>
#include <stdbool.h>
static int signalled;
// ...
main()
{
struct termios cooked, raw;
unsigned char c;
unsigned int i, timeouts;
char intrchar[32], quitchar[32];
for (i = SIGHUP; i <= SIGIO; i++)
(void) signal(c, catcher);
// Get the state of the tty
(void) tcgetattr(0, &cooked);
// Make a copy we can mess with
(void) memcpy(&raw, &cooked, sizeof(struct termios));
// Turn off echoing, linebuffering, and special-character processing,
// but not the SIGINT or SIGQUIT keys.
raw.c_lflag &=~ (ICANON | ECHO);
// Ship the raw control blts
(void) tcsetattr(0, TCSANOW, &raw);
(void) printf("Type any key to see the sequence it sends.\n");
visualize(raw.c_cc[VINTR], intrchar);
visualize(raw.c_cc[VQUIT], quitchar);
(void) printf("Terminate with your shell interrupt %s or quit %s character.\n",
intrchar, quitchar);
signalled = 0;
while (!signalled)
{
char cbuf[32];
read(0, &c, 1);
visualize(c, cbuf);
(void)fputs(cbuf, stdout);
(void) fflush(stdout);
}
(void) printf("\nBye...\n");
// Restore the cooked state
(void) tcsetattr(0, TCSANOW, &cooked);
}