Skip to content

Commit 8ca38d0

Browse files
Chen Ridonggregkh
authored andcommitted
padata: avoid UAF for reorder_work
[ Upstream commit dd7d37c ] Although the previous patch can avoid ps and ps UAF for _do_serial, it can not avoid potential UAF issue for reorder_work. This issue can happen just as below: crypto_request crypto_request crypto_del_alg padata_do_serial ... padata_reorder // processes all remaining // requests then breaks while (1) { if (!padata) break; ... } padata_do_serial // new request added list_add // sees the new request queue_work(reorder_work) padata_reorder queue_work_on(squeue->work) ... <kworker context> padata_serial_worker // completes new request, // no more outstanding // requests crypto_del_alg // free pd <kworker context> invoke_padata_reorder // UAF of pd To avoid UAF for 'reorder_work', get 'pd' ref before put 'reorder_work' into the 'serial_wq' and put 'pd' ref until the 'serial_wq' finish. Fixes: bbefa1d ("crypto: pcrypt - Avoid deadlock by using per-instance padata queues") Signed-off-by: Chen Ridong <[email protected]> Acked-by: Daniel Jordan <[email protected]> Signed-off-by: Herbert Xu <[email protected]> Signed-off-by: Sasha Levin <[email protected]>
1 parent c629808 commit 8ca38d0

File tree

1 file changed

+9
-1
lines changed

1 file changed

+9
-1
lines changed

kernel/padata.c

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -352,8 +352,14 @@ static void padata_reorder(struct parallel_data *pd)
352352
smp_mb();
353353

354354
reorder = per_cpu_ptr(pd->reorder_list, pd->cpu);
355-
if (!list_empty(&reorder->list) && padata_find_next(pd, false))
355+
if (!list_empty(&reorder->list) && padata_find_next(pd, false)) {
356+
/*
357+
* Other context(eg. the padata_serial_worker) can finish the request.
358+
* To avoid UAF issue, add pd ref here, and put pd ref after reorder_work finish.
359+
*/
360+
padata_get_pd(pd);
356361
queue_work(pinst->serial_wq, &pd->reorder_work);
362+
}
357363
}
358364

359365
static void invoke_padata_reorder(struct work_struct *work)
@@ -364,6 +370,8 @@ static void invoke_padata_reorder(struct work_struct *work)
364370
pd = container_of(work, struct parallel_data, reorder_work);
365371
padata_reorder(pd);
366372
local_bh_enable();
373+
/* Pairs with putting the reorder_work in the serial_wq */
374+
padata_put_pd(pd);
367375
}
368376

369377
static void padata_serial_worker(struct work_struct *serial_work)

0 commit comments

Comments
 (0)