diff options
Diffstat (limited to 'src/yuzu')
-rw-r--r-- | src/yuzu/CMakeLists.txt | 2 | ||||
-rw-r--r-- | src/yuzu/configuration/config.cpp | 10 | ||||
-rw-r--r-- | src/yuzu/configuration/config.h | 1 | ||||
-rw-r--r-- | src/yuzu/configuration/configure_dialog.cpp | 5 | ||||
-rw-r--r-- | src/yuzu/configuration/configure_dialog.h | 7 | ||||
-rw-r--r-- | src/yuzu/configuration/configure_graphics.cpp | 55 | ||||
-rw-r--r-- | src/yuzu/configuration/configure_graphics.h | 3 | ||||
-rw-r--r-- | src/yuzu/configuration/configure_graphics_advanced.cpp | 18 | ||||
-rw-r--r-- | src/yuzu/configuration/configure_graphics_advanced.h | 2 | ||||
-rw-r--r-- | src/yuzu/configuration/configure_graphics_advanced.ui | 20 | ||||
-rw-r--r-- | src/yuzu/configuration/configure_per_game.cpp | 5 | ||||
-rw-r--r-- | src/yuzu/configuration/configure_per_game.h | 3 | ||||
-rw-r--r-- | src/yuzu/configuration/configure_system.cpp | 3 | ||||
-rw-r--r-- | src/yuzu/main.cpp | 18 | ||||
-rw-r--r-- | src/yuzu/main.h | 6 | ||||
-rw-r--r-- | src/yuzu/vk_device_info.cpp | 61 | ||||
-rw-r--r-- | src/yuzu/vk_device_info.h | 36 |
17 files changed, 201 insertions, 54 deletions
diff --git a/src/yuzu/CMakeLists.txt b/src/yuzu/CMakeLists.txt index 84d9ca796..733c296e4 100644 --- a/src/yuzu/CMakeLists.txt +++ b/src/yuzu/CMakeLists.txt @@ -210,6 +210,8 @@ add_executable(yuzu util/url_request_interceptor.h util/util.cpp util/util.h + vk_device_info.cpp + vk_device_info.h compatdb.cpp compatdb.h yuzu.qrc diff --git a/src/yuzu/configuration/config.cpp b/src/yuzu/configuration/config.cpp index 6288fef62..edc206a25 100644 --- a/src/yuzu/configuration/config.cpp +++ b/src/yuzu/configuration/config.cpp @@ -101,6 +101,12 @@ const std::map<Settings::RendererBackend, QString> Config::renderer_backend_text {Settings::RendererBackend::Null, QStringLiteral(QT_TRANSLATE_NOOP("GMainWindow", "Null"))}, }; +const std::map<Settings::ShaderBackend, QString> Config::shader_backend_texts_map = { + {Settings::ShaderBackend::GLSL, QStringLiteral(QT_TRANSLATE_NOOP("GMainWindow", "GLSL"))}, + {Settings::ShaderBackend::GLASM, QStringLiteral(QT_TRANSLATE_NOOP("GMainWindow", "GLASM"))}, + {Settings::ShaderBackend::SPIRV, QStringLiteral(QT_TRANSLATE_NOOP("GMainWindow", "SPIRV"))}, +}; + // This shouldn't have anything except static initializers (no functions). So // QKeySequence(...).toString() is NOT ALLOWED HERE. // This must be in alphabetical order according to action name as it must have the same order as @@ -754,6 +760,8 @@ void Config::ReadRendererValues() { ReadGlobalSetting(Settings::values.use_fast_gpu_time); ReadGlobalSetting(Settings::values.use_vulkan_driver_pipeline_cache); ReadGlobalSetting(Settings::values.enable_compute_pipelines); + ReadGlobalSetting(Settings::values.use_video_framerate); + ReadGlobalSetting(Settings::values.barrier_feedback_loops); ReadGlobalSetting(Settings::values.bg_red); ReadGlobalSetting(Settings::values.bg_green); ReadGlobalSetting(Settings::values.bg_blue); @@ -1409,6 +1417,8 @@ void Config::SaveRendererValues() { WriteGlobalSetting(Settings::values.use_fast_gpu_time); WriteGlobalSetting(Settings::values.use_vulkan_driver_pipeline_cache); WriteGlobalSetting(Settings::values.enable_compute_pipelines); + WriteGlobalSetting(Settings::values.use_video_framerate); + WriteGlobalSetting(Settings::values.barrier_feedback_loops); WriteGlobalSetting(Settings::values.bg_red); WriteGlobalSetting(Settings::values.bg_green); WriteGlobalSetting(Settings::values.bg_blue); diff --git a/src/yuzu/configuration/config.h b/src/yuzu/configuration/config.h index ad590ea9e..0fd4baf6b 100644 --- a/src/yuzu/configuration/config.h +++ b/src/yuzu/configuration/config.h @@ -54,6 +54,7 @@ public: static const std::map<bool, QString> use_docked_mode_texts_map; static const std::map<Settings::GPUAccuracy, QString> gpu_accuracy_texts_map; static const std::map<Settings::RendererBackend, QString> renderer_backend_texts_map; + static const std::map<Settings::ShaderBackend, QString> shader_backend_texts_map; static constexpr UISettings::Theme default_theme{ #ifdef _WIN32 diff --git a/src/yuzu/configuration/configure_dialog.cpp b/src/yuzu/configuration/configure_dialog.cpp index 8e76a819a..bdf83ebfe 100644 --- a/src/yuzu/configuration/configure_dialog.cpp +++ b/src/yuzu/configuration/configure_dialog.cpp @@ -6,6 +6,7 @@ #include "common/settings.h" #include "core/core.h" #include "ui_configure.h" +#include "vk_device_info.h" #include "yuzu/configuration/config.h" #include "yuzu/configuration/configure_audio.h" #include "yuzu/configuration/configure_cpu.h" @@ -28,6 +29,7 @@ ConfigureDialog::ConfigureDialog(QWidget* parent, HotkeyRegistry& registry_, InputCommon::InputSubsystem* input_subsystem, + std::vector<VkDeviceInfo::Record>& vk_device_records, Core::System& system_, bool enable_web_config) : QDialog(parent), ui{std::make_unique<Ui::ConfigureDialog>()}, registry(registry_), system{system_}, audio_tab{std::make_unique<ConfigureAudio>(system_, @@ -38,7 +40,8 @@ ConfigureDialog::ConfigureDialog(QWidget* parent, HotkeyRegistry& registry_, general_tab{std::make_unique<ConfigureGeneral>(system_, this)}, graphics_advanced_tab{std::make_unique<ConfigureGraphicsAdvanced>(system_, this)}, graphics_tab{std::make_unique<ConfigureGraphics>( - system_, [&]() { graphics_advanced_tab->ExposeComputeOption(); }, this)}, + system_, vk_device_records, [&]() { graphics_advanced_tab->ExposeComputeOption(); }, + this)}, hotkeys_tab{std::make_unique<ConfigureHotkeys>(system_.HIDCore(), this)}, input_tab{std::make_unique<ConfigureInput>(system_, this)}, network_tab{std::make_unique<ConfigureNetwork>(system_, this)}, diff --git a/src/yuzu/configuration/configure_dialog.h b/src/yuzu/configuration/configure_dialog.h index a086a07c4..2a08b7fee 100644 --- a/src/yuzu/configuration/configure_dialog.h +++ b/src/yuzu/configuration/configure_dialog.h @@ -4,7 +4,9 @@ #pragma once #include <memory> +#include <vector> #include <QDialog> +#include "yuzu/vk_device_info.h" namespace Core { class System; @@ -40,8 +42,9 @@ class ConfigureDialog : public QDialog { public: explicit ConfigureDialog(QWidget* parent, HotkeyRegistry& registry_, - InputCommon::InputSubsystem* input_subsystem, Core::System& system_, - bool enable_web_config = true); + InputCommon::InputSubsystem* input_subsystem, + std::vector<VkDeviceInfo::Record>& vk_device_records, + Core::System& system_, bool enable_web_config = true); ~ConfigureDialog() override; void ApplyConfiguration(); diff --git a/src/yuzu/configuration/configure_graphics.cpp b/src/yuzu/configuration/configure_graphics.cpp index 431585216..a4965524a 100644 --- a/src/yuzu/configuration/configure_graphics.cpp +++ b/src/yuzu/configuration/configure_graphics.cpp @@ -1,10 +1,6 @@ // SPDX-FileCopyrightText: 2016 Citra Emulator Project // SPDX-License-Identifier: GPL-2.0-or-later -// Include this early to include Vulkan headers how we want to -#include "video_core/vulkan_common/vulkan_device.h" -#include "video_core/vulkan_common/vulkan_wrapper.h" - #include <algorithm> #include <functional> #include <iosfwd> @@ -34,13 +30,11 @@ #include "common/settings.h" #include "core/core.h" #include "ui_configure_graphics.h" -#include "video_core/vulkan_common/vulkan_instance.h" -#include "video_core/vulkan_common/vulkan_library.h" -#include "video_core/vulkan_common/vulkan_surface.h" #include "yuzu/configuration/configuration_shared.h" #include "yuzu/configuration/configure_graphics.h" #include "yuzu/qt_common.h" #include "yuzu/uisettings.h" +#include "yuzu/vk_device_info.h" static const std::vector<VkPresentModeKHR> default_present_modes{VK_PRESENT_MODE_IMMEDIATE_KHR, VK_PRESENT_MODE_FIFO_KHR}; @@ -77,9 +71,10 @@ static constexpr Settings::VSyncMode PresentModeToSetting(VkPresentModeKHR mode) } ConfigureGraphics::ConfigureGraphics(const Core::System& system_, + std::vector<VkDeviceInfo::Record>& records_, const std::function<void()>& expose_compute_option_, QWidget* parent) - : QWidget(parent), ui{std::make_unique<Ui::ConfigureGraphics>()}, + : QWidget(parent), ui{std::make_unique<Ui::ConfigureGraphics>()}, records{records_}, expose_compute_option{expose_compute_option_}, system{system_} { vulkan_device = Settings::values.vulkan_device.GetValue(); RetrieveVulkanDevices(); @@ -504,47 +499,19 @@ void ConfigureGraphics::UpdateAPILayout() { } } -void ConfigureGraphics::RetrieveVulkanDevices() try { - if (UISettings::values.has_broken_vulkan) { - return; - } - - using namespace Vulkan; - - auto* window = this->window()->windowHandle(); - auto wsi = QtCommon::GetWindowSystemInfo(window); - - vk::InstanceDispatch dld; - const auto library = OpenLibrary(); - const vk::Instance instance = CreateInstance(*library, dld, VK_API_VERSION_1_1, wsi.type); - const std::vector<VkPhysicalDevice> physical_devices = instance.EnumeratePhysicalDevices(); - vk::SurfaceKHR surface = CreateSurface(instance, wsi); - +void ConfigureGraphics::RetrieveVulkanDevices() { vulkan_devices.clear(); - vulkan_devices.reserve(physical_devices.size()); + vulkan_devices.reserve(records.size()); device_present_modes.clear(); - device_present_modes.reserve(physical_devices.size()); - for (const VkPhysicalDevice device : physical_devices) { - const auto physical_device = vk::PhysicalDevice(device, dld); - const std::string name = physical_device.GetProperties().deviceName; - const std::vector<VkPresentModeKHR> present_modes = - physical_device.GetSurfacePresentModesKHR(*surface); - vulkan_devices.push_back(QString::fromStdString(name)); - device_present_modes.push_back(present_modes); - - VkPhysicalDeviceDriverProperties driver_properties{}; - driver_properties.sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_DRIVER_PROPERTIES; - driver_properties.pNext = nullptr; - VkPhysicalDeviceProperties2 properties{}; - properties.sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_PROPERTIES_2_KHR; - properties.pNext = &driver_properties; - dld.vkGetPhysicalDeviceProperties2(physical_device, &properties); - if (driver_properties.driverID == VK_DRIVER_ID_INTEL_PROPRIETARY_WINDOWS) { + device_present_modes.reserve(records.size()); + for (const auto& record : records) { + vulkan_devices.push_back(QString::fromStdString(record.name)); + device_present_modes.push_back(record.vsync_support); + + if (record.has_broken_compute) { expose_compute_option(); } } -} catch (const Vulkan::vk::Exception& exception) { - LOG_ERROR(Frontend, "Failed to enumerate devices with error: {}", exception.what()); } Settings::RendererBackend ConfigureGraphics::GetCurrentGraphicsBackend() const { diff --git a/src/yuzu/configuration/configure_graphics.h b/src/yuzu/configuration/configure_graphics.h index 364b1cac2..be9310b74 100644 --- a/src/yuzu/configuration/configure_graphics.h +++ b/src/yuzu/configuration/configure_graphics.h @@ -12,6 +12,7 @@ #include <qobjectdefs.h> #include <vulkan/vulkan_core.h> #include "common/common_types.h" +#include "vk_device_info.h" class QEvent; class QObject; @@ -39,6 +40,7 @@ class ConfigureGraphics : public QWidget { public: explicit ConfigureGraphics(const Core::System& system_, + std::vector<VkDeviceInfo::Record>& records, const std::function<void()>& expose_compute_option_, QWidget* parent = nullptr); ~ConfigureGraphics() override; @@ -77,6 +79,7 @@ private: ConfigurationShared::CheckState use_disk_shader_cache; ConfigurationShared::CheckState use_asynchronous_gpu_emulation; + std::vector<VkDeviceInfo::Record>& records; std::vector<QString> vulkan_devices; std::vector<std::vector<VkPresentModeKHR>> device_present_modes; std::vector<VkPresentModeKHR> diff --git a/src/yuzu/configuration/configure_graphics_advanced.cpp b/src/yuzu/configuration/configure_graphics_advanced.cpp index 896863f87..c0a044767 100644 --- a/src/yuzu/configuration/configure_graphics_advanced.cpp +++ b/src/yuzu/configuration/configure_graphics_advanced.cpp @@ -42,6 +42,9 @@ void ConfigureGraphicsAdvanced::SetConfiguration() { Settings::values.use_vulkan_driver_pipeline_cache.GetValue()); ui->enable_compute_pipelines_checkbox->setChecked( Settings::values.enable_compute_pipelines.GetValue()); + ui->use_video_framerate_checkbox->setChecked(Settings::values.use_video_framerate.GetValue()); + ui->barrier_feedback_loops_checkbox->setChecked( + Settings::values.barrier_feedback_loops.GetValue()); if (Settings::IsConfiguringGlobal()) { ui->gpu_accuracy->setCurrentIndex( @@ -91,6 +94,11 @@ void ConfigureGraphicsAdvanced::ApplyConfiguration() { ConfigurationShared::ApplyPerGameSetting(&Settings::values.enable_compute_pipelines, ui->enable_compute_pipelines_checkbox, enable_compute_pipelines); + ConfigurationShared::ApplyPerGameSetting(&Settings::values.use_video_framerate, + ui->use_video_framerate_checkbox, use_video_framerate); + ConfigurationShared::ApplyPerGameSetting(&Settings::values.barrier_feedback_loops, + ui->barrier_feedback_loops_checkbox, + barrier_feedback_loops); } void ConfigureGraphicsAdvanced::changeEvent(QEvent* event) { @@ -125,6 +133,10 @@ void ConfigureGraphicsAdvanced::SetupPerGameUI() { Settings::values.max_anisotropy.UsingGlobal()); ui->enable_compute_pipelines_checkbox->setEnabled( Settings::values.enable_compute_pipelines.UsingGlobal()); + ui->use_video_framerate_checkbox->setEnabled( + Settings::values.use_video_framerate.UsingGlobal()); + ui->barrier_feedback_loops_checkbox->setEnabled( + Settings::values.barrier_feedback_loops.UsingGlobal()); return; } @@ -149,6 +161,12 @@ void ConfigureGraphicsAdvanced::SetupPerGameUI() { ConfigurationShared::SetColoredTristate(ui->enable_compute_pipelines_checkbox, Settings::values.enable_compute_pipelines, enable_compute_pipelines); + ConfigurationShared::SetColoredTristate(ui->use_video_framerate_checkbox, + Settings::values.use_video_framerate, + use_video_framerate); + ConfigurationShared::SetColoredTristate(ui->barrier_feedback_loops_checkbox, + Settings::values.barrier_feedback_loops, + barrier_feedback_loops); ConfigurationShared::SetColoredComboBox( ui->gpu_accuracy, ui->label_gpu_accuracy, static_cast<int>(Settings::values.gpu_accuracy.GetValue(true))); diff --git a/src/yuzu/configuration/configure_graphics_advanced.h b/src/yuzu/configuration/configure_graphics_advanced.h index 1c7b636b9..369a7c83e 100644 --- a/src/yuzu/configuration/configure_graphics_advanced.h +++ b/src/yuzu/configuration/configure_graphics_advanced.h @@ -47,6 +47,8 @@ private: ConfigurationShared::CheckState use_fast_gpu_time; ConfigurationShared::CheckState use_vulkan_driver_pipeline_cache; ConfigurationShared::CheckState enable_compute_pipelines; + ConfigurationShared::CheckState use_video_framerate; + ConfigurationShared::CheckState barrier_feedback_loops; const Core::System& system; }; diff --git a/src/yuzu/configuration/configure_graphics_advanced.ui b/src/yuzu/configuration/configure_graphics_advanced.ui index 37757a918..d527a6f38 100644 --- a/src/yuzu/configuration/configure_graphics_advanced.ui +++ b/src/yuzu/configuration/configure_graphics_advanced.ui @@ -192,6 +192,26 @@ Compute pipelines are always enabled on all other drivers.</string> </widget> </item> <item> + <widget class="QCheckBox" name="use_video_framerate_checkbox"> + <property name="toolTip"> + <string>Run the game at normal speed during video playback, even when the framerate is unlocked.</string> + </property> + <property name="text"> + <string>Sync to framerate of video playback</string> + </property> + </widget> + </item> + <item> + <widget class="QCheckBox" name="barrier_feedback_loops_checkbox"> + <property name="toolTip"> + <string>Improves rendering of transparency effects in specific games.</string> + </property> + <property name="text"> + <string>Barrier feedback loops</string> + </property> + </widget> + </item> + <item> <widget class="QWidget" name="af_layout" native="true"> <layout class="QHBoxLayout" name="horizontalLayout_1"> <property name="leftMargin"> diff --git a/src/yuzu/configuration/configure_per_game.cpp b/src/yuzu/configuration/configure_per_game.cpp index 7ac162586..eb96e6068 100644 --- a/src/yuzu/configuration/configure_per_game.cpp +++ b/src/yuzu/configuration/configure_per_game.cpp @@ -6,6 +6,7 @@ #include <memory> #include <string> #include <utility> +#include <vector> #include <fmt/format.h> @@ -34,8 +35,10 @@ #include "yuzu/configuration/configure_system.h" #include "yuzu/uisettings.h" #include "yuzu/util/util.h" +#include "yuzu/vk_device_info.h" ConfigurePerGame::ConfigurePerGame(QWidget* parent, u64 title_id_, const std::string& file_name, + std::vector<VkDeviceInfo::Record>& vk_device_records, Core::System& system_) : QDialog(parent), ui(std::make_unique<Ui::ConfigurePerGame>()), title_id{title_id_}, system{system_} { @@ -50,7 +53,7 @@ ConfigurePerGame::ConfigurePerGame(QWidget* parent, u64 title_id_, const std::st general_tab = std::make_unique<ConfigureGeneral>(system_, this); graphics_advanced_tab = std::make_unique<ConfigureGraphicsAdvanced>(system_, this); graphics_tab = std::make_unique<ConfigureGraphics>( - system_, [&]() { graphics_advanced_tab->ExposeComputeOption(); }, this); + system_, vk_device_records, [&]() { graphics_advanced_tab->ExposeComputeOption(); }, this); input_tab = std::make_unique<ConfigureInputPerGame>(system_, game_config.get(), this); system_tab = std::make_unique<ConfigureSystem>(system_, this); diff --git a/src/yuzu/configuration/configure_per_game.h b/src/yuzu/configuration/configure_per_game.h index 85752f1fa..7ec1ded06 100644 --- a/src/yuzu/configuration/configure_per_game.h +++ b/src/yuzu/configuration/configure_per_game.h @@ -5,11 +5,13 @@ #include <memory> #include <string> +#include <vector> #include <QDialog> #include <QList> #include "core/file_sys/vfs_types.h" +#include "vk_device_info.h" #include "yuzu/configuration/config.h" namespace Core { @@ -45,6 +47,7 @@ class ConfigurePerGame : public QDialog { public: // Cannot use std::filesystem::path due to https://bugreports.qt.io/browse/QTBUG-73263 explicit ConfigurePerGame(QWidget* parent, u64 title_id_, const std::string& file_name, + std::vector<VkDeviceInfo::Record>& vk_device_records, Core::System& system_); ~ConfigurePerGame() override; diff --git a/src/yuzu/configuration/configure_system.cpp b/src/yuzu/configuration/configure_system.cpp index 286ccc5cd..f1ae312c6 100644 --- a/src/yuzu/configuration/configure_system.cpp +++ b/src/yuzu/configuration/configure_system.cpp @@ -144,8 +144,7 @@ void ConfigureSystem::ApplyConfiguration() { if (ui->custom_rtc_checkbox->isChecked()) { Settings::values.custom_rtc = ui->custom_rtc_edit->dateTime().toSecsSinceEpoch(); if (system.IsPoweredOn()) { - const s64 posix_time{*Settings::values.custom_rtc + - Service::Time::TimeManager::GetExternalTimeZoneOffset()}; + const s64 posix_time{*Settings::values.custom_rtc}; system.GetTimeManager().UpdateLocalSystemClockTime(posix_time); } } else { diff --git a/src/yuzu/main.cpp b/src/yuzu/main.cpp index 145fea5f1..8768a7c3c 100644 --- a/src/yuzu/main.cpp +++ b/src/yuzu/main.cpp @@ -147,6 +147,7 @@ static FileSys::VirtualFile VfsDirectoryCreateFileWrapper(const FileSys::Virtual #include "yuzu/startup_checks.h" #include "yuzu/uisettings.h" #include "yuzu/util/clickable_label.h" +#include "yuzu/vk_device_info.h" #ifdef YUZU_DBGHELP #include "yuzu/mini_dump.h" @@ -440,6 +441,8 @@ GMainWindow::GMainWindow(std::unique_ptr<Config> config_, bool has_broken_vulkan renderer_status_button->setDisabled(true); renderer_status_button->setChecked(false); + } else { + VkDeviceInfo::PopulateRecords(vk_device_records, this->window()->windowHandle()); } #if defined(HAVE_SDL2) && !defined(_WIN32) @@ -3067,7 +3070,7 @@ InstallResult GMainWindow::InstallNSPXCI(const QString& filename) { return false; } - std::array<u8, 0x1000> buffer{}; + std::vector<u8> buffer(1_MiB); for (std::size_t i = 0; i < src->GetSize(); i += buffer.size()) { if (install_progress->wasCanceled()) { @@ -3494,7 +3497,8 @@ void GMainWindow::OnConfigure() { const auto old_language_index = Settings::values.language_index.GetValue(); Settings::SetConfiguringGlobal(true); - ConfigureDialog configure_dialog(this, hotkey_registry, input_subsystem.get(), *system, + ConfigureDialog configure_dialog(this, hotkey_registry, input_subsystem.get(), + vk_device_records, *system, !multiplayer_state->IsHostingPublicRoom()); connect(&configure_dialog, &ConfigureDialog::LanguageChanged, this, &GMainWindow::OnLanguageChanged); @@ -3765,7 +3769,7 @@ void GMainWindow::OpenPerGameConfiguration(u64 title_id, const std::string& file const auto v_file = Core::GetGameFileFromPath(vfs, file_name); Settings::SetConfiguringGlobal(false); - ConfigurePerGame dialog(this, title_id, file_name, *system); + ConfigurePerGame dialog(this, title_id, file_name, vk_device_records, *system); dialog.LoadFromFile(v_file); const auto result = dialog.exec(); @@ -4116,7 +4120,13 @@ void GMainWindow::UpdateDockedButton() { void GMainWindow::UpdateAPIText() { const auto api = Settings::values.renderer_backend.GetValue(); const auto renderer_status_text = Config::renderer_backend_texts_map.find(api)->second; - renderer_status_button->setText(renderer_status_text.toUpper()); + renderer_status_button->setText( + api == Settings::RendererBackend::OpenGL + ? tr("%1 %2").arg( + renderer_status_text.toUpper(), + Config::shader_backend_texts_map.find(Settings::values.shader_backend.GetValue()) + ->second) + : renderer_status_text.toUpper()); } void GMainWindow::UpdateFilterText() { diff --git a/src/yuzu/main.h b/src/yuzu/main.h index 6bb70972f..e0e775d87 100644 --- a/src/yuzu/main.h +++ b/src/yuzu/main.h @@ -118,6 +118,10 @@ enum class ReinitializeKeyBehavior { Warning, }; +namespace VkDeviceInfo { +class Record; +} + class GMainWindow : public QMainWindow { Q_OBJECT @@ -418,6 +422,8 @@ private: GameListPlaceholder* game_list_placeholder; + std::vector<VkDeviceInfo::Record> vk_device_records; + // Status bar elements QLabel* message_label = nullptr; QLabel* shader_building_label = nullptr; diff --git a/src/yuzu/vk_device_info.cpp b/src/yuzu/vk_device_info.cpp new file mode 100644 index 000000000..7c26a3dc7 --- /dev/null +++ b/src/yuzu/vk_device_info.cpp @@ -0,0 +1,61 @@ +// SPDX-FileCopyrightText: 2023 yuzu Emulator Project +// SPDX-License-Identifier: GPL-2.0-or-later + +#include <utility> +#include <vector> +#include "common/dynamic_library.h" +#include "common/logging/log.h" +#include "video_core/vulkan_common/vulkan_device.h" +#include "video_core/vulkan_common/vulkan_instance.h" +#include "video_core/vulkan_common/vulkan_library.h" +#include "video_core/vulkan_common/vulkan_surface.h" +#include "video_core/vulkan_common/vulkan_wrapper.h" +#include "vulkan/vulkan_core.h" +#include "yuzu/qt_common.h" +#include "yuzu/vk_device_info.h" + +class QWindow; + +namespace VkDeviceInfo { +Record::Record(std::string_view name_, const std::vector<VkPresentModeKHR>& vsync_modes_, + bool has_broken_compute_) + : name{name_}, vsync_support{vsync_modes_}, has_broken_compute{has_broken_compute_} {} + +Record::~Record() = default; + +void PopulateRecords(std::vector<Record>& records, QWindow* window) try { + using namespace Vulkan; + + auto wsi = QtCommon::GetWindowSystemInfo(window); + + vk::InstanceDispatch dld; + const auto library = OpenLibrary(); + const vk::Instance instance = CreateInstance(*library, dld, VK_API_VERSION_1_1, wsi.type); + const std::vector<VkPhysicalDevice> physical_devices = instance.EnumeratePhysicalDevices(); + vk::SurfaceKHR surface = CreateSurface(instance, wsi); + + records.clear(); + records.reserve(physical_devices.size()); + for (const VkPhysicalDevice device : physical_devices) { + const auto physical_device = vk::PhysicalDevice(device, dld); + const std::string name = physical_device.GetProperties().deviceName; + const std::vector<VkPresentModeKHR> present_modes = + physical_device.GetSurfacePresentModesKHR(*surface); + + VkPhysicalDeviceDriverProperties driver_properties{}; + driver_properties.sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_DRIVER_PROPERTIES; + driver_properties.pNext = nullptr; + VkPhysicalDeviceProperties2 properties{}; + properties.sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_PROPERTIES_2_KHR; + properties.pNext = &driver_properties; + dld.vkGetPhysicalDeviceProperties2(physical_device, &properties); + + bool has_broken_compute{Vulkan::Device::CheckBrokenCompute( + driver_properties.driverID, properties.properties.driverVersion)}; + + records.push_back(VkDeviceInfo::Record(name, present_modes, has_broken_compute)); + } +} catch (const Vulkan::vk::Exception& exception) { + LOG_ERROR(Frontend, "Failed to enumerate devices with error: {}", exception.what()); +} +} // namespace VkDeviceInfo diff --git a/src/yuzu/vk_device_info.h b/src/yuzu/vk_device_info.h new file mode 100644 index 000000000..bda8262f4 --- /dev/null +++ b/src/yuzu/vk_device_info.h @@ -0,0 +1,36 @@ +// SPDX-FileCopyrightText: 2023 yuzu Emulator Project +// SPDX-License-Identifier: GPL-2.0-or-later + +#pragma once + +#include <algorithm> +#include <iterator> +#include <memory> +#include <string> +#include <string_view> +#include <vector> +#include "common/common_types.h" +#include "vulkan/vulkan_core.h" + +class QWindow; + +namespace Settings { +enum class VSyncMode : u32; +} +// #include "common/settings.h" + +namespace VkDeviceInfo { +// Short class to record Vulkan driver information for configuration purposes +class Record { +public: + explicit Record(std::string_view name, const std::vector<VkPresentModeKHR>& vsync_modes, + bool has_broken_compute); + ~Record(); + + const std::string name; + const std::vector<VkPresentModeKHR> vsync_support; + const bool has_broken_compute; +}; + +void PopulateRecords(std::vector<Record>& records, QWindow* window); +} // namespace VkDeviceInfo |