From 01aa74e4a86be3b999383ccec8d8a54738eaa1fd Mon Sep 17 00:00:00 2001 From: Nekotekina Date: Mon, 14 Jul 2014 23:15:30 +0400 Subject: [PATCH] IsGoodAddr() bug fixed --- Utilities/GNU.h | 6 + rpcs3/Emu/Memory/Memory.cpp | 188 +---------------------- rpcs3/Emu/Memory/Memory.h | 195 ++++++++++++++++++++---- rpcs3/Emu/SysCalls/Modules/libmixer.cpp | 6 +- rpcs3/Emu/SysCalls/lv2/sys_timer.cpp | 4 +- rpcs3/Emu/SysCalls/lv2/sys_tty.cpp | 2 +- 6 files changed, 181 insertions(+), 220 deletions(-) diff --git a/Utilities/GNU.h b/Utilities/GNU.h index c0286b0491..89cb3a1cfa 100644 --- a/Utilities/GNU.h +++ b/Utilities/GNU.h @@ -6,6 +6,12 @@ #define thread_local __thread #endif +#ifdef _WIN32 +#define noinline __declspec(noinline) +#else +#define noinline __attribute__((noinline)) +#endif + template void strcpy_trunc(char (&dst)[size], const std::string& src) { diff --git a/rpcs3/Emu/Memory/Memory.cpp b/rpcs3/Emu/Memory/Memory.cpp index e804900963..c69afb5a9a 100644 --- a/rpcs3/Emu/Memory/Memory.cpp +++ b/rpcs3/Emu/Memory/Memory.cpp @@ -364,193 +364,7 @@ bool MemoryBlockLE::Write128(const u64 addr, const u128 value) return true; } -//MemoryBase -void MemoryBase::Write8(u64 addr, const u8 data) -{ - if ((u32)addr == addr) - { - *(u8*)((u8*)GetBaseAddr() + addr) = data; - } - else - { - LOG_ERROR(MEMORY, "%s(): invalid address (0x%llx)", __FUNCTION__, addr); - Emu.Pause(); - } -} - -void MemoryBase::Write16(u64 addr, const u16 data) -{ - if ((u32)addr == addr) - { - *(u16*)((u8*)GetBaseAddr() + addr) = re16(data); - } - else - { - LOG_ERROR(MEMORY, "%s(): invalid address (0x%llx)", __FUNCTION__, addr); - Emu.Pause(); - } -} - -void MemoryBase::Write32(u64 addr, const u32 data) -{ - if ((u32)addr == addr) - { - if (addr < RAW_SPU_BASE_ADDR || (addr % RAW_SPU_OFFSET) < RAW_SPU_PROB_OFFSET || !RawSPUMem[(addr - RAW_SPU_BASE_ADDR) / RAW_SPU_OFFSET]) - { - *(u32*)((u8*)GetBaseAddr() + addr) = re32(data); - } - else - { - RawSPUMem[(addr - RAW_SPU_BASE_ADDR) / RAW_SPU_OFFSET]->Write32(addr, data); - } - } - else - { - LOG_ERROR(MEMORY, "%s(): invalid address (0x%llx)", __FUNCTION__, addr); - Emu.Pause(); - } -} - -void MemoryBase::Write64(u64 addr, const u64 data) -{ - if ((u32)addr == addr) - { - *(u64*)((u8*)GetBaseAddr() + addr) = re64(data); - } - else - { - LOG_ERROR(MEMORY, "%s(): invalid address (0x%llx)", __FUNCTION__, addr); - Emu.Pause(); - } -} - -void MemoryBase::Write128(u64 addr, const u128 data) -{ - if ((u32)addr == addr) - { - *(u128*)((u8*)GetBaseAddr() + addr) = re128(data); - } - else - { - LOG_ERROR(MEMORY, "%s(): invalid address (0x%llx)", __FUNCTION__, addr); - Emu.Pause(); - } -} - -bool MemoryBase::Write8NN(u64 addr, const u8 data) -{ - if(!IsGoodAddr(addr)) return false; - Write8(addr, data); - return true; -} - -bool MemoryBase::Write16NN(u64 addr, const u16 data) -{ - if(!IsGoodAddr(addr, 2)) return false; - Write16(addr, data); - return true; -} - -bool MemoryBase::Write32NN(u64 addr, const u32 data) -{ - if(!IsGoodAddr(addr, 4)) return false; - Write32(addr, data); - return true; -} - -bool MemoryBase::Write64NN(u64 addr, const u64 data) -{ - if(!IsGoodAddr(addr, 8)) return false; - Write64(addr, data); - return true; -} - -bool MemoryBase::Write128NN(u64 addr, const u128 data) -{ - if(!IsGoodAddr(addr, 16)) return false; - Write128(addr, data); - return true; -} - -u8 MemoryBase::Read8(u64 addr) -{ - if ((u32)addr == addr) - { - return *(u8*)((u8*)GetBaseAddr() + addr); - } - else - { - LOG_ERROR(MEMORY, "%s(): invalid address (0x%llx)", __FUNCTION__, addr); - Emu.Pause(); - return 0; - } -} - -u16 MemoryBase::Read16(u64 addr) -{ - if ((u32)addr == addr) - { - return re16(*(u16*)((u8*)GetBaseAddr() + addr)); - } - else - { - LOG_ERROR(MEMORY, "%s(): invalid address (0x%llx)", __FUNCTION__, addr); - Emu.Pause(); - return 0; - } -} - -u32 MemoryBase::Read32(u64 addr) -{ - if ((u32)addr == addr) - { - if (addr < RAW_SPU_BASE_ADDR || (addr % RAW_SPU_OFFSET) < RAW_SPU_PROB_OFFSET || !RawSPUMem[(addr - RAW_SPU_BASE_ADDR) / RAW_SPU_OFFSET]) - { - return re32(*(u32*)((u8*)GetBaseAddr() + addr)); - } - else - { - u32 res; - RawSPUMem[(addr - RAW_SPU_BASE_ADDR) / RAW_SPU_OFFSET]->Read32(addr, &res); - return res; - } - } - else - { - LOG_ERROR(MEMORY, "%s(): invalid address (0x%llx)", __FUNCTION__, addr); - Emu.Pause(); - return 0; - } -} - -u64 MemoryBase::Read64(u64 addr) -{ - if ((u32)addr == addr) - { - return re64(*(u64*)((u8*)GetBaseAddr() + addr)); - } - else - { - LOG_ERROR(MEMORY, "%s(): invalid address (0x%llx)", __FUNCTION__, addr); - Emu.Pause(); - return 0; - } -} - -u128 MemoryBase::Read128(u64 addr) -{ - if ((u32)addr == addr) - { - return re128(*(u128*)((u8*)GetBaseAddr() + addr)); - } - else - { - LOG_ERROR(MEMORY, "%s(): invalid address (0x%llx)", __FUNCTION__, addr); - Emu.Pause(); - return u128::From128(0, 0); - } -} - +// MemoryBase template<> __forceinline u64 MemoryBase::ReverseData<1>(u64 val) { return val; } template<> __forceinline u64 MemoryBase::ReverseData<2>(u64 val) { return Reverse16(val); } template<> __forceinline u64 MemoryBase::ReverseData<4>(u64 val) { return Reverse32(val); } diff --git a/rpcs3/Emu/Memory/Memory.h b/rpcs3/Emu/Memory/Memory.h index 5f7681301b..9ac13daba6 100644 --- a/rpcs3/Emu/Memory/Memory.h +++ b/rpcs3/Emu/Memory/Memory.h @@ -111,17 +111,26 @@ public: return m_base_addr; } + noinline void InvalidAddress(const char* func, const u64 addr) + { + LOG_ERROR(MEMORY, "%s(): invalid address (0x%llx)", func, addr); + } + void RegisterPages(u64 addr, u32 size) { std::lock_guard lock(m_mutex); //LOG_NOTICE(MEMORY, "RegisterPages(addr=0x%llx, size=0x%x)", addr, size); - for (u32 i = addr / 4096; i < (addr + size) / 4096; i++) + for (u64 i = addr / 4096; i < (addr + size) / 4096; i++) { - if (i >= sizeof(m_pages) / sizeof(m_pages[0])) break; + if (i >= sizeof(m_pages) / sizeof(m_pages[0])) + { + InvalidAddress(__FUNCTION__, i * 4096); + break; + } if (m_pages[i]) { - LOG_ERROR(MEMORY, "Page already registered (page=0x%x)", i * 4096); + LOG_ERROR(MEMORY, "Page already registered (addr=0x%llx)", i * 4096); } m_pages[i] = 1; // TODO: define page parameters } @@ -132,12 +141,16 @@ public: std::lock_guard lock(m_mutex); //LOG_NOTICE(MEMORY, "UnregisterPages(addr=0x%llx, size=0x%x)", addr, size); - for (u32 i = addr / 4096; i < (addr + size) / 4096; i++) + for (u64 i = addr / 4096; i < (addr + size) / 4096; i++) { - if (i >= sizeof(m_pages) / sizeof(m_pages[0])) break; + if (i >= sizeof(m_pages) / sizeof(m_pages[0])) + { + InvalidAddress(__FUNCTION__, i * 4096); + break; + } if (!m_pages[i]) { - LOG_ERROR(MEMORY, "Page not registered (page=0x%x)", i * 4096); + LOG_ERROR(MEMORY, "Page not registered (addr=0x%llx)", i * 4096); } m_pages[i] = 0; // TODO: define page parameters } @@ -181,8 +194,7 @@ public: } else { - LOG_ERROR(MEMORY, "%s(): invalid address (0x%llx)", __FUNCTION__, addr); - assert(0); + InvalidAddress(__FUNCTION__, addr); return (u8*)GetBaseAddr(); } } @@ -287,9 +299,9 @@ public: LOG_NOTICE(MEMORY, "Memory initialized."); } - bool IsGoodAddr(const u64 addr) + template bool IsGoodAddr(const T addr) { - if (addr >= 0x100000000 || !m_pages[addr / 4096]) // TODO: define page parameters + if ((u32)addr != addr || !m_pages[addr / 4096]) // TODO: define page parameters { return false; } @@ -299,9 +311,9 @@ public: } } - bool IsGoodAddr(const u64 addr, const u32 size) + template bool IsGoodAddr(const T addr, const u32 size) { - if (addr + size > 0x100000000) + if ((u32)addr != addr || (u64)addr + (u64)size > 0x100000000ull) { return false; } @@ -346,23 +358,152 @@ public: #endif } - void Write8(const u64 addr, const u8 data); - void Write16(const u64 addr, const u16 data); - void Write32(const u64 addr, const u32 data); - void Write64(const u64 addr, const u64 data); - void Write128(const u64 addr, const u128 data); + //MemoryBase + template void Write8(T addr, const u8 data) + { + if ((u32)addr == addr) + { + *(u8*)((u8*)GetBaseAddr() + addr) = data; + } + else + { + InvalidAddress(__FUNCTION__, addr); + *(u8*)GetBaseAddr() = data; + } + } - bool Write8NN(const u64 addr, const u8 data); - bool Write16NN(const u64 addr, const u16 data); - bool Write32NN(const u64 addr, const u32 data); - bool Write64NN(const u64 addr, const u64 data); - bool Write128NN(const u64 addr, const u128 data); + template void Write16(T addr, const u16 data) + { + if ((u32)addr == addr) + { + *(u16*)((u8*)GetBaseAddr() + addr) = re16(data); + } + else + { + InvalidAddress(__FUNCTION__, addr); + *(u16*)GetBaseAddr() = data; + } + } - u8 Read8(const u64 addr); - u16 Read16(const u64 addr); - u32 Read32(const u64 addr); - u64 Read64(const u64 addr); - u128 Read128(const u64 addr); + template void Write32(T addr, const u32 data) + { + if ((u32)addr == addr) + { + if (addr < RAW_SPU_BASE_ADDR || (addr % RAW_SPU_OFFSET) < RAW_SPU_PROB_OFFSET || !RawSPUMem[(addr - RAW_SPU_BASE_ADDR) / RAW_SPU_OFFSET]) + { + *(u32*)((u8*)GetBaseAddr() + addr) = re32(data); + } + else + { + RawSPUMem[(addr - RAW_SPU_BASE_ADDR) / RAW_SPU_OFFSET]->Write32(addr, data); + } + } + else + { + InvalidAddress(__FUNCTION__, addr); + *(u32*)GetBaseAddr() = data; + } + } + + template void Write64(T addr, const u64 data) + { + if ((u32)addr == addr) + { + *(u64*)((u8*)GetBaseAddr() + addr) = re64(data); + } + else + { + InvalidAddress(__FUNCTION__, addr); + *(u64*)GetBaseAddr() = data; + } + } + + template void Write128(T addr, const u128 data) + { + if ((u32)addr == addr) + { + *(u128*)((u8*)GetBaseAddr() + addr) = re128(data); + } + else + { + InvalidAddress(__FUNCTION__, addr); + *(u128*)GetBaseAddr() = data; + } + } + + template u8 Read8(T addr) + { + if ((u32)addr == addr) + { + return *(u8*)((u8*)GetBaseAddr() + addr); + } + else + { + InvalidAddress(__FUNCTION__, addr); + return *(u8*)GetBaseAddr(); + } + } + + template u16 Read16(T addr) + { + if ((u32)addr == addr) + { + return re16(*(u16*)((u8*)GetBaseAddr() + addr)); + } + else + { + InvalidAddress(__FUNCTION__, addr); + return *(u16*)GetBaseAddr(); + } + } + + template u32 Read32(T addr) + { + if ((u32)addr == addr) + { + if (addr < RAW_SPU_BASE_ADDR || (addr % RAW_SPU_OFFSET) < RAW_SPU_PROB_OFFSET || !RawSPUMem[(addr - RAW_SPU_BASE_ADDR) / RAW_SPU_OFFSET]) + { + return re32(*(u32*)((u8*)GetBaseAddr() + addr)); + } + else + { + u32 res; + RawSPUMem[(addr - RAW_SPU_BASE_ADDR) / RAW_SPU_OFFSET]->Read32(addr, &res); + return res; + } + } + else + { + InvalidAddress(__FUNCTION__, addr); + return *(u32*)GetBaseAddr(); + } + } + + template u64 Read64(T addr) + { + if ((u32)addr == addr) + { + return re64(*(u64*)((u8*)GetBaseAddr() + addr)); + } + else + { + InvalidAddress(__FUNCTION__, addr); + return *(u64*)GetBaseAddr(); + } + } + + template u128 Read128(T addr) + { + if ((u32)addr == addr) + { + return re128(*(u128*)((u8*)GetBaseAddr() + addr)); + } + else + { + InvalidAddress(__FUNCTION__, addr); + return *(u128*)GetBaseAddr(); + } + } bool CopyToReal(void* real, u64 from, u32 count) { diff --git a/rpcs3/Emu/SysCalls/Modules/libmixer.cpp b/rpcs3/Emu/SysCalls/Modules/libmixer.cpp index 0685b0e90c..3532fbf1e7 100644 --- a/rpcs3/Emu/SysCalls/Modules/libmixer.cpp +++ b/rpcs3/Emu/SysCalls/Modules/libmixer.cpp @@ -531,7 +531,8 @@ int cellSurMixerStart() int cellSurMixerSetParameter(u32 param, float value) { - libmixer->Error("cellSurMixerSetParameter(param=0x%x, value=%f)", param, value); + declCPU(); + libmixer->Error("cellSurMixerSetParameter(param=0x%x, value=%f, FPR[1]=%f, FPR[2]=%f)", param, value, (float&)CPU.FPR[1], (float&)CPU.FPR[2]); return CELL_OK; } @@ -559,8 +560,7 @@ int cellSurMixerSurBusAddData(u32 busNo, u32 offset, u32 addr, u32 samples) } else { - libmixer->Error("cellSurMixerSurBusAddData(busNo=%d, offset=0x%x, addr=0x%x, samples=%d)", busNo, offset, addr, samples); - Emu.Pause(); + libmixer->Error("cellSurMixerSurBusAddData(busNo=%d, offset=0x%x, addr=0x%x, samples=%d): unknown parameters", busNo, offset, addr, samples); return CELL_OK; } diff --git a/rpcs3/Emu/SysCalls/lv2/sys_timer.cpp b/rpcs3/Emu/SysCalls/lv2/sys_timer.cpp index d1907c0dc7..3aa176e46a 100644 --- a/rpcs3/Emu/SysCalls/lv2/sys_timer.cpp +++ b/rpcs3/Emu/SysCalls/lv2/sys_timer.cpp @@ -109,7 +109,7 @@ s32 sys_timer_sleep(u32 sleep_time) std::this_thread::sleep_for(std::chrono::seconds(1)); if (Emu.IsStopped()) { - sys_timer.Warning("sys_timer_sleep(sleep_time=%d)", sleep_time); + sys_timer.Warning("sys_timer_sleep(sleep_time=%d) aborted", sleep_time); return CELL_OK; } } @@ -125,7 +125,7 @@ s32 sys_timer_usleep(u64 sleep_time) std::this_thread::sleep_for(std::chrono::seconds(1)); if (Emu.IsStopped()) { - sys_timer.Warning("sys_timer_usleep(sleep_time=%lld)", sleep_time); + sys_timer.Warning("sys_timer_usleep(sleep_time=%lld) aborted", sleep_time); return CELL_OK; } } diff --git a/rpcs3/Emu/SysCalls/lv2/sys_tty.cpp b/rpcs3/Emu/SysCalls/lv2/sys_tty.cpp index 630f00a959..073e1a0176 100644 --- a/rpcs3/Emu/SysCalls/lv2/sys_tty.cpp +++ b/rpcs3/Emu/SysCalls/lv2/sys_tty.cpp @@ -9,7 +9,7 @@ s32 sys_tty_read(u32 ch, u64 buf_addr, u32 len, u64 preadlen_addr) { // We currently do not support reading from the Console LOG_WARNING(HLE, "sys_tty_read: ch: %d, buf addr: %llx, len: %d", ch, buf_addr, len); - Memory.Write32NN(preadlen_addr, len); + Memory.Write32(preadlen_addr, len); Emu.Pause(); return CELL_OK;