mirror of
https://github.com/yuzu-mirror/yuzu.git
synced 2024-11-08 04:59:58 +00:00
service: vi: Implement CloseLayer.
- Needed for Undertale.
This commit is contained in:
parent
624a0f7f3f
commit
64c5631579
5 changed files with 48 additions and 11 deletions
|
@ -88,6 +88,12 @@ std::optional<u64> NVFlinger::CreateLayer(u64 display_id) {
|
||||||
return layer_id;
|
return layer_id;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void NVFlinger::CloseLayer(u64 layer_id) {
|
||||||
|
for (auto& display : displays) {
|
||||||
|
display.CloseLayer(layer_id);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
std::optional<u32> NVFlinger::FindBufferQueueId(u64 display_id, u64 layer_id) const {
|
std::optional<u32> NVFlinger::FindBufferQueueId(u64 display_id, u64 layer_id) const {
|
||||||
const auto* const layer = FindLayer(display_id, layer_id);
|
const auto* const layer = FindLayer(display_id, layer_id);
|
||||||
|
|
||||||
|
|
|
@ -54,6 +54,9 @@ public:
|
||||||
/// If an invalid display ID is specified, then an empty optional is returned.
|
/// If an invalid display ID is specified, then an empty optional is returned.
|
||||||
std::optional<u64> CreateLayer(u64 display_id);
|
std::optional<u64> CreateLayer(u64 display_id);
|
||||||
|
|
||||||
|
/// Closes a layer on all displays for the given layer ID.
|
||||||
|
void CloseLayer(u64 layer_id);
|
||||||
|
|
||||||
/// Finds the buffer queue ID of the specified layer in the specified display.
|
/// Finds the buffer queue ID of the specified layer in the specified display.
|
||||||
///
|
///
|
||||||
/// If an invalid display ID or layer ID is provided, then an empty optional is returned.
|
/// If an invalid display ID or layer ID is provided, then an empty optional is returned.
|
||||||
|
|
|
@ -24,11 +24,11 @@ Display::Display(u64 id, std::string name, Core::System& system) : id{id}, name{
|
||||||
Display::~Display() = default;
|
Display::~Display() = default;
|
||||||
|
|
||||||
Layer& Display::GetLayer(std::size_t index) {
|
Layer& Display::GetLayer(std::size_t index) {
|
||||||
return layers.at(index);
|
return *layers.at(index);
|
||||||
}
|
}
|
||||||
|
|
||||||
const Layer& Display::GetLayer(std::size_t index) const {
|
const Layer& Display::GetLayer(std::size_t index) const {
|
||||||
return layers.at(index);
|
return *layers.at(index);
|
||||||
}
|
}
|
||||||
|
|
||||||
std::shared_ptr<Kernel::ReadableEvent> Display::GetVSyncEvent() const {
|
std::shared_ptr<Kernel::ReadableEvent> Display::GetVSyncEvent() const {
|
||||||
|
@ -43,29 +43,38 @@ void Display::CreateLayer(u64 id, NVFlinger::BufferQueue& buffer_queue) {
|
||||||
// TODO(Subv): Support more than 1 layer.
|
// TODO(Subv): Support more than 1 layer.
|
||||||
ASSERT_MSG(layers.empty(), "Only one layer is supported per display at the moment");
|
ASSERT_MSG(layers.empty(), "Only one layer is supported per display at the moment");
|
||||||
|
|
||||||
layers.emplace_back(id, buffer_queue);
|
layers.emplace_back(std::make_shared<Layer>(id, buffer_queue));
|
||||||
|
}
|
||||||
|
|
||||||
|
void Display::CloseLayer(u64 id) {
|
||||||
|
layers.erase(
|
||||||
|
std::remove_if(layers.begin(), layers.end(),
|
||||||
|
[id](const std::shared_ptr<Layer>& layer) { return layer->GetID() == id; }),
|
||||||
|
layers.end());
|
||||||
}
|
}
|
||||||
|
|
||||||
Layer* Display::FindLayer(u64 id) {
|
Layer* Display::FindLayer(u64 id) {
|
||||||
const auto itr = std::find_if(layers.begin(), layers.end(),
|
const auto itr =
|
||||||
[id](const VI::Layer& layer) { return layer.GetID() == id; });
|
std::find_if(layers.begin(), layers.end(),
|
||||||
|
[id](const std::shared_ptr<Layer>& layer) { return layer->GetID() == id; });
|
||||||
|
|
||||||
if (itr == layers.end()) {
|
if (itr == layers.end()) {
|
||||||
return nullptr;
|
return nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
return &*itr;
|
return itr->get();
|
||||||
}
|
}
|
||||||
|
|
||||||
const Layer* Display::FindLayer(u64 id) const {
|
const Layer* Display::FindLayer(u64 id) const {
|
||||||
const auto itr = std::find_if(layers.begin(), layers.end(),
|
const auto itr =
|
||||||
[id](const VI::Layer& layer) { return layer.GetID() == id; });
|
std::find_if(layers.begin(), layers.end(),
|
||||||
|
[id](const std::shared_ptr<Layer>& layer) { return layer->GetID() == id; });
|
||||||
|
|
||||||
if (itr == layers.end()) {
|
if (itr == layers.end()) {
|
||||||
return nullptr;
|
return nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
return &*itr;
|
return itr->get();
|
||||||
}
|
}
|
||||||
|
|
||||||
} // namespace Service::VI
|
} // namespace Service::VI
|
||||||
|
|
|
@ -4,6 +4,7 @@
|
||||||
|
|
||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
|
#include <memory>
|
||||||
#include <string>
|
#include <string>
|
||||||
#include <vector>
|
#include <vector>
|
||||||
|
|
||||||
|
@ -69,6 +70,12 @@ public:
|
||||||
///
|
///
|
||||||
void CreateLayer(u64 id, NVFlinger::BufferQueue& buffer_queue);
|
void CreateLayer(u64 id, NVFlinger::BufferQueue& buffer_queue);
|
||||||
|
|
||||||
|
/// Closes and removes a layer from this display with the given ID.
|
||||||
|
///
|
||||||
|
/// @param id The ID assigned to the layer to close.
|
||||||
|
///
|
||||||
|
void CloseLayer(u64 id);
|
||||||
|
|
||||||
/// Attempts to find a layer with the given ID.
|
/// Attempts to find a layer with the given ID.
|
||||||
///
|
///
|
||||||
/// @param id The layer ID.
|
/// @param id The layer ID.
|
||||||
|
@ -91,7 +98,7 @@ private:
|
||||||
u64 id;
|
u64 id;
|
||||||
std::string name;
|
std::string name;
|
||||||
|
|
||||||
std::vector<Layer> layers;
|
std::vector<std::shared_ptr<Layer>> layers;
|
||||||
Kernel::EventPair vsync_event;
|
Kernel::EventPair vsync_event;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
|
@ -1066,6 +1066,18 @@ private:
|
||||||
rb.Push<u64>(ctx.WriteBuffer(native_window.Serialize()));
|
rb.Push<u64>(ctx.WriteBuffer(native_window.Serialize()));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void CloseLayer(Kernel::HLERequestContext& ctx) {
|
||||||
|
IPC::RequestParser rp{ctx};
|
||||||
|
const auto layer_id{rp.Pop<u64>()};
|
||||||
|
|
||||||
|
LOG_DEBUG(Service_VI, "called. layer_id=0x{:016X}", layer_id);
|
||||||
|
|
||||||
|
nv_flinger->CloseLayer(layer_id);
|
||||||
|
|
||||||
|
IPC::ResponseBuilder rb{ctx, 2};
|
||||||
|
rb.Push(RESULT_SUCCESS);
|
||||||
|
}
|
||||||
|
|
||||||
void CreateStrayLayer(Kernel::HLERequestContext& ctx) {
|
void CreateStrayLayer(Kernel::HLERequestContext& ctx) {
|
||||||
IPC::RequestParser rp{ctx};
|
IPC::RequestParser rp{ctx};
|
||||||
const u32 flags = rp.Pop<u32>();
|
const u32 flags = rp.Pop<u32>();
|
||||||
|
@ -1178,7 +1190,7 @@ IApplicationDisplayService::IApplicationDisplayService(
|
||||||
{1101, &IApplicationDisplayService::SetDisplayEnabled, "SetDisplayEnabled"},
|
{1101, &IApplicationDisplayService::SetDisplayEnabled, "SetDisplayEnabled"},
|
||||||
{1102, &IApplicationDisplayService::GetDisplayResolution, "GetDisplayResolution"},
|
{1102, &IApplicationDisplayService::GetDisplayResolution, "GetDisplayResolution"},
|
||||||
{2020, &IApplicationDisplayService::OpenLayer, "OpenLayer"},
|
{2020, &IApplicationDisplayService::OpenLayer, "OpenLayer"},
|
||||||
{2021, nullptr, "CloseLayer"},
|
{2021, &IApplicationDisplayService::CloseLayer, "CloseLayer"},
|
||||||
{2030, &IApplicationDisplayService::CreateStrayLayer, "CreateStrayLayer"},
|
{2030, &IApplicationDisplayService::CreateStrayLayer, "CreateStrayLayer"},
|
||||||
{2031, &IApplicationDisplayService::DestroyStrayLayer, "DestroyStrayLayer"},
|
{2031, &IApplicationDisplayService::DestroyStrayLayer, "DestroyStrayLayer"},
|
||||||
{2101, &IApplicationDisplayService::SetLayerScalingMode, "SetLayerScalingMode"},
|
{2101, &IApplicationDisplayService::SetLayerScalingMode, "SetLayerScalingMode"},
|
||||||
|
|
Loading…
Reference in a new issue