From 45cff1219c2f29fe4267758a2a3cc6f50f1e66d7 Mon Sep 17 00:00:00 2001 From: Eladash Date: Sat, 21 Dec 2019 08:16:47 +0200 Subject: [PATCH] Allow sys_raw_spu_create_tag to be called more than once --- rpcs3/Emu/Cell/SPUThread.cpp | 6 +++--- rpcs3/Emu/Cell/SPUThread.h | 4 ++-- rpcs3/Emu/Cell/lv2/sys_spu.cpp | 8 ++++---- 3 files changed, 9 insertions(+), 9 deletions(-) diff --git a/rpcs3/Emu/Cell/SPUThread.cpp b/rpcs3/Emu/Cell/SPUThread.cpp index ed9b4931b6..c896ea8a2e 100644 --- a/rpcs3/Emu/Cell/SPUThread.cpp +++ b/rpcs3/Emu/Cell/SPUThread.cpp @@ -936,13 +936,13 @@ void spu_int_ctrl_t::set(u64 ints) ints &= mask; // notify if at least 1 bit was set - if (ints && ~stat.fetch_or(ints) & ints && tag) + if (ints && ~stat.fetch_or(ints) & ints && !tag.expired()) { reader_lock rlock(id_manager::g_mutex); - if (tag) + if (const auto tag_ptr = tag.lock()) { - if (auto handler = tag->handler.lock()) + if (auto handler = tag_ptr->handler.lock()) { handler->exec(); } diff --git a/rpcs3/Emu/Cell/SPUThread.h b/rpcs3/Emu/Cell/SPUThread.h index dbe3db80ad..e27bd3cce9 100644 --- a/rpcs3/Emu/Cell/SPUThread.h +++ b/rpcs3/Emu/Cell/SPUThread.h @@ -353,7 +353,7 @@ struct spu_int_ctrl_t atomic_t mask; atomic_t stat; - std::shared_ptr tag; + std::weak_ptr tag; void set(u64 ints); @@ -366,7 +366,7 @@ struct spu_int_ctrl_t { mask.release(0); stat.release(0); - tag = nullptr; + tag.reset(); } }; diff --git a/rpcs3/Emu/Cell/lv2/sys_spu.cpp b/rpcs3/Emu/Cell/lv2/sys_spu.cpp index b957af2889..48d72d2b4a 100644 --- a/rpcs3/Emu/Cell/lv2/sys_spu.cpp +++ b/rpcs3/Emu/Cell/lv2/sys_spu.cpp @@ -1473,16 +1473,16 @@ error_code sys_raw_spu_destroy(ppu_thread& ppu, u32 id) // Clear interrupt handlers for (auto& intr : thread->int_ctrl) { - if (intr.tag) + if (const auto tag = intr.tag.lock()) { - if (auto handler = intr.tag->handler.lock()) + if (auto handler = tag->handler.lock()) { // SLEEP handler->join(); to_remove.emplace(handler.get(), 0); } - to_remove.emplace(intr.tag.get(), 0); + to_remove.emplace(tag.get(), 0); } } @@ -1537,7 +1537,7 @@ error_code sys_raw_spu_create_interrupt_tag(ppu_thread& ppu, u32 id, u32 class_i auto& int_ctrl = thread->int_ctrl[class_id]; - if (int_ctrl.tag) + if (!int_ctrl.tag.expired()) { error = CELL_EAGAIN; return result;