diff --git a/fs/erofs/zdata.c b/fs/erofs/zdata.c index eed8d174a315..f31e1d2ab67f 100644 --- a/fs/erofs/zdata.c +++ b/fs/erofs/zdata.c @@ -709,6 +709,7 @@ static int z_erofs_do_read_page(struct z_erofs_decompress_frontend *fe, goto out; } +static void z_erofs_decompressqueue_work(struct work_struct *work); static void z_erofs_decompress_kickoff(struct z_erofs_decompressqueue *io, bool sync, int bios) { @@ -723,8 +724,14 @@ static void z_erofs_decompress_kickoff(struct z_erofs_decompressqueue *io, return; } - if (!atomic_add_return(bios, &io->pending_bios)) + if (atomic_add_return(bios, &io->pending_bios)) + return; + /* Use workqueue decompression for atomic contexts only */ + if (in_atomic() || irqs_disabled()) { queue_work(z_erofs_workqueue, &io->u.work); + return; + } + z_erofs_decompressqueue_work(&io->u.work); } static bool z_erofs_page_is_invalidated(struct page *page)