diff --git a/core/libs/prx/libSceAgc/DcbState/include/ContextState.hpp b/core/libs/prx/libSceAgc/DcbState/include/ContextState.hpp index 409da75f33..99d37d3c6a 100644 --- a/core/libs/prx/libSceAgc/DcbState/include/ContextState.hpp +++ b/core/libs/prx/libSceAgc/DcbState/include/ContextState.hpp @@ -1,4 +1,17 @@ #ifndef CORE_LIBS_PRX_LIBSCEAGC_DCBSTATE_INCLUDE_CONTEXTSTATE_HPP #define CORE_LIBS_PRX_LIBSCEAGC_DCBSTATE_INCLUDE_CONTEXTSTATE_HPP +#include "SceTypes.hpp" +#include + +struct CommandBuffer; + +extern "C" { + +uint32_t* APS5_VABI sceAgcDcbContextStateOp(CommandBuffer* buf, uint32_t operation); +uint32_t* APS5_VABI sceAgcDcbContextStateOp_0100(CommandBuffer* buf, uint32_t operation); +uint64_t APS5_VABI sceAgcDcbContextStateOpGetSize(uint32_t operation); + +} + #endif diff --git a/core/libs/prx/libSceAgc/DcbState/src/ContextState.cpp b/core/libs/prx/libSceAgc/DcbState/src/ContextState.cpp index ffdf58c810..ad1eddc97a 100644 --- a/core/libs/prx/libSceAgc/DcbState/src/ContextState.cpp +++ b/core/libs/prx/libSceAgc/DcbState/src/ContextState.cpp @@ -9,10 +9,7 @@ extern "C" { uint32_t* APS5_VABI sceAgcDcbContextStateOp(CommandBuffer* buf, uint32_t operation) { - (void)buf; - (void)operation; - NotImplemented_nid_no_patch(__func__); - return nullptr; + return sceAgcDcbContextStateOp_0100(buf, operation); } uint64_t APS5_VABI sceAgcDcbContextStateOpGetSize(uint32_t operation) { diff --git a/core/libs/prx/libSceAgc/tests/ContextStateSize.cpp b/core/libs/prx/libSceAgc/tests/ContextStateSize.cpp index 415b81e362..3de0a5eda6 100644 --- a/core/libs/prx/libSceAgc/tests/ContextStateSize.cpp +++ b/core/libs/prx/libSceAgc/tests/ContextStateSize.cpp @@ -8,6 +8,7 @@ #include extern "C" std::uint64_t APS5_VABI sceAgcDcbContextStateOpGetSize(std::uint32_t operation); +extern "C" std::uint32_t* APS5_VABI sceAgcDcbContextStateOp(CommandBuffer* buf, std::uint32_t operation); extern "C" std::uint32_t* APS5_VABI sceAgcDcbContextStateOp_0100(CommandBuffer* buf, std::uint32_t operation); namespace { @@ -37,6 +38,15 @@ void testSizes() { check(sceAgcDcbContextStateOp_0100(&buffer, operation) == words.data(), "context state op did not start at the cursor"); const auto written = static_cast(buffer.cursor_up - words.data()) * sizeof(std::uint32_t); check(written == sizes[operation], "context state size differs from the written packets"); + + std::array unversionedWords{}; + CommandBuffer unversionedBuffer{unversionedWords.data(), unversionedWords.data() + unversionedWords.size(), + unversionedWords.data(), unversionedWords.data() + unversionedWords.size(), + nullptr, nullptr, 0}; + check(sceAgcDcbContextStateOp(&unversionedBuffer, operation) == unversionedWords.data(), "context state op did not start at the cursor"); + const auto unversionedWritten = static_cast(unversionedBuffer.cursor_up - unversionedWords.data()) * sizeof(std::uint32_t); + check(unversionedWritten == sizes[operation], "context state size differs from the written packets"); + check(words == unversionedWords, "unversioned context state op mismatch with versioned op"); } } diff --git a/docs/dev/debt/libSceAgc.md b/docs/dev/debt/libSceAgc.md index 83a5cbca52..5f54222d08 100644 --- a/docs/dev/debt/libSceAgc.md +++ b/docs/dev/debt/libSceAgc.md @@ -17,6 +17,7 @@ - [sceAgcGetIsTrinityMode](../../../core/libs/prx/libSceAgc/Misc/src/Platform.cpp) (libSceAgc) - signature from the only PPSA26344 call (a pointer to a one-byte flag, result ignored); a null pointer throws because its error code is unknown - [sceAgcDcbAtomicGds_0900](../../../core/libs/prx/libSceAgc/DcbFlow/src/Control.cpp) (libSceAgc) - name from its NID (`zARR5aCmkoY`), the DCB counterpart of `sceAgcAcbAtomicGds_0900`, signature unknown - [sceAgcDcbContextStateOpGetSize](../../../core/libs/prx/libSceAgc/DcbState/src/ContextState.cpp) (libSceAgc) - sizes from KytyPS5 only (5, 27, 27 and 32 dwords), equal to what `sceAgcDcbContextStateOp_0100` writes; KytyPS5 returns 0 for an operation above 3, here it throws +- [sceAgcDcbContextStateOp](../../../core/libs/prx/libSceAgc/DcbState/src/ContextState.cpp) (libSceAgc) - delegates to `sceAgcDcbContextStateOp_0100` (same packets as KytyPS5's `AgcDcbContextStateOp`); KytyPS5 returns nullptr for an operation above 3, here it throws; the packet words were not compared with a real console - [sceAgcBranchPatchSetThenTarget_0300, sceAgcBranchPatchSetElseTarget_0300](../../../core/libs/prx/libSceAgc/Patch/src/Branch.cpp) (libSceAgc) - names from their NIDs (`7Wa3aeJgeVU`, `rP5xLdOf26k`); the `(packet, cachePolicy, target, sizeInDwords)` signature is inferred from PPSA28416's calls (a branch packet, 0, an aligned target, 4), with the policy stored where `sceAgcCbBranch` puts it - [sceAgcDcbSet{Cx,Sh,Uc}RegistersIndirectGetSize](../../../core/libs/prx/libSceAgc/DcbState/src/Registers.cpp) (libSceAgc) - the count argument is ignored: PPSA28416 calls them with leftover register contents (0xf5f5039c), so the real functions likely take none; the size is 20 bytes either way - [sceAgcUpdateInterpolantMapping_0100](../../../core/libs/prx/libSceAgc/Misc/src/ShaderFusion.cpp) (libSceAgc) - name from its NID (`k0E7vkgqAuE`); the `(regs, vs, ps)` arguments are the declared ones, behaviour unknown