summary refs log tree commit diff stats
path: root/util/fdmon-io_uring.c
diff options
context:
space:
mode:
authorStefan Hajnoczi <stefanha@redhat.com>2020-05-11 19:36:29 +0100
committerStefan Hajnoczi <stefanha@redhat.com>2020-05-18 18:16:00 +0100
commitde137e44f75d9868f5b548638081850f6ac771f2 (patch)
treea65668f7666bb2b8c4c25f073095dee296db862c /util/fdmon-io_uring.c
parent6fb5f0842aab0f744eebfabefb447b3a3a1af7cc (diff)
downloadfocaccia-qemu-de137e44f75d9868f5b548638081850f6ac771f2.tar.gz
focaccia-qemu-de137e44f75d9868f5b548638081850f6ac771f2.zip
aio-posix: don't duplicate fd handler deletion in fdmon_io_uring_destroy()
The io_uring file descriptor monitoring implementation has an internal
list of fd handlers that are pending submission to io_uring.
fdmon_io_uring_destroy() deletes all fd handlers on the list.

Don't delete fd handlers directly in fdmon_io_uring_destroy() for two
reasons:
1. This duplicates the aio-posix.c AioHandler deletion code and could
   become outdated if the struct changes.
2. Only handlers with the FDMON_IO_URING_REMOVE flag set are safe to
   remove. If the flag is not set then something still has a pointer to
   the fd handler. Let aio-posix.c and its user worry about that. In
   practice this isn't an issue because fdmon_io_uring_destroy() is only
   called when shutting down so all users have removed their fd
   handlers, but the next patch will need this!

Signed-off-by: Stefan Hajnoczi <stefanha@redhat.com>
Tested-by: Oleksandr Natalenko <oleksandr@redhat.com>
Message-id: 20200511183630.279750-2-stefanha@redhat.com
Signed-off-by: Stefan Hajnoczi <stefanha@redhat.com>
Diffstat (limited to 'util/fdmon-io_uring.c')
-rw-r--r--util/fdmon-io_uring.c13
1 files changed, 10 insertions, 3 deletions
diff --git a/util/fdmon-io_uring.c b/util/fdmon-io_uring.c
index d5a80ed6fb..1d14177df0 100644
--- a/util/fdmon-io_uring.c
+++ b/util/fdmon-io_uring.c
@@ -342,11 +342,18 @@ void fdmon_io_uring_destroy(AioContext *ctx)
 
         io_uring_queue_exit(&ctx->fdmon_io_uring);
 
-        /* No need to submit these anymore, just free them. */
+        /* Move handlers due to be removed onto the deleted list */
         while ((node = QSLIST_FIRST_RCU(&ctx->submit_list))) {
+            unsigned flags = atomic_fetch_and(&node->flags,
+                    ~(FDMON_IO_URING_PENDING |
+                      FDMON_IO_URING_ADD |
+                      FDMON_IO_URING_REMOVE));
+
+            if (flags & FDMON_IO_URING_REMOVE) {
+                QLIST_INSERT_HEAD_RCU(&ctx->deleted_aio_handlers, node, node_deleted);
+            }
+
             QSLIST_REMOVE_HEAD_RCU(&ctx->submit_list, node_submitted);
-            QLIST_REMOVE(node, node);
-            g_free(node);
         }
 
         ctx->fdmon_ops = &fdmon_poll_ops;