Messages in this thread | | | Date | Thu, 15 Jul 2021 21:52:19 +0300 | From | Pavel Skripkin <> | Subject | Re: [PATCH v3] workqueue: fix UAF in pwq_unbound_release_workfn() |
| |
On Thu, 15 Jul 2021 16:08:12 +0800 Lai Jiangshan <jiangshanlai@gmail.com> wrote:
> On Wed, Jul 14, 2021 at 5:16 PM Yang Yingliang > <yangyingliang@huawei.com> wrote: > > > > > Fixes: 2d5f0764b526 ("workqueue: split apply_workqueue_attrs() into > > 3 stages") Reported-by: Hulk Robot <hulkci@huawei.com> > > Suggested-by: Lai Jiangshan <jiangshanlai@gmail.com> > > Signed-off-by: Yang Yingliang <yangyingliang@huawei.com> > > --- > > v3: > > drop the v2 and v1 changes, add check pwq in > > pwq_unbound_release_workfn() v2: > > also use free_wqattrs_ctx() in workqueue_apply_unbound_cpumask() > > --- > > kernel/workqueue.c | 20 +++++++++++++------- > > 1 file changed, 13 insertions(+), 7 deletions(-) > > > > I'm fine with the code. > > Reviewed-by: Lai Jiangshan <jiangshanlai@gmail.com> > > Hello, Pavel > > Could you have a test again, please? >
Hi, Lai!
Sorry for late response.
Yes, I have started local syzkaller instance just now, so I will share the results tomorrow.
> Thanks, > Lai > > > diff --git a/kernel/workqueue.c b/kernel/workqueue.c > > index 50142fc08902..f148eacda55a 100644 > > --- a/kernel/workqueue.c > > +++ b/kernel/workqueue.c > > @@ -3676,15 +3676,21 @@ static void > > pwq_unbound_release_workfn(struct work_struct *work) > > unbound_release_work); struct workqueue_struct *wq = pwq->wq; > > struct worker_pool *pool = pwq->pool; > > - bool is_last; > > + bool is_last = false; > > > > - if (WARN_ON_ONCE(!(wq->flags & WQ_UNBOUND))) > > - return; > > + /* > > + * when @pwq is not linked, it doesn't hold any reference > > to the > > + * @wq, and @wq is invalid to access. > > + */ > > + if (!list_empty(&pwq->pwqs_node)) { > > + if (WARN_ON_ONCE(!(wq->flags & WQ_UNBOUND))) > > + return; > > > > - mutex_lock(&wq->mutex); > > - list_del_rcu(&pwq->pwqs_node); > > - is_last = list_empty(&wq->pwqs); > > - mutex_unlock(&wq->mutex); > > + mutex_lock(&wq->mutex); > > + list_del_rcu(&pwq->pwqs_node); > > + is_last = list_empty(&wq->pwqs); > > + mutex_unlock(&wq->mutex); > > + } > > > > mutex_lock(&wq_pool_mutex); > > put_unbound_pool(pool); > > -- > > 2.25.1 > >
With regards, Pavel Skripkin
| |