qemu-devel.nongnu.org archive mirror
 help / color / mirror / Atom feed
From: Kevin Wolf <kwolf@redhat.com>
To: Eric Blake <eblake@redhat.com>
Cc: qemu-block@nongnu.org, hreitz@redhat.com, stefanha@redhat.com,
	f.ebner@proxmox.com, qemu-devel@nongnu.org
Subject: Re: [PATCH 1/8] block: Call .bdrv_co_create(_opts) unlocked
Date: Mon, 15 May 2023 18:19:41 +0200	[thread overview]
Message-ID: <ZGJbnbx9vjXVEUuv@redhat.com> (raw)
In-Reply-To: <lqumtxeofbejjvf5f45zf5ywdrae2wckhgwrud5ggly4jganfz@sbb23gf53wbg>

Am 12.05.2023 um 18:12 hat Eric Blake geschrieben:
> 
> On Wed, May 10, 2023 at 10:35:54PM +0200, Kevin Wolf wrote:
> > 
> > These are functions that modify the graph, so they must be able to take
> > a writer lock. This is impossible if they already hold the reader lock.
> > If they need a reader lock for some of their operations, they should
> > take it internally.
> > 
> > Many of them go through blk_*(), which will always take the lock itself.
> > Direct calls of bdrv_*() need to take the reader lock. Note that while
> > locking for bdrv_co_*() calls is checked by TSA, this is not the case
> > for the mixed_coroutine_fns bdrv_*(). Holding the lock is still required
> > when they are called from coroutine context like here!
> > 
> > This effectively reverts 4ec8df0183, but adds some internal locking
> > instead.
> > 
> > Signed-off-by: Kevin Wolf <kwolf@redhat.com>
> > ---
> 
> > +++ b/block/qcow2.c
> 
> > -static int coroutine_fn
> > +static int coroutine_fn GRAPH_UNLOCKED
> >  qcow2_co_create(BlockdevCreateOptions *create_options, Error **errp)
> >  {
> >      BlockdevCreateOptionsQcow2 *qcow2_opts;
> > @@ -3724,8 +3726,10 @@ qcow2_co_create(BlockdevCreateOptions *create_options, Error **errp)
> >          goto out;
> >      }
> >  
> > +    bdrv_graph_co_rdlock();
> >      ret = qcow2_alloc_clusters(blk_bs(blk), 3 * cluster_size);
> >      if (ret < 0) {
> > +        bdrv_graph_co_rdunlock();
> >          error_setg_errno(errp, -ret, "Could not allocate clusters for qcow2 "
> >                           "header and refcount table");
> >          goto out;
> > @@ -3743,6 +3747,8 @@ qcow2_co_create(BlockdevCreateOptions *create_options, Error **errp)
> >  
> >      /* Create a full header (including things like feature table) */
> >      ret = qcow2_update_header(blk_bs(blk));
> > +    bdrv_graph_co_rdunlock();
> > +
> 
> If we ever inject any 'goto out' in the elided lines, we're in
> trouble.  Would this be any safer by wrapping the intervening
> statements in a scope-guarded lock?

TSA doesn't understand these guards, which is why they are only
annotated as assertions (I think we talked about this in my previous
series), at the cost of leaving unlocking unchecked. So in cases where
the scope isn't the full function, individual calls are better at the
moment. Once clang implements support for __attribute__((cleanup)), we
can maybe change this.

Of course, TSA solves the very maintenance problem you're concerned
about: With a 'goto out' added, compilation on clang fails because it
sees that there is a code path that doesn't unlock. So at least it makes
the compromise not terrible.

For example, if I comment out the unlock in the error case in the first,
this is what I get:

../block/qcow2.c:3825:5: error: mutex 'graph_lock' is not held on every path through here [-Werror,-Wthread-safety-analysis]
    blk_co_unref(blk);
    ^
../block/qcow2.c:3735:5: note: mutex acquired here
    bdrv_graph_co_rdlock();
    ^
1 error generated.

Kevin



  reply	other threads:[~2023-05-15 16:20 UTC|newest]

Thread overview: 21+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2023-05-10 20:35 [PATCH 0/8] block: Honour graph read lock even in the main thread Kevin Wolf
2023-05-10 20:35 ` [PATCH 1/8] block: Call .bdrv_co_create(_opts) unlocked Kevin Wolf
2023-05-12 16:12   ` Eric Blake
2023-05-15 16:19     ` Kevin Wolf [this message]
2023-05-15 21:08       ` Eric Blake
2023-05-10 20:35 ` [PATCH 2/8] block/export: Fix null pointer dereference in error path Kevin Wolf
2023-05-12 15:31   ` Peter Maydell
2023-05-12 16:16   ` Eric Blake
2023-05-12 18:46     ` Eric Blake
2023-05-10 20:35 ` [PATCH 3/8] qcow2: Unlock the graph in qcow2_do_open() where necessary Kevin Wolf
2023-05-12 16:19   ` Eric Blake
2023-05-10 20:35 ` [PATCH 4/8] qemu-img: Take graph lock more selectively Kevin Wolf
2023-05-12 16:20   ` Eric Blake
2023-05-10 20:35 ` [PATCH 5/8] test-bdrv-drain: " Kevin Wolf
2023-05-12 16:26   ` Eric Blake
2023-05-10 20:35 ` [PATCH 6/8] test-bdrv-drain: Call bdrv_co_unref() in coroutine context Kevin Wolf
2023-05-12 16:27   ` Eric Blake
2023-05-10 20:36 ` [PATCH 7/8] blockjob: Adhere to rate limit even when reentered early Kevin Wolf
2023-05-12 16:35   ` Eric Blake
2023-05-10 20:36 ` [PATCH 8/8] graph-lock: Honour read locks even in the main thread Kevin Wolf
2023-05-12 16:37   ` Eric Blake

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=ZGJbnbx9vjXVEUuv@redhat.com \
    --to=kwolf@redhat.com \
    --cc=eblake@redhat.com \
    --cc=f.ebner@proxmox.com \
    --cc=hreitz@redhat.com \
    --cc=qemu-block@nongnu.org \
    --cc=qemu-devel@nongnu.org \
    --cc=stefanha@redhat.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 a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).