From 4ddae3a7928f6da9aaff75f5d2c9cfb3a6fdbd56 Mon Sep 17 00:00:00 2001 From: Adam Lyon-Jones Date: Mon, 13 May 2024 13:02:00 +0100 Subject: [PATCH] librbd: Modify locks and atomics in AioCompletion to improve performance Signed-off-by: Adam Lyon-Jones --- src/librbd/io/AioCompletion.cc | 16 ++++------------ src/librbd/io/AioCompletion.h | 9 +-------- 2 files changed, 5 insertions(+), 20 deletions(-) diff --git a/src/librbd/io/AioCompletion.cc b/src/librbd/io/AioCompletion.cc index 5452edf5fd37d..df628909bc096 100644 --- a/src/librbd/io/AioCompletion.cc +++ b/src/librbd/io/AioCompletion.cc @@ -33,12 +33,7 @@ namespace io { int AioCompletion::wait_for_complete() { tracepoint(librbd, aio_wait_for_complete_enter, this); - { - std::unique_lock locker(lock); - while (state != AIO_STATE_COMPLETE) { - cond.wait(locker); - } - } + completed.wait(false, std::memory_order_acquire); tracepoint(librbd, aio_wait_for_complete_exit, 0); return 0; } @@ -237,7 +232,7 @@ void AioCompletion::complete_request(ssize_t r) bool AioCompletion::is_complete() { tracepoint(librbd, aio_is_complete_enter, this); - bool done = (this->state == AIO_STATE_COMPLETE); + bool done = completed.load(std::memory_order_acquire); tracepoint(librbd, aio_is_complete_exit, done); return done; } @@ -262,17 +257,14 @@ void AioCompletion::complete_external_callback() { } void AioCompletion::mark_complete_and_notify() { - state = AIO_STATE_COMPLETE; + completed.store(true, std::memory_order_release); if (ictx != nullptr && event_notify && ictx->event_socket.is_valid()) { ictx->event_socket_completions.push(this); ictx->event_socket.notify(); } - { - std::unique_lock locker(lock); - cond.notify_all(); - } + completed.notify_all(); if (image_dispatcher_ctx != nullptr) { image_dispatcher_ctx->complete(rval); diff --git a/src/librbd/io/AioCompletion.h b/src/librbd/io/AioCompletion.h index d98055878cd9a..c50b282b13089 100644 --- a/src/librbd/io/AioCompletion.h +++ b/src/librbd/io/AioCompletion.h @@ -38,20 +38,13 @@ namespace io { * context or via a thread pool context for cache read hits). */ struct AioCompletion { - typedef enum { - AIO_STATE_PENDING = 0, - AIO_STATE_COMPLETE, - } aio_state_t; - mutable std::mutex lock; - std::condition_variable cond; callback_t complete_cb = nullptr; void *complete_arg = nullptr; rbd_completion_t rbd_comp = nullptr; - /// note: only using atomic for built-in memory barrier - std::atomic state{AIO_STATE_PENDING}; + std::atomic completed{false}; std::atomic rval{0}; std::atomic error_rval{0}; -- 2.39.5