From: Kevin Wolf <kwolf@redhat.com>
To: Stefan Hajnoczi <stefanha@redhat.com>
Cc: Hanna Reitz <hreitz@redhat.com>,
Vladimir Sementsov-Ogievskiy <vsementsov@virtuozzo.com>,
qemu-devel@nongnu.org, qemu-block@nongnu.org,
qemu-stable@nongnu.org
Subject: Re: [PATCH v2] block-backend: prevent dangling BDS pointers across aio_poll()
Date: Tue, 14 Dec 2021 15:59:49 +0100 [thread overview]
Message-ID: <YbixZeHqqImnPbwL@redhat.com> (raw)
In-Reply-To: <20211214143542.14758-1-stefanha@redhat.com>
Am 14.12.2021 um 15:35 hat Stefan Hajnoczi geschrieben:
> The BlockBackend root child can change when aio_poll() is invoked. This
> happens when a temporary filter node is removed upon blockjob
> completion, for example.
>
> Functions in block/block-backend.c must be aware of this when using a
> blk_bs() pointer across aio_poll() because the BlockDriverState refcnt
> may reach 0, resulting in a stale pointer.
>
> One example is scsi_device_purge_requests(), which calls blk_drain() to
> wait for in-flight requests to cancel. If the backup blockjob is active,
> then the BlockBackend root child is a temporary filter BDS owned by the
> blockjob. The blockjob can complete during bdrv_drained_begin() and the
> last reference to the BDS is released when the temporary filter node is
> removed. This results in a use-after-free when blk_drain() calls
> bdrv_drained_end(bs) on the dangling pointer.
>
> Explicitly hold a reference to bs across block APIs that invoke
> aio_poll().
>
> Signed-off-by: Stefan Hajnoczi <stefanha@redhat.com>
> ---
> v2:
> - Audit block/block-backend.c and fix additional cases
> ---
> block/block-backend.c | 11 +++++++++++
> 1 file changed, 11 insertions(+)
>
> diff --git a/block/block-backend.c b/block/block-backend.c
> index 12ef80ea17..a40ad7fa92 100644
> --- a/block/block-backend.c
> +++ b/block/block-backend.c
> @@ -828,10 +828,12 @@ void blk_remove_bs(BlockBackend *blk)
> notifier_list_notify(&blk->remove_bs_notifiers, blk);
> if (tgm->throttle_state) {
> bs = blk_bs(blk);
> + bdrv_ref(bs);
> bdrv_drained_begin(bs);
> throttle_group_detach_aio_context(tgm);
> throttle_group_attach_aio_context(tgm, qemu_get_aio_context());
> bdrv_drained_end(bs);
> + bdrv_unref(bs);
> }
>
> blk_update_root_state(blk);
This hunk is unnecessary, we still hold a reference that is only given
up a few lines down with bdrv_root_unref_child(root).
The rest looks good to me, so without this hunk:
Reviewed-by: Kevin Wolf <kwolf@redhat.com>
next prev parent reply other threads:[~2021-12-14 15:07 UTC|newest]
Thread overview: 8+ messages / expand[flat|nested] mbox.gz Atom feed top
2021-12-14 14:35 [PATCH v2] block-backend: prevent dangling BDS pointers across aio_poll() Stefan Hajnoczi
2021-12-14 14:59 ` Kevin Wolf [this message]
2021-12-15 11:28 ` Stefan Hajnoczi
2021-12-15 15:31 ` Kevin Wolf
2021-12-15 16:46 ` Stefan Hajnoczi
2022-01-11 11:09 ` Stefan Hajnoczi
2022-01-10 18:57 ` Hanna Reitz
2022-01-11 15:36 ` Stefan Hajnoczi
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=YbixZeHqqImnPbwL@redhat.com \
--to=kwolf@redhat.com \
--cc=hreitz@redhat.com \
--cc=qemu-block@nongnu.org \
--cc=qemu-devel@nongnu.org \
--cc=qemu-stable@nongnu.org \
--cc=stefanha@redhat.com \
--cc=vsementsov@virtuozzo.com \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.