From 9aa2f204f5ff1a77977ee215b0f4f4f305ef42bb Mon Sep 17 00:00:00 2001 From: Ben Vanik Date: Mon, 6 Jan 2014 23:57:12 -0800 Subject: [PATCH] PulseEvent. Surprised anyone uses this. --- src/xenia/kernel/objects/xevent.cc | 4 ++ src/xenia/kernel/objects/xevent.h | 1 + src/xenia/kernel/xboxkrnl_threading.cc | 52 ++++++++++++++++++++++++++ 3 files changed, 57 insertions(+) diff --git a/src/xenia/kernel/objects/xevent.cc b/src/xenia/kernel/objects/xevent.cc index cf1242a8d..ff0b73cc1 100644 --- a/src/xenia/kernel/objects/xevent.cc +++ b/src/xenia/kernel/objects/xevent.cc @@ -56,6 +56,10 @@ int32_t XEvent::Set(uint32_t priority_increment, bool wait) { return SetEvent(handle_) ? 1 : 0; } +int32_t XEvent::Pulse(uint32_t priority_increment, bool wait) { + return PulseEvent(handle_) ? 1 : 0; +} + int32_t XEvent::Reset() { return ResetEvent(handle_) ? 1 : 0; } diff --git a/src/xenia/kernel/objects/xevent.h b/src/xenia/kernel/objects/xevent.h index f9c7fea44..eb2b9a070 100644 --- a/src/xenia/kernel/objects/xevent.h +++ b/src/xenia/kernel/objects/xevent.h @@ -28,6 +28,7 @@ public: void InitializeNative(void* native_ptr, DISPATCH_HEADER& header); int32_t Set(uint32_t priority_increment, bool wait); + int32_t Pulse(uint32_t priority_increment, bool wait); int32_t Reset(); void Clear(); diff --git a/src/xenia/kernel/xboxkrnl_threading.cc b/src/xenia/kernel/xboxkrnl_threading.cc index 4dda918f1..cad9cc8e0 100644 --- a/src/xenia/kernel/xboxkrnl_threading.cc +++ b/src/xenia/kernel/xboxkrnl_threading.cc @@ -661,6 +661,56 @@ SHIM_CALL NtSetEvent_shim( } +SHIM_CALL KePulseEvent_shim( + PPCContext* ppc_state, KernelState* state) { + uint32_t event_ref = SHIM_GET_ARG_32(0); + uint32_t increment = SHIM_GET_ARG_32(1); + uint32_t wait = SHIM_GET_ARG_32(2); + + XELOGD( + "KePulseEvent(%.8X, %.8X, %.8X)", + event_ref, increment, wait); + + int32_t result = 0; + + void* event_ptr = SHIM_MEM_ADDR(event_ref); + XEvent* ev = (XEvent*)XObject::GetObject(state, event_ptr); + XEASSERTNOTNULL(ev); + if (ev) { + result = ev->Pulse(increment, !!wait); + } + + SHIM_SET_RETURN(result); +} + + +SHIM_CALL NtPulseEvent_shim( + PPCContext* ppc_state, KernelState* state) { + uint32_t event_handle = SHIM_GET_ARG_32(0); + uint32_t previous_state_ptr = SHIM_GET_ARG_32(1); + + XELOGD( + "NtPulseEvent(%.8X, %.8X)", + event_handle, previous_state_ptr); + + X_STATUS result = X_STATUS_SUCCESS; + + XEvent* ev = NULL; + result = state->object_table()->GetObject( + event_handle, (XObject**)&ev); + if (XSUCCEEDED(result)) { + int32_t was_signalled = ev->Pulse(0, false); + if (previous_state_ptr) { + SHIM_SET_MEM_32(previous_state_ptr, was_signalled); + } + + ev->Release(); + } + + SHIM_SET_RETURN(result); +} + + int32_t xeKeResetEvent(void* event_ptr) { KernelState* state = shared_kernel_state_; XEASSERTNOTNULL(state); @@ -1045,6 +1095,8 @@ void xe::kernel::xboxkrnl::RegisterThreadingExports( SHIM_SET_MAPPING("xboxkrnl.exe", NtCreateEvent, state); SHIM_SET_MAPPING("xboxkrnl.exe", KeSetEvent, state); SHIM_SET_MAPPING("xboxkrnl.exe", NtSetEvent, state); + SHIM_SET_MAPPING("xboxkrnl.exe", KePulseEvent, state); + SHIM_SET_MAPPING("xboxkrnl.exe", NtPulseEvent, state); SHIM_SET_MAPPING("xboxkrnl.exe", KeResetEvent, state); SHIM_SET_MAPPING("xboxkrnl.exe", NtClearEvent, state);