On 7/1/20 2:17 AM, Richard W.M. Jones wrote:
This option didn't work except when using --foreground (or using
another option that implies this).  This is because it creates a
background reader thread, but that thread is invalidated if nbdkit
forks, resulting in deadlocks because the worker threads are
fruitlessly sending notifications to a background thread that no
longer exists.

The fix is to move this work to .after_fork.
---
  plugins/nbd/nbd.c | 12 ++++++++++--
  1 file changed, 10 insertions(+), 2 deletions(-)

Good catch.


diff --git a/plugins/nbd/nbd.c b/plugins/nbd/nbd.c
index 05f78777..91ed91e0 100644
--- a/plugins/nbd/nbd.c
+++ b/plugins/nbd/nbd.c
@@ -109,7 +109,7 @@ static void nbdplug_close_handle (struct handle *h);
  static void
  nbdplug_unload (void)
  {
-  if (shared)
+  if (shared && shared_handle)
      nbdplug_close_handle (shared_handle);
    free (sockname);
    free (tls_certificates);
@@ -266,8 +266,15 @@ nbdplug_config_complete (void)
      }
      nbd_close (nbd);
    }
+  return 0;
+}
- /* Create the shared connection. */
+/* Create the shared connection.  Because this may create a background
+ * thread it must be done after we fork.
+ */
+static int
+nbdplug_after_fork (void)
+{
    if (shared && (shared_handle = nbdplug_open_handle (false)) == NULL)
      return -1;
    return 0;
@@ -858,6 +865,7 @@ static struct nbdkit_plugin plugin = {
    .config_complete    = nbdplug_config_complete,
    .config_help        = nbdplug_config_help,
    .magic_config_key   = "uri",
+  .after_fork         = nbdplug_after_fork,
    .dump_plugin        = nbdplug_dump_plugin,
    .open               = nbdplug_open,
    .close              = nbdplug_close,


--
Eric Blake, Principal Software Engineer
Red Hat, Inc.           +1-919-301-3226
Virtualization:  qemu.org | libvirt.org

_______________________________________________
Libguestfs mailing list
Libguestfs@redhat.com
https://www.redhat.com/mailman/listinfo/libguestfs

Reply via email to