[Devel] [RFC PATCH vz9 v6 40/62] dm-ploop: make ploop_bat_write_complete ready for parallel pio completion
Pavel Tikhomirov
ptikhomirov at virtuozzo.com
Fri Jan 17 11:09:42 MSK 2025
> --- a/drivers/md/dm-ploop-map.c
> +++ b/drivers/md/dm-ploop-map.c
> @@ -893,35 +893,47 @@ static void ploop_bat_write_complete(struct pio *pio, void *piwb_ptr,
> struct ploop_cow *cow;
> struct pio *data_pio;
> unsigned long flags;
> -
> - if (!bi_status) {
> - /*
> - * Success: now update local BAT copy. We could do this
> - * from our delayed work, but we want to publish new
> - * mapping in the fastest way. This must be done before
> - * data bios completion, since right after we complete
> - * a bio, subsequent read wants to see written data
> - * (ploop_map() wants to see not zero bat_entries[.]).
> - */
> - ploop_advance_local_after_bat_wb(ploop, piwb, true);
> + LIST_HEAD(lready_pios);
> + LIST_HEAD(lcow_pios);
> + int completed = atomic_read(&piwb->count) == 1;
Maybe we can use this construct:
if (atomic_dec_and_test(&piwb->count)) {do}
> +
> + if (completed) {
> + /* We are the last count so it is safe to advance bat */
> + if (!bi_status) {
> + /*
> + * Success: now update local BAT copy. We could do this
> + * from our delayed work, but we want to publish new
> + * mapping in the fastest way. This must be done before
> + * data bios completion, since right after we complete
> + * a bio, subsequent read wants to see written data
> + * (ploop_map() wants to see not zero bat_entries[.]).
> + */
> + ploop_advance_local_after_bat_wb(ploop, piwb, true);
> + }
> }
>
> spin_lock_irqsave(&piwb->lock, flags);
> - piwb->completed = true;
> + if (completed)
> + piwb->completed = completed;
> piwb->bi_status = bi_status;
> + list_splice_init(&piwb->ready_data_pios, &lready_pios);
> spin_unlock_irqrestore(&piwb->lock, flags);
>
> + spin_lock_irqsave(&ploop->deferred_lock, flags);
> + list_splice_init(&piwb->cow_list, &lcow_pios);
> + spin_unlock_irqrestore(&ploop->deferred_lock, flags);
> +
> /*
> - * End pending data bios. Unlocked, as nobody can
> - * add a new element after piwc->completed is true.
> + * End pending data bios.
> */
> - while ((data_pio = ploop_pio_list_pop(&piwb->ready_data_pios)) != NULL) {
> +
> + while ((data_pio = ploop_pio_list_pop(&lready_pios)) != NULL) {
> if (bi_status)
> data_pio->bi_status = bi_status;
> ploop_pio_endio(data_pio);
> }
>
> - while ((aux_pio = ploop_pio_list_pop(&piwb->cow_list))) {
> + while ((aux_pio = ploop_pio_list_pop(&lcow_pios))) {
> cow = aux_pio->endio_cb_data;
> ploop_complete_cow(cow, bi_status);
> }
--
Best regards, Tikhomirov Pavel
Senior Software Developer, Virtuozzo.
More information about the Devel
mailing list