mirror of
https://github.com/apache/nuttx.git
synced 2026-06-07 01:05:54 +08:00
wqueue: fix race-condition on work_queue
CPU0 CPU1
work_queue(a) work_queue(a)
-> work_cancel(a)
-> work_cancel(a)
-> enter_critical()
-> sq_addlast(a)
-> leave_critical()
-> enter_critical()
-> sq_addlast(a) // double add, wrong
-> leave_critical()
Also, this happens in mulit-threads in one CPU.
Fix:
work_cancel() should in critical section.
Signed-off-by: ligd <liguiding1@xiaomi.com>
This commit is contained in:
@@ -110,16 +110,16 @@ int work_queue(int qid, FAR struct work_s *work, worker_t worker,
|
||||
irqstate_t flags;
|
||||
int ret = OK;
|
||||
|
||||
/* Remove the entry from the timer and work queue. */
|
||||
|
||||
work_cancel(qid, work);
|
||||
|
||||
/* Interrupts are disabled so that this logic can be called from with
|
||||
* task logic or from interrupt handling logic.
|
||||
*/
|
||||
|
||||
flags = enter_critical_section();
|
||||
|
||||
/* Remove the entry from the timer and work queue. */
|
||||
|
||||
work_cancel(qid, work);
|
||||
|
||||
/* Initialize the work structure. */
|
||||
|
||||
work->worker = worker; /* Work callback. non-NULL means queued */
|
||||
|
||||
Reference in New Issue
Block a user