Re: [BUG] I think sleepqueue need to be protected in sleepq_broadcast

From: John Baldwin <jhb_at_freebsd.org>
Date: Sat, 23 Aug 2008 00:03:43 -0400
On Friday 22 August 2008 01:33:28 pm kevinxlinuz wrote:
> Hi,
>   I'm looking in the problem ( amd64/124200: kernel panic on mutex sleepq
> chain).It troubles me for a long time.I add a KASSERT in sleepq_broadcast()
> to check the sleepqueue's wait channel.At last it turn out that the
> sleepqueue's wait channel was changed before sleepq_resume_thread(). In
> sleepq_lookup(),We can easily find sq->sq_wchan == wchan.But after a short
> time,the sq->sq_wchan nolonger equal with wchan,so I think it was changed
> by other threads.

The sleepq chain lock is already held for all of sleepq_broadcast() by the 
caller (see wakeup() and cv_broadcastpri()).  That said, I don't have any 
other good ideas for the panic you are seeing.  Do you have a crash dump?  It 
might be interesting to see what other thread is using that sleep queue.

>  sleepq_broadcast(void *wchan, int flags, int pri, int queue)
> {
>         struct sleepqueue *sq;
>         struct thread *td;
>         int wakeup_swapper;
>
>         CTR2(KTR_PROC, "sleepq_broadcast(%p, %d)", wchan, flags);
>         KASSERT(wchan != NULL, ("%s: invalid NULL wait channel",
> __func__)); MPASS((queue >= 0) && (queue < NR_SLEEPQS));
>         sq = sleepq_lookup(wchan);
>         if (sq == NULL)
>                 return (0);
>         KASSERT(sq->sq_type == (flags & SLEEPQ_TYPE),
>             ("%s: mismatch between sleep/wakeup and cv_*", __func__));
>
>         /* Resume all blocked threads on the sleep queue. */
>         wakeup_swapper = 0;
>         while (!TAILQ_EMPTY(&sq->sq_blocked[queue])) {
>                 td = TAILQ_FIRST(&sq->sq_blocked[queue]);
>                 thread_lock(td);
>         /*       test     */
>                 KASSERT(sq->sq_wchan == wchan,
>                       ("%s:mismatch between wchan and sq_wchan in
> sq",__func__)); /* I find the panic here */
>                 if (sleepq_resume_thread(sq, td, pri))
>                         wakeup_swapper = 1;
>                 thread_unlock(td);
>         }
>         return (wakeup_swapper);
> }
>
> Thanks,
> kevin  2008/08/23
>
> _______________________________________________
> freebsd-current_at_freebsd.org mailing list
> http://lists.freebsd.org/mailman/listinfo/freebsd-current
> To unsubscribe, send any mail to "freebsd-current-unsubscribe_at_freebsd.org"



-- 
John Baldwin
Received on Sat Aug 23 2008 - 02:08:29 UTC

This archive was generated by hypermail 2.4.0 : Wed May 19 2021 - 11:39:34 UTC