Flutter Engine
 
Loading...
Searching...
No Matches
vulkan_debug_report.cc
Go to the documentation of this file.
1// Copyright 2013 The Flutter Authors. All rights reserved.
2// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
6
7#include <algorithm>
8#include <iomanip>
9#include <vector>
10
11#include "vulkan_utilities.h"
12
13namespace vulkan {
14
15[[maybe_unused]]
16static const VkDebugReportFlagsEXT kVulkanErrorFlags =
17 VK_DEBUG_REPORT_WARNING_BIT_EXT |
18 VK_DEBUG_REPORT_PERFORMANCE_WARNING_BIT_EXT | VK_DEBUG_REPORT_ERROR_BIT_EXT;
19
20[[maybe_unused]]
21static const VkDebugReportFlagsEXT kVulkanInfoFlags =
22 VK_DEBUG_REPORT_INFORMATION_BIT_EXT | VK_DEBUG_REPORT_DEBUG_BIT_EXT;
23
25 return VK_EXT_DEBUG_REPORT_EXTENSION_NAME;
26}
27
28static const char* VkDebugReportFlagsEXTToString(VkDebugReportFlagsEXT flags) {
29 if (flags & VK_DEBUG_REPORT_INFORMATION_BIT_EXT) {
30 return "Information";
31 } else if (flags & VK_DEBUG_REPORT_WARNING_BIT_EXT) {
32 return "Warning";
33 } else if (flags & VK_DEBUG_REPORT_PERFORMANCE_WARNING_BIT_EXT) {
34 return "Performance Warning";
35 } else if (flags & VK_DEBUG_REPORT_ERROR_BIT_EXT) {
36 return "Error";
37 } else if (flags & VK_DEBUG_REPORT_DEBUG_BIT_EXT) {
38 return "Debug";
39 }
40 return "UNKNOWN";
41}
42
44 VkDebugReportObjectTypeEXT type) {
45 switch (type) {
46 case VK_DEBUG_REPORT_OBJECT_TYPE_UNKNOWN_EXT:
47 return "Unknown";
48 case VK_DEBUG_REPORT_OBJECT_TYPE_INSTANCE_EXT:
49 return "Instance";
50 case VK_DEBUG_REPORT_OBJECT_TYPE_PHYSICAL_DEVICE_EXT:
51 return "Physical Device";
52 case VK_DEBUG_REPORT_OBJECT_TYPE_DEVICE_EXT:
53 return "Device";
54 case VK_DEBUG_REPORT_OBJECT_TYPE_QUEUE_EXT:
55 return "Queue";
56 case VK_DEBUG_REPORT_OBJECT_TYPE_SEMAPHORE_EXT:
57 return "Semaphore";
58 case VK_DEBUG_REPORT_OBJECT_TYPE_COMMAND_BUFFER_EXT:
59 return "Command Buffer";
60 case VK_DEBUG_REPORT_OBJECT_TYPE_FENCE_EXT:
61 return "Fence";
62 case VK_DEBUG_REPORT_OBJECT_TYPE_DEVICE_MEMORY_EXT:
63 return "Device Memory";
64 case VK_DEBUG_REPORT_OBJECT_TYPE_BUFFER_EXT:
65 return "Buffer";
66 case VK_DEBUG_REPORT_OBJECT_TYPE_IMAGE_EXT:
67 return "Image";
68 case VK_DEBUG_REPORT_OBJECT_TYPE_EVENT_EXT:
69 return "Event";
70 case VK_DEBUG_REPORT_OBJECT_TYPE_QUERY_POOL_EXT:
71 return "Query Pool";
72 case VK_DEBUG_REPORT_OBJECT_TYPE_BUFFER_VIEW_EXT:
73 return "Buffer View";
74 case VK_DEBUG_REPORT_OBJECT_TYPE_IMAGE_VIEW_EXT:
75 return "Image_view";
76 case VK_DEBUG_REPORT_OBJECT_TYPE_SHADER_MODULE_EXT:
77 return "Shader Module";
78 case VK_DEBUG_REPORT_OBJECT_TYPE_PIPELINE_CACHE_EXT:
79 return "Pipeline Cache";
80 case VK_DEBUG_REPORT_OBJECT_TYPE_PIPELINE_LAYOUT_EXT:
81 return "Pipeline Layout";
82 case VK_DEBUG_REPORT_OBJECT_TYPE_RENDER_PASS_EXT:
83 return "Render Pass";
84 case VK_DEBUG_REPORT_OBJECT_TYPE_PIPELINE_EXT:
85 return "Pipeline";
86 case VK_DEBUG_REPORT_OBJECT_TYPE_DESCRIPTOR_SET_LAYOUT_EXT:
87 return "Descriptor Set Layout";
88 case VK_DEBUG_REPORT_OBJECT_TYPE_SAMPLER_EXT:
89 return "Sampler";
90 case VK_DEBUG_REPORT_OBJECT_TYPE_DESCRIPTOR_POOL_EXT:
91 return "Descriptor Pool";
92 case VK_DEBUG_REPORT_OBJECT_TYPE_DESCRIPTOR_SET_EXT:
93 return "Descriptor Set";
94 case VK_DEBUG_REPORT_OBJECT_TYPE_FRAMEBUFFER_EXT:
95 return "Framebuffer";
96 case VK_DEBUG_REPORT_OBJECT_TYPE_COMMAND_POOL_EXT:
97 return "Command Pool";
98 case VK_DEBUG_REPORT_OBJECT_TYPE_SURFACE_KHR_EXT:
99 return "Surface";
100 case VK_DEBUG_REPORT_OBJECT_TYPE_SWAPCHAIN_KHR_EXT:
101 return "Swapchain";
102 case VK_DEBUG_REPORT_OBJECT_TYPE_DEBUG_REPORT_EXT:
103 return "Debug";
104 default:
105 break;
106 }
107
108 return "Unknown";
109}
110
111static VKAPI_ATTR VkBool32
112#ifdef WIN32
113 __stdcall
114#endif
115 OnVulkanDebugReportCallback(VkDebugReportFlagsEXT flags,
116 VkDebugReportObjectTypeEXT object_type,
117 uint64_t object,
118 size_t location,
119 int32_t message_code,
120 const char* layer_prefix,
121 const char* message,
122 void* user_data) {
123 std::vector<std::pair<std::string, std::string>> items;
124
125 items.emplace_back("Severity", VkDebugReportFlagsEXTToString(flags));
126
127 items.emplace_back("Object Type",
129
130 items.emplace_back("Object Handle", std::to_string(object));
131
132 if (location != 0) {
133 items.emplace_back("Location", std::to_string(location));
134 }
135
136 if (message_code != 0) {
137 items.emplace_back("Message Code", std::to_string(message_code));
138 }
139
140 if (layer_prefix != nullptr) {
141 items.emplace_back("Layer", layer_prefix);
142 }
143
144 if (message != nullptr) {
145 items.emplace_back("Message", message);
146 }
147
148 size_t padding = 0;
149
150 for (const auto& item : items) {
151 padding = std::max(padding, item.first.size());
152 }
153
154 padding += 1;
155
156 std::stringstream stream;
157
158 stream << std::endl;
159
160 stream << "--- Vulkan Debug Report ----------------------------------------";
161
162 stream << std::endl;
163
164 for (const auto& item : items) {
165 stream << "| " << std::setw(static_cast<int>(padding)) << item.first
166 << std::setw(0) << ": " << item.second << std::endl;
167 }
168
169 stream << "-----------------------------------------------------------------";
170
171 if (flags & kVulkanErrorFlags) {
172 if (ValidationErrorsFatal()) {
173 FML_DCHECK(false) << stream.str();
174 } else {
175 FML_LOG(ERROR) << stream.str();
176 }
177 } else {
178 FML_LOG(INFO) << stream.str();
179 }
180
181 // Returning false tells the layer not to stop when the event occurs, so
182 // they see the same behavior with and without validation layers enabled.
183 return VK_FALSE;
184}
185
187 const VulkanProcTable& p_vk,
188 const VulkanHandle<VkInstance>& application)
189 : vk_(p_vk), application_(application), valid_(false) {
190 if (!vk_.CreateDebugReportCallbackEXT || !vk_.DestroyDebugReportCallbackEXT) {
191 return;
192 }
193
194 if (!application_) {
195 return;
196 }
197
198 VkDebugReportFlagsEXT flags = kVulkanErrorFlags;
200 flags |= kVulkanInfoFlags;
201 }
202 const VkDebugReportCallbackCreateInfoEXT create_info = {
203 .sType = VK_STRUCTURE_TYPE_DEBUG_REPORT_CREATE_INFO_EXT,
204 .pNext = nullptr,
205 .flags = flags,
207 .pUserData = nullptr,
208 };
209
210 VkDebugReportCallbackEXT handle = VK_NULL_HANDLE;
211 if (VK_CALL_LOG_ERROR(vk_.CreateDebugReportCallbackEXT(
212 application_, &create_info, nullptr, &handle)) != VK_SUCCESS) {
213 return;
214 }
215
217 handle, [this](VkDebugReportCallbackEXT handle) {
218 vk_.DestroyDebugReportCallbackEXT(application_, handle, nullptr);
219 }};
220
221 valid_ = true;
222}
223
225
227 return valid_;
228}
229
230} // namespace vulkan
GLenum type
VulkanDebugReport(const VulkanProcTable &vk, const VulkanHandle< VkInstance > &application)
static std::string DebugExtensionName()
G_BEGIN_DECLS GBytes * message
#define FML_LOG(severity)
Definition logging.h:101
#define FML_DCHECK(condition)
Definition logging.h:122
Vector2 padding
The halo padding in source space.
bool ValidationErrorsFatal()
static const char * VkDebugReportFlagsEXTToString(VkDebugReportFlagsEXT flags)
static VKAPI_ATTR VkBool32 OnVulkanDebugReportCallback(VkDebugReportFlagsEXT flags, VkDebugReportObjectTypeEXT object_type, uint64_t object, size_t location, int32_t message_code, const char *layer_prefix, const char *message, void *user_data)
static const VkDebugReportFlagsEXT kVulkanErrorFlags
static const VkDebugReportFlagsEXT kVulkanInfoFlags
static const char * VkDebugReportObjectTypeEXTToString(VkDebugReportObjectTypeEXT type)
bool ValidationLayerInfoMessagesEnabled()
#define VK_CALL_LOG_ERROR(expression)