diff --git a/rpcs3/Emu/Cell/MFC.h b/rpcs3/Emu/Cell/MFC.h index a5f0a72f39..c7fe58835e 100644 --- a/rpcs3/Emu/Cell/MFC.h +++ b/rpcs3/Emu/Cell/MFC.h @@ -98,9 +98,11 @@ struct alignas(16) spu_mfc_cmd u32 eah; }; +enum class spu_block_hash : u64; + struct mfc_cmd_dump { spu_mfc_cmd cmd; - + u64 block_hash; alignas(16) u8 data[128]; }; diff --git a/rpcs3/Emu/Cell/SPUThread.cpp b/rpcs3/Emu/Cell/SPUThread.cpp index 9531304fdf..db97696d69 100644 --- a/rpcs3/Emu/Cell/SPUThread.cpp +++ b/rpcs3/Emu/Cell/SPUThread.cpp @@ -97,6 +97,18 @@ void fmt_class_string::format(std::string& out, u64 arg) }); } +template <> +void fmt_class_string::format(std::string& out, u64 arg) +{ + fmt::append(out, "%s", fmt::base57(be_t{arg})); + + // Print only 7 hash characters out of 11 (which covers roughly 48 bits) + out.resize(out.size() - 4); + + // Print chunk address from lowest 16 bits + fmt::append(out, "...chunk-0x%05x", (arg & 0xffff) * 4); +} + // Verify AVX availability for TSX transactions static const bool s_tsx_avx = utils::has_avx(); @@ -1441,16 +1453,8 @@ std::string spu_thread::dump_misc() const if (g_cfg.core.spu_prof) { - // Get short function hash - const u64 name = atomic_storage::load(block_hash); - - fmt::append(ret, "\nCurrent block: %s", fmt::base57(be_t{name})); - - // Print only 7 hash characters out of 11 (which covers roughly 48 bits) - ret.resize(ret.size() - 4); - - // Print chunk address from lowest 16 bits - fmt::append(ret, "...chunk-0x%05x", (name & 0xffff) * 4); + // Get short function hash and position in chunk + fmt::append(ret, "\nCurrent block: %s", spu_block_hash{atomic_storage::load(block_hash)}); } const u32 offset = group ? SPU_FAKE_BASE_ADDR + (id & 0xffffff) * SPU_LS_SIZE : RAW_SPU_BASE_ADDR + index * RAW_SPU_OFFSET; @@ -2426,6 +2430,7 @@ void spu_thread::do_dma_transfer(spu_thread* _this, const spu_mfc_cmd& args, u8* auto& dump = _this->mfc_history[_this->mfc_dump_idx++ % spu_thread::max_mfc_dump_idx]; dump.cmd = args; dump.cmd.eah = _this->pc; + dump.block_hash = _this->block_hash; std::memcpy(dump.data, is_get ? dst : src, std::min(args.size, 128)); } @@ -2624,6 +2629,7 @@ void spu_thread::do_dma_transfer(spu_thread* _this, const spu_mfc_cmd& args, u8* auto& dump = _this->mfc_history[_this->mfc_dump_idx++ % spu_thread::max_mfc_dump_idx]; dump.cmd = args; dump.cmd.eah = _this->pc; + dump.block_hash = _this->block_hash; std::memcpy(dump.data, is_get ? dst : src, std::min(args.size, 128)); } @@ -2787,6 +2793,7 @@ void spu_thread::do_dma_transfer(spu_thread* _this, const spu_mfc_cmd& args, u8* auto& dump = _this->mfc_history[_this->mfc_dump_idx++ % spu_thread::max_mfc_dump_idx]; dump.cmd = args; dump.cmd.eah = _this->pc; + dump.block_hash = _this->block_hash; std::memcpy(dump.data, is_get ? dst : src, std::min(args.size, 128)); } @@ -2863,6 +2870,7 @@ plain_access: auto& dump = _this->mfc_history[_this->mfc_dump_idx++ % spu_thread::max_mfc_dump_idx]; dump.cmd = args; dump.cmd.eah = _this->pc; + dump.block_hash = _this->block_hash; std::memcpy(dump.data, is_get ? dst : src, std::min(args.size, 128)); } } @@ -4239,6 +4247,7 @@ bool spu_thread::process_mfc_cmd() auto& dump = mfc_history[mfc_dump_idx++ % spu_thread::max_mfc_dump_idx]; dump.cmd = ch_mfc_cmd; dump.cmd.eah = pc; + dump.block_hash = block_hash; std::memcpy(dump.data, rdata, 128); } @@ -4294,6 +4303,7 @@ bool spu_thread::process_mfc_cmd() auto& dump = mfc_history[mfc_dump_idx++ % spu_thread::max_mfc_dump_idx]; dump.cmd = ch_mfc_cmd; dump.cmd.eah = pc; + dump.block_hash = block_hash; std::memcpy(dump.data, rdata, 128); } @@ -4411,6 +4421,7 @@ bool spu_thread::process_mfc_cmd() auto& dump = mfc_history[mfc_dump_idx++ % spu_thread::max_mfc_dump_idx]; dump.cmd = ch_mfc_cmd; dump.cmd.eah = pc; + dump.block_hash = block_hash; std::memcpy(dump.data, rdata, 128); } @@ -4437,6 +4448,7 @@ bool spu_thread::process_mfc_cmd() dump.cmd = ch_mfc_cmd; dump.cmd.eah = pc; dump.cmd.tag = static_cast(ch_atomic_stat.get_value()); // Use tag as atomic status + dump.block_hash = block_hash; std::memcpy(dump.data, _ptr(ch_mfc_cmd.lsa & 0x3ff80), 128); } @@ -4450,6 +4462,7 @@ bool spu_thread::process_mfc_cmd() auto& dump = mfc_history[mfc_dump_idx++ % max_mfc_dump_idx]; dump.cmd = ch_mfc_cmd; dump.cmd.eah = pc; + dump.block_hash = block_hash; std::memcpy(dump.data, _ptr(ch_mfc_cmd.lsa & 0x3ff80), 128); } @@ -4465,6 +4478,7 @@ bool spu_thread::process_mfc_cmd() auto& dump = mfc_history[mfc_dump_idx++ % max_mfc_dump_idx]; dump.cmd = ch_mfc_cmd; dump.cmd.eah = pc; + dump.block_hash = block_hash; std::memcpy(dump.data, _ptr(ch_mfc_cmd.lsa & 0x3ff80), 128); } diff --git a/rpcs3/Emu/Cell/SPUThread.h b/rpcs3/Emu/Cell/SPUThread.h index 28fc40f7da..80567a9745 100644 --- a/rpcs3/Emu/Cell/SPUThread.h +++ b/rpcs3/Emu/Cell/SPUThread.h @@ -617,6 +617,8 @@ enum class spu_debugger_mode : u32 max_mode, }; +enum class spu_block_hash : u64 {}; + class spu_thread : public cpu_thread { public: diff --git a/rpcs3/rpcs3qt/debugger_frame.cpp b/rpcs3/rpcs3qt/debugger_frame.cpp index 64579a910a..041484d5ea 100644 --- a/rpcs3/rpcs3qt/debugger_frame.cpp +++ b/rpcs3/rpcs3qt/debugger_frame.cpp @@ -506,7 +506,7 @@ void debugger_frame::keyPressEvent(QKeyEvent* event) auto& dump = *it; const u32 pc = std::exchange(dump.cmd.eah, 0); - fmt::append(ret, "\n(%d) PC 0x%05x: [%s]", i, pc, dump.cmd); + fmt::append(ret, "\n(%d) PC 0x%05x: [%s] (%s)", i, pc, dump.cmd, spu_block_hash{dump.block_hash}); if (dump.cmd.cmd == MFC_PUTLLC_CMD) {