diff --git a/Content/Documentation/ScriptingAPI-Documentation.md b/Content/Documentation/ScriptingAPI-Documentation.md index c0453049e..352ca5df7 100644 --- a/Content/Documentation/ScriptingAPI-Documentation.md +++ b/Content/Documentation/ScriptingAPI-Documentation.md @@ -640,6 +640,7 @@ This is the main entry point and manages the lifetime of the application. Even t - SetLogicalSizeDisplay(bool active) -- toggle display of logical size of canvas if info display is enabled - SetPipelineCountDisplay(bool active) -- toggle display of active graphics pipeline count if info display is enabled - SetHeapAllocationCountDisplay(bool active) -- toggle display of heap allocation statistics if info display is enabled +- SetVRAMUsageDisplay(bool active) -- toggle display of video memory usage if info display is enabled - GetCanvas() : Canvas canvas -- returns a copy of the application's current canvas - SetCanvas(Canvas canvas) -- applies the specified canvas to the application - [outer]SetProfilerEnabled(bool enabled) diff --git a/Editor/Editor.cpp b/Editor/Editor.cpp index 5fcca8e89..81572d7ac 100644 --- a/Editor/Editor.cpp +++ b/Editor/Editor.cpp @@ -30,6 +30,7 @@ void Editor::Initialize() //infoDisplay.logical_size = true; infoDisplay.colorspace = true; infoDisplay.heap_allocation_counter = true; + infoDisplay.vram_usage = true; wi::renderer::SetOcclusionCullingEnabled(true); diff --git a/WickedEngine/wiApplication.cpp b/WickedEngine/wiApplication.cpp index 7789e5855..0d4b41cc9 100644 --- a/WickedEngine/wiApplication.cpp +++ b/WickedEngine/wiApplication.cpp @@ -371,6 +371,21 @@ namespace wi wi::font::Params params = wi::font::Params(4, 4, infoDisplay.size, wi::font::WIFALIGN_LEFT, wi::font::WIFALIGN_TOP, wi::Color(255, 255, 255, 255), wi::Color(0, 0, 0, 255)); params.cursor = wi::font::Draw(infodisplay_str, params, cmd); + if (infoDisplay.vram_usage) + { + GraphicsDevice::MemoryUsage vram = graphicsDevice->GetMemoryUsage(); + if (vram.usage > vram.budget) + { + params.color = wi::Color::Error(); + } + else if (float(vram.usage) / float(vram.budget) > 0.9f) + { + params.color = wi::Color::Warning(); + } + params.cursor = wi::font::Draw("VRAM usage: " + std::to_string(vram.usage / 1024 / 1024) + "MB / " + std::to_string(vram.budget / 1024 / 1024) + "MB\n", params, cmd); + params.color = wi::Color::White(); + } + // Write warnings below: params.color = wi::Color::Warning(); #ifdef _DEBUG diff --git a/WickedEngine/wiApplication.h b/WickedEngine/wiApplication.h index df2b68806..36b70f754 100644 --- a/WickedEngine/wiApplication.h +++ b/WickedEngine/wiApplication.h @@ -109,6 +109,8 @@ namespace wi bool heap_allocation_counter = false; // display the active graphics pipeline count bool pipeline_count = false; + // display video memory usage and budget + bool vram_usage = false; // text size int size = 16; // display default color grading helper texture in top left corner of the screen diff --git a/WickedEngine/wiApplication_BindLua.cpp b/WickedEngine/wiApplication_BindLua.cpp index cfaef5e24..4fc1d0cb2 100644 --- a/WickedEngine/wiApplication_BindLua.cpp +++ b/WickedEngine/wiApplication_BindLua.cpp @@ -23,6 +23,7 @@ namespace wi::lua lunamethod(Application_BindLua, SetLogicalSizeDisplay), lunamethod(Application_BindLua, SetPipelineCountDisplay), lunamethod(Application_BindLua, SetHeapAllocationCountDisplay), + lunamethod(Application_BindLua, SetVRAMUsageDisplay), lunamethod(Application_BindLua, GetCanvas), lunamethod(Application_BindLua, SetCanvas), { NULL, NULL } @@ -311,6 +312,22 @@ namespace wi::lua wi::lua::SError(L, "SetHeapAllocationCountDisplay(bool active) not enough arguments!"); return 0; } + int Application_BindLua::SetVRAMUsageDisplay(lua_State* L) + { + if (component == nullptr) + { + wi::lua::SError(L, "SetVRAMUsageDisplay() component is empty!"); + return 0; + } + int argc = wi::lua::SGetArgCount(L); + if (argc > 0) + { + component->infoDisplay.vram_usage = wi::lua::SGetBool(L, 1); + } + else + wi::lua::SError(L, "SetVRAMUsageDisplay(bool active) not enough arguments!"); + return 0; + } int Application_BindLua::GetCanvas(lua_State* L) { diff --git a/WickedEngine/wiApplication_BindLua.h b/WickedEngine/wiApplication_BindLua.h index f7c461b5e..e703562c3 100644 --- a/WickedEngine/wiApplication_BindLua.h +++ b/WickedEngine/wiApplication_BindLua.h @@ -53,6 +53,7 @@ namespace wi::lua int SetLogicalSizeDisplay(lua_State* L); int SetPipelineCountDisplay(lua_State* L); int SetHeapAllocationCountDisplay(lua_State* L); + int SetVRAMUsageDisplay(lua_State* L); int GetCanvas(lua_State* L); int SetCanvas(lua_State* L); diff --git a/WickedEngine/wiGraphicsDevice.h b/WickedEngine/wiGraphicsDevice.h index 287f4f4b8..2d3bc7303 100644 --- a/WickedEngine/wiGraphicsDevice.h +++ b/WickedEngine/wiGraphicsDevice.h @@ -136,6 +136,14 @@ namespace wi::graphics // Returns the minimum required alignment for buffer offsets when creating subresources virtual uint64_t GetMinOffsetAlignment(const GPUBufferDesc* desc) const = 0; + struct MemoryUsage + { + uint64_t budget = 0ull; // total video memory available for use by the current application (in bytes) + uint64_t usage = 0ull; // used video memory by the current application (in bytes) + }; + // Returns video memory statistics for the current application + virtual MemoryUsage GetMemoryUsage() const = 0; + ///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// // Command List functions are below: // - These are used to record rendering commands to a CommandList diff --git a/WickedEngine/wiGraphicsDevice_DX12.h b/WickedEngine/wiGraphicsDevice_DX12.h index 338f46178..1821a5b3c 100644 --- a/WickedEngine/wiGraphicsDevice_DX12.h +++ b/WickedEngine/wiGraphicsDevice_DX12.h @@ -241,6 +241,16 @@ namespace wi::graphics return alignment; } + MemoryUsage GetMemoryUsage() const override + { + MemoryUsage retval; + D3D12MA::Budget budget; + allocationhandler->allocator->GetBudget(&budget, nullptr); + retval.budget = budget.BudgetBytes; + retval.usage = budget.UsageBytes; + return retval; + } + ///////////////Thread-sensitive//////////////////////// void WaitCommandList(CommandList cmd, CommandList wait_for) override; diff --git a/WickedEngine/wiGraphicsDevice_Vulkan.cpp b/WickedEngine/wiGraphicsDevice_Vulkan.cpp index 09ba7cb43..59d905e1d 100644 --- a/WickedEngine/wiGraphicsDevice_Vulkan.cpp +++ b/WickedEngine/wiGraphicsDevice_Vulkan.cpp @@ -2770,6 +2770,8 @@ using namespace vulkan_internal; } } + memory_properties_2.sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_MEMORY_PROPERTIES_2; + vkGetPhysicalDeviceMemoryProperties2(physicalDevice, &memory_properties_2); allocationhandler = std::make_shared(); allocationhandler->device = device; @@ -2803,7 +2805,9 @@ using namespace vulkan_internal; allocatorInfo.instance = instance; // Core in 1.1 - allocatorInfo.flags = VMA_ALLOCATOR_CREATE_KHR_DEDICATED_ALLOCATION_BIT | VMA_ALLOCATOR_CREATE_KHR_BIND_MEMORY2_BIT; + allocatorInfo.flags = + VMA_ALLOCATOR_CREATE_KHR_DEDICATED_ALLOCATION_BIT | + VMA_ALLOCATOR_CREATE_KHR_BIND_MEMORY2_BIT; vma_vulkan_func.vkGetBufferMemoryRequirements2KHR = vkGetBufferMemoryRequirements2; vma_vulkan_func.vkGetImageMemoryRequirements2KHR = vkGetImageMemoryRequirements2; diff --git a/WickedEngine/wiGraphicsDevice_Vulkan.h b/WickedEngine/wiGraphicsDevice_Vulkan.h index 4b6082fa6..a2d8c067a 100644 --- a/WickedEngine/wiGraphicsDevice_Vulkan.h +++ b/WickedEngine/wiGraphicsDevice_Vulkan.h @@ -54,6 +54,7 @@ namespace wi::graphics VkPhysicalDeviceRayTracingPipelinePropertiesKHR raytracing_properties = {}; VkPhysicalDeviceFragmentShadingRatePropertiesKHR fragment_shading_rate_properties = {}; VkPhysicalDeviceMeshShaderPropertiesNV mesh_shader_properties = {}; + VkPhysicalDeviceMemoryProperties2 memory_properties_2 = {}; VkPhysicalDeviceFeatures2 features2 = {}; VkPhysicalDeviceVulkan11Features features_1_1 = {}; @@ -340,6 +341,22 @@ namespace wi::graphics return alignment; } + MemoryUsage GetMemoryUsage() const override + { + MemoryUsage retval; + VmaBudget budgets[VK_MAX_MEMORY_HEAPS] = {}; + vmaGetHeapBudgets(allocationhandler->allocator, budgets); + for (uint32_t i = 0; i < memory_properties_2.memoryProperties.memoryHeapCount; ++i) + { + if (memory_properties_2.memoryProperties.memoryHeaps[i].flags & VK_MEMORY_PROPERTY_DEVICE_LOCAL_BIT) + { + retval.budget += budgets[i].budget; + retval.usage += budgets[i].usage; + } + } + return retval; + } + ///////////////Thread-sensitive//////////////////////// void WaitCommandList(CommandList cmd, CommandList wait_for) override; diff --git a/WickedEngine/wiVersion.cpp b/WickedEngine/wiVersion.cpp index 4aa61a67a..e58b57348 100644 --- a/WickedEngine/wiVersion.cpp +++ b/WickedEngine/wiVersion.cpp @@ -9,7 +9,7 @@ namespace wi::version // minor features, major updates, breaking compatibility changes const int minor = 60; // minor bug fixes, alterations, refactors, updates - const int revision = 80; + const int revision = 81; const std::string version_string = std::to_string(major) + "." + std::to_string(minor) + "." + std::to_string(revision);