当前位置: 首页 > 面试题库 >

如何加入挂在阻塞IO上的线程?

鲜于允晨
2023-03-14
问题内容

我有一个在后台运行的线程正在以阻塞方式从输入设备读取事件,现在当我退出应用程序时,我想正确清理线程,但是我不能只运行pthread_join(),因为该线程由于IO阻塞而永远不会退出。

我如何正确解决这种情况?我应该发送一个pthread_kill(theard,SIGIORM)还是一个pthread_kill(theard,SIGALRM)来中断该块?那两个信号是否正确?还是有另一种方法来解决这种情况,并让该子线程退出阻塞读取?

由于我的所有谷歌搜索人员都没有找到解决方案,因此目前有些不解。

这是在Linux上并使用pthreads。

编辑:我在SIGIO和SIGALRM上玩了一些,当我不安装信号处理程序时,它们破坏了阻塞的IO,但在控制台上给出了一条消息(“可能有I /
O”),但是当我安装信号处理程序时,为避免出现该消息,它们不再破坏阻塞的IO,因此线程不会终止。所以我有点回到第一步。


问题答案:

随着事情的发展,旧问题很可能会得到新的答案,现在可以使用新技术 更好地 处理线程中的信号。

从Linux内核2.6.22开始,该系统提供了一个称为的新功能,该功能signalfd()可用于为给定的Unix信号集(完全杀死进程的信号)打开文件描述符。

// defined a set of signals
sigset_t set;
sigemptyset(&set);
sigaddset(&set, SIGUSR1);
// ... you can add more than one ...

// prevent the default signal behavior (very important)
sigprocmask(SIG_BLOCK, &html" target="_blank">set, nullptr);

// open a file descriptor using that set of Unix signals
f_socket = signalfd(-1, &set, SFD_NONBLOCK | SFD_CLOEXEC);

现在,您可以使用poll()select()函数沿您正在监听的更常用的文件描述符(套接字,磁盘上的文件等)监听信号。

如果您想要一个可以一遍又一遍地检查信号和其他文件描述符的循环,则NONBLOCK很重要(即,在其他文件描述符上也很重要)。

我有一个这样的实现,可以与(1)计时器,(2)套接字,(3)管道,(4)Unix信号,(5)常规文件一起使用。实际上,实际上任何文件描述符加上计时器。

https://github.com/m2osw/snapcpp/blob/master/snapwebsites/libsnapwebsites/src/snapwebsites/snap_communicator.cpp


https://github.com/m2osw/snapcpp/blob/master/snapwebsites/libsnapwebsites/src/snap
/snap_communicator.h

您可能也对libevent等库感兴趣



 类似资料:
  • 在Java中,线程可以有不同的状态: 新建、可运行、阻止、等待、定时等待、终止 但是,当线程被IO阻塞时,其状态为“RUNNABLE”。我如何判断它是否被IO阻止?

  • 非阻塞 IO 仅对在 Servlet 和 Filter(2.3.3.3节定义的,“异步处理”)中的异步请求处理和升级处理(2.3.3.5节定义的,“升级处理”)有效。否则,当调用 ServletInputStream.setReadListener 或ServletOutputStream.setWriteListener 方法时将抛出IllegalStateException。为了支持在 Ser

  • Web 容器中的非阻塞请求处理有助于提高对改善 Web 容器可扩展性不断增加的需求,增加 Web 容器可同时处理请求的连接数量。servlet 容器的非阻塞 IO 允许开发人员在数据可用时读取数据或在数据可写时写数据。非阻塞 IO 仅对在 Servlet 和 Filter(2.3.3.3节定义的,“异步处理”)中的异步请求处理和升级处理(2.3.3.5节定义的,“升级处理”)有效。否则,当调用 S

  • 这一次,第一个选项卡将等待5秒,第二个选项卡将等待10秒 为什么会这样?

  • Go提供的网络接口,在用户层是阻塞的,这样最符合人们的编程习惯。在runtime层面,是用epoll/kqueue实现的非阻塞io,为性能提供了保障。 如何实现 底层非阻塞io是如何实现的呢?简单地说,所有文件描述符都被设置成非阻塞的,某个goroutine进行io操作,读或者写文件描述符,如果此刻io还没准备好,则这个goroutine会被放到系统的等待队列中,这个goroutine失去了运行权

  • 夸克有一件事我很难理解。我在Oracle中使用JPA。因此,我有错误IllegalStateExcema:您试图在IO线程上执行阻塞操作。这是不允许的,因为阻塞了IO线程,我在QUUKUS文档中查看了如何在没有这个困难的情况下进行JPA调用。但是所有的例子和文档都使用PostgreSQL或MariaDB与响应客户端。但是我没有找到任何用于经典JDBC客户端的客户端。 我找到了一个部分有效的解决方案