diff --git a/core/libs/prx/libkernel/Apr/src/Apr.cpp b/core/libs/prx/libkernel/Apr/src/Apr.cpp index 0fe1b7c5b..a363671b9 100644 --- a/core/libs/prx/libkernel/Apr/src/Apr.cpp +++ b/core/libs/prx/libkernel/Apr/src/Apr.cpp @@ -590,7 +590,7 @@ void _execute(const Apr::CommandBufferObject& buffer) { } case Apr::Opcode::WriteKernelEventQueue: { const auto command = _read(buffer, cursor); - EqueueTriggerEvent_nid_postfix(static_cast(command.equeue), static_cast(command.ident), EVFILT_USER, reinterpret_cast(command.data)); + EqueueTriggerEvent_nid_postfix(static_cast(command.equeue), static_cast(command.ident), EVFILT_AMPR, reinterpret_cast(command.data)); break; } case Apr::Opcode::WriteAddressFromTimeCounter: { diff --git a/core/libs/prx/libkernel/Equeue/Equeue.cpp b/core/libs/prx/libkernel/Equeue/Equeue.cpp index 7d4769d6e..b8d41b762 100644 --- a/core/libs/prx/libkernel/Equeue/Equeue.cpp +++ b/core/libs/prx/libkernel/Equeue/Equeue.cpp @@ -441,7 +441,7 @@ int APS5_VABI sceKernelAddAmprEvent(KernelEqueue eq, int id, void* udata) { } KernelEqueueEvent event{}; event.event.ident = static_cast(id); - event.event.filter = EVFILT_USER; + event.event.filter = EVFILT_AMPR; event.event.flags = EV_ADD | EV_CLEAR; event.event.udata = udata; event.filter.triggerFunc = [](KernelEqueueEvent* e, void* data) { @@ -473,7 +473,7 @@ int APS5_VABI sceKernelDeleteAmprEvent(KernelEqueue eq, int id) { if (eq == 0) { return EQUEUE_OK; } - EqueueDeleteEvent_nid_postfix(eq, static_cast(id), EVFILT_USER); + EqueueDeleteEvent_nid_postfix(eq, static_cast(id), EVFILT_AMPR); return EQUEUE_OK; } diff --git a/core/libs/prx/libkernel/Equeue/Equeue.hpp b/core/libs/prx/libkernel/Equeue/Equeue.hpp index c5d4f3e5d..dd3a47706 100644 --- a/core/libs/prx/libkernel/Equeue/Equeue.hpp +++ b/core/libs/prx/libkernel/Equeue/Equeue.hpp @@ -18,6 +18,7 @@ static constexpr int16_t EVFILT_TIMER = -7; static constexpr int16_t EVFILT_USER = -11; static constexpr int16_t EVFILT_VIDEO_OUT = -13; static constexpr int16_t EVFILT_HRTIMER = -15; +static constexpr int16_t EVFILT_AMPR = -25; static constexpr uint16_t EV_ADD = 0x0001; static constexpr uint16_t EV_ONESHOT = 0x0010; diff --git a/core/libs/tests/GuestAmpr.cpp b/core/libs/tests/GuestAmpr.cpp index c36095250..caf6408de 100644 --- a/core/libs/tests/GuestAmpr.cpp +++ b/core/libs/tests/GuestAmpr.cpp @@ -1,3 +1,4 @@ +#include "SceTypes.hpp" #include "prx/libc/include/general/VabiMacros.hpp" #include "prx/libkernel/Apr/include/AprCommandBuffer.hpp" #include @@ -112,6 +113,15 @@ std::int64_t APS5_VABI sceAmprAmmMeasureAmmCommandSizeModifyProtect(std::uint64_ std::int64_t APS5_VABI sceAmprAmmMeasureAmmCommandSizeModifyProtectWithGpuMaskId(std::uint64_t, std::uint64_t, std::int32_t, std::int32_t, std::uint8_t); std::int64_t APS5_VABI sceAmprAmmMeasureAmmCommandSizeModifyMtypeProtect(std::uint64_t, std::uint64_t, std::int32_t, std::int32_t, std::int32_t); std::int64_t APS5_VABI sceAmprAmmMeasureAmmCommandSizeModifyMtypeProtectWithGpuMaskId(std::uint64_t, std::uint64_t, std::int32_t, std::int32_t, std::int32_t, std::uint8_t); +int APS5_VABI sceKernelCreateEqueue(KernelEqueue*, const char*); +int APS5_VABI sceKernelDeleteEqueue(KernelEqueue); +int APS5_VABI sceKernelWaitEqueue(KernelEqueue, KernelEvent*, int, int*, const KernelUseconds*); +int APS5_VABI sceKernelAddAmprEvent(KernelEqueue, int, void*); +int APS5_VABI sceKernelDeleteAmprEvent(KernelEqueue, int); +int APS5_VABI sceKernelGetEventFilter(const KernelEvent*); +std::uintptr_t APS5_VABI sceKernelGetEventId(const KernelEvent*); +std::intptr_t APS5_VABI sceKernelGetEventData(const KernelEvent*); +void* APS5_VABI sceKernelGetEventUserData(const KernelEvent*); } static void RequireAt(bool value, int line) { @@ -247,6 +257,24 @@ void TestSubmission() { Require(first == 0x1111 && second == 0x2222); } +void TestKernelEventQueue() { + KernelEqueue eq = 0; + int userData = 0; + Require(sceKernelCreateEqueue(&eq, "ampr") == 0); + Require(sceKernelAddAmprEvent(eq, 7, &userData) == 0); + Recorder recorder; + Require(sceAmprCommandBufferWriteKernelEventQueue_04_00(&recorder.buffer, static_cast(eq), 7, 0x1234, 0) == 0); + Require(sceKernelAprSubmitCommandBuffer(&recorder.buffer, 0) == 0); + KernelEvent event{}; + int count = 0; + const KernelUseconds poll = 0; + Require(sceKernelWaitEqueue(eq, &event, 1, &count, &poll) == 0 && count == 1); + Require(sceKernelGetEventFilter(&event) == -25); + Require(sceKernelGetEventId(&event) == 7 && sceKernelGetEventData(&event) == 0x1234 && sceKernelGetEventUserData(&event) == &userData); + Require(sceKernelDeleteAmprEvent(eq, 7) == 0); + Require(sceKernelDeleteEqueue(eq) == 0); +} + void TestWaits() { Recorder recorder; alignas(8) std::uint64_t value = 5; @@ -902,6 +930,7 @@ int main() { TestRejectedArguments(); TestFullBuffer(); TestSubmission(); + TestKernelEventQueue(); TestWaits(); TestCounters(); TestRejectedWaitsAndCounters();