summaryrefslogtreecommitdiffstats
path: root/src/core/hle/service/nvdrv/interface.cpp
diff options
context:
space:
mode:
authorFernando Sahmkow <fsahmkow27@gmail.com>2019-06-16 17:43:41 +0200
committerFernandoS27 <fsahmkow27@gmail.com>2019-07-05 21:49:28 +0200
commitb6844bec608ed82511738e9f3911e72aeb05243a (patch)
tree4a06bdb82d2cbceedee70ac41725c7354d1ec723 /src/core/hle/service/nvdrv/interface.cpp
parentGPU: Correct Interrupts to interrupt on syncpt/value instead of event, mirroring hardware (diff)
downloadyuzu-b6844bec608ed82511738e9f3911e72aeb05243a.tar
yuzu-b6844bec608ed82511738e9f3911e72aeb05243a.tar.gz
yuzu-b6844bec608ed82511738e9f3911e72aeb05243a.tar.bz2
yuzu-b6844bec608ed82511738e9f3911e72aeb05243a.tar.lz
yuzu-b6844bec608ed82511738e9f3911e72aeb05243a.tar.xz
yuzu-b6844bec608ed82511738e9f3911e72aeb05243a.tar.zst
yuzu-b6844bec608ed82511738e9f3911e72aeb05243a.zip
Diffstat (limited to 'src/core/hle/service/nvdrv/interface.cpp')
-rw-r--r--src/core/hle/service/nvdrv/interface.cpp34
1 files changed, 30 insertions, 4 deletions
diff --git a/src/core/hle/service/nvdrv/interface.cpp b/src/core/hle/service/nvdrv/interface.cpp
index a4cb8cb81..45912153d 100644
--- a/src/core/hle/service/nvdrv/interface.cpp
+++ b/src/core/hle/service/nvdrv/interface.cpp
@@ -8,6 +8,7 @@
#include "core/hle/ipc_helpers.h"
#include "core/hle/kernel/kernel.h"
#include "core/hle/kernel/readable_event.h"
+#include "core/hle/kernel/thread.h"
#include "core/hle/kernel/writable_event.h"
#include "core/hle/service/nvdrv/interface.h"
#include "core/hle/service/nvdrv/nvdata.h"
@@ -41,11 +42,36 @@ void NVDRV::Ioctl(Kernel::HLERequestContext& ctx) {
std::vector<u8> output(ctx.GetWriteBufferSize());
- IPC::ResponseBuilder rb{ctx, 3};
- rb.Push(RESULT_SUCCESS);
- rb.Push(nvdrv->Ioctl(fd, command, ctx.ReadBuffer(), output));
+ IoctlCtrl ctrl{};
+
+ u32 result = nvdrv->Ioctl(fd, command, ctx.ReadBuffer(), output, ctrl);
- ctx.WriteBuffer(output);
+ if (!ctrl.must_delay) {
+ IPC::ResponseBuilder rb{ctx, 3};
+ rb.Push(RESULT_SUCCESS);
+ rb.Push(result);
+
+ ctx.WriteBuffer(output);
+ return;
+ }
+ ctrl.fresh_call = false;
+ ctx.SleepClientThread(
+ "NVServices::DelayedResponse", ctrl.timeout,
+ [this, ctrl = ctrl](Kernel::SharedPtr<Kernel::Thread> thread, Kernel::HLERequestContext& ctx,
+ Kernel::ThreadWakeupReason reason) {
+ IPC::RequestParser rp{ctx};
+ u32 fd = rp.Pop<u32>();
+ u32 command = rp.Pop<u32>();
+ std::vector<u8> output(ctx.GetWriteBufferSize());
+ IoctlCtrl ctrl2{ctrl};
+ u32 result = nvdrv->Ioctl(fd, command, ctx.ReadBuffer(), output, ctrl2);
+ IPC::ResponseBuilder rb{ctx, 3};
+ rb.Push(RESULT_SUCCESS);
+ rb.Push(result);
+
+ ctx.WriteBuffer(output);
+ },
+ nvdrv->GetEventWriteable(ctrl.event_id));
}
void NVDRV::Close(Kernel::HLERequestContext& ctx) {