看到各种与锁定相关的问题并且(几乎)总是找到“由于虚假唤醒而导致的循环”术语1我想知道,有没有人经历过这种唤醒(例如,假设一个体面的硬件/软件环境)?
我知道“虚假”一词没有明显的原因,但这种事件的原因是什么?
(1注意:我不是在质疑循环练习。)
编辑: 一个帮助问题(对于那些喜欢代码示例的人):
如果我有以下程序并运行它:
public class Spurious { public static void main(String[] args) { Lock lock = new ReentrantLock(); Condition cond = lock.newCondition(); lock.lock(); try { try { cond.await(); System.out.println("Spurious wakeup!"); } catch (InterruptedException ex) { System.out.println("Just a regular interrupt."); } } finally { lock.unlock(); } } }
我该怎么做才能在await不永远等待随机事件的情况下虚假地唤醒它?
await
维基百科关于虚假唤醒的文章有这个花絮:
pthread_cond_wait()Linux中的功能是使用futex系统调用来实现的。EINTR当进程收到信号时,Linux 上的每个阻塞系统调用都会突然返回。…pthread_cond_wait()无法重新开始等待,因为它可能会在futex系统调用之外的一小段时间内错过真正的唤醒。这种竞争条件只能通过调用者检查不变量来避免。因此,POSIX 信号将产生虚假唤醒。
pthread_cond_wait()
futex
EINTR
简介 : 如果一个 Linux 进程收到信号,它的等待线程将享受一个不错的、热的 虚假唤醒 。
我买它。这比通常给出的通常含糊的“这是为了性能”的原因更容易下咽。