C - SIGALRM 阻止 getchar()

Posted

技术标签:

【中文标题】C - SIGALRM 阻止 getchar()【英文标题】:C - SIGALRM blocks getchar() 【发布时间】:2015-01-03 22:53:27 【问题描述】:

我正在开发一个 C 终端多进程应用程序。该应用程序是基于菜单的,因此用户必须从执行操作的可能性中进行选择。菜单被 getchar() 阻止。让我展示一下代码部分:

do

    do
    
        printf("\n\n---------------\nMenu\n\n");
        printf("1. Option 1\n");
        printf("2. Option 2\n");
        printf("3. Option 3\n");
        printf("4. Exit");
        printf("\n\n---------------\n");

        scanf("%d", &end);

        int c = getchar();

        if(end < 1 || end > 4)
        
            printf("Try it again!!!\n\n");
        
    
    while(end < 1 || end > 4);

while(end != 4);

所以用户需要选择其中一个选项。但问题是第二个选项需要在后台每 5 秒启动一个功能。其中一个孩子将由该函数处理。所以我首先使用简单的 signal() 方法创建了一个 alarm() 处理程序。之后,我意识到 getchar() I/O 进程被接收到的信号阻塞。我试图创建一个应该处理标准输入进程的新子进程,并将结果在管道中发回给父进程,但这也不起作用。 让我分享一下当前的信号处理部分,以便更好地理解:

// Alarm handling
void CatchAlarm(int sig)

    if(someCounts > 0)
    
        DoSomething();
        alarm(5);
    

还有报警绑定:

struct sigaction alarmAction;
alarmAction.sa_handler = CatchAlarm;
sigemptyset(&alarmAction.sa_mask);
alarmAction.sa_flags = SA_RESTART;
sigaction(SIGALRM, &alarmAction, NULL);

我的问题是,我不能让父进程进入睡眠状态,因为用户必须能够在警报挂起期间进行其他活动。当我得到 SIGALRM 时,完整的标准输入读取过程将变得疯狂。请帮助我用什么来阻止读取和等待用户交互而不是 getchar(),因为我已经尝试了所有方法。或者,如果有人可以帮助我,我该如何解决这个问题,我会很感激。 当然,如果您还有其他问题或疑虑,请告诉我,我会尽快更新我的问题。 提前致谢

【问题讨论】:

假设posix看看selectpoll @Jasen 你能稍微描述一下吗,你为什么这么建议?非常感谢 它们是一种有效等待多个文件句柄(如管道和 STDIN_FILENO)上的传入数据的方法。但不是在 ms-windows 上。 关于触发后台进程:建议后台进程是捕捉警报、启动警报等的进程,完成它的事情后,等待/休眠警报。然后主进程只启动一次后台进程。主进程可以记住后台进程的进程id,并在主进程准备退出时向其发送kill信号 @MontyX、man selectman poll 手册页很好地解释了这些系统调用。 【参考方案1】:

只需在getchar(); 之前调用alarm(5);,因此建议内核发送SIGALRM 信号以中断getchar(3)。然后,您不必在信号处理程序中放入任何代码(但您确实需要信号处理程序,否则程序将被终止,请参阅 alarm(2)kill(2) 解释)你必须在 getchar 调用之后卸载它,否则信号处理程序将在 5 秒后被调用,但这留给读者作为练习。

符号说明

长期以来,作为 unix 的标准,getchar(3) 之类的参考是指 getchar 例程的手册页,位于在线 unix 参考手册的第 3 节中。第 2 节专门介绍系统调用,第 3 节专门介绍历史上的库调用。

【讨论】:

感谢您的回答。当然,在我的代码中,第一个警报发送是在第一个菜单执行之前,所以是第一个 getchar()。但这也是一样的。我也有启动 DoSomething 函数的信号处理程序。

以上是关于C - SIGALRM 阻止 getchar()的主要内容,如果未能解决你的问题,请参考以下文章

c_cpp C,SIGINT,SIGALRM,SIGHUP中的Unix信号处理示例......

C语言实验题——统计子字符串个数

C语言alarm()函数(延时一段时间执行signal SIGALRM信号处理事件)

如何在c中立即发出信号

质量检测——洛谷——2251——RMQ

c语言中(c=getchar())!=EOF与c=getchar()!=EOF的区别?