mirror of
				https://github.com/PabloMK7/citra.git
				synced 2025-10-30 21:30:04 +00:00 
			
		
		
		
	vk_instance: Perform vulkan logging as early as possible (#7058)
This commit is contained in:
		
							parent
							
								
									775a25b492
								
							
						
					
					
						commit
						40ba5226c6
					
				
					 4 changed files with 64 additions and 72 deletions
				
			
		|  | @ -11,7 +11,6 @@ | ||||||
| #include "core/hw/gpu.h" | #include "core/hw/gpu.h" | ||||||
| #include "core/hw/hw.h" | #include "core/hw/hw.h" | ||||||
| #include "core/hw/lcd.h" | #include "core/hw/lcd.h" | ||||||
| #include "core/telemetry_session.h" |  | ||||||
| #include "video_core/renderer_vulkan/renderer_vulkan.h" | #include "video_core/renderer_vulkan/renderer_vulkan.h" | ||||||
| #include "video_core/renderer_vulkan/vk_shader_util.h" | #include "video_core/renderer_vulkan/vk_shader_util.h" | ||||||
| 
 | 
 | ||||||
|  | @ -26,9 +25,6 @@ MICROPROFILE_DEFINE(Vulkan_RenderFrame, "Vulkan", "Render Frame", MP_RGB(128, 12 | ||||||
| 
 | 
 | ||||||
| namespace Vulkan { | namespace Vulkan { | ||||||
| 
 | 
 | ||||||
| /**
 |  | ||||||
|  * Vertex structure that the drawn screen rectangles are composed of. |  | ||||||
|  */ |  | ||||||
| struct ScreenRectVertex { | struct ScreenRectVertex { | ||||||
|     ScreenRectVertex() = default; |     ScreenRectVertex() = default; | ||||||
|     ScreenRectVertex(float x, float y, float u, float v) |     ScreenRectVertex(float x, float y, float u, float v) | ||||||
|  | @ -49,46 +45,16 @@ constexpr std::array<f32, 4 * 4> MakeOrthographicMatrix(u32 width, u32 height) { | ||||||
|     // clang-format on
 |     // clang-format on
 | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| namespace { | constexpr static std::array<vk::DescriptorSetLayoutBinding, 1> PRESENT_BINDINGS = {{ | ||||||
| 
 |  | ||||||
| std::string GetReadableVersion(u32 version) { |  | ||||||
|     return fmt::format("{}.{}.{}", VK_VERSION_MAJOR(version), VK_VERSION_MINOR(version), |  | ||||||
|                        VK_VERSION_PATCH(version)); |  | ||||||
| } |  | ||||||
| 
 |  | ||||||
| std::string GetDriverVersion(const Instance& instance) { |  | ||||||
|     // Extracted from
 |  | ||||||
|     // https://github.com/SaschaWillems/vulkan.gpuinfo.org/blob/5dddea46ea1120b0df14eef8f15ff8e318e35462/functions.php#L308-L314
 |  | ||||||
|     const u32 version = instance.GetDriverVersion(); |  | ||||||
|     if (instance.GetDriverID() == vk::DriverId::eNvidiaProprietary) { |  | ||||||
|         const u32 major = (version >> 22) & 0x3ff; |  | ||||||
|         const u32 minor = (version >> 14) & 0x0ff; |  | ||||||
|         const u32 secondary = (version >> 6) & 0x0ff; |  | ||||||
|         const u32 tertiary = version & 0x003f; |  | ||||||
|         return fmt::format("{}.{}.{}.{}", major, minor, secondary, tertiary); |  | ||||||
|     } |  | ||||||
|     if (instance.GetDriverID() == vk::DriverId::eIntelProprietaryWindows) { |  | ||||||
|         const u32 major = version >> 14; |  | ||||||
|         const u32 minor = version & 0x3fff; |  | ||||||
|         return fmt::format("{}.{}", major, minor); |  | ||||||
|     } |  | ||||||
|     return GetReadableVersion(version); |  | ||||||
| } |  | ||||||
| 
 |  | ||||||
| constexpr std::array<vk::DescriptorSetLayoutBinding, 1> PRESENT_BINDINGS = {{ |  | ||||||
|     {0, vk::DescriptorType::eCombinedImageSampler, 3, vk::ShaderStageFlagBits::eFragment}, |     {0, vk::DescriptorType::eCombinedImageSampler, 3, vk::ShaderStageFlagBits::eFragment}, | ||||||
| }}; | }}; | ||||||
| 
 | 
 | ||||||
| } // Anonymous namespace
 |  | ||||||
| 
 |  | ||||||
| RendererVulkan::RendererVulkan(Core::System& system, Frontend::EmuWindow& window, | RendererVulkan::RendererVulkan(Core::System& system, Frontend::EmuWindow& window, | ||||||
|                                Frontend::EmuWindow* secondary_window) |                                Frontend::EmuWindow* secondary_window) | ||||||
|     : RendererBase{system, window, secondary_window}, memory{system.Memory()}, |     : RendererBase{system, window, secondary_window}, memory{system.Memory()}, | ||||||
|       telemetry_session{system.TelemetrySession()}, |       instance{system.TelemetrySession(), window, Settings::values.physical_device.GetValue()}, | ||||||
|       instance{window, Settings::values.physical_device.GetValue()}, scheduler{instance, |       scheduler{instance, renderpass_cache}, renderpass_cache{instance, scheduler}, pool{instance}, | ||||||
|                                                                                renderpass_cache}, |       main_window{window, instance, scheduler}, | ||||||
|       renderpass_cache{instance, scheduler}, pool{instance}, main_window{window, instance, |  | ||||||
|                                                                          scheduler}, |  | ||||||
|       vertex_buffer{instance, scheduler, vk::BufferUsageFlagBits::eVertexBuffer, |       vertex_buffer{instance, scheduler, vk::BufferUsageFlagBits::eVertexBuffer, | ||||||
|                     VERTEX_BUFFER_SIZE}, |                     VERTEX_BUFFER_SIZE}, | ||||||
|       rasterizer{memory, |       rasterizer{memory, | ||||||
|  | @ -101,7 +67,6 @@ RendererVulkan::RendererVulkan(Core::System& system, Frontend::EmuWindow& window | ||||||
|                  renderpass_cache, |                  renderpass_cache, | ||||||
|                  main_window.ImageCount()}, |                  main_window.ImageCount()}, | ||||||
|       present_set_provider{instance, pool, PRESENT_BINDINGS} { |       present_set_provider{instance, pool, PRESENT_BINDINGS} { | ||||||
|     ReportDriver(); |  | ||||||
|     CompileShaders(); |     CompileShaders(); | ||||||
|     BuildLayouts(); |     BuildLayouts(); | ||||||
|     BuildPipelines(); |     BuildPipelines(); | ||||||
|  | @ -1086,27 +1051,4 @@ void RendererVulkan::RenderScreenshot() { | ||||||
|     settings.screenshot_complete_callback(); |     settings.screenshot_complete_callback(); | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| void RendererVulkan::ReportDriver() const { |  | ||||||
|     const std::string vendor_name{instance.GetVendorName()}; |  | ||||||
|     const std::string model_name{instance.GetModelName()}; |  | ||||||
|     const std::string driver_version = GetDriverVersion(instance); |  | ||||||
|     const std::string driver_name = fmt::format("{} {}", vendor_name, driver_version); |  | ||||||
| 
 |  | ||||||
|     const std::string api_version = GetReadableVersion(instance.ApiVersion()); |  | ||||||
| 
 |  | ||||||
|     const std::string extensions = |  | ||||||
|         fmt::format("{}", fmt::join(instance.GetAvailableExtensions(), ", ")); |  | ||||||
| 
 |  | ||||||
|     LOG_INFO(Render_Vulkan, "VK_DRIVER: {}", driver_name); |  | ||||||
|     LOG_INFO(Render_Vulkan, "VK_DEVICE: {}", model_name); |  | ||||||
|     LOG_INFO(Render_Vulkan, "VK_VERSION: {}", api_version); |  | ||||||
| 
 |  | ||||||
|     static constexpr auto field = Common::Telemetry::FieldType::UserSystem; |  | ||||||
|     telemetry_session.AddField(field, "GPU_Vendor", vendor_name); |  | ||||||
|     telemetry_session.AddField(field, "GPU_Model", model_name); |  | ||||||
|     telemetry_session.AddField(field, "GPU_Vulkan_Driver", driver_name); |  | ||||||
|     telemetry_session.AddField(field, "GPU_Vulkan_Version", api_version); |  | ||||||
|     telemetry_session.AddField(field, "GPU_Vulkan_Extensions", extensions); |  | ||||||
| } |  | ||||||
| 
 |  | ||||||
| } // namespace Vulkan
 | } // namespace Vulkan
 | ||||||
|  |  | ||||||
|  | @ -21,8 +21,7 @@ | ||||||
| 
 | 
 | ||||||
| namespace Core { | namespace Core { | ||||||
| class System; | class System; | ||||||
| class TelemetrySession; | } | ||||||
| } // namespace Core
 |  | ||||||
| 
 | 
 | ||||||
| namespace Memory { | namespace Memory { | ||||||
| class MemorySystem; | class MemorySystem; | ||||||
|  | @ -82,7 +81,6 @@ public: | ||||||
|     void Sync() override; |     void Sync() override; | ||||||
| 
 | 
 | ||||||
| private: | private: | ||||||
|     void ReportDriver() const; |  | ||||||
|     void ReloadPipeline(); |     void ReloadPipeline(); | ||||||
|     void CompileShaders(); |     void CompileShaders(); | ||||||
|     void BuildLayouts(); |     void BuildLayouts(); | ||||||
|  | @ -111,7 +109,6 @@ private: | ||||||
| 
 | 
 | ||||||
| private: | private: | ||||||
|     Memory::MemorySystem& memory; |     Memory::MemorySystem& memory; | ||||||
|     Core::TelemetrySession& telemetry_session; |  | ||||||
| 
 | 
 | ||||||
|     Instance instance; |     Instance instance; | ||||||
|     Scheduler scheduler; |     Scheduler scheduler; | ||||||
|  |  | ||||||
|  | @ -8,6 +8,7 @@ | ||||||
| #include "common/assert.h" | #include "common/assert.h" | ||||||
| #include "common/settings.h" | #include "common/settings.h" | ||||||
| #include "core/frontend/emu_window.h" | #include "core/frontend/emu_window.h" | ||||||
|  | #include "core/telemetry_session.h" | ||||||
| #include "video_core/custom_textures/custom_format.h" | #include "video_core/custom_textures/custom_format.h" | ||||||
| #include "video_core/renderer_vulkan/vk_instance.h" | #include "video_core/renderer_vulkan/vk_instance.h" | ||||||
| #include "video_core/renderer_vulkan/vk_platform.h" | #include "video_core/renderer_vulkan/vk_platform.h" | ||||||
|  | @ -21,6 +22,7 @@ | ||||||
| namespace Vulkan { | namespace Vulkan { | ||||||
| 
 | 
 | ||||||
| namespace { | namespace { | ||||||
|  | 
 | ||||||
| vk::Format MakeFormat(VideoCore::PixelFormat format) { | vk::Format MakeFormat(VideoCore::PixelFormat format) { | ||||||
|     switch (format) { |     switch (format) { | ||||||
|     case VideoCore::PixelFormat::RGBA8: |     case VideoCore::PixelFormat::RGBA8: | ||||||
|  | @ -125,6 +127,12 @@ std::vector<std::string> GetSupportedExtensions(vk::PhysicalDevice physical) { | ||||||
|     } |     } | ||||||
|     return supported_extensions; |     return supported_extensions; | ||||||
| } | } | ||||||
|  | 
 | ||||||
|  | std::string GetReadableVersion(u32 version) { | ||||||
|  |     return fmt::format("{}.{}.{}", VK_VERSION_MAJOR(version), VK_VERSION_MINOR(version), | ||||||
|  |                        VK_VERSION_PATCH(version)); | ||||||
|  | } | ||||||
|  | 
 | ||||||
| } // Anonymous namespace
 | } // Anonymous namespace
 | ||||||
| 
 | 
 | ||||||
| Instance::Instance(bool enable_validation, bool dump_command_buffers) | Instance::Instance(bool enable_validation, bool dump_command_buffers) | ||||||
|  | @ -133,7 +141,8 @@ Instance::Instance(bool enable_validation, bool dump_command_buffers) | ||||||
|                                                       enable_validation, dump_command_buffers)}, |                                                       enable_validation, dump_command_buffers)}, | ||||||
|       physical_devices{instance->enumeratePhysicalDevices()} {} |       physical_devices{instance->enumeratePhysicalDevices()} {} | ||||||
| 
 | 
 | ||||||
| Instance::Instance(Frontend::EmuWindow& window, u32 physical_device_index) | Instance::Instance(Core::TelemetrySession& telemetry, Frontend::EmuWindow& window, | ||||||
|  |                    u32 physical_device_index) | ||||||
|     : library{OpenLibrary(&window)}, instance{CreateInstance( |     : library{OpenLibrary(&window)}, instance{CreateInstance( | ||||||
|                                          *library, window.GetWindowInfo().type, |                                          *library, window.GetWindowInfo().type, | ||||||
|                                          Settings::values.renderer_debug.GetValue(), |                                          Settings::values.renderer_debug.GetValue(), | ||||||
|  | @ -146,9 +155,10 @@ Instance::Instance(Frontend::EmuWindow& window, u32 physical_device_index) | ||||||
|                physical_device_index, num_physical_devices); |                physical_device_index, num_physical_devices); | ||||||
| 
 | 
 | ||||||
|     physical_device = physical_devices[physical_device_index]; |     physical_device = physical_devices[physical_device_index]; | ||||||
|  |     available_extensions = GetSupportedExtensions(physical_device); | ||||||
|     properties = physical_device.getProperties(); |     properties = physical_device.getProperties(); | ||||||
| 
 | 
 | ||||||
|     CollectTelemetryParameters(); |     CollectTelemetryParameters(telemetry); | ||||||
|     CreateDevice(); |     CreateDevice(); | ||||||
|     CollectToolingInfo(); |     CollectToolingInfo(); | ||||||
|     CreateFormatTable(); |     CreateFormatTable(); | ||||||
|  | @ -180,6 +190,25 @@ const FormatTraits& Instance::GetTraits(Pica::PipelineRegs::VertexAttributeForma | ||||||
|     return attrib_table[index * 4 + count - 1]; |     return attrib_table[index * 4 + count - 1]; | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
|  | std::string Instance::GetDriverVersionName() { | ||||||
|  |     // Extracted from
 | ||||||
|  |     // https://github.com/SaschaWillems/vulkan.gpuinfo.org/blob/5dddea46ea1120b0df14eef8f15ff8e318e35462/functions.php#L308-L314
 | ||||||
|  |     const u32 version = properties.driverVersion; | ||||||
|  |     if (driver_id == vk::DriverId::eNvidiaProprietary) { | ||||||
|  |         const u32 major = (version >> 22) & 0x3ff; | ||||||
|  |         const u32 minor = (version >> 14) & 0x0ff; | ||||||
|  |         const u32 secondary = (version >> 6) & 0x0ff; | ||||||
|  |         const u32 tertiary = version & 0x003f; | ||||||
|  |         return fmt::format("{}.{}.{}.{}", major, minor, secondary, tertiary); | ||||||
|  |     } | ||||||
|  |     if (driver_id == vk::DriverId::eIntelProprietaryWindows) { | ||||||
|  |         const u32 major = version >> 14; | ||||||
|  |         const u32 minor = version & 0x3fff; | ||||||
|  |         return fmt::format("{}.{}", major, minor); | ||||||
|  |     } | ||||||
|  |     return GetReadableVersion(version); | ||||||
|  | } | ||||||
|  | 
 | ||||||
| FormatTraits Instance::DetermineTraits(VideoCore::PixelFormat pixel_format, vk::Format format) { | FormatTraits Instance::DetermineTraits(VideoCore::PixelFormat pixel_format, vk::Format format) { | ||||||
|     const vk::ImageAspectFlags format_aspect = MakeAspect(VideoCore::GetFormatType(pixel_format)); |     const vk::ImageAspectFlags format_aspect = MakeAspect(VideoCore::GetFormatType(pixel_format)); | ||||||
|     const vk::FormatProperties format_properties = physical_device.getFormatProperties(format); |     const vk::FormatProperties format_properties = physical_device.getFormatProperties(format); | ||||||
|  | @ -380,7 +409,6 @@ bool Instance::CreateDevice() { | ||||||
|                                        vk::PhysicalDevicePortabilitySubsetPropertiesKHR>(); |                                        vk::PhysicalDevicePortabilitySubsetPropertiesKHR>(); | ||||||
| 
 | 
 | ||||||
|     features = feature_chain.get().features; |     features = feature_chain.get().features; | ||||||
|     available_extensions = GetSupportedExtensions(physical_device); |  | ||||||
|     if (available_extensions.empty()) { |     if (available_extensions.empty()) { | ||||||
|         LOG_CRITICAL(Render_Vulkan, "No extensions supported by device."); |         LOG_CRITICAL(Render_Vulkan, "No extensions supported by device."); | ||||||
|         return false; |         return false; | ||||||
|  | @ -598,7 +626,7 @@ void Instance::CreateAllocator() { | ||||||
|     } |     } | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| void Instance::CollectTelemetryParameters() { | void Instance::CollectTelemetryParameters(Core::TelemetrySession& telemetry) { | ||||||
|     const vk::StructureChain property_chain = |     const vk::StructureChain property_chain = | ||||||
|         physical_device |         physical_device | ||||||
|             .getProperties2<vk::PhysicalDeviceProperties2, vk::PhysicalDeviceDriverProperties>(); |             .getProperties2<vk::PhysicalDeviceProperties2, vk::PhysicalDeviceDriverProperties>(); | ||||||
|  | @ -607,6 +635,23 @@ void Instance::CollectTelemetryParameters() { | ||||||
| 
 | 
 | ||||||
|     driver_id = driver.driverID; |     driver_id = driver.driverID; | ||||||
|     vendor_name = driver.driverName.data(); |     vendor_name = driver.driverName.data(); | ||||||
|  | 
 | ||||||
|  |     const std::string model_name{GetModelName()}; | ||||||
|  |     const std::string driver_version = GetDriverVersionName(); | ||||||
|  |     const std::string driver_name = fmt::format("{} {}", vendor_name, driver_version); | ||||||
|  |     const std::string api_version = GetReadableVersion(properties.apiVersion); | ||||||
|  |     const std::string extensions = fmt::format("{}", fmt::join(available_extensions, ", ")); | ||||||
|  | 
 | ||||||
|  |     LOG_INFO(Render_Vulkan, "VK_DRIVER: {}", driver_name); | ||||||
|  |     LOG_INFO(Render_Vulkan, "VK_DEVICE: {}", model_name); | ||||||
|  |     LOG_INFO(Render_Vulkan, "VK_VERSION: {}", api_version); | ||||||
|  | 
 | ||||||
|  |     static constexpr auto field = Common::Telemetry::FieldType::UserSystem; | ||||||
|  |     telemetry.AddField(field, "GPU_Vendor", vendor_name); | ||||||
|  |     telemetry.AddField(field, "GPU_Model", model_name); | ||||||
|  |     telemetry.AddField(field, "GPU_Vulkan_Driver", driver_name); | ||||||
|  |     telemetry.AddField(field, "GPU_Vulkan_Version", api_version); | ||||||
|  |     telemetry.AddField(field, "GPU_Vulkan_Extensions", extensions); | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| void Instance::CollectToolingInfo() { | void Instance::CollectToolingInfo() { | ||||||
|  |  | ||||||
|  | @ -10,6 +10,10 @@ | ||||||
| #include "video_core/regs_pipeline.h" | #include "video_core/regs_pipeline.h" | ||||||
| #include "video_core/renderer_vulkan/vk_platform.h" | #include "video_core/renderer_vulkan/vk_platform.h" | ||||||
| 
 | 
 | ||||||
|  | namespace Core { | ||||||
|  | class TelemetrySession; | ||||||
|  | } | ||||||
|  | 
 | ||||||
| namespace Frontend { | namespace Frontend { | ||||||
| class EmuWindow; | class EmuWindow; | ||||||
| } | } | ||||||
|  | @ -37,7 +41,8 @@ struct FormatTraits { | ||||||
| class Instance { | class Instance { | ||||||
| public: | public: | ||||||
|     explicit Instance(bool validation = false, bool dump_command_buffers = false); |     explicit Instance(bool validation = false, bool dump_command_buffers = false); | ||||||
|     explicit Instance(Frontend::EmuWindow& window, u32 physical_device_index); |     explicit Instance(Core::TelemetrySession& telemetry, Frontend::EmuWindow& window, | ||||||
|  |                       u32 physical_device_index); | ||||||
|     ~Instance(); |     ~Instance(); | ||||||
| 
 | 
 | ||||||
|     /// Returns the FormatTraits struct for the provided pixel format
 |     /// Returns the FormatTraits struct for the provided pixel format
 | ||||||
|  | @ -48,6 +53,9 @@ public: | ||||||
|     const FormatTraits& GetTraits(Pica::PipelineRegs::VertexAttributeFormat format, |     const FormatTraits& GetTraits(Pica::PipelineRegs::VertexAttributeFormat format, | ||||||
|                                   u32 count) const; |                                   u32 count) const; | ||||||
| 
 | 
 | ||||||
|  |     /// Returns a formatted string for the driver version
 | ||||||
|  |     std::string GetDriverVersionName(); | ||||||
|  | 
 | ||||||
|     /// Returns the Vulkan instance
 |     /// Returns the Vulkan instance
 | ||||||
|     vk::Instance GetInstance() const { |     vk::Instance GetInstance() const { | ||||||
|         return *instance; |         return *instance; | ||||||
|  | @ -263,7 +271,7 @@ private: | ||||||
|     void CreateAllocator(); |     void CreateAllocator(); | ||||||
| 
 | 
 | ||||||
|     /// Collects telemetry information from the device.
 |     /// Collects telemetry information from the device.
 | ||||||
|     void CollectTelemetryParameters(); |     void CollectTelemetryParameters(Core::TelemetrySession& telemetry); | ||||||
|     void CollectToolingInfo(); |     void CollectToolingInfo(); | ||||||
| 
 | 
 | ||||||
|     /// Sets MoltenVK configuration to the desired state.
 |     /// Sets MoltenVK configuration to the desired state.
 | ||||||
|  |  | ||||||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue