From cd11ae5d8b621428f5c2ec8153dba37d096d5593 Mon Sep 17 00:00:00 2001 From: eladash Date: Wed, 12 Sep 2018 22:39:00 +0300 Subject: [PATCH] ppu: Fix extreme reservation corner case --- rpcs3/Emu/Cell/PPUThread.cpp | 4 ++++ rpcs3/Emu/Cell/PPUThread.h | 1 + 2 files changed, 5 insertions(+) diff --git a/rpcs3/Emu/Cell/PPUThread.cpp b/rpcs3/Emu/Cell/PPUThread.cpp index 8924434fd9..b45f665fc0 100644 --- a/rpcs3/Emu/Cell/PPUThread.cpp +++ b/rpcs3/Emu/Cell/PPUThread.cpp @@ -1005,11 +1005,13 @@ static T ppu_load_acquire_reservation(ppu_thread& ppu, u32 addr) extern u32 ppu_lwarx(ppu_thread& ppu, u32 addr) { + ppu.lr_64 = false; return ppu_load_acquire_reservation(ppu, addr); } extern u64 ppu_ldarx(ppu_thread& ppu, u32 addr) { + ppu.lr_64 = true; return ppu_load_acquire_reservation(ppu, addr); } @@ -1064,6 +1066,8 @@ extern bool ppu_stwcx(ppu_thread& ppu, u32 addr, u32 reg_value) { atomic_be_t& data = vm::_ref>(addr); + if (UNLIKELY(ppu.lr_64)) ppu.rdata >>= 32; + if (ppu.raddr != addr || ppu.rdata != data.load() || ppu.rtime != vm::reservation_acquire(addr, sizeof(u32))) { ppu.raddr = 0; diff --git a/rpcs3/Emu/Cell/PPUThread.h b/rpcs3/Emu/Cell/PPUThread.h index c4394dbbc4..d9bc6a9981 100644 --- a/rpcs3/Emu/Cell/PPUThread.h +++ b/rpcs3/Emu/Cell/PPUThread.h @@ -135,6 +135,7 @@ public: u32 raddr{0}; // Reservation addr u64 rtime{0}; u64 rdata{0}; // Reservation data + bool lr_64{false}; // Reservation size (true for 64 bit, false for 32 bit) atomic_t prio{0}; // Thread priority (0..3071) const u32 stack_size; // Stack size