summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/core/hle/service/nvflinger/nvflinger.cpp7
-rw-r--r--src/core/hle/service/nvflinger/nvflinger.h6
-rw-r--r--src/core/hle/service/vi/display/vi_display.cpp15
-rw-r--r--src/core/hle/service/vi/display/vi_display.h14
-rw-r--r--src/core/hle/service/vi/vi.cpp14
5 files changed, 42 insertions, 14 deletions
diff --git a/src/core/hle/service/nvflinger/nvflinger.cpp b/src/core/hle/service/nvflinger/nvflinger.cpp
index 9b382bf56..93057e800 100644
--- a/src/core/hle/service/nvflinger/nvflinger.cpp
+++ b/src/core/hle/service/nvflinger/nvflinger.cpp
@@ -22,6 +22,7 @@
22#include "core/hle/service/nvflinger/ui/graphic_buffer.h" 22#include "core/hle/service/nvflinger/ui/graphic_buffer.h"
23#include "core/hle/service/vi/display/vi_display.h" 23#include "core/hle/service/vi/display/vi_display.h"
24#include "core/hle/service/vi/layer/vi_layer.h" 24#include "core/hle/service/vi/layer/vi_layer.h"
25#include "core/hle/service/vi/vi_results.h"
25#include "video_core/gpu.h" 26#include "video_core/gpu.h"
26 27
27namespace Service::NVFlinger { 28namespace Service::NVFlinger {
@@ -163,15 +164,15 @@ std::optional<u32> NVFlinger::FindBufferQueueId(u64 display_id, u64 layer_id) {
163 return layer->GetBinderId(); 164 return layer->GetBinderId();
164} 165}
165 166
166Kernel::KReadableEvent* NVFlinger::FindVsyncEvent(u64 display_id) { 167ResultVal<Kernel::KReadableEvent*> NVFlinger::FindVsyncEvent(u64 display_id) {
167 const auto lock_guard = Lock(); 168 const auto lock_guard = Lock();
168 auto* const display = FindDisplay(display_id); 169 auto* const display = FindDisplay(display_id);
169 170
170 if (display == nullptr) { 171 if (display == nullptr) {
171 return nullptr; 172 return VI::ResultNotFound;
172 } 173 }
173 174
174 return &display->GetVSyncEvent(); 175 return display->GetVSyncEvent();
175} 176}
176 177
177VI::Display* NVFlinger::FindDisplay(u64 display_id) { 178VI::Display* NVFlinger::FindDisplay(u64 display_id) {
diff --git a/src/core/hle/service/nvflinger/nvflinger.h b/src/core/hle/service/nvflinger/nvflinger.h
index 044ac6ac8..3bbe5d92b 100644
--- a/src/core/hle/service/nvflinger/nvflinger.h
+++ b/src/core/hle/service/nvflinger/nvflinger.h
@@ -11,6 +11,7 @@
11#include <vector> 11#include <vector>
12 12
13#include "common/common_types.h" 13#include "common/common_types.h"
14#include "core/hle/result.h"
14#include "core/hle/service/kernel_helpers.h" 15#include "core/hle/service/kernel_helpers.h"
15 16
16namespace Common { 17namespace Common {
@@ -71,8 +72,9 @@ public:
71 72
72 /// Gets the vsync event for the specified display. 73 /// Gets the vsync event for the specified display.
73 /// 74 ///
74 /// If an invalid display ID is provided, then nullptr is returned. 75 /// If an invalid display ID is provided, then VI::ResultNotFound is returned.
75 [[nodiscard]] Kernel::KReadableEvent* FindVsyncEvent(u64 display_id); 76 /// If the vsync event has already been retrieved, then VI::ResultPermissionDenied is returned.
77 [[nodiscard]] ResultVal<Kernel::KReadableEvent*> FindVsyncEvent(u64 display_id);
76 78
77 /// Performs a composition request to the emulated nvidia GPU and triggers the vsync events when 79 /// Performs a composition request to the emulated nvidia GPU and triggers the vsync events when
78 /// finished. 80 /// finished.
diff --git a/src/core/hle/service/vi/display/vi_display.cpp b/src/core/hle/service/vi/display/vi_display.cpp
index b34febb50..aa49aa775 100644
--- a/src/core/hle/service/vi/display/vi_display.cpp
+++ b/src/core/hle/service/vi/display/vi_display.cpp
@@ -19,6 +19,7 @@
19#include "core/hle/service/nvflinger/hos_binder_driver_server.h" 19#include "core/hle/service/nvflinger/hos_binder_driver_server.h"
20#include "core/hle/service/vi/display/vi_display.h" 20#include "core/hle/service/vi/display/vi_display.h"
21#include "core/hle/service/vi/layer/vi_layer.h" 21#include "core/hle/service/vi/layer/vi_layer.h"
22#include "core/hle/service/vi/vi_results.h"
22 23
23namespace Service::VI { 24namespace Service::VI {
24 25
@@ -55,8 +56,18 @@ const Layer& Display::GetLayer(std::size_t index) const {
55 return *layers.at(index); 56 return *layers.at(index);
56} 57}
57 58
58Kernel::KReadableEvent& Display::GetVSyncEvent() { 59ResultVal<Kernel::KReadableEvent*> Display::GetVSyncEvent() {
59 return vsync_event->GetReadableEvent(); 60 if (got_vsync_event) {
61 return ResultPermissionDenied;
62 }
63
64 got_vsync_event = true;
65
66 return GetVSyncEventUnchecked();
67}
68
69Kernel::KReadableEvent* Display::GetVSyncEventUnchecked() {
70 return &vsync_event->GetReadableEvent();
60} 71}
61 72
62void Display::SignalVSyncEvent() { 73void Display::SignalVSyncEvent() {
diff --git a/src/core/hle/service/vi/display/vi_display.h b/src/core/hle/service/vi/display/vi_display.h
index 3838bb599..8dbb0ef80 100644
--- a/src/core/hle/service/vi/display/vi_display.h
+++ b/src/core/hle/service/vi/display/vi_display.h
@@ -9,6 +9,7 @@
9 9
10#include "common/common_funcs.h" 10#include "common/common_funcs.h"
11#include "common/common_types.h" 11#include "common/common_types.h"
12#include "core/hle/result.h"
12 13
13namespace Kernel { 14namespace Kernel {
14class KEvent; 15class KEvent;
@@ -73,8 +74,16 @@ public:
73 return layers.size(); 74 return layers.size();
74 } 75 }
75 76
76 /// Gets the readable vsync event. 77 /**
77 Kernel::KReadableEvent& GetVSyncEvent(); 78 * Gets the internal vsync event.
79 *
80 * @returns The internal Vsync event if it has not yet been retrieved,
81 * VI::ResultPermissionDenied otherwise.
82 */
83 [[nodiscard]] ResultVal<Kernel::KReadableEvent*> GetVSyncEvent();
84
85 /// Gets the internal vsync event.
86 Kernel::KReadableEvent* GetVSyncEventUnchecked();
78 87
79 /// Signals the internal vsync event. 88 /// Signals the internal vsync event.
80 void SignalVSyncEvent(); 89 void SignalVSyncEvent();
@@ -118,6 +127,7 @@ private:
118 127
119 std::vector<std::unique_ptr<Layer>> layers; 128 std::vector<std::unique_ptr<Layer>> layers;
120 Kernel::KEvent* vsync_event{}; 129 Kernel::KEvent* vsync_event{};
130 bool got_vsync_event{false};
121}; 131};
122 132
123} // namespace Service::VI 133} // namespace Service::VI
diff --git a/src/core/hle/service/vi/vi.cpp b/src/core/hle/service/vi/vi.cpp
index 0a347a0e9..f083811ec 100644
--- a/src/core/hle/service/vi/vi.cpp
+++ b/src/core/hle/service/vi/vi.cpp
@@ -671,19 +671,23 @@ private:
671 IPC::RequestParser rp{ctx}; 671 IPC::RequestParser rp{ctx};
672 const u64 display_id = rp.Pop<u64>(); 672 const u64 display_id = rp.Pop<u64>();
673 673
674 LOG_WARNING(Service_VI, "(STUBBED) called. display_id=0x{:016X}", display_id); 674 LOG_DEBUG(Service_VI, "called. display_id={}", display_id);
675 675
676 const auto vsync_event = nv_flinger.FindVsyncEvent(display_id); 676 const auto vsync_event = nv_flinger.FindVsyncEvent(display_id);
677 if (!vsync_event) { 677 if (vsync_event.Failed()) {
678 LOG_ERROR(Service_VI, "Vsync event was not found for display_id={}", display_id); 678 const auto result = vsync_event.Code();
679 if (result == ResultNotFound) {
680 LOG_ERROR(Service_VI, "Vsync event was not found for display_id={}", display_id);
681 }
682
679 IPC::ResponseBuilder rb{ctx, 2}; 683 IPC::ResponseBuilder rb{ctx, 2};
680 rb.Push(ResultNotFound); 684 rb.Push(result);
681 return; 685 return;
682 } 686 }
683 687
684 IPC::ResponseBuilder rb{ctx, 2, 1}; 688 IPC::ResponseBuilder rb{ctx, 2, 1};
685 rb.Push(ResultSuccess); 689 rb.Push(ResultSuccess);
686 rb.PushCopyObjects(vsync_event); 690 rb.PushCopyObjects(*vsync_event);
687 } 691 }
688 692
689 void ConvertScalingMode(Kernel::HLERequestContext& ctx) { 693 void ConvertScalingMode(Kernel::HLERequestContext& ctx) {