内存使用KBHIT泄漏用于Linux

Memory leaks with kbhit for Linux

本文关键字:用于 Linux 泄漏 KBHIT 内存      更新时间:2023-10-16

代码在这里。当我运行程序时(我将KBHIT保存为标头文件并将其保存在程序文件夹中),我在使用KBHIT的第一案中获得了一个非初始化的读取访问(我正在使用DRMemory进行内存调试)。我将SYS/ioctl.h包括在内,因为没有它,我的程序就无法使用Fionread。遇到问题的是呼吁tcsetattr(stdin,tcsanow,& term);我不完全了解这是如何工作的,因此将不胜感激。谢谢!

编辑:确切的消息是"单次读取:读取12个字节"。系统调用ioctl.0x5402参数#2。"该行来自TCSETATTR()调用。此错误是在将KBHIT作为CPP文件保存并在另一个文件中模板模板后出现的。该程序运行良好,除了一个错误。

这是我修改为实际c而不是C 的代码的一个版本,因为它仅是出于c 而出于c 的bool bool true/falue和struct关键字。

,哦,是的,不要将其放在标题文件中。将其放入名为kbhit.c的文件中,然后删除或评论测试主函数。在标题文件中,只需写入该行:

int _kbhit(void);

否则您可能需要:

extern "C" int _kbhit(void);

这就是您在标题中需要的。

/**
 Linux (POSIX) implementation of _kbhit().
 Morgan McGuire, morgan@cs.brown.edu
 */
#include <stdbool.h>
#include <stdio.h>
#include <sys/ioctl.h>
#include <termios.h>
#include <unistd.h>
int _kbhit(void) {
        static bool initialized = false;
        if (! initialized) {
                // Use termios to turn off line buffering
                struct termios term;
                tcgetattr(STDIN_FILENO, &term);
                term.c_lflag &= ~ICANON;
                tcsetattr(STDIN_FILENO, TCSANOW, &term);
                setbuf(stdin, NULL);
                initialized = true;
        }
        int bytesWaiting;
        ioctl(STDIN_FILENO, FIONREAD, &bytesWaiting);
        return bytesWaiting;
}
//////////////////////////////////////////////
//      Simple demo of _kbhit()
int main() {
        printf("Press any key");
        while (! _kbhit()) {
                printf(".");
                fflush(stdout);
                usleep(1000);
        }
        printf("nDone.n");
        return 0;
}

对我来说看起来很正确,瓦尔格林德不抱怨。我没有记忆博士可以检查。

此代码的工作原理是它首先使用 tcgetattr读取术语iOS(我认为终端输入输出设置)结构。然后,它通过揭开icanon位来修改它。佳能是终端的规范设置,包括线条缓冲。然后,它将新的术语值重新写回终端。使用tcsetattr

ioctl呼叫获取缓冲区中有多少个字节在等待。如果有字节等待,则有人按下某种键。