diff --git a/rpcs3/Emu/Cell/Modules/cellSync2.cpp b/rpcs3/Emu/Cell/Modules/cellSync2.cpp index c1bb519fb7..8b0bf58ad1 100644 --- a/rpcs3/Emu/Cell/Modules/cellSync2.cpp +++ b/rpcs3/Emu/Cell/Modules/cellSync2.cpp @@ -15,10 +15,38 @@ vm::gvar gCellSync2NotifierPpuFiber; vm::gvar gCellSync2NotifierSpursTask; vm::gvar gCellSync2NotifierSpursJobQueueJob; -s32 _cellSync2MutexAttributeInitialize(vm::ptr attr, u32 sdkVersion) +template<> +void fmt_class_string::format(std::string& out, u64 arg) +{ + format_enum(out, arg, [](auto error) + { + switch (error) + { + STR_CASE(CELL_SYNC2_ERROR_AGAIN); + STR_CASE(CELL_SYNC2_ERROR_INVAL); + STR_CASE(CELL_SYNC2_ERROR_NOMEM); + STR_CASE(CELL_SYNC2_ERROR_DEADLK); + STR_CASE(CELL_SYNC2_ERROR_PERM); + STR_CASE(CELL_SYNC2_ERROR_BUSY); + STR_CASE(CELL_SYNC2_ERROR_STAT); + STR_CASE(CELL_SYNC2_ERROR_ALIGN); + STR_CASE(CELL_SYNC2_ERROR_NULL_POINTER); + STR_CASE(CELL_SYNC2_ERROR_NOT_SUPPORTED_THREAD); + STR_CASE(CELL_SYNC2_ERROR_NO_NOTIFIER); + STR_CASE(CELL_SYNC2_ERROR_NO_SPU_CONTEXT_STORAGE); + } + + return unknown; + }); +} + +error_code _cellSync2MutexAttributeInitialize(vm::ptr attr, u32 sdkVersion) { cellSync2.warning("_cellSync2MutexAttributeInitialize(attr=*0x%x, sdkVersion=0x%x)", attr, sdkVersion); + if (!attr) + return CELL_SYNC2_ERROR_NULL_POINTER; + attr->sdkVersion = sdkVersion; attr->threadTypes = CELL_SYNC2_THREAD_TYPE_PPU_THREAD | CELL_SYNC2_THREAD_TYPE_PPU_FIBER | CELL_SYNC2_THREAD_TYPE_SPURS_TASK | CELL_SYNC2_THREAD_TYPE_SPURS_JOB | @@ -30,50 +58,82 @@ s32 _cellSync2MutexAttributeInitialize(vm::ptr attr, u3 return CELL_OK; } -s32 cellSync2MutexEstimateBufferSize(vm::cptr attr, vm::ptr bufferSize) +error_code cellSync2MutexEstimateBufferSize(vm::cptr attr, vm::ptr bufferSize) { cellSync2.todo("cellSync2MutexEstimateBufferSize(attr=*0x%x, bufferSize=*0x%x)", attr, bufferSize); - if (attr->maxWaiters > 32768) + if (!attr || !bufferSize) + return CELL_SYNC2_ERROR_NULL_POINTER; + + if (attr->maxWaiters > 0x8000) return CELL_SYNC2_ERROR_INVAL; return CELL_OK; } -s32 cellSync2MutexInitialize() +error_code cellSync2MutexInitialize(vm::ptr mutex, vm::ptr buffer, vm::cptr attr) { - UNIMPLEMENTED_FUNC(cellSync2); + cellSync2.todo("cellSync2MutexInitialize(mutex=*0x%x, buffer=*0x%x, attr=*0x%x)", mutex, buffer, attr); + + if (!mutex || !attr) + return CELL_SYNC2_ERROR_NULL_POINTER; + + if ((attr->maxWaiters > 0) && !buffer) + return CELL_SYNC2_ERROR_NULL_POINTER; + + if (attr->maxWaiters > 0x8000) + return CELL_SYNC2_ERROR_INVAL; + return CELL_OK; } -s32 cellSync2MutexFinalize() +error_code cellSync2MutexFinalize(vm::ptr mutex) { - UNIMPLEMENTED_FUNC(cellSync2); + cellSync2.todo("cellSync2MutexFinalize(mutex=*0x%x)", mutex); + + if (!mutex) + return CELL_SYNC2_ERROR_NULL_POINTER; + return CELL_OK; } -s32 cellSync2MutexLock() +error_code cellSync2MutexLock(vm::ptr mutex, vm::cptr config) { - UNIMPLEMENTED_FUNC(cellSync2); + cellSync2.todo("cellSync2MutexLock(mutex=*0x%x, config=*0x%x)", mutex, config); + + if (!mutex) + return CELL_SYNC2_ERROR_NULL_POINTER; + return CELL_OK; } -s32 cellSync2MutexTryLock() +error_code cellSync2MutexTryLock(vm::ptr mutex, vm::cptr config) { - UNIMPLEMENTED_FUNC(cellSync2); + cellSync2.todo("cellSync2MutexTryLock(mutex=*0x%x, config=*0x%x)", mutex, config); + + if (!mutex) + return CELL_SYNC2_ERROR_NULL_POINTER; + return CELL_OK; } -s32 cellSync2MutexUnlock() +error_code cellSync2MutexUnlock(vm::ptr mutex, vm::cptr config) { - UNIMPLEMENTED_FUNC(cellSync2); + cellSync2.todo("cellSync2MutexUnlock(mutex=*0x%x, config=*0x%x)", mutex, config); + + if (!mutex) + return CELL_SYNC2_ERROR_NULL_POINTER; + return CELL_OK; } -s32 _cellSync2CondAttributeInitialize(vm::ptr attr, u32 sdkVersion) +error_code _cellSync2CondAttributeInitialize(vm::ptr attr, u32 sdkVersion) { cellSync2.warning("_cellSync2CondAttributeInitialize(attr=*0x%x, sdkVersion=0x%x)", attr, sdkVersion); + if (!attr) + return CELL_SYNC2_ERROR_NULL_POINTER; + attr->sdkVersion = sdkVersion; attr->maxWaiters = 15; strcpy_trunc(attr->name, "CellSync2Cond"); @@ -81,50 +141,79 @@ s32 _cellSync2CondAttributeInitialize(vm::ptr attr, u32 return CELL_OK; } -s32 cellSync2CondEstimateBufferSize(vm::cptr attr, vm::ptr bufferSize) +error_code cellSync2CondEstimateBufferSize(vm::cptr attr, vm::ptr bufferSize) { cellSync2.todo("cellSync2CondEstimateBufferSize(attr=*0x%x, bufferSize=*0x%x)", attr, bufferSize); - if (attr->maxWaiters == 0 || attr->maxWaiters > 32768) + if (!attr || !bufferSize) + return CELL_SYNC2_ERROR_NULL_POINTER; + + if (attr->maxWaiters == 0 || attr->maxWaiters > 0x8000) return CELL_SYNC2_ERROR_INVAL; return CELL_OK; } -s32 cellSync2CondInitialize() +error_code cellSync2CondInitialize(vm::ptr cond, vm::ptr mutex, vm::ptr buffer, vm::cptr attr) { - UNIMPLEMENTED_FUNC(cellSync2); + cellSync2.todo("cellSync2CondInitialize(cond=*0x%x, mutex=*0x%x, buffer=*0x%x, attr=*0x%x)", cond, mutex, buffer, attr); + + if (!cond || !mutex || !buffer || !attr) + return CELL_SYNC2_ERROR_NULL_POINTER; + + if (attr->maxWaiters == 0) + return CELL_SYNC2_ERROR_INVAL; + return CELL_OK; } -s32 cellSync2CondFinalize() +error_code cellSync2CondFinalize(vm::ptr cond) { - UNIMPLEMENTED_FUNC(cellSync2); + cellSync2.todo("cellSync2CondFinalize(cond=*0x%x)", cond); + + if (!cond) + return CELL_SYNC2_ERROR_NULL_POINTER; + return CELL_OK; } -s32 cellSync2CondWait() +error_code cellSync2CondWait(vm::ptr cond, vm::cptr config) { - UNIMPLEMENTED_FUNC(cellSync2); + cellSync2.todo("cellSync2CondWait(cond=*0x%x, config=*0x%x)", cond, config); + + if (!cond) + return CELL_SYNC2_ERROR_NULL_POINTER; + return CELL_OK; } -s32 cellSync2CondSignal() +error_code cellSync2CondSignal(vm::ptr cond, vm::cptr config) { - UNIMPLEMENTED_FUNC(cellSync2); + cellSync2.todo("cellSync2CondSignal(cond=*0x%x, config=*0x%x)", cond, config); + + if (!cond) + return CELL_SYNC2_ERROR_NULL_POINTER; + return CELL_OK; } -s32 cellSync2CondSignalAll() +error_code cellSync2CondSignalAll(vm::ptr cond, vm::cptr config) { - UNIMPLEMENTED_FUNC(cellSync2); + cellSync2.todo("cellSync2CondSignalAll(cond=*0x%x, config=*0x%x)", cond, config); + + if (!cond) + return CELL_SYNC2_ERROR_NULL_POINTER; + return CELL_OK; } -s32 _cellSync2SemaphoreAttributeInitialize(vm::ptr attr, u32 sdkVersion) +error_code _cellSync2SemaphoreAttributeInitialize(vm::ptr attr, u32 sdkVersion) { cellSync2.warning("_cellSync2SemaphoreAttributeInitialize(attr=*0x%x, sdkVersion=0x%x)", attr, sdkVersion); + if (!attr) + return CELL_SYNC2_ERROR_NULL_POINTER; + attr->sdkVersion = sdkVersion; attr->threadTypes = CELL_SYNC2_THREAD_TYPE_PPU_THREAD | CELL_SYNC2_THREAD_TYPE_PPU_FIBER | CELL_SYNC2_THREAD_TYPE_SPURS_TASK | CELL_SYNC2_THREAD_TYPE_SPURS_JOB | @@ -135,56 +224,98 @@ s32 _cellSync2SemaphoreAttributeInitialize(vm::ptr return CELL_OK; } -s32 cellSync2SemaphoreEstimateBufferSize(vm::cptr attr, vm::ptr bufferSize) +error_code cellSync2SemaphoreEstimateBufferSize(vm::cptr attr, vm::ptr bufferSize) { cellSync2.todo("cellSync2SemaphoreEstimateBufferSize(attr=*0x%x, bufferSize=*0x%x)", attr, bufferSize); - if (attr->maxWaiters == 0 || attr->maxWaiters > 32768) + if (!attr || !bufferSize) + return CELL_SYNC2_ERROR_NULL_POINTER; + + if (attr->maxWaiters == 0 || attr->maxWaiters > 0x8000) return CELL_SYNC2_ERROR_INVAL; return CELL_OK; } -s32 cellSync2SemaphoreInitialize() +error_code cellSync2SemaphoreInitialize(vm::ptr semaphore, vm::ptr buffer, s32 initialValue, vm::cptr attr) { - UNIMPLEMENTED_FUNC(cellSync2); + cellSync2.todo("cellSync2SemaphoreInitialize(semaphore=*0x%x, buffer=*0x%x, initialValue=0x%x, attr=*0x%x)", semaphore, buffer, initialValue, attr); + + if (!semaphore || !attr || ((attr->maxWaiters >= 2) && !buffer)) + return CELL_SYNC2_ERROR_NULL_POINTER; + + if ((initialValue > s32{0x7FFFFF}) || (initialValue < s32{-0x800000}) || (attr->maxWaiters == 0) || ((attr->maxWaiters == 1) && buffer)) + return CELL_SYNC2_ERROR_INVAL; + return CELL_OK; } -s32 cellSync2SemaphoreFinalize() +error_code cellSync2SemaphoreFinalize(vm::ptr semaphore) { - UNIMPLEMENTED_FUNC(cellSync2); + cellSync2.todo("cellSync2SemaphoreFinalize(semaphore=*0x%x)", semaphore); + + if (!semaphore) + return CELL_SYNC2_ERROR_NULL_POINTER; + return CELL_OK; } -s32 cellSync2SemaphoreAcquire() +error_code cellSync2SemaphoreAcquire(vm::ptr semaphore, u32 count, vm::cptr config) { - UNIMPLEMENTED_FUNC(cellSync2); + cellSync2.todo("cellSync2SemaphoreAcquire(semaphore=*0x%x, count=0x%x, config=*0x%x)", semaphore, count, config); + + if (!semaphore) + return CELL_SYNC2_ERROR_NULL_POINTER; + + if (count > 0x7FFFFF) + return CELL_SYNC2_ERROR_INVAL; + return CELL_OK; } -s32 cellSync2SemaphoreTryAcquire() +error_code cellSync2SemaphoreTryAcquire(vm::ptr semaphore, u32 count, vm::cptr config) { - UNIMPLEMENTED_FUNC(cellSync2); + cellSync2.todo("cellSync2SemaphoreTryAcquire(semaphore=*0x%x, count=0x%x, config=*0x%x)", semaphore, count, config); + + if (!semaphore) + return CELL_SYNC2_ERROR_NULL_POINTER; + + if (count > 0x7FFFFF) + return CELL_SYNC2_ERROR_INVAL; + return CELL_OK; } -s32 cellSync2SemaphoreRelease() +error_code cellSync2SemaphoreRelease(vm::ptr semaphore, u32 count, vm::cptr config) { - UNIMPLEMENTED_FUNC(cellSync2); + cellSync2.todo("cellSync2SemaphoreRelease(semaphore=*0x%x, count=0x%x, config=*0x%x)", semaphore, count, config); + + if (!semaphore) + return CELL_SYNC2_ERROR_NULL_POINTER; + + if (count > 0x7FFFFF) + return CELL_SYNC2_ERROR_INVAL; + return CELL_OK; } -s32 cellSync2SemaphoreGetCount() +error_code cellSync2SemaphoreGetCount(vm::ptr semaphore, vm::ptr count) { - UNIMPLEMENTED_FUNC(cellSync2); + cellSync2.todo("cellSync2SemaphoreGetCount(semaphore=*0x%x, count=*0x%x)", semaphore, count); + + if (!semaphore || !count) + return CELL_SYNC2_ERROR_NULL_POINTER; + return CELL_OK; } -s32 _cellSync2QueueAttributeInitialize(vm::ptr attr, u32 sdkVersion) +error_code _cellSync2QueueAttributeInitialize(vm::ptr attr, u32 sdkVersion) { cellSync2.warning("_cellSync2QueueAttributeInitialize(attr=*0x%x, sdkVersion=0x%x)", attr, sdkVersion); + if (!attr) + return CELL_SYNC2_ERROR_NULL_POINTER; + attr->sdkVersion = sdkVersion; attr->threadTypes = CELL_SYNC2_THREAD_TYPE_PPU_THREAD | CELL_SYNC2_THREAD_TYPE_PPU_FIBER | CELL_SYNC2_THREAD_TYPE_SPURS_TASK | CELL_SYNC2_THREAD_TYPE_SPURS_JOB | @@ -198,62 +329,101 @@ s32 _cellSync2QueueAttributeInitialize(vm::ptr attr, u3 return CELL_OK; } -s32 cellSync2QueueEstimateBufferSize(vm::cptr attr, vm::ptr bufferSize) +error_code cellSync2QueueEstimateBufferSize(vm::cptr attr, vm::ptr bufferSize) { cellSync2.todo("cellSync2QueueEstimateBufferSize(attr=*0x%x, bufferSize=*0x%x)", attr, bufferSize); - if (attr->elementSize == 0 || attr->elementSize > 16384 || attr->elementSize % 16 || attr->depth == 0 || attr->depth > 4294967292 || - attr->maxPushWaiters > 32768 || attr->maxPopWaiters > 32768) + if (!attr || !bufferSize) + return CELL_SYNC2_ERROR_NULL_POINTER; + + if (attr->elementSize == 0 || attr->elementSize > 0x4000 || attr->elementSize % 16 || attr->depth == 0 || attr->depth > 0xFFFFFFFC || + attr->maxPushWaiters > 0x8000 || attr->maxPopWaiters > 0x8000) return CELL_SYNC2_ERROR_INVAL; return CELL_OK; } -s32 cellSync2QueueInitialize() +error_code cellSync2QueueInitialize(vm::ptr queue, vm::ptr buffer, vm::cptr attr) { - UNIMPLEMENTED_FUNC(cellSync2); + cellSync2.todo("cellSync2QueueInitialize(queue=*0x%x, buffer=*0x%x, attr=*0x%x)", queue, buffer, attr); + + if (!queue || !buffer || !attr) + return CELL_SYNC2_ERROR_NULL_POINTER; + + if (attr->elementSize == 0 || attr->elementSize > 0x4000 || attr->elementSize % 16 || attr->depth == 0 || attr->depth > 0xFFFFFFFC || + attr->maxPushWaiters > 0x8000 || attr->maxPopWaiters > 0x8000) + return CELL_SYNC2_ERROR_INVAL; + return CELL_OK; } -s32 cellSync2QueueFinalize() +error_code cellSync2QueueFinalize(vm::ptr queue) { - UNIMPLEMENTED_FUNC(cellSync2); + cellSync2.todo("cellSync2QueueFinalize(queue=*0x%x)", queue); + + if (!queue) + return CELL_SYNC2_ERROR_NULL_POINTER; + return CELL_OK; } -s32 cellSync2QueuePush() +error_code cellSync2QueuePush(vm::ptr queue, vm::cptr data, vm::cptr config) { - UNIMPLEMENTED_FUNC(cellSync2); + cellSync2.todo("cellSync2QueuePush(queue=*0x%x, data=*0x%x, config=*0x%x)", queue, data, config); + + if (!queue || !data) + return CELL_SYNC2_ERROR_NULL_POINTER; + return CELL_OK; } -s32 cellSync2QueueTryPush() +error_code cellSync2QueueTryPush(vm::ptr queue, vm::cpptr data, u32 numData, vm::cptr config) { - UNIMPLEMENTED_FUNC(cellSync2); + cellSync2.todo("cellSync2QueueTryPush(queue=*0x%x, data=**0x%x, numData=0x%x, config=*0x%x)", queue, data, numData, config); + + if (!queue || !data) + return CELL_SYNC2_ERROR_NULL_POINTER; + return CELL_OK; } -s32 cellSync2QueuePop() +error_code cellSync2QueuePop(vm::ptr queue, vm::ptr buffer, vm::cptr config) { - UNIMPLEMENTED_FUNC(cellSync2); + cellSync2.todo("cellSync2QueuePop(queue=*0x%x, buffer=*0x%x, config=*0x%x)", queue, buffer, config); + + if (!queue || !buffer) + return CELL_SYNC2_ERROR_NULL_POINTER; + return CELL_OK; } -s32 cellSync2QueueTryPop() +error_code cellSync2QueueTryPop(vm::ptr queue, vm::ptr buffer, vm::cptr config) { - UNIMPLEMENTED_FUNC(cellSync2); + cellSync2.todo("cellSync2QueueTryPop(queue=*0x%x, buffer=*0x%x, config=*0x%x)", queue, buffer, config); + + if (!queue || !buffer) + return CELL_SYNC2_ERROR_NULL_POINTER; + return CELL_OK; } -s32 cellSync2QueueGetSize() +error_code cellSync2QueueGetSize(vm::ptr queue, vm::ptr size) { - UNIMPLEMENTED_FUNC(cellSync2); + cellSync2.todo("cellSync2QueueGetSize(queue=*0x%x, size=*0x%x)", queue, size); + + if (!queue || !size) + return CELL_SYNC2_ERROR_NULL_POINTER; + return CELL_OK; } -s32 cellSync2QueueGetDepth() +error_code cellSync2QueueGetDepth(vm::ptr queue, vm::ptr depth) { - UNIMPLEMENTED_FUNC(cellSync2); + cellSync2.todo("cellSync2QueueGetDepth(queue=*0x%x, depth=*0x%x)", queue, depth); + + if (!queue || !depth) + return CELL_SYNC2_ERROR_NULL_POINTER; + return CELL_OK; } diff --git a/rpcs3/Emu/Cell/Modules/cellSync2.h b/rpcs3/Emu/Cell/Modules/cellSync2.h index 17f0035504..a890007a37 100644 --- a/rpcs3/Emu/Cell/Modules/cellSync2.h +++ b/rpcs3/Emu/Cell/Modules/cellSync2.h @@ -3,7 +3,7 @@ // Return Codes -enum +enum CellSync2Error : u32 { CELL_SYNC2_ERROR_AGAIN = 0x80410C01, CELL_SYNC2_ERROR_INVAL = 0x80410C02, @@ -95,3 +95,38 @@ struct CellSync2Notifier vm::bptr sendSignal; be_t callbackArg; }; + +struct alignas(128) CellSync2Mutex +{ + u8 skip[128]; +}; + +CHECK_SIZE_ALIGN(CellSync2Mutex, 128, 128); + +struct alignas(128) CellSync2Cond +{ + u8 skip[128]; +}; + +CHECK_SIZE_ALIGN(CellSync2Cond, 128, 128); + +struct alignas(128) CellSync2Semaphore +{ + u8 skip[128]; +}; + +CHECK_SIZE_ALIGN(CellSync2Semaphore, 128, 128); + +struct alignas(128) CellSync2Queue +{ + u8 skip[128]; +}; + +CHECK_SIZE_ALIGN(CellSync2Queue, 128, 128); + +struct CellSync2ThreadConfig +{ + vm::bptr callerThreadType; + vm::bpptr notifierTable; + be_t numNotifier; +};