From 7c4ddb59430df022841fa9c1bca02402f61dcd71 Mon Sep 17 00:00:00 2001 From: Max Kellermann <max.kellermann@gmail.com> Date: Thu, 30 Jan 2025 19:57:17 +0100 Subject: [PATCH] input/uring: initialize uring_input_queue lazily The BlockingCall() in InitUringInputPlugin() did not work because the EventThread was not yet started. This was never noticed until commit e309941646e which enabled `IORING_SETUP_SINGLE_ISSUER`, and suddenly the kernel refused to accept io_uring_submit() calls from the io_thread because io_uring_setup() had been called from the main thread. --- src/input/plugins/UringInputPlugin.cxx | 15 +++++++++++---- 1 file changed, 11 insertions(+), 4 deletions(-) diff --git a/src/input/plugins/UringInputPlugin.cxx b/src/input/plugins/UringInputPlugin.cxx index bea7c523b..f001c5775 100644 --- a/src/input/plugins/UringInputPlugin.cxx +++ b/src/input/plugins/UringInputPlugin.cxx @@ -33,6 +33,7 @@ static const size_t URING_RESUME_AT = 384 * 1024; static EventLoop *uring_input_event_loop; static Uring::Queue *uring_input_queue; +static bool uring_input_initialized = false; class UringInputStream final : public AsyncInputStream, Uring::ReadHandler { Uring::Queue ů @@ -163,6 +164,16 @@ UringInputStream::OnReadError(int error) noexcept InputStreamPtr OpenUringInputStream(const char *path, Mutex &mutex) { + if (!uring_input_initialized) { + BlockingCall(*uring_input_event_loop, [](){ + if (uring_input_initialized) + return; + + uring_input_queue = uring_input_event_loop->GetUring(); + uring_input_initialized = true; + }); + } + if (uring_input_queue == nullptr) return nullptr; @@ -187,8 +198,4 @@ void InitUringInputPlugin(EventLoop &event_loop) noexcept { uring_input_event_loop = &event_loop; - - BlockingCall(event_loop, [](){ - uring_input_queue = uring_input_event_loop->GetUring(); - }); }