阻塞性系统调用失败,errno(ENTIR)4 [Interrupted system call]系统调用被信号中断

1.阻塞与非阻塞

非阻塞:程序调用后,不管能不能立刻得到结果,当前进程都会直接返回。如果得到结果则返回成功,否则返回失败。

阻塞:程序调用后,如果不能立刻得到结果,则当前进程会被挂起,无限期等待,直到得到结果时才会返回。

系统调用一般可通过参数控制阻塞或者非阻塞。

常用在IPC通信和网络通信中,需要根据同步或异步设置阻塞和非阻塞:

msgsnd/msgrcv:消息队列发送、接收消息。

semop:信号量操作,用户改变信号量的值。P、V操作。

send/recv,read/write:socket 发送、读写缓冲区。

2.errno ENTIR

        errno ENTIR(4) 系统调用被信号中断,一般发生在被阻塞的系统调用中。

        在阻塞期间,被阻塞的进程收到了不可屏蔽的信号,操作系统会将信号写入该阻塞进程信号描述符,然后强行将进程状态从 TASK_INTERRUPTABLE 改变至 TASK_RUNNING,调用 schedule() 函数执行,由于进程之前一直被阻塞,而linux是交互型系统,因此,阻塞时间越长,进程动态优先级会被调高,因此该进程能在极短的时间内得到相应。但此时,系统调用需要完成的工作并没完成,提前返回将导致错误,设置 errno 为 EINTR。
 

3.解决办法

        在阻塞调用失败后,检查系统错误码 errno 是否是 ENTIR, 重复当前系统调用。

        msgsnd代码示例(msgsnd最后一个参数为0代表当消息队列满时,msgsnd将会阻塞,直到消息能写进消息队列):

...
while (1) {
    if (msgsnd( msqid, &sendbuf, sendlen, 0) < 0 && errno == ENTIR) {
        continue;
    }
    break;
}
...

参考true0face-系统调用中断。链接:https://blog.csdn.net/true0face/article/details/48132091 

  • 3
    点赞
  • 9
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值