From 6119e8fad2677e731e6105af6063cabe7be069f8 Mon Sep 17 00:00:00 2001 From: lizzie Date: Tue, 7 Jul 2026 19:52:22 +0200 Subject: [hid_core] fix LM2 crash due to callbacks not being removed properly (#4178) the function returned the key AFTER this one, which points to an invalid object basically its like "oh im returning the index AFTER Myself" off-by-1 error basically; now it returns OUR own key. Signed-off-by: lizzie Reviewed-on: https://git.eden-emu.dev/eden-emu/eden/pulls/4178 Reviewed-by: MaranBr Reviewed-by: CamilleLaVey --- src/hid_core/frontend/emulated_controller.cpp | 22 +++++++++------------- 1 file changed, 9 insertions(+), 13 deletions(-) (limited to 'src/hid_core/frontend/emulated_controller.cpp') diff --git a/src/hid_core/frontend/emulated_controller.cpp b/src/hid_core/frontend/emulated_controller.cpp index 3ebb9133dd..6022f90951 100644 --- a/src/hid_core/frontend/emulated_controller.cpp +++ b/src/hid_core/frontend/emulated_controller.cpp @@ -10,6 +10,7 @@ #include #include "common/thread.h" +#include "common/assert.h" #include "hid_core/frontend/emulated_controller.h" #include "hid_core/frontend/input_converter.h" #include "hid_core/hid_util.h" @@ -1876,12 +1877,9 @@ NpadColor EmulatedController::GetNpadColor(u32 color) { void EmulatedController::TriggerOnChange(ControllerTriggerType type, bool is_npad_service_update) { std::unique_lock lock{callback_mutex}; - for (const auto& poller_pair : callback_list) { - const ControllerUpdateCallback& poller = poller_pair.second; - if (!is_npad_service_update && poller.is_npad_service) { - continue; - } - if (poller.on_change) { + for (auto const& p : callback_list) { + auto const& poller = p.second; + if (is_npad_service_update || !poller.is_npad_service) { poller.on_change(type); } } @@ -1889,18 +1887,16 @@ void EmulatedController::TriggerOnChange(ControllerTriggerType type, bool is_npa int EmulatedController::SetCallback(ControllerUpdateCallback update_callback) { std::unique_lock lock{callback_mutex}; + ++last_callback_key; callback_list.insert_or_assign(last_callback_key, std::move(update_callback)); - return last_callback_key++; + return last_callback_key; } void EmulatedController::DeleteCallback(int key) { std::unique_lock lock{callback_mutex}; - const auto& iterator = callback_list.find(key); - if (iterator == callback_list.end()) { - LOG_ERROR(Input, "Tried to delete non-existent callback {}", key); - return; - } - callback_list.erase(iterator); + auto const it = callback_list.find(key); + ASSERT_MSG(it != callback_list.end(), "Tried to delete non-existent callback {}", key); + callback_list.erase(it); } void EmulatedController::StatusUpdate() { -- cgit v1.2.3