From ed40732e7b92649270067f57e0b59e7503dae1bf Mon Sep 17 00:00:00 2001 From: Nekotekina Date: Sat, 8 Feb 2014 01:55:25 +0400 Subject: [PATCH] Reservation review Minor changes SC_Event_flag.cpp module detached --- rpcs3/Emu/CPU/CPUThread.h | 34 +------ rpcs3/Emu/Cell/PPUInterpreter.h | 12 ++- rpcs3/Emu/Cell/SPUInterpreter.h | 2 +- rpcs3/Emu/Cell/SPUThread.h | 24 +++-- rpcs3/Emu/SysCalls/SysCalls.h | 19 ++-- rpcs3/Emu/SysCalls/lv2/SC_Event.cpp | 97 ------------------- rpcs3/Emu/SysCalls/lv2/SC_Event_flag.cpp | 115 +++++++++++++++++++++++ rpcs3/Emu/SysCalls/lv2/SC_Event_flag.h | 31 ++++++ rpcs3/Emu/SysCalls/lv2/SC_Heap.cpp | 2 +- rpcs3/Emu/SysCalls/lv2/SC_Lwcond.cpp | 17 ++-- rpcs3/Emu/SysCalls/lv2/SC_Process.cpp | 1 + rpcs3/Emu/SysCalls/lv2/SC_Rwlock.cpp | 1 - rpcs3/Emu/SysCalls/lv2/SC_SPU_Thread.cpp | 6 +- rpcs3/Emu/event.h | 96 ++++++++----------- rpcs3/rpcs3.vcxproj | 1 + rpcs3/rpcs3.vcxproj.filters | 3 + 16 files changed, 244 insertions(+), 217 deletions(-) create mode 100644 rpcs3/Emu/SysCalls/lv2/SC_Event_flag.cpp create mode 100644 rpcs3/Emu/SysCalls/lv2/SC_Event_flag.h diff --git a/rpcs3/Emu/CPU/CPUThread.h b/rpcs3/Emu/CPU/CPUThread.h index 6a8bad0596..b4f2e90b84 100644 --- a/rpcs3/Emu/CPU/CPUThread.h +++ b/rpcs3/Emu/CPU/CPUThread.h @@ -6,39 +6,15 @@ struct reservation_struct { SMutex mutex; // mutex for updating reservation_owner and data - u32 owner; // id of thread that got reservation - u32 addr; - u32 size; - union - { - u32 data32[32]; - u64 data64[16]; - }; + volatile u32 owner; // id of thread that got reservation + volatile u32 addr; + volatile u32 size; __forceinline void clear() { owner = 0; - } - - __forceinline bool compare128(u8* pointer) - { - return - data64[0] == *(u64*)(pointer + 0) && - data64[1] == *(u64*)(pointer + 8) && - data64[2] == *(u64*)(pointer + 16) && - data64[3] == *(u64*)(pointer + 24) && - data64[4] == *(u64*)(pointer + 32) && - data64[5] == *(u64*)(pointer + 40) && - data64[6] == *(u64*)(pointer + 48) && - data64[7] == *(u64*)(pointer + 56) && - data64[8] == *(u64*)(pointer + 64) && - data64[9] == *(u64*)(pointer + 72) && - data64[10] == *(u64*)(pointer + 80) && - data64[11] == *(u64*)(pointer + 88) && - data64[12] == *(u64*)(pointer + 96) && - data64[13] == *(u64*)(pointer + 104) && - data64[14] == *(u64*)(pointer + 112) && - data64[15] == *(u64*)(pointer + 120); + addr = 0; + size = 0; } }; diff --git a/rpcs3/Emu/Cell/PPUInterpreter.h b/rpcs3/Emu/Cell/PPUInterpreter.h index 547fa39b0a..3277b9c446 100644 --- a/rpcs3/Emu/Cell/PPUInterpreter.h +++ b/rpcs3/Emu/Cell/PPUInterpreter.h @@ -2361,13 +2361,14 @@ private: } void LWARX(u32 rd, u32 ra, u32 rb) { + ConLog.Warning("LWARX"); const u64 addr = ra ? CPU.GPR[ra] + CPU.GPR[rb] : CPU.GPR[rb]; SMutexLocker lock(reservation.mutex); reservation.owner = lock.tid; reservation.addr = addr; reservation.size = 4; - reservation.data32[0] = CPU.GPR[rd] = Memory.Read32(addr); + CPU.GPR[rd] = Memory.Read32(addr); } void LDX(u32 rd, u32 ra, u32 rb) { @@ -2537,13 +2538,14 @@ private: } void LDARX(u32 rd, u32 ra, u32 rb) { + ConLog.Warning("LDARX"); const u64 addr = ra ? CPU.GPR[ra] + CPU.GPR[rb] : CPU.GPR[rb]; SMutexLocker lock(reservation.mutex); reservation.owner = lock.tid; reservation.addr = addr; reservation.size = 8; - reservation.data64[0] = CPU.GPR[rd] = Memory.Read64(addr); + CPU.GPR[rd] = Memory.Read64(addr); } void DCBF(u32 ra, u32 rb) { @@ -2656,10 +2658,11 @@ private: } void STWCX_(u32 rs, u32 ra, u32 rb) { + ConLog.Warning("STWCX_"); const u64 addr = ra ? CPU.GPR[ra] + CPU.GPR[rb] : CPU.GPR[rb]; SMutexLocker lock(reservation.mutex); - if (lock.tid == reservation.owner && reservation.addr == addr && reservation.size == 4 && reservation.data32[0] == Memory.Read32(addr)) + if (lock.tid == reservation.owner && reservation.addr == addr && reservation.size == 4) { Memory.Write32(addr, CPU.GPR[rs]); CPU.SetCR_EQ(0, true); @@ -2709,10 +2712,11 @@ private: } void STDCX_(u32 rs, u32 ra, u32 rb) { + ConLog.Warning("STDCX_"); const u64 addr = ra ? CPU.GPR[ra] + CPU.GPR[rb] : CPU.GPR[rb]; SMutexLocker lock(reservation.mutex); - if (lock.tid == reservation.owner && reservation.addr == addr && reservation.size == 8 && reservation.data64[0] == Memory.Read64(addr)) + if (lock.tid == reservation.owner && reservation.addr == addr && reservation.size == 8) { Memory.Write64(addr, CPU.GPR[rs]); CPU.SetCR_EQ(0, true); diff --git a/rpcs3/Emu/Cell/SPUInterpreter.h b/rpcs3/Emu/Cell/SPUInterpreter.h index cff281c03b..63d67deb2d 100644 --- a/rpcs3/Emu/Cell/SPUInterpreter.h +++ b/rpcs3/Emu/Cell/SPUInterpreter.h @@ -32,7 +32,7 @@ private: //0 - 10 void STOP(u32 code) { - ConLog.Warning("STOP: 0x%x (exit_status -> 0)", code); + ConLog.Warning("STOP: 0x%x (m_exit_status -> 0)", code); CPU.SetExitStatus(0); CPU.Stop(); } diff --git a/rpcs3/Emu/Cell/SPUThread.h b/rpcs3/Emu/Cell/SPUThread.h index 7ca5771b15..e4cd1ea0e6 100644 --- a/rpcs3/Emu/Cell/SPUThread.h +++ b/rpcs3/Emu/Cell/SPUThread.h @@ -389,7 +389,7 @@ public: else { #ifdef _M_X64 - _InterlockedOr64((volatile __int64*)m_indval, ((u64)value << 32) | 1); + InterlockedOr64((volatile __int64*)m_indval, ((u64)value << 32) | 1); #else ConLog.Error("PushUncond_OR(): no code compiled"); #endif @@ -519,7 +519,20 @@ public: op & MFC_BARRIER_MASK ? "B" : "", op & MFC_FENCE_MASK ? "F" : "", lsa, ea, tag, size, cmd); */ - MFCArgs.CMDStatus.SetValue(dmac.Cmd(cmd, tag, lsa, ea, size)); + if (op & MFC_PUT_CMD) + { + SMutexLocker lock(reservation.mutex); + MFCArgs.CMDStatus.SetValue(dmac.Cmd(cmd, tag, lsa, ea, size)); + if ((reservation.addr + reservation.size > ea && reservation.addr <= ea + size) || + (ea + size > reservation.addr && ea <= reservation.addr + reservation.size)) + { + reservation.clear(); + } + } + else + { + MFCArgs.CMDStatus.SetValue(dmac.Cmd(cmd, tag, lsa, ea, size)); + } } break; @@ -528,9 +541,9 @@ public: case MFC_PUTLLUC_CMD: case MFC_PUTQLLUC_CMD: { - /* if (enable_log) ConLog.Write("DMA %s: lsa=0x%x, ea = 0x%llx, (tag) = 0x%x, (size) = 0x%x, cmd = 0x%x", + if (enable_log) ConLog.Write("DMA %s: lsa=0x%x, ea = 0x%llx, (tag) = 0x%x, (size) = 0x%x, cmd = 0x%x", op == MFC_GETLLAR_CMD ? "GETLLAR" : op == MFC_PUTLLC_CMD ? "PUTLLC" : op == MFC_PUTLLUC_CMD ? "PUTLLUC" : "PUTQLLUC", - lsa, ea, tag, size, cmd); */ + lsa, ea, tag, size, cmd); if (op == MFC_GETLLAR_CMD) // get reservation { @@ -539,7 +552,6 @@ public: reservation.addr = ea; reservation.size = 128; dmac.ProcessCmd(MFC_GET_CMD, tag, lsa, ea, 128); - memcpy(&reservation.data64[0], Memory + ea, 128); Prxy.AtomicStat.PushUncond(MFC_GETLLAR_SUCCESS); } else if (op == MFC_PUTLLC_CMD) // store conditional @@ -547,7 +559,7 @@ public: SMutexLocker lock(reservation.mutex); if (reservation.owner == lock.tid) // succeeded { - if (reservation.addr == ea && reservation.size == 128 && reservation.compare128(Memory + ea)) + if (reservation.addr == ea && reservation.size == 128) { dmac.ProcessCmd(MFC_PUT_CMD, tag, lsa, ea, 128); Prxy.AtomicStat.PushUncond(MFC_PUTLLC_SUCCESS); diff --git a/rpcs3/Emu/SysCalls/SysCalls.h b/rpcs3/Emu/SysCalls/SysCalls.h index c7666d93bb..4797f57270 100644 --- a/rpcs3/Emu/SysCalls/SysCalls.h +++ b/rpcs3/Emu/SysCalls/SysCalls.h @@ -7,6 +7,7 @@ #include "lv2/SC_SPU_Thread.h" #include "lv2/SC_Lwmutex.h" #include "lv2/SC_Lwcond.h" +#include "lv2/SC_Event_flag.h" #include "Emu/event.h" //#define SYSCALLS_DEBUG @@ -126,14 +127,6 @@ extern int sys_game_process_exitspawn(u32 path_addr, u32 argv_addr, u32 envp_add u32 data, u32 data_size, int prio, u64 flags ); //sys_event -extern int sys_event_flag_create(u32 eflag_id_addr, u32 attr_addr, u64 init); -extern int sys_event_flag_destroy(u32 eflag_id); -extern int sys_event_flag_wait(u32 eflag_id, u64 bitptn, u32 mode, u32 result_addr, u32 timeout); -extern int sys_event_flag_trywait(u32 eflag_id, u64 bitptn, u32 mode, u32 result_addr); -extern int sys_event_flag_set(u32 eflag_id, u64 bitptn); -extern int sys_event_flag_clear(u32 eflag_id, u64 bitptn); -extern int sys_event_flag_cancel(u32 eflag_id, u32 num_addr); -extern int sys_event_flag_get(u32 eflag_id, u32 flag_addr); extern int sys_event_queue_create(u32 equeue_id_addr, u32 attr_addr, u64 event_queue_key, int size); extern int sys_event_queue_receive(u32 equeue_id, u32 event_addr, u32 timeout); extern int sys_event_port_create(u32 eport_id_addr, int port_type, u64 name); @@ -141,6 +134,16 @@ extern int sys_event_port_connect_local(u32 event_port_id, u32 event_queue_id); extern int sys_event_port_send(u32 event_port_id, u64 data1, u64 data2, u64 data3); extern int sys_event_queue_drain(u32 event_queue_id); +//sys_event_flag +extern int sys_event_flag_create(mem32_t eflag_id, mem_ptr_t attr, u64 init); +extern int sys_event_flag_destroy(u32 eflag_id); +extern int sys_event_flag_wait(u32 eflag_id, u64 bitptn, u32 mode, mem64_t result, u32 timeout); +extern int sys_event_flag_trywait(u32 eflag_id, u64 bitptn, u32 mode, mem64_t result); +extern int sys_event_flag_set(u32 eflag_id, u64 bitptn); +extern int sys_event_flag_clear(u32 eflag_id, u64 bitptn); +extern int sys_event_flag_cancel(u32 eflag_id, mem32_t num); +extern int sys_event_flag_get(u32 eflag_id, mem64_t flags); + //sys_semaphore extern int sys_semaphore_create(u32 sem_addr, u32 attr_addr, int initial_val, int max_val); extern int sys_semaphore_destroy(u32 sem); diff --git a/rpcs3/Emu/SysCalls/lv2/SC_Event.cpp b/rpcs3/Emu/SysCalls/lv2/SC_Event.cpp index 1455882cf2..be08331641 100644 --- a/rpcs3/Emu/SysCalls/lv2/SC_Event.cpp +++ b/rpcs3/Emu/SysCalls/lv2/SC_Event.cpp @@ -5,103 +5,6 @@ SysCallBase sys_event("sys_event"); -int sys_event_flag_create(u32 eflag_id_addr, u32 attr_addr, u64 init) -{ - sys_event.Warning("sys_event_flag_create(eflag_id_addr=0x%x, attr_addr=0x%x, init=0x%llx)", eflag_id_addr, attr_addr, init); - - if(!Memory.IsGoodAddr(eflag_id_addr, 4) || !Memory.IsGoodAddr(attr_addr, sizeof(sys_event_flag_attr))) - { - return CELL_EFAULT; - } - - sys_event_flag_attr attr = (sys_event_flag_attr&)Memory[attr_addr]; - attr.protocol = re(attr.protocol); - attr.pshared = re(attr.pshared); - attr.ipc_key = re(attr.ipc_key); - attr.flags = re(attr.flags); - attr.type = re(attr.type); - - sys_event.Warning("name = %s", attr.name); - sys_event.Warning("type = %d", attr.type); - - Memory.Write32(eflag_id_addr, sys_event.GetNewId(new event_flag(init, attr))); - - return CELL_OK; -} - -int sys_event_flag_destroy(u32 eflag_id) -{ - sys_event.Warning("sys_event_flag_destroy(eflag_id=0x%x)", eflag_id); - - if(!sys_event.CheckId(eflag_id)) return CELL_ESRCH; - - Emu.GetIdManager().RemoveID(eflag_id); - - return CELL_OK; -} - -int sys_event_flag_wait(u32 eflag_id, u64 bitptn, u32 mode, u32 result_addr, u32 timeout) -{ - sys_event.Warning("Unimplemented function: sys_event_flag_wait(eflag_id=0x%x, bitptn=0x%llx, mode=0x%x, result_addr=0x%x, timeout=0x%x)" - , eflag_id, bitptn, mode, result_addr, timeout); - return CELL_OK; -} - -int sys_event_flag_trywait(u32 eflag_id, u64 bitptn, u32 mode, u32 result_addr) -{ - sys_event.Warning("Unimplemented function: sys_event_flag_trywait(eflag_id=0x%x, bitptn=0x%llx, mode=0x%x, result_addr=0x%x)" - , eflag_id, bitptn, mode, result_addr); - return CELL_OK; -} - -int sys_event_flag_set(u32 eflag_id, u64 bitptn) -{ - sys_event.Warning("sys_event_flag_set(eflag_id=0x%x, bitptn=0x%llx)", eflag_id, bitptn); - - event_flag* event_flag_data = nullptr; - if(!sys_event.CheckId(eflag_id, event_flag_data)) return CELL_ESRCH; - - event_flag_data->pattern |= bitptn; - - return CELL_OK; -} - -int sys_event_flag_clear(u32 eflag_id, u64 bitptn) -{ - sys_event.Warning("sys_event_flag_clear(eflag_id=0x%x, bitptn=0x%llx)", eflag_id, bitptn); - - event_flag* event_flag_data = nullptr; - if(!sys_event.CheckId(eflag_id, event_flag_data)) return CELL_ESRCH; - - event_flag_data->pattern &= bitptn; - - return CELL_OK; -} - -int sys_event_flag_cancel(u32 eflag_id, u32 num_addr) -{ - sys_event.Warning("Unimplemented function: sys_event_flag_cancel(eflag_id=0x%x, num_addr=0x%x)" - , eflag_id, num_addr); - return CELL_OK; -} - -int sys_event_flag_get(u32 eflag_id, u32 flag_addr) -{ - sys_event.Warning("sys_event_flag_get(eflag_id=0x%x, flag_addr=0x%x)", eflag_id, flag_addr); - - if(!Memory.IsGoodAddr(flag_addr, 4)) - { - return CELL_EFAULT; - } - - event_flag* event_flag_data = nullptr; - if(!sys_event.CheckId(eflag_id, event_flag_data)) return CELL_ESRCH; - - Memory.Write64(flag_addr, event_flag_data->pattern); - - return CELL_OK; -} - //128 int sys_event_queue_create(u32 equeue_id_addr, u32 attr_addr, u64 event_queue_key, int size) { diff --git a/rpcs3/Emu/SysCalls/lv2/SC_Event_flag.cpp b/rpcs3/Emu/SysCalls/lv2/SC_Event_flag.cpp new file mode 100644 index 0000000000..607d21aae2 --- /dev/null +++ b/rpcs3/Emu/SysCalls/lv2/SC_Event_flag.cpp @@ -0,0 +1,115 @@ +#include "stdafx.h" +#include "Emu/SysCalls/SysCalls.h" +#include "Emu/SysCalls/lv2/SC_Event_flag.h" + +SysCallBase sys_event_flag("sys_event_flag"); + +int sys_event_flag_create(mem32_t eflag_id, mem_ptr_t attr, u64 init) +{ + sys_event_flag.Warning("sys_event_flag_create(eflag_id_addr=0x%x, attr_addr=0x%x, init=0x%llx)", eflag_id.GetAddr(), attr.GetAddr(), init); + + if(!eflag_id.IsGood() || !attr.IsGood()) + { + return CELL_EFAULT; + } + + switch (attr->protocol.ToBE()) + { + case se32(SYS_SYNC_PRIORITY): sys_event_flag.Warning("TODO: SYS_SYNC_PRIORITY attr"); break; + case se32(SYS_SYNC_RETRY): break; + case se32(SYS_SYNC_PRIORITY_INHERIT): sys_event_flag.Warning("TODO: SYS_SYNC_PRIORITY_INHERIT attr"); break; + case se32(SYS_SYNC_FIFO): sys_event_flag.Warning("TODO: SYS_SYNC_FIFO attr"); break; + default: return CELL_EINVAL; + } + + if (attr->pshared.ToBE() != se32(0x200)) + { + return CELL_EINVAL; + } + + switch (attr->type.ToBE()) + { + case se32(SYS_SYNC_WAITER_SINGLE): sys_event_flag.Warning("TODO: SYS_SYNC_WAITER_SINGLE type"); break; + case se32(SYS_SYNC_WAITER_MULTIPLE): sys_event_flag.Warning("TODO: SYS_SYNC_WAITER_MULTIPLE type"); break; + default: return CELL_EINVAL; + } + + eflag_id = sys_event_flag.GetNewId(new event_flag(init, (u32)attr->protocol, (int)attr->type)); + + sys_event_flag.Warning("*** event_flag created[%s] (protocol=%d, type=%d): id = %d", attr->name, (u32)attr->protocol, (int)attr->type, eflag_id.GetValue()); + + return CELL_OK; +} + +int sys_event_flag_destroy(u32 eflag_id) +{ + sys_event_flag.Warning("sys_event_flag_destroy(eflag_id=0x%x)", eflag_id); + + event_flag* ef; + if(!sys_event_flag.CheckId(eflag_id, ef)) return CELL_ESRCH; + + Emu.GetIdManager().RemoveID(eflag_id); + + return CELL_OK; +} + +int sys_event_flag_wait(u32 eflag_id, u64 bitptn, u32 mode, mem64_t result, u32 timeout) +{ + sys_event_flag.Error("sys_event_flag_wait(eflag_id=0x%x, bitptn=0x%llx, mode=0x%x, result_addr=0x%x, timeout=0x%x)", + eflag_id, bitptn, mode, result.GetAddr(), timeout); + return CELL_OK; +} + +int sys_event_flag_trywait(u32 eflag_id, u64 bitptn, u32 mode, mem64_t result) +{ + sys_event_flag.Error("sys_event_flag_trywait(eflag_id=0x%x, bitptn=0x%llx, mode=0x%x, result_addr=0x%x)", + eflag_id, bitptn, mode, result.GetAddr()); + return CELL_OK; +} + +int sys_event_flag_set(u32 eflag_id, u64 bitptn) +{ + sys_event_flag.Warning("sys_event_flag_set(eflag_id=0x%x, bitptn=0x%llx)", eflag_id, bitptn); + + event_flag* ef; + if(!sys_event_flag.CheckId(eflag_id, ef)) return CELL_ESRCH; + + ef->flags |= bitptn; + + return CELL_OK; +} + +int sys_event_flag_clear(u32 eflag_id, u64 bitptn) +{ + sys_event_flag.Warning("sys_event_flag_clear(eflag_id=0x%x, bitptn=0x%llx)", eflag_id, bitptn); + + event_flag* ef; + if(!sys_event_flag.CheckId(eflag_id, ef)) return CELL_ESRCH; + + ef->flags &= bitptn; + + return CELL_OK; +} + +int sys_event_flag_cancel(u32 eflag_id, mem32_t num) +{ + sys_event_flag.Error("sys_event_flag_cancel(eflag_id=0x%x, num_addr=0x%x)", eflag_id, num.GetAddr()); + return CELL_OK; +} + +int sys_event_flag_get(u32 eflag_id, mem64_t flags) +{ + sys_event_flag.Warning("sys_event_flag_get(eflag_id=0x%x, flags_addr=0x%x)", eflag_id, flags.GetAddr()); + + if (!flags.IsGood()) + { + return CELL_EFAULT; + } + + event_flag* ef; + if(!sys_event_flag.CheckId(eflag_id, ef)) return CELL_ESRCH; + + flags = ef->flags; + + return CELL_OK; +} \ No newline at end of file diff --git a/rpcs3/Emu/SysCalls/lv2/SC_Event_flag.h b/rpcs3/Emu/SysCalls/lv2/SC_Event_flag.h new file mode 100644 index 0000000000..80983e6a6d --- /dev/null +++ b/rpcs3/Emu/SysCalls/lv2/SC_Event_flag.h @@ -0,0 +1,31 @@ +#pragma once + +enum +{ + SYS_SYNC_WAITER_SINGLE = 0x10000, + SYS_SYNC_WAITER_MULTIPLE = 0x20000, +}; + +struct sys_event_flag_attr +{ + be_t protocol; + be_t pshared; + be_t ipc_key; + be_t flags; + be_t type; + char name[8]; +}; + +struct event_flag +{ + std::atomic flags; + const u32 m_protocol; + const int m_type; + + event_flag(u64 pattern, u32 protocol, int type) + : flags(pattern) + , m_protocol(protocol) + , m_type(type) + { + } +}; \ No newline at end of file diff --git a/rpcs3/Emu/SysCalls/lv2/SC_Heap.cpp b/rpcs3/Emu/SysCalls/lv2/SC_Heap.cpp index 8899c3658f..eff04fb5cc 100644 --- a/rpcs3/Emu/SysCalls/lv2/SC_Heap.cpp +++ b/rpcs3/Emu/SysCalls/lv2/SC_Heap.cpp @@ -33,7 +33,7 @@ int sys_heap_malloc(const u32 heap_id, const u32 size) HeapInfo* heap; if(!sc_heap.CheckId(heap_id, heap)) return CELL_ESRCH; - return Memory.Alloc(size, heap->align); + return Memory.Alloc(size, 1); } int _sys_heap_memalign(u32 heap_id, u32 align, u32 size, u64 p4) diff --git a/rpcs3/Emu/SysCalls/lv2/SC_Lwcond.cpp b/rpcs3/Emu/SysCalls/lv2/SC_Lwcond.cpp index 9ab3eb73c1..9dbcef51e6 100644 --- a/rpcs3/Emu/SysCalls/lv2/SC_Lwcond.cpp +++ b/rpcs3/Emu/SysCalls/lv2/SC_Lwcond.cpp @@ -12,20 +12,19 @@ int sys_lwcond_create(mem_ptr_t lwcond, mem_ptr_t l if (!lwcond.IsGood() || !lwmutex.IsGood() || !attr.IsGood()) return CELL_EFAULT; - u32 protocol = (u32)lwmutex->attribute & SYS_SYNC_ATTR_PROTOCOL_MASK; - switch (protocol) + switch (lwmutex->attribute.ToBE()) { - case SYS_SYNC_PRIORITY: break; - case SYS_SYNC_RETRY: sys_lwcond.Error("Invalid SYS_SYNC_RETRY attr"); break; - case SYS_SYNC_PRIORITY_INHERIT: sys_lwcond.Warning("TODO: SYS_SYNC_PRIORITY_INHERIT attr"); break; - case SYS_SYNC_FIFO: break; - default: sys_lwcond.Error("Invalid lwmutex protocol(%d)", protocol); break; + case se32(SYS_SYNC_PRIORITY): break; + case se32(SYS_SYNC_RETRY): sys_lwcond.Error("Invalid SYS_SYNC_RETRY attr"); break; + case se32(SYS_SYNC_PRIORITY_INHERIT): sys_lwcond.Warning("TODO: SYS_SYNC_PRIORITY_INHERIT attr"); break; + case se32(SYS_SYNC_FIFO): break; + default: sys_lwcond.Error("Invalid lwmutex protocol(%d)", (u32)lwmutex->attribute); break; } lwcond->lwmutex_addr = lwmutex.GetAddr(); - lwcond->lwcond_queue = sys_lwcond.GetNewId(new LWCond(protocol, *(u64*)&attr->name)); + lwcond->lwcond_queue = sys_lwcond.GetNewId(new LWCond((u32)lwmutex->attribute, *(u64*)&attr->name)); - sys_lwcond.Warning("*** lwcond created [%s] (protocol=0x%x): id=%d", attr->name, protocol, (u32)lwcond->lwcond_queue); + sys_lwcond.Warning("*** lwcond created [%s] (protocol=0x%x): id=%d", attr->name, (u32)lwmutex->attribute, (u32)lwcond->lwcond_queue); return CELL_OK; } diff --git a/rpcs3/Emu/SysCalls/lv2/SC_Process.cpp b/rpcs3/Emu/SysCalls/lv2/SC_Process.cpp index 46627882d8..7e4ddd320c 100644 --- a/rpcs3/Emu/SysCalls/lv2/SC_Process.cpp +++ b/rpcs3/Emu/SysCalls/lv2/SC_Process.cpp @@ -41,6 +41,7 @@ int sys_process_exit(int errorcode) { sc_p.Warning("sys_process_exit(%d)", errorcode); Emu.Pause(); // Emu.Stop() does crash + ConLog.Success("Process finished"); return CELL_OK; } diff --git a/rpcs3/Emu/SysCalls/lv2/SC_Rwlock.cpp b/rpcs3/Emu/SysCalls/lv2/SC_Rwlock.cpp index acd930bb45..c86afcd372 100644 --- a/rpcs3/Emu/SysCalls/lv2/SC_Rwlock.cpp +++ b/rpcs3/Emu/SysCalls/lv2/SC_Rwlock.cpp @@ -21,7 +21,6 @@ int sys_rwlock_create(mem32_t rw_lock_id, mem_ptr_t attr if (attr->attr_pshared.ToBE() != se32(0x200)) { - sys_rwlock.Error("Invalid attr_pshared(0x%x)", (u32)attr->attr_pshared); return CELL_EINVAL; } diff --git a/rpcs3/Emu/SysCalls/lv2/SC_SPU_Thread.cpp b/rpcs3/Emu/SysCalls/lv2/SC_SPU_Thread.cpp index 5800beb13c..cf2e6e4a29 100644 --- a/rpcs3/Emu/SysCalls/lv2/SC_SPU_Thread.cpp +++ b/rpcs3/Emu/SysCalls/lv2/SC_SPU_Thread.cpp @@ -194,12 +194,14 @@ int sys_spu_thread_get_exit_status(u32 id, mem32_t status) return CELL_ESRCH; } - if (!thr->IsStopped()) // (!!!) if SPU thread doesn't have exit status + if (!(*(SPUThread*)thr).SPU.Out_MBox.GetCount() || !thr->IsStopped()) { return CELL_ESTAT; } - status = thr->GetExitStatus(); + u32 res; + (*(SPUThread*)thr).SPU.Out_MBox.PopUncond(res); + status = res; return CELL_OK; } diff --git a/rpcs3/Emu/event.h b/rpcs3/Emu/event.h index 8c5d94c360..4cf5472f6b 100644 --- a/rpcs3/Emu/event.h +++ b/rpcs3/Emu/event.h @@ -1,61 +1,39 @@ -#pragma once - -struct sys_event_flag_attr -{ - u32 protocol; - u32 pshared; - u64 ipc_key; - int flags; +#pragma once + +struct sys_event_queue_attr +{ + u32 attr_protocol; int type; - char name[8]; -}; - -struct event_flag -{ - sys_event_flag_attr attr; - u64 pattern; - - event_flag(u64 pattern, sys_event_flag_attr attr) - : pattern(pattern) - , attr(attr) - { - } -}; - -struct sys_event_queue_attr -{ - u32 attr_protocol; - int type; - char name[8]; -}; - -struct sys_event_data -{ - u64 source; - u64 data1; - u64 data2; - u64 data3; -}; - -struct EventQueue; - -struct EventPort -{ - u64 name; - u64 data1; - u64 data2; - u64 data3; - bool has_data; - CPUThread* thread; - EventQueue* queue[127]; - int pos; -}; - -struct EventQueue -{ - EventPort* ports[127]; - int size; - int pos; - int type; - char name[8]; + char name[8]; +}; + +struct sys_event_data +{ + u64 source; + u64 data1; + u64 data2; + u64 data3; +}; + +struct EventQueue; + +struct EventPort +{ + u64 name; + u64 data1; + u64 data2; + u64 data3; + bool has_data; + CPUThread* thread; + EventQueue* queue[127]; + int pos; +}; + +struct EventQueue +{ + EventPort* ports[127]; + int size; + int pos; + int type; + char name[8]; }; \ No newline at end of file diff --git a/rpcs3/rpcs3.vcxproj b/rpcs3/rpcs3.vcxproj index a1508186ac..7fa98fa362 100644 --- a/rpcs3/rpcs3.vcxproj +++ b/rpcs3/rpcs3.vcxproj @@ -248,6 +248,7 @@ + diff --git a/rpcs3/rpcs3.vcxproj.filters b/rpcs3/rpcs3.vcxproj.filters index 81d08d002f..302473ead6 100644 --- a/rpcs3/rpcs3.vcxproj.filters +++ b/rpcs3/rpcs3.vcxproj.filters @@ -382,6 +382,9 @@ Utilities + + Emu\SysCalls\lv2 +