From 95ed2ef62ec2486f22ba63dbe99ceffe929b4b79 Mon Sep 17 00:00:00 2001 From: Eladash Date: Thu, 16 Jan 2020 23:31:58 +0200 Subject: [PATCH] cellGcm HLE: Add error_code --- rpcs3/Emu/Cell/Modules/cellGcmSys.cpp | 220 +++++++++++++------------- rpcs3/Emu/Cell/Modules/cellGcmSys.h | 5 +- 2 files changed, 112 insertions(+), 113 deletions(-) diff --git a/rpcs3/Emu/Cell/Modules/cellGcmSys.cpp b/rpcs3/Emu/Cell/Modules/cellGcmSys.cpp index c6aada414c..b08a1e66dd 100644 --- a/rpcs3/Emu/Cell/Modules/cellGcmSys.cpp +++ b/rpcs3/Emu/Cell/Modules/cellGcmSys.cpp @@ -16,6 +16,25 @@ LOG_CHANNEL(cellGcmSys); +template<> +void fmt_class_string::format(std::string& out, u64 arg) +{ + format_enum(out, arg, [](auto error) + { + switch (error) + { + STR_CASE(CELL_GCM_ERROR_FAILURE); + STR_CASE(CELL_GCM_ERROR_NO_IO_PAGE_TABLE); + STR_CASE(CELL_GCM_ERROR_INVALID_ENUM); + STR_CASE(CELL_GCM_ERROR_INVALID_VALUE); + STR_CASE(CELL_GCM_ERROR_INVALID_ALIGNMENT); + STR_CASE(CELL_GCM_ERROR_ADDRESS_OVERWRAP); + } + + return unknown; + }); +} + extern s32 cellGcmCallback(ppu_thread& ppu, vm::ptr context, u32 count); const u32 tiled_pitches[] = { @@ -77,6 +96,8 @@ u32 gcmGetLocalMemorySize(u32 sdk_version) CellGcmOffsetTable offsetTable; atomic_t IoMapTable[0xC00]{}; +error_code gcmMapEaIoAddress(u32 ea, u32 io, u32 size, bool is_strict); + void InitOffsetTable() { offsetTable.ioAddress.set(vm::alloc(3072 * sizeof(u16), vm::main)); @@ -246,13 +267,13 @@ u32 cellGcmGetDefaultSegmentWordSize() return g_fxo->get()->gcm_info.segment_size; } -s32 cellGcmInitDefaultFifoMode(s32 mode) +error_code cellGcmInitDefaultFifoMode(s32 mode) { cellGcmSys.warning("cellGcmInitDefaultFifoMode(mode=%d)", mode); return CELL_OK; } -s32 cellGcmSetDefaultFifoSize(u32 bufferSize, u32 segmentSize) +error_code cellGcmSetDefaultFifoSize(u32 bufferSize, u32 segmentSize) { cellGcmSys.warning("cellGcmSetDefaultFifoSize(bufferSize=0x%x, segmentSize=0x%x)", bufferSize, segmentSize); return CELL_OK; @@ -262,13 +283,12 @@ s32 cellGcmSetDefaultFifoSize(u32 bufferSize, u32 segmentSize) // Hardware Resource Management //---------------------------------------------------------------------------- -s32 cellGcmBindTile(u8 index) +error_code cellGcmBindTile(u8 index) { cellGcmSys.warning("cellGcmBindTile(index=%d)", index); if (index >= rsx::limits::tiles_count) { - cellGcmSys.error("cellGcmBindTile: CELL_GCM_ERROR_INVALID_VALUE"); return CELL_GCM_ERROR_INVALID_VALUE; } @@ -277,14 +297,13 @@ s32 cellGcmBindTile(u8 index) return CELL_OK; } -s32 cellGcmBindZcull(u8 index, u32 offset, u32 width, u32 height, u32 cullStart, u32 zFormat, u32 aaFormat, u32 zCullDir, u32 zCullFormat, u32 sFunc, u32 sRef, u32 sMask) +error_code cellGcmBindZcull(u8 index, u32 offset, u32 width, u32 height, u32 cullStart, u32 zFormat, u32 aaFormat, u32 zCullDir, u32 zCullFormat, u32 sFunc, u32 sRef, u32 sMask) { cellGcmSys.warning("cellGcmBindZcull(index=%d, offset=0x%x, width=%d, height=%d, cullStart=0x%x, zFormat=0x%x, aaFormat=0x%x, zCullDir=0x%x, zCullFormat=0x%x, sFunc=0x%x, sRef=0x%x, sMask=0x%x)", index, offset, width, height, cullStart, zFormat, aaFormat, zCullDir, zCullFormat, sFunc, sRef, sMask); if (index >= rsx::limits::zculls_count) { - cellGcmSys.error("cellGcmBindZcull: CELL_GCM_ERROR_INVALID_VALUE"); return CELL_GCM_ERROR_INVALID_VALUE; } @@ -308,7 +327,7 @@ u32 cellGcmGetFlipStatus() return status; } -s32 cellGcmGetFlipStatus2() +error_code cellGcmGetFlipStatus2() { UNIMPLEMENTED_FUNC(cellGcmSys); return CELL_OK; @@ -341,7 +360,7 @@ void _cellGcmFunc15(vm::ptr context) u32 g_defaultCommandBufferBegin, g_defaultCommandBufferFragmentCount; // Called by cellGcmInit -s32 _cellGcmInitBody(ppu_thread& ppu, vm::pptr context, u32 cmdSize, u32 ioSize, u32 ioAddress) +error_code _cellGcmInitBody(ppu_thread& ppu, vm::pptr context, u32 cmdSize, u32 ioSize, u32 ioAddress) { cellGcmSys.warning("_cellGcmInitBody(context=**0x%x, cmdSize=0x%x, ioSize=0x%x, ioAddress=0x%x)", context, cmdSize, ioSize, ioAddress); @@ -377,7 +396,6 @@ s32 _cellGcmInitBody(ppu_thread& ppu, vm::pptr context, u32 if (gcmMapEaIoAddress(ioAddress, 0, ioSize, false) != CELL_OK) { - cellGcmSys.error("cellGcmInit: CELL_GCM_ERROR_FAILURE"); return CELL_GCM_ERROR_FAILURE; } @@ -441,7 +459,7 @@ void cellGcmResetFlipStatus() rsx::get_current_renderer()->flip_status = CELL_GCM_DISPLAY_FLIP_STATUS_WAITING; } -s32 cellGcmResetFlipStatus2() +error_code cellGcmResetFlipStatus2() { UNIMPLEMENTED_FUNC(cellGcmSys); return CELL_OK; @@ -464,7 +482,7 @@ void cellGcmSetDebugOutputLevel(s32 level) } } -s32 cellGcmSetDisplayBuffer(u8 id, u32 offset, u32 pitch, u32 width, u32 height) +error_code cellGcmSetDisplayBuffer(u8 id, u32 offset, u32 pitch, u32 width, u32 height) { cellGcmSys.trace("cellGcmSetDisplayBuffer(id=0x%x, offset=0x%x, pitch=%d, width=%d, height=%d)", id, offset, width ? pitch / width : pitch, width, height); @@ -472,7 +490,6 @@ s32 cellGcmSetDisplayBuffer(u8 id, u32 offset, u32 pitch, u32 width, u32 height) if (id > 7) { - cellGcmSys.error("cellGcmSetDisplayBuffer: CELL_GCM_ERROR_FAILURE"); return CELL_GCM_ERROR_FAILURE; } @@ -505,7 +522,7 @@ void cellGcmSetFlipHandler(vm::ptr handler) rsx::get_current_renderer()->flip_handler = handler; } -s32 cellGcmSetFlipHandler2() +error_code cellGcmSetFlipHandler2() { UNIMPLEMENTED_FUNC(cellGcmSys); return CELL_OK; @@ -518,7 +535,7 @@ void cellGcmSetFlipMode(u32 mode) rsx::get_current_renderer()->requested_vsync.store(mode == CELL_GCM_DISPLAY_VSYNC); } -s32 cellGcmSetFlipMode2() +error_code cellGcmSetFlipMode2() { UNIMPLEMENTED_FUNC(cellGcmSys); return CELL_OK; @@ -531,50 +548,55 @@ void cellGcmSetFlipStatus() rsx::get_current_renderer()->flip_status = CELL_GCM_DISPLAY_FLIP_STATUS_DONE; } -s32 cellGcmSetFlipStatus2() +error_code cellGcmSetFlipStatus2() { UNIMPLEMENTED_FUNC(cellGcmSys); return CELL_OK; } -s32 cellGcmSetPrepareFlip(ppu_thread& ppu, vm::ptr ctxt, u32 id) +template > +ret_type gcmSetPrepareFlip(ppu_thread& ppu, vm::ptr ctxt, u32 id) { - cellGcmSys.trace("cellGcmSetPrepareFlip(ctxt=*0x%x, id=0x%x)", ctxt, id); - const auto gcm_cfg = g_fxo->get(); if (id > 7) { - cellGcmSys.error("cellGcmSetPrepareFlip: CELL_GCM_ERROR_FAILURE"); return CELL_GCM_ERROR_FAILURE; } - if (ctxt->current + 2 >= ctxt->end) + if (!old_api && ctxt->current + 2 >= ctxt->end) { if (s32 res = ctxt->callback(ppu, ctxt, 8 /* ??? */)) { cellGcmSys.error("cellGcmSetPrepareFlip: callback failed (0x%08x)", res); - return res; + return static_cast(not_an_error(res)); } } const u32 cmd_size = rsx::make_command(ctxt->current, GCM_FLIP_COMMAND, { id }); - if (ctxt.addr() == gcm_cfg->gcm_info.context_addr) + if (!old_api && ctxt.addr() == gcm_cfg->gcm_info.context_addr) { vm::_ref(gcm_cfg->gcm_info.control_addr).put += cmd_size; } - return id; + return static_cast(not_an_error(id)); } -s32 cellGcmSetFlip(ppu_thread& ppu, vm::ptr ctxt, u32 id) +error_code cellGcmSetPrepareFlip(ppu_thread& ppu, vm::ptr ctxt, u32 id) +{ + cellGcmSys.trace("cellGcmSetPrepareFlip(ctxt=*0x%x, id=0x%x)", ctxt, id); + + return gcmSetPrepareFlip(ppu, ctxt, id); +} + +error_code cellGcmSetFlip(ppu_thread& ppu, vm::ptr ctxt, u32 id) { cellGcmSys.trace("cellGcmSetFlip(ctxt=*0x%x, id=0x%x)", ctxt, id); - if (s32 res = cellGcmSetPrepareFlip(ppu, ctxt, id)) + if (auto res = gcmSetPrepareFlip(ppu, ctxt, id); res < 0) { - if (res < 0) return CELL_GCM_ERROR_FAILURE; + return CELL_GCM_ERROR_FAILURE; } return CELL_OK; @@ -603,7 +625,7 @@ void cellGcmSetSecondVFrequency(u32 freq) } } -s32 cellGcmSetTileInfo(u8 index, u8 location, u32 offset, u32 size, u32 pitch, u8 comp, u16 base, u8 bank) +error_code cellGcmSetTileInfo(u8 index, u8 location, u32 offset, u32 size, u32 pitch, u8 comp, u16 base, u8 bank) { cellGcmSys.warning("cellGcmSetTileInfo(index=%d, location=%d, offset=%d, size=%d, pitch=%d, comp=%d, base=%d, bank=%d)", index, location, offset, size, pitch, comp, base, bank); @@ -612,19 +634,16 @@ s32 cellGcmSetTileInfo(u8 index, u8 location, u32 offset, u32 size, u32 pitch, u if (index >= rsx::limits::tiles_count || base >= 2048 || bank >= 4) { - cellGcmSys.error("cellGcmSetTileInfo: CELL_GCM_ERROR_INVALID_VALUE"); return CELL_GCM_ERROR_INVALID_VALUE; } if (offset & 0xffff || size & 0xffff || pitch & 0xff) { - cellGcmSys.error("cellGcmSetTileInfo: CELL_GCM_ERROR_INVALID_ALIGNMENT"); return CELL_GCM_ERROR_INVALID_ALIGNMENT; } if (location >= 2 || (comp != 0 && (comp < 7 || comp > 12))) { - cellGcmSys.error("cellGcmSetTileInfo: CELL_GCM_ERROR_INVALID_ENUM"); return CELL_GCM_ERROR_INVALID_ENUM; } @@ -674,7 +693,7 @@ void cellGcmSetWaitFlip(vm::ptr ctxt) // TODO: emit RSX command for "wait flip" operation } -s32 cellGcmSetWaitFlipUnsafe() +error_code cellGcmSetWaitFlipUnsafe() { cellGcmSys.todo("cellGcmSetWaitFlipUnsafe()"); @@ -713,13 +732,12 @@ void cellGcmSetZcull(u8 index, u32 offset, u32 width, u32 height, u32 cullStart, vm::_ptr(gcm_cfg->zculls_addr)[index] = zcull.pack(); } -s32 cellGcmUnbindTile(u8 index) +error_code cellGcmUnbindTile(u8 index) { cellGcmSys.warning("cellGcmUnbindTile(index=%d)", index); if (index >= rsx::limits::tiles_count) { - cellGcmSys.error("cellGcmUnbindTile: CELL_GCM_ERROR_INVALID_VALUE"); return CELL_GCM_ERROR_INVALID_VALUE; } @@ -728,13 +746,12 @@ s32 cellGcmUnbindTile(u8 index) return CELL_OK; } -s32 cellGcmUnbindZcull(u8 index) +error_code cellGcmUnbindZcull(u8 index) { cellGcmSys.warning("cellGcmUnbindZcull(index=%d)", index); if (index >= 8) { - cellGcmSys.error("cellGcmUnbindZcull: CELL_GCM_ERROR_INVALID_VALUE"); return CELL_GCM_ERROR_INVALID_VALUE; } @@ -761,7 +778,7 @@ u32 cellGcmGetDisplayInfo() return g_fxo->get()->gcm_buffers.addr(); } -s32 cellGcmGetCurrentDisplayBufferId(vm::ptr id) +error_code cellGcmGetCurrentDisplayBufferId(vm::ptr id) { cellGcmSys.warning("cellGcmGetCurrentDisplayBufferId(id=*0x%x)", id); @@ -778,13 +795,13 @@ void cellGcmSetInvalidateTile(u8 index) cellGcmSys.todo("cellGcmSetInvalidateTile(index=%d)", index); } -s32 cellGcmTerminate() +error_code cellGcmTerminate() { // The firmware just return CELL_OK as well return CELL_OK; } -s32 cellGcmDumpGraphicsError() +error_code cellGcmDumpGraphicsError() { cellGcmSys.todo("cellGcmDumpGraphicsError()"); return CELL_OK; @@ -793,7 +810,7 @@ s32 cellGcmDumpGraphicsError() s32 cellGcmGetDisplayBufferByFlipIndex(u32 qid) { cellGcmSys.todo("cellGcmGetDisplayBufferByFlipIndex(qid=%d)", qid); - return -1; + return -1; // Invalid id, todo } u64 cellGcmGetLastFlipTime() @@ -803,7 +820,7 @@ u64 cellGcmGetLastFlipTime() return rsx::get_current_renderer()->last_flip_time; } -s32 cellGcmGetLastFlipTime2() +error_code cellGcmGetLastFlipTime2() { UNIMPLEMENTED_FUNC(cellGcmSys); return CELL_OK; @@ -822,19 +839,19 @@ u64 cellGcmGetVBlankCount() return rsx::get_current_renderer()->vblank_count; } -s32 cellGcmGetVBlankCount2() +error_code cellGcmGetVBlankCount2() { UNIMPLEMENTED_FUNC(cellGcmSys); return CELL_OK; } -s32 cellGcmSysGetLastVBlankTime() +error_code cellGcmSysGetLastVBlankTime() { cellGcmSys.todo("cellGcmSysGetLastVBlankTime()"); return CELL_OK; } -s32 cellGcmInitSystemMode(u64 mode) +error_code cellGcmInitSystemMode(u64 mode) { cellGcmSys.trace("cellGcmInitSystemMode(mode=0x%x)", mode); @@ -843,13 +860,12 @@ s32 cellGcmInitSystemMode(u64 mode) return CELL_OK; } -s32 cellGcmSetFlipImmediate(u8 id) +error_code cellGcmSetFlipImmediate(u8 id) { cellGcmSys.todo("cellGcmSetFlipImmediate(id=0x%x)", id); if (id > 7) { - cellGcmSys.error("cellGcmSetFlipImmediate: CELL_GCM_ERROR_FAILURE"); return CELL_GCM_ERROR_FAILURE; } @@ -858,7 +874,7 @@ s32 cellGcmSetFlipImmediate(u8 id) return CELL_OK; } -s32 cellGcmSetFlipImmediate2() +error_code cellGcmSetFlipImmediate2() { UNIMPLEMENTED_FUNC(cellGcmSys); return CELL_OK; @@ -874,7 +890,7 @@ void cellGcmSetQueueHandler(vm::ptr handler) cellGcmSys.todo("cellGcmSetQueueHandler(handler=*0x%x)", handler); } -s32 cellGcmSetSecondVHandler(vm::ptr handler) +error_code cellGcmSetSecondVHandler(vm::ptr handler) { cellGcmSys.todo("cellGcmSetSecondVHandler(handler=0x%x)", handler); return CELL_OK; @@ -885,7 +901,7 @@ void cellGcmSetVBlankFrequency(u32 freq) cellGcmSys.todo("cellGcmSetVBlankFrequency(freq=%d)", freq); } -s32 cellGcmSortRemapEaIoAddress() +error_code cellGcmSortRemapEaIoAddress() { cellGcmSys.todo("cellGcmSortRemapEaIoAddress()"); return CELL_OK; @@ -894,7 +910,7 @@ s32 cellGcmSortRemapEaIoAddress() //---------------------------------------------------------------------------- // Memory Mapping //---------------------------------------------------------------------------- -s32 cellGcmAddressToOffset(u32 address, vm::ptr offset) +error_code cellGcmAddressToOffset(u32 address, vm::ptr offset) { cellGcmSys.trace("cellGcmAddressToOffset(address=0x%x, offset=*0x%x)", address, offset); @@ -946,7 +962,7 @@ void cellGcmGetOffsetTable(vm::ptr table) table->eaAddress = offsetTable.eaAddress; } -s32 cellGcmIoOffsetToAddress(u32 ioOffset, vm::ptr address) +error_code cellGcmIoOffsetToAddress(u32 ioOffset, vm::ptr address) { cellGcmSys.trace("cellGcmIoOffsetToAddress(ioOffset=0x%x, address=*0x%x)", ioOffset, address); @@ -954,7 +970,6 @@ s32 cellGcmIoOffsetToAddress(u32 ioOffset, vm::ptr address) if (static_cast(upper12Bits) < 0) { - cellGcmSys.error("cellGcmIoOffsetToAddress: CELL_GCM_ERROR_FAILURE"); return CELL_GCM_ERROR_FAILURE; } @@ -963,14 +978,14 @@ s32 cellGcmIoOffsetToAddress(u32 ioOffset, vm::ptr address) return CELL_OK; } -s32 gcmMapEaIoAddress(u32 ea, u32 io, u32 size, bool is_strict) +error_code gcmMapEaIoAddress(u32 ea, u32 io, u32 size, bool is_strict) { if (!size || (ea & 0xFFFFF) || (io & 0xFFFFF) || (size & 0xFFFFF)) { return CELL_GCM_ERROR_FAILURE; } - if (s32 error = sys_rsx_context_iomap(0x55555555, io, ea, size, 0xe000000000000800ull | (u64{is_strict} << 60))) + if (auto error = sys_rsx_context_iomap(0x55555555, io, ea, size, 0xe000000000000800ull | (u64{is_strict} << 60))) { return error; } @@ -988,14 +1003,14 @@ s32 gcmMapEaIoAddress(u32 ea, u32 io, u32 size, bool is_strict) return CELL_OK; } -s32 cellGcmMapEaIoAddress(u32 ea, u32 io, u32 size) +error_code cellGcmMapEaIoAddress(u32 ea, u32 io, u32 size) { cellGcmSys.warning("cellGcmMapEaIoAddress(ea=0x%x, io=0x%x, size=0x%x)", ea, io, size); return gcmMapEaIoAddress(ea, io, size, false); } -s32 cellGcmMapEaIoAddressWithFlags(u32 ea, u32 io, u32 size, u32 flags) +error_code cellGcmMapEaIoAddressWithFlags(u32 ea, u32 io, u32 size, u32 flags) { cellGcmSys.warning("cellGcmMapEaIoAddressWithFlags(ea=0x%x, io=0x%x, size=0x%x, flags=0x%x)", ea, io, size, flags); @@ -1004,7 +1019,7 @@ s32 cellGcmMapEaIoAddressWithFlags(u32 ea, u32 io, u32 size, u32 flags) return gcmMapEaIoAddress(ea, io, size, true); } -s32 cellGcmMapLocalMemory(vm::ptr address, vm::ptr size) +error_code cellGcmMapLocalMemory(vm::ptr address, vm::ptr size) { cellGcmSys.warning("cellGcmMapLocalMemory(address=*0x%x, size=*0x%x)", address, size); @@ -1015,14 +1030,13 @@ s32 cellGcmMapLocalMemory(vm::ptr address, vm::ptr size) } else { - cellGcmSys.error("RSX local memory already mapped"); return CELL_GCM_ERROR_FAILURE; } return CELL_OK; } -s32 cellGcmMapMainMemory(u32 ea, u32 size, vm::ptr offset) +error_code cellGcmMapMainMemory(u32 ea, u32 size, vm::ptr offset) { cellGcmSys.warning("cellGcmMapMainMemory(ea=0x%x, size=0x%x, offset=*0x%x)", ea, size, offset); @@ -1035,22 +1049,11 @@ s32 cellGcmMapMainMemory(u32 ea, u32 size, vm::ptr offset) { if (unmap_count >= (size >> 20)) { - if (s32 error = sys_rsx_context_iomap(0x55555555, io << 20, ea, size, 0xe000000000000800ull)) + if (auto error = gcmMapEaIoAddress(io << 20, ea, size, false)) { return error; } - ea >>= 20, size >>= 20; - - // Fill the offset table - for (u32 i = 0; i < size; i++) - { - offsetTable.ioAddress[ea + i] = io + i; - offsetTable.eaAddress[io + i] = ea + i; - } - - IoMapTable[ea] = size; - *offset = io << 20; return CELL_OK; } @@ -1062,23 +1065,20 @@ s32 cellGcmMapMainMemory(u32 ea, u32 size, vm::ptr offset) } } - cellGcmSys.error("cellGcmMapMainMemory: CELL_GCM_ERROR_NO_IO_PAGE_TABLE"); return CELL_GCM_ERROR_NO_IO_PAGE_TABLE; } -s32 cellGcmReserveIoMapSize(u32 size) +error_code cellGcmReserveIoMapSize(u32 size) { cellGcmSys.trace("cellGcmReserveIoMapSize(size=0x%x)", size); if (size & 0xFFFFF) { - cellGcmSys.error("cellGcmReserveIoMapSize: CELL_GCM_ERROR_INVALID_ALIGNMENT"); return CELL_GCM_ERROR_INVALID_ALIGNMENT; } if (size > cellGcmGetMaxIoMapSize()) { - cellGcmSys.error("cellGcmReserveIoMapSize: CELL_GCM_ERROR_INVALID_VALUE"); return CELL_GCM_ERROR_INVALID_VALUE; } @@ -1086,9 +1086,9 @@ s32 cellGcmReserveIoMapSize(u32 size) return CELL_OK; } -s32 cellGcmUnmapEaIoAddress(u32 ea) +error_code cellGcmUnmapEaIoAddress(u32 ea) { - cellGcmSys.trace("cellGcmUnmapEaIoAddress(ea=0x%x)", ea); + cellGcmSys.warning("cellGcmUnmapEaIoAddress(ea=0x%x)", ea); if (const u32 size = IoMapTable[ea >>= 20].exchange(0)) { @@ -1104,16 +1104,15 @@ s32 cellGcmUnmapEaIoAddress(u32 ea) } else { - cellGcmSys.error("cellGcmUnmapEaIoAddress(ea=0x%x): UnmapRealAddress() failed", ea); return CELL_GCM_ERROR_FAILURE; } return CELL_OK; } -s32 cellGcmUnmapIoAddress(u32 io) +error_code cellGcmUnmapIoAddress(u32 io) { - cellGcmSys.trace("cellGcmUnmapIoAddress(io=0x%x)", io); + cellGcmSys.warning("cellGcmUnmapIoAddress(io=0x%x)", io); if (u32 size = IoMapTable[RSXIOMem.ea[io >>= 20]].exchange(0)) { @@ -1129,26 +1128,23 @@ s32 cellGcmUnmapIoAddress(u32 io) } else { - cellGcmSys.error("cellGcmUnmapIoAddress(io=0x%x): UnmapAddress() failed", io); return CELL_GCM_ERROR_FAILURE; } return CELL_OK; } -s32 cellGcmUnreserveIoMapSize(u32 size) +error_code cellGcmUnreserveIoMapSize(u32 size) { cellGcmSys.trace("cellGcmUnreserveIoMapSize(size=0x%x)", size); if (size & 0xFFFFF) { - cellGcmSys.error("cellGcmUnreserveIoMapSize: CELL_GCM_ERROR_INVALID_ALIGNMENT"); return CELL_GCM_ERROR_INVALID_ALIGNMENT; } if (size > reserved_size) { - cellGcmSys.error("cellGcmUnreserveIoMapSize: CELL_GCM_ERROR_INVALID_VALUE"); return CELL_GCM_ERROR_INVALID_VALUE; } @@ -1160,37 +1156,37 @@ s32 cellGcmUnreserveIoMapSize(u32 size) // Cursor Functions //---------------------------------------------------------------------------- -s32 cellGcmInitCursor() +error_code cellGcmInitCursor() { cellGcmSys.todo("cellGcmInitCursor()"); return CELL_OK; } -s32 cellGcmSetCursorPosition(s32 x, s32 y) +error_code cellGcmSetCursorPosition(s32 x, s32 y) { cellGcmSys.todo("cellGcmSetCursorPosition(x=%d, y=%d)", x, y); return CELL_OK; } -s32 cellGcmSetCursorDisable() +error_code cellGcmSetCursorDisable() { cellGcmSys.todo("cellGcmSetCursorDisable()"); return CELL_OK; } -s32 cellGcmUpdateCursor() +error_code cellGcmUpdateCursor() { cellGcmSys.todo("cellGcmUpdateCursor()"); return CELL_OK; } -s32 cellGcmSetCursorEnable() +error_code cellGcmSetCursorEnable() { cellGcmSys.todo("cellGcmSetCursorEnable()"); return CELL_OK; } -s32 cellGcmSetCursorImageOffset(u32 offset) +error_code cellGcmSetCursorImageOffset(u32 offset) { cellGcmSys.todo("cellGcmSetCursorImageOffset(offset=0x%x)", offset); return CELL_OK; @@ -1209,7 +1205,7 @@ void cellGcmSetDefaultCommandBuffer() vm::write32(gcm_cfg->ctxt_addr, gcm_cfg->gcm_info.context_addr); } -s32 cellGcmSetDefaultCommandBufferAndSegmentWordSize(u32 bufferSize, u32 segmentSize) +error_code cellGcmSetDefaultCommandBufferAndSegmentWordSize(u32 bufferSize, u32 segmentSize) { cellGcmSys.warning("cellGcmSetDefaultCommandBufferAndSegmentWordSize(bufferSize=0x%x, segmentSize=0x%x)", bufferSize, segmentSize); @@ -1233,31 +1229,40 @@ s32 cellGcmSetDefaultCommandBufferAndSegmentWordSize(u32 bufferSize, u32 segment // Other //------------------------------------------------------------------------ -s32 _cellGcmSetFlipCommand(ppu_thread& ppu, vm::ptr ctx, u32 id) +void _cellGcmSetFlipCommand(ppu_thread& ppu, vm::ptr ctx, u32 id) { cellGcmSys.trace("cellGcmSetFlipCommand(ctx=*0x%x, id=0x%x)", ctx, id); - return cellGcmSetPrepareFlip(ppu, ctx, id); + if (auto error = gcmSetPrepareFlip(ppu, ctx, id); error < 0) + { + // TODO: On actual fw this function doesn't have error checks at all + cellGcmSys.error("cellGcmSetFlipCommand(): gcmSetPrepareFlip failed with %s", CellGcmError{error + 0u}); + } } -s32 _cellGcmSetFlipCommand2() +error_code _cellGcmSetFlipCommand2() { UNIMPLEMENTED_FUNC(cellGcmSys); return CELL_OK; } -s32 _cellGcmSetFlipCommandWithWaitLabel(ppu_thread& ppu, vm::ptr ctx, u32 id, u32 label_index, u32 label_value) +void _cellGcmSetFlipCommandWithWaitLabel(ppu_thread& ppu, vm::ptr ctx, u32 id, u32 label_index, u32 label_value) { - cellGcmSys.trace("cellGcmSetFlipCommandWithWaitLabel(ctx=*0x%x, id=0x%x, label_index=0x%x, label_value=0x%x)", ctx, id, label_index, label_value); + cellGcmSys.todo("cellGcmSetFlipCommandWithWaitLabel(ctx=*0x%x, id=0x%x, label_index=0x%x, label_value=0x%x)", ctx, id, label_index, label_value); const auto gcm_cfg = g_fxo->get(); - s32 res = cellGcmSetPrepareFlip(ppu, ctx, id); + if (auto error = gcmSetPrepareFlip(ppu, ctx, id); error < 0) + { + // TODO: On actual fw this function doesn't have error checks at all + cellGcmSys.error("cellGcmSetFlipCommandWithWaitLabel(): gcmSetPrepareFlip failed with %s", CellGcmError{error + 0u}); + } + + // TODO: Fix this (must enqueue WaitLabel command instead) vm::write32(gcm_cfg->gcm_info.label_addr + 0x10 * label_index, label_value); - return res < 0 ? CELL_GCM_ERROR_FAILURE : CELL_OK; } -s32 cellGcmSetTile(u8 index, u8 location, u32 offset, u32 size, u32 pitch, u8 comp, u16 base, u8 bank) +error_code cellGcmSetTile(u8 index, u8 location, u32 offset, u32 size, u32 pitch, u8 comp, u16 base, u8 bank) { cellGcmSys.warning("cellGcmSetTile(index=%d, location=%d, offset=%d, size=%d, pitch=%d, comp=%d, base=%d, bank=%d)", index, location, offset, size, pitch, comp, base, bank); @@ -1267,19 +1272,16 @@ s32 cellGcmSetTile(u8 index, u8 location, u32 offset, u32 size, u32 pitch, u8 co // Copied form cellGcmSetTileInfo if (index >= rsx::limits::tiles_count || base >= 2048 || bank >= 4) { - cellGcmSys.error("cellGcmSetTile: CELL_GCM_ERROR_INVALID_VALUE"); return CELL_GCM_ERROR_INVALID_VALUE; } if (offset & 0xffff || size & 0xffff || pitch & 0xff) { - cellGcmSys.error("cellGcmSetTile: CELL_GCM_ERROR_INVALID_ALIGNMENT"); return CELL_GCM_ERROR_INVALID_ALIGNMENT; } if (location >= 2 || (comp != 0 && (comp < 7 || comp > 12))) { - cellGcmSys.error("cellGcmSetTile: CELL_GCM_ERROR_INVALID_ENUM"); return CELL_GCM_ERROR_INVALID_ENUM; } @@ -1304,49 +1306,49 @@ s32 cellGcmSetTile(u8 index, u8 location, u32 offset, u32 size, u32 pitch, u8 co return CELL_OK; } -s32 _cellGcmFunc2() +error_code _cellGcmFunc2() { cellGcmSys.todo("_cellGcmFunc2()"); return CELL_OK; } -s32 _cellGcmFunc3() +error_code _cellGcmFunc3() { cellGcmSys.todo("_cellGcmFunc3()"); return CELL_OK; } -s32 _cellGcmFunc4() +error_code _cellGcmFunc4() { cellGcmSys.todo("_cellGcmFunc4()"); return CELL_OK; } -s32 _cellGcmFunc13() +error_code _cellGcmFunc13() { cellGcmSys.todo("_cellGcmFunc13()"); return CELL_OK; } -s32 _cellGcmFunc38() +error_code _cellGcmFunc38() { cellGcmSys.todo("_cellGcmFunc38()"); return CELL_OK; } -s32 cellGcmGpadGetStatus(vm::ptr status) +error_code cellGcmGpadGetStatus(vm::ptr status) { cellGcmSys.todo("cellGcmGpadGetStatus(status=*0x%x)", status); return CELL_OK; } -s32 cellGcmGpadNotifyCaptureSurface(vm::ptr surface) +error_code cellGcmGpadNotifyCaptureSurface(vm::ptr surface) { cellGcmSys.todo("cellGcmGpadNotifyCaptureSurface(surface=*0x%x)", surface); return CELL_OK; } -s32 cellGcmGpadCaptureSnapshot(u32 num) +error_code cellGcmGpadCaptureSnapshot(u32 num) { cellGcmSys.todo("cellGcmGpadCaptureSnapshot(num=%d)", num); return CELL_OK; diff --git a/rpcs3/Emu/Cell/Modules/cellGcmSys.h b/rpcs3/Emu/Cell/Modules/cellGcmSys.h index 3b3ea8b76e..3f8606835d 100644 --- a/rpcs3/Emu/Cell/Modules/cellGcmSys.h +++ b/rpcs3/Emu/Cell/Modules/cellGcmSys.h @@ -3,7 +3,7 @@ #include "Emu/RSX/GCM.h" #include "Emu/Memory/vm_ptr.h" -enum +enum CellGcmError : u32 { CELL_GCM_ERROR_FAILURE = 0x802100ff, CELL_GCM_ERROR_NO_IO_PAGE_TABLE = 0x80210001, @@ -20,6 +20,3 @@ struct CellGcmOffsetTable }; void InitOffsetTable(); - -// Auxiliary functions -s32 gcmMapEaIoAddress(u32 ea, u32 io, u32 size, bool is_strict);