引起等待的线程返回到用户空间

是否有可能唤醒正在等待futex锁的线程? 我尝试使用信号机制,但似乎并没有工作。 还有其他方法可以尝试吗? 下面,我已经添加了一个可能类似于我想要实现的示例。

  1. 我有一个线程A获取futex锁“lockA”,如下所示: – ret = syscall(__NR_futex, &lockA, FUTEX_LOCK_PI, 1, 0, NULL, 0);

  2. 我有一个线程B试图获取futex锁“lockA”,并locking在内核中,因为线程A获得了锁。 ret = syscall(__NR_futex, &lockA, FUTEX_LOCK_PI, 1, 0, NULL, 0);

  3. 如果线程B获得了lockA,则另一个线程C将知道它。 如果线程B没有获得锁,线程C想要线程B停止等待锁,并做其他事情。

所以基本上,在这一点上,我试图找出是否我可以让线程C“信号”线程B,以便它不会再在内核中阻塞。 为了做到这一点,我在线程B中设置了一个信号处理程序,如下所示:

 struct sigaction act; act.sa_handler = handler; sigemptyset(&act.sa_mask); act.sa_flags = 0; act.sa_restorer = NULL; sigaction(SIGSYS, &act, NULL); ... ... void handler() { fprintf(stderr, "Inside the handler, outta the kernel\n"); } 

从线程CI尝试发送信号为: – pthread_kill(tid_of_B, SIGSYS);

我究竟做错了什么? 线程B可以被唤醒吗? 如果是的话,我应该用另一种方法吗?

[编辑]根据下面的评论,我试图检查从pthread_kill的返回值,并意识到电话没有返回。

一些东西。

您正在使用FUTEX_LOCK_PI手册页中的FUTEX_LOCK_PI 。 我刚才看了内核源码和一个文档,看来这个版本只是在内核里面使用的。 它被用来实现一个“PI互斥量”来代替内核spinlock

如果使用futex ,则必须在指向的地址上实现数据的语义。

这是一个粗糙的伪代码,可能是/可能是错误的例子:

 int mysem = 1; void lock(void) { // atomic_dec returns new value while (1) { if (atomic_dec(&mysem) == 0) break; futex(&mysem,FUTEX_WAIT,...) } } void unlock(void) { // non_atomic_swap returns old value if (non_atomic_swap(&mysem,1) != 0) futex(&mysem,FUTEX_WAKE,...) }