bool completion_done(struct completion *x)
用于判断是否还有wait等待在completion *x 这个完成量上,然后true 表示没有等待,false 表示有wait在等待
其源码分析如下:
bool completion_done(struct completion *x)
{
if (!READ_ONCE(x->done))
return false;
/*
* If ->done, we need to wait for complete() to release ->wait.lock
* otherwise we can end up freeing the completion before complete()
* is done referencing it.
*
* The RMB pairs with complete()'s RELEASE of ->wait.lock and orders
* the loads of ->done and ->wait.lock such that we cannot observe
* the lock before complete() acquires it while observing the ->done
* after it's acquired the lock.
*/
smp_rmb();
spin_unlock_wait(&x->wait.lock);
return true;
}
判断的核心是x->done 是否等于零。如果为零,则说明没有wait再等待了。
为什么这么说呢,因为完成量等待完成量的函数do_wait_for_common 中会对x->done 做减件操作
do_wait_for_common(struct completion *x,
long (*action)(long), long timeout, int state)
{
if (x->done != UINT_MAX)
x->done--;
return timeout ?: 1;
}
而在释放完成量的函数complete 中会做加加操作
void complete(struct completion *x)
{
unsigned long flags;
spin_lock_irqsave(&x->wait.lock, flags);
if (x->done != UINT_MAX)
x->done++;
__wake_up_locked(&x->wait, TASK_NORMAL, 1);
spin_unlock_irqrestore(&x->wait.lock, flags);
}
并且这两者是可以嵌套配对的
所以当x->done 为零时,说明没有人操作完成量了.
进程调度API之completion_done
最新推荐文章于 2024-04-05 17:34:05 发布