Re: uring regression - lost write request

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



On Fri, Nov 12, 2021 at 10:44 AM Jens Axboe <axboe@xxxxxxxxx> wrote:
>
> Alright, give this one a go if you can. Against -git, but will apply to
> 5.15 as well.


Works. Thank you very much.

https://jira.mariadb.org/browse/MDEV-26674?page=com.atlassian.jira.plugin.system.issuetabpanels:comment-tabpanel&focusedCommentId=205599#comment-205599

Tested-by: Marko Mäkelä <marko.makela@xxxxxxxxxxx>


>
>
> diff --git a/fs/io-wq.c b/fs/io-wq.c
> index afd955d53db9..88202de519f6 100644
> --- a/fs/io-wq.c
> +++ b/fs/io-wq.c
> @@ -423,9 +423,10 @@ static inline unsigned int io_get_work_hash(struct io_wq_work *work)
>         return work->flags >> IO_WQ_HASH_SHIFT;
>  }
>
> -static void io_wait_on_hash(struct io_wqe *wqe, unsigned int hash)
> +static bool io_wait_on_hash(struct io_wqe *wqe, unsigned int hash)
>  {
>         struct io_wq *wq = wqe->wq;
> +       bool ret = false;
>
>         spin_lock_irq(&wq->hash->wait.lock);
>         if (list_empty(&wqe->wait.entry)) {
> @@ -433,9 +434,11 @@ static void io_wait_on_hash(struct io_wqe *wqe, unsigned int hash)
>                 if (!test_bit(hash, &wq->hash->map)) {
>                         __set_current_state(TASK_RUNNING);
>                         list_del_init(&wqe->wait.entry);
> +                       ret = true;
>                 }
>         }
>         spin_unlock_irq(&wq->hash->wait.lock);
> +       return ret;
>  }
>
>  static struct io_wq_work *io_get_next_work(struct io_wqe_acct *acct,
> @@ -475,14 +478,21 @@ static struct io_wq_work *io_get_next_work(struct io_wqe_acct *acct,
>         }
>
>         if (stall_hash != -1U) {
> +               bool unstalled;
> +
>                 /*
>                  * Set this before dropping the lock to avoid racing with new
>                  * work being added and clearing the stalled bit.
>                  */
>                 set_bit(IO_ACCT_STALLED_BIT, &acct->flags);
>                 raw_spin_unlock(&wqe->lock);
> -               io_wait_on_hash(wqe, stall_hash);
> +               unstalled = io_wait_on_hash(wqe, stall_hash);
>                 raw_spin_lock(&wqe->lock);
> +               if (unstalled) {
> +                       clear_bit(IO_ACCT_STALLED_BIT, &acct->flags);
> +                       if (wq_has_sleeper(&wqe->wq->hash->wait))
> +                               wake_up(&wqe->wq->hash->wait);
> +               }
>         }
>
>         return NULL;
> @@ -564,8 +574,11 @@ static void io_worker_handle_work(struct io_worker *worker)
>                                 io_wqe_enqueue(wqe, linked);
>
>                         if (hash != -1U && !next_hashed) {
> +                               /* serialize hash clear with wake_up() */
> +                               spin_lock_irq(&wq->hash->wait.lock);
>                                 clear_bit(hash, &wq->hash->map);
>                                 clear_bit(IO_ACCT_STALLED_BIT, &acct->flags);
> +                               spin_unlock_irq(&wq->hash->wait.lock);
>                                 if (wq_has_sleeper(&wq->hash->wait))
>                                         wake_up(&wq->hash->wait);
>                                 raw_spin_lock(&wqe->lock);
>
> --
> Jens Axboe
>




[Index of Archives]     [Linux RAID]     [Linux SCSI]     [Linux ATA RAID]     [IDE]     [Linux Wireless]     [Linux Kernel]     [ATH6KL]     [Linux Bluetooth]     [Linux Netdev]     [Kernel Newbies]     [Security]     [Git]     [Netfilter]     [Bugtraq]     [Yosemite News]     [MIPS Linux]     [ARM Linux]     [Linux Security]     [Device Mapper]

  Powered by Linux