• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 //
2 // Copyright 2018 The ANGLE Project Authors. All rights reserved.
3 // Use of this source code is governed by a BSD-style license that can be
4 // found in the LICENSE file.
5 //
6 // FeaturesVk.h: Optional features for the Vulkan renderer.
7 //
8 
9 #ifndef ANGLE_PLATFORM_FEATURESVK_H_
10 #define ANGLE_PLATFORM_FEATURESVK_H_
11 
12 #include "platform/Feature.h"
13 
14 #include <array>
15 
16 namespace angle
17 {
18 
19 struct FeaturesVk : FeatureSetBase
20 {
21     FeaturesVk();
22     ~FeaturesVk();
23 
24     // Line segment rasterization must follow OpenGL rules. This means using an algorithm similar
25     // to Bresenham's. Vulkan uses a different algorithm. This feature enables the use of pixel
26     // shader patching to implement OpenGL basic line rasterization rules. This feature will
27     // normally always be enabled. Exposing it as an option enables performance testing.
28     Feature basicGLLineRasterization = {
29         "basicGLLineRasterization", FeatureCategory::VulkanFeatures,
30         "Enable the use of pixel shader patching to implement OpenGL basic line "
31         "rasterization rules",
32         &members};
33 
34     // If the VK_EXT_line_rasterization extension is available we'll use it to get
35     // Bresenham line rasterization.
36     Feature bresenhamLineRasterization = {
37         "bresenhamLineRasterization", FeatureCategory::VulkanFeatures,
38         "Enable Bresenham line rasterization via VK_EXT_line_rasterization extension", &members};
39 
40     // If the VK_EXT_provoking_vertex extension is available, we'll use it to set
41     // the provoking vertex mode
42     Feature provokingVertex = {"provokingVertex", FeatureCategory::VulkanFeatures,
43                                "Enable provoking vertex mode via VK_EXT_provoking_vertex extension",
44                                &members};
45 
46     // This flag is added for the sole purpose of end2end tests, to test the correctness
47     // of various algorithms when a fallback format is used, such as using a packed format to
48     // emulate a depth- or stencil-only format.
49     Feature forceFallbackFormat = {"forceFallbackFormat", FeatureCategory::VulkanWorkarounds,
50                                    "Force a fallback format for angle_end2end_tests", &members};
51 
52     // On some NVIDIA drivers the point size range reported from the API is inconsistent with the
53     // actual behavior. Clamp the point size to the value from the API to fix this.
54     // Tracked in http://anglebug.com/2970.
55     Feature clampPointSize = {
56         "clampPointSize", FeatureCategory::VulkanWorkarounds,
57         "The point size range reported from the API is inconsistent with the actual behavior",
58         &members, "http://anglebug.com/2970"};
59 
60     // On some NVIDIA drivers the depth value is not clamped to [0,1] for floating point depth
61     // buffers. This is NVIDIA bug 3171019, see http://anglebug.com/3970 for details.
62     Feature depthClamping = {
63         "depth_clamping", FeatureCategory::VulkanWorkarounds,
64         "The depth value is not clamped to [0,1] for floating point depth buffers.", &members,
65         "http://anglebug.com/3970"};
66 
67     Feature supportsRenderpass2 = {"supportsRenderpass2", FeatureCategory::VulkanFeatures,
68                                    "VkDevice supports the VK_KHR_create_renderpass2 extension",
69                                    &members};
70 
71     // Whether the VkDevice supports the VK_KHR_incremental_present extension, on which the
72     // EGL_KHR_swap_buffers_with_damage extension can be layered.
73     Feature supportsIncrementalPresent = {
74         "supportsIncrementalPresent", FeatureCategory::VulkanFeatures,
75         "VkDevice supports the VK_KHR_incremental_present extension", &members};
76 
77     // Whether the VkDevice supports the VK_ANDROID_external_memory_android_hardware_buffer
78     // extension, on which the EGL_ANDROID_image_native_buffer extension can be layered.
79     Feature supportsAndroidHardwareBuffer = {
80         "supportsAndroidHardwareBuffer", FeatureCategory::VulkanFeatures,
81         "VkDevice supports the VK_ANDROID_external_memory_android_hardware_buffer extension",
82         &members};
83 
84     // Whether the VkDevice supports the VK_GGP_frame_token extension, on which
85     // the EGL_ANGLE_swap_with_frame_token extension can be layered.
86     Feature supportsGGPFrameToken = {"supportsGGPFrameToken", FeatureCategory::VulkanFeatures,
87                                      "VkDevice supports the VK_GGP_frame_token extension",
88                                      &members};
89 
90     // Whether the VkDevice supports the VK_KHR_external_memory_fd extension, on which the
91     // GL_EXT_memory_object_fd extension can be layered.
92     Feature supportsExternalMemoryFd = {"supportsExternalMemoryFd", FeatureCategory::VulkanFeatures,
93                                         "VkDevice supports the VK_KHR_external_memory_fd extension",
94                                         &members};
95 
96     // Whether the VkDevice supports the VK_FUCHSIA_external_memory
97     // extension, on which the GL_ANGLE_memory_object_fuchsia extension can be layered.
98     Feature supportsExternalMemoryFuchsia = {
99         "supportsExternalMemoryFuchsia", FeatureCategory::VulkanFeatures,
100         "VkDevice supports the VK_FUCHSIA_external_memory extension", &members};
101 
102     Feature supportsFilteringPrecision = {
103         "supportsFilteringPrecision", FeatureCategory::VulkanFeatures,
104         "VkDevice supports the VK_GOOGLE_sampler_filtering_precision extension", &members};
105 
106     // Whether the VkDevice supports the VK_KHR_external_fence_capabilities extension.
107     Feature supportsExternalFenceCapabilities = {
108         "supportsExternalFenceCapabilities", FeatureCategory::VulkanFeatures,
109         "VkDevice supports the VK_KHR_external_fence_capabilities extension", &members};
110 
111     // Whether the VkDevice supports the VK_KHR_external_semaphore_capabilities extension.
112     Feature supportsExternalSemaphoreCapabilities = {
113         "supportsExternalSemaphoreCapabilities", FeatureCategory::VulkanFeatures,
114         "VkDevice supports the VK_KHR_external_semaphore_capabilities extension", &members};
115 
116     // Whether the VkDevice supports the VK_KHR_external_semaphore_fd extension, on which the
117     // GL_EXT_semaphore_fd extension can be layered.
118     Feature supportsExternalSemaphoreFd = {
119         "supportsExternalSemaphoreFd", FeatureCategory::VulkanFeatures,
120         "VkDevice supports the VK_KHR_external_semaphore_fd extension", &members};
121 
122     // Whether the VkDevice supports the VK_FUCHSIA_external_semaphore
123     // extension, on which the GL_ANGLE_semaphore_fuchsia extension can be layered.
124     angle::Feature supportsExternalSemaphoreFuchsia = {
125         "supportsExternalSemaphoreFuchsia", FeatureCategory::VulkanFeatures,
126         "VkDevice supports the VK_FUCHSIA_external_semaphore extension", &members};
127 
128     // Whether the VkDevice supports the VK_KHR_external_fence_fd extension, on which the
129     // EGL_ANDROID_native_fence extension can be layered.
130     Feature supportsExternalFenceFd = {"supportsExternalFenceFd", FeatureCategory::VulkanFeatures,
131                                        "VkDevice supports the VK_KHR_external_fence_fd extension",
132                                        &members, "http://anglebug.com/2517"};
133 
134     // Whether the VkDevice can support EGL_ANDROID_native_fence_sync extension.
135     Feature supportsAndroidNativeFenceSync = {
136         "supportsAndroidNativeFenceSync", FeatureCategory::VulkanFeatures,
137         "VkDevice supports the EGL_ANDROID_native_fence_sync extension", &members,
138         "http://anglebug.com/2517"};
139 
140     // Whether the VkDevice can support the imageCubeArray feature properly.
141     Feature supportsImageCubeArray = {"supportsImageCubeArray", FeatureCategory::VulkanFeatures,
142                                       "VkDevice supports the imageCubeArray feature properly",
143                                       &members, "http://anglebug.com/3584"};
144 
145     // Whether the VkDevice supports the pipelineStatisticsQuery feature.
146     Feature supportsPipelineStatisticsQuery = {
147         "supportsPipelineStatisticsQuery", FeatureCategory::VulkanFeatures,
148         "VkDevice supports the pipelineStatisticsQuery feature", &members,
149         "http://anglebug.com/5430"};
150 
151     // Whether the VkDevice supports the VK_EXT_shader_stencil_export extension, which is used to
152     // perform multisampled resolve of stencil buffer.  A multi-step workaround is used instead if
153     // this extension is not available.
154     Feature supportsShaderStencilExport = {
155         "supportsShaderStencilExport", FeatureCategory::VulkanFeatures,
156         "VkDevice supports the VK_EXT_shader_stencil_export extension", &members};
157 
158     // Whether the VkDevice supports the VK_KHR_sampler_ycbcr_conversion extension, which is needed
159     // to support Ycbcr conversion with external images.
160     Feature supportsYUVSamplerConversion = {
161         "supportsYUVSamplerConversion", FeatureCategory::VulkanFeatures,
162         "VkDevice supports the VK_KHR_sampler_ycbcr_conversion extension", &members};
163 
164     // Where VK_EXT_transform_feedback is not support, an emulation path is used.
165     // http://anglebug.com/3205
166     Feature emulateTransformFeedback = {
167         "emulateTransformFeedback", FeatureCategory::VulkanFeatures,
168         "Emulate transform feedback as the VK_EXT_transform_feedback is not present.", &members,
169         "http://anglebug.com/3205"};
170 
171     // Where VK_EXT_transform_feedback is supported, it's preferred over an emulation path.
172     // http://anglebug.com/3206
173     Feature supportsTransformFeedbackExtension = {
174         "supportsTransformFeedbackExtension", FeatureCategory::VulkanFeatures,
175         "Transform feedback uses the VK_EXT_transform_feedback extension.", &members,
176         "http://anglebug.com/3206"};
177 
178     Feature supportsGeometryStreamsCapability = {
179         "supportsGeometryStreamsCapability", FeatureCategory::VulkanFeatures,
180         "Implementation supports the GeometryStreams SPIR-V capability.", &members,
181         "http://anglebug.com/3206"};
182 
183     // Whether the VkDevice supports the VK_EXT_index_type_uint8 extension
184     // http://anglebug.com/4405
185     Feature supportsIndexTypeUint8 = {"supportsIndexTypeUint8", FeatureCategory::VulkanFeatures,
186                                       "VkDevice supports the VK_EXT_index_type_uint8 extension",
187                                       &members, "http://anglebug.com/4405"};
188 
189     // Whether the VkDevice supports the VK_EXT_custom_border_color extension
190     // http://anglebug.com/3577
191     Feature supportsCustomBorderColorEXT = {
192         "supports_custom_border_color", FeatureCategory::VulkanFeatures,
193         "VkDevice supports the VK_EXT_custom_border_color extension", &members,
194         "http://anglebug.com/3577"};
195 
196     // Whether the VkDevice supports multiDrawIndirect (drawIndirect with drawCount > 1)
197     // http://anglebug.com/6439
198     Feature supportsMultiDrawIndirect = {
199         "supportsMultiDrawIndirect", FeatureCategory::VulkanFeatures,
200         "VkDevice supports the multiDrawIndirect extension", &members, "http://anglebug.com/6439"};
201 
202     // Whether the VkDevice supports the VK_KHR_depth_stencil_resolve extension with the
203     // independentResolveNone feature.
204     // http://anglebug.com/4836
205     Feature supportsDepthStencilResolve = {"supportsDepthStencilResolve",
206                                            FeatureCategory::VulkanFeatures,
207                                            "VkDevice supports the VK_KHR_depth_stencil_resolve "
208                                            "extension with the independentResolveNone feature",
209                                            &members, "http://anglebug.com/4836"};
210 
211     // Whether the VkDevice supports the VK_EXT_multisampled_render_to_single_sampled extension.
212     // http://anglebug.com/4836
213     Feature supportsMultisampledRenderToSingleSampled = {
214         "supportsMultisampledRenderToSingleSampled", FeatureCategory::VulkanFeatures,
215         "VkDevice supports the VK_EXT_multisampled_render_to_single_sampled extension", &members,
216         "http://anglebug.com/4836"};
217 
218     // Whether the VkDevice supports the VK_KHR_multiview extension.  http://anglebug.com/6048
219     Feature supportsMultiview = {"supportsMultiview", FeatureCategory::VulkanFeatures,
220                                  "VkDevice supports the VK_KHR_multiview extension", &members,
221                                  "http://anglebug.com/6048"};
222 
223     // VK_PRESENT_MODE_FIFO_KHR causes random timeouts on Linux Intel. http://anglebug.com/3153
224     Feature disableFifoPresentMode = {"disableFifoPresentMode", FeatureCategory::VulkanWorkarounds,
225                                       "VK_PRESENT_MODE_FIFO_KHR causes random timeouts", &members,
226                                       "http://anglebug.com/3153"};
227 
228     // On Qualcomm, gaps in bound descriptor set indices causes the post-gap sets to misbehave.
229     // For example, binding only descriptor set 3 results in zero being read from a uniform buffer
230     // object within that set.  This flag results in empty descriptor sets being bound for any
231     // unused descriptor set to work around this issue.  http://anglebug.com/2727
232     Feature bindEmptyForUnusedDescriptorSets = {
233         "bindEmptyForUnusedDescriptorSets", FeatureCategory::VulkanWorkarounds,
234         "Gaps in bound descriptor set indices causes the post-gap sets to misbehave", &members,
235         "http://anglebug.com/2727"};
236 
237     // OES_depth_texture is a commonly expected feature on Android. However it
238     // requires that D16_UNORM support texture filtering
239     // (e.g. VK_FORMAT_FEATURE_SAMPLED_IMAGE_FILTER_LINEAR_BIT) and some devices
240     // do not. Work-around this by setting saying D16_UNORM supports filtering
241     // anyway.
242     Feature forceD16TexFilter = {
243         "forceD16TexFilter", FeatureCategory::VulkanWorkarounds,
244         "VK_FORMAT_D16_UNORM does not support VK_FORMAT_FEATURE_SAMPLED_IMAGE_FILTER_LINEAR_BIT, "
245         "which prevents OES_depth_texture from being supported.",
246         &members, "http://anglebug.com/3452"};
247 
248     // On some android devices, vkCmdBlitImage with flipped coordinates blits incorrectly.  This
249     // workaround makes sure this path is avoided.  http://anglebug.com/3498
250     Feature disableFlippingBlitWithCommand = {
251         "disableFlippingBlitWithCommand", FeatureCategory::VulkanWorkarounds,
252         "vkCmdBlitImage with flipped coordinates blits incorrectly.", &members,
253         "http://anglebug.com/3498"};
254 
255     // On platform with Intel or AMD GPU, a window resizing would not trigger the vulkan driver to
256     // return VK_ERROR_OUT_OF_DATE on swapchain present.  Work-around by query current window extent
257     // every frame to detect a window resizing.
258     // http://anglebug.com/3623, http://anglebug.com/3624, http://anglebug.com/3625
259     Feature perFrameWindowSizeQuery = {
260         "perFrameWindowSizeQuery", FeatureCategory::VulkanWorkarounds,
261         "Vulkan swapchain is not returning VK_ERROR_OUT_OF_DATE when window resizing", &members,
262         "http://anglebug.com/3623, http://anglebug.com/3624, http://anglebug.com/3625"};
263 
264     // Seamful cube map emulation misbehaves on the AMD windows driver, so it's disallowed.
265     Feature disallowSeamfulCubeMapEmulation = {
266         "disallowSeamfulCubeMapEmulation", FeatureCategory::VulkanWorkarounds,
267         "Seamful cube map emulation misbehaves on some drivers, so it's disallowed", &members,
268         "http://anglebug.com/3243"};
269 
270     // Vulkan considers vertex attribute accesses to count up to the last multiple of the stride.
271     // This additional access supports AMD's robust buffer access implementation.
272     // AMDVLK in particular will return incorrect values when the vertex access extends into the
273     // range that would be the stride padding and the buffer is too small.
274     // This workaround limits GL_MAX_VERTEX_ATTRIB_STRIDE to a reasonable value and pads out
275     // every buffer allocation size to be large enough to support a maximum vertex stride.
276     // http://anglebug.com/4428
277     Feature padBuffersToMaxVertexAttribStride = {
278         "padBuffersToMaxVertexAttribStride", FeatureCategory::VulkanWorkarounds,
279         "Vulkan considers vertex attribute accesses to count up to the last multiple of the "
280         "stride. This additional access supports AMD's robust buffer access implementation. "
281         "AMDVLK in particular will return incorrect values when the vertex access extends into "
282         "the range that would be the stride padding and the buffer is too small. "
283         "This workaround limits GL_MAX_VERTEX_ATTRIB_STRIDE to a maximum value and "
284         "pads up every buffer allocation size to be a multiple of the maximum stride.",
285         &members, "http://anglebug.com/4428"};
286 
287     // Whether the VkDevice supports the VK_EXT_swapchain_colorspace extension
288     // http://anglebug.com/2514
289     Feature supportsSwapchainColorspace = {
290         "supportsSwapchainColorspace", FeatureCategory::VulkanFeatures,
291         "VkDevice supports the VK_EXT_swapchain_colorspace extension", &members,
292         "http://anglebug.com/2514"};
293 
294     // Whether the VkDevice supports the VK_EXT_external_memory_dma_buf and
295     // VK_EXT_image_drm_format_modifier extensions.  These extensions are always used together to
296     // implement EGL_EXT_image_dma_buf_import and EGL_EXT_image_dma_buf_import_modifiers.
297     Feature supportsExternalMemoryDmaBufAndModifiers = {
298         "supportsExternalMemoryDmaBufAndModifiers", FeatureCategory::VulkanFeatures,
299         "VkDevice supports the VK_EXT_external_memory_dma_buf and VK_EXT_image_drm_format_modifier "
300         "extensions",
301         &members, "http://anglebug.com/6248"};
302 
303     // Whether the VkDevice supports the VK_EXT_external_memory_host extension, on which the
304     // ANGLE_iosurface_client_buffer extension can be layered.
305     Feature supportsExternalMemoryHost = {
306         "supportsExternalMemoryHost", FeatureCategory::VulkanFeatures,
307         "VkDevice supports the VK_EXT_external_memory_host extension", &members};
308 
309     // Whether to fill new buffers and textures with nonzero data to sanitize robust resource
310     // initialization and flush out assumptions about zero init.
311     Feature allocateNonZeroMemory = {
312         "allocateNonZeroMemory", FeatureCategory::VulkanFeatures,
313         "Fill new allocations with non-zero values to flush out errors.", &members,
314         "http://anglebug.com/4384"};
315 
316     // Whether to log each callback from the VK_EXT_device_memory_report extension.  This feature is
317     // used for trying to debug GPU memory leaks.
318     Feature logMemoryReportCallbacks = {"logMemoryReportCallbacks", FeatureCategory::VulkanFeatures,
319                                         "Log each callback from VK_EXT_device_memory_report",
320                                         &members};
321 
322     // Whether to log statistics from the VK_EXT_device_memory_report extension each eglSwapBuffer.
323     Feature logMemoryReportStats = {"logMemoryReportStats", FeatureCategory::VulkanFeatures,
324                                     "Log stats from VK_EXT_device_memory_report each swap",
325                                     &members};
326 
327     // Allocate a "shadow" buffer for GL buffer objects. For GPU-read only buffers
328     // glMap* latency can be reduced by maintaining a copy of the buffer which is
329     // writeable only by the CPU. We then return this shadow buffer on glMap* calls.
330     Feature shadowBuffers = {
331         "shadowBuffers", FeatureCategory::VulkanFeatures,
332         "Allocate a shadow buffer for GL buffer objects to reduce glMap* latency.", &members,
333         "http://anglebug.com/4339"};
334 
335     // When we update buffer data we usually face a choice to either clone a buffer and copy the
336     // data or stage a buffer update and use the GPU to do the copy. For some GPUs, a performance
337     // penalty to use the GPU to do copies. Setting this flag to true will always try to create a
338     // new buffer and use the CPU to copy data when possible.
339     Feature preferCPUForBufferSubData = {
340         "preferCPUForBufferSubData", FeatureCategory::VulkanFeatures,
341         "Prefer use CPU to do bufferSubData instead of staged update.", &members,
342         "http://issuetracker.google.com/200067929"};
343 
344     // Persistently map buffer memory until destroy, saves on map/unmap IOCTL overhead
345     // for buffers that are updated frequently.
346     Feature persistentlyMappedBuffers = {
347         "persistentlyMappedBuffers", FeatureCategory::VulkanFeatures,
348         "Persistently map buffer memory to reduce map/unmap IOCTL overhead.", &members,
349         "http://anglebug.com/2162"};
350 
351     // Android needs to pre-rotate surfaces that are not oriented per the native device's
352     // orientation (e.g. a landscape application on a Pixel phone).  This feature works for
353     // full-screen applications. http://anglebug.com/3502
354     Feature enablePreRotateSurfaces = {"enablePreRotateSurfaces", FeatureCategory::VulkanFeatures,
355                                        "Enable Android pre-rotation for landscape applications",
356                                        &members, "http://anglebug.com/3502"};
357 
358     // Enable precision qualifiers for shaders generated by Vulkan backend http://anglebug.com/3078
359     Feature enablePrecisionQualifiers = {
360         "enablePrecisionQualifiers", FeatureCategory::VulkanFeatures,
361         "Enable precision qualifiers in shaders", &members, "http://anglebug.com/3078"};
362 
363     // Desktop (at least NVIDIA) drivers prefer combining barriers into one vkCmdPipelineBarrier
364     // call over issuing multiple barrier calls with fine grained dependency information to have
365     // better performance. http://anglebug.com/4633
366     Feature preferAggregateBarrierCalls = {
367         "preferAggregateBarrierCalls", FeatureCategory::VulkanWorkarounds,
368         "Single barrier call is preferred over multiple calls with "
369         "fine grained pipeline stage dependency information",
370         &members, "http://anglebug.com/4633"};
371 
372     // Tell the Vulkan back-end to use the async command queue to dispatch work to the GPU. Command
373     // buffer work will happened in a worker thread. Otherwise use Renderer::CommandQueue directly.
374     Feature asyncCommandQueue = {"asyncCommandQueue", FeatureCategory::VulkanFeatures,
375                                  "Use CommandQueue worker thread to dispatch work to GPU.",
376                                  &members, "http://anglebug.com/4324"};
377 
378     // Whether the VkDevice supports the VK_KHR_shader_float16_int8 extension and has the
379     // shaderFloat16 feature.
380     Feature supportsShaderFloat16 = {"supportsShaderFloat16", FeatureCategory::VulkanFeatures,
381                                      "VkDevice supports the VK_KHR_shader_float16_int8 extension "
382                                      "and has the shaderFloat16 feature",
383                                      &members, "http://anglebug.com/4551"};
384 
385     // Some devices don't meet the limits required to perform mipmap generation using the built-in
386     // compute shader.  On some other devices, VK_IMAGE_USAGE_STORAGE_BIT is detrimental to
387     // performance, making this solution impractical.
388     Feature allowGenerateMipmapWithCompute = {
389         "allowGenerateMipmapWithCompute", FeatureCategory::VulkanFeatures,
390         "Use the compute path to generate mipmaps on devices that meet the minimum requirements, "
391         "and the performance is better.",
392         &members, "http://anglebug.com/4551"};
393 
394     // Whether the VkDevice supports the VK_QCOM_render_pass_store_ops extension
395     // http://anglebug.com/5505
396     Feature supportsRenderPassStoreOpNoneQCOM = {
397         "supportsRenderPassStoreOpNoneQCOM", FeatureCategory::VulkanFeatures,
398         "VkDevice supports VK_QCOM_render_pass_store_ops extension.", &members,
399         "http://anglebug.com/5055"};
400 
401     // Whether the VkDevice supports the VK_EXT_load_store_op_none extension
402     // http://anglebug.com/5371
403     Feature supportsRenderPassLoadStoreOpNone = {
404         "supportsRenderPassLoadStoreOpNone", FeatureCategory::VulkanFeatures,
405         "VkDevice supports VK_EXT_load_store_op_none extension.", &members,
406         "http://anglebug.com/5371"};
407 
408     // Force maxUniformBufferSize to 16K on Qualcomm's Adreno 540. Pixel2's Adreno540 reports
409     // maxUniformBufferSize 64k but various tests failed with that size. For that specific
410     // device, we set to 16k for now which is known to pass all tests.
411     // https://issuetracker.google.com/161903006
412     Feature forceMaxUniformBufferSize16KB = {
413         "forceMaxUniformBufferSize16KB", FeatureCategory::VulkanWorkarounds,
414         "Force max uniform buffer size to 16K on some device due to bug", &members,
415         "https://issuetracker.google.com/161903006"};
416 
417     // Enable mutable bit by default for ICD's that support VK_KHR_image_format_list.
418     // http://anglebug.com/5281
419     Feature supportsImageFormatList = {
420         "supportsImageFormatList", FeatureCategory::VulkanFeatures,
421         "Enable VK_IMAGE_CREATE_MUTABLE_FORMAT_BIT by default for ICDs "
422         "that support VK_KHR_image_format_list",
423         &members, "http://anglebug.com/5281"};
424 
425     // Swiftshader on mac fails to initialize WebGL context when EXT_multisampled_render_to_texture
426     // is used by Chromium.
427     // http://anglebug.com/4937
428     Feature enableMultisampledRenderToTexture = {
429         "enableMultisampledRenderToTexture", FeatureCategory::VulkanWorkarounds,
430         "Expose EXT_multisampled_render_to_texture", &members, "http://anglebug.com/4937"};
431 
432     // Qualcomm fails some tests when reducing the preferred block size to 4M.
433     // http://anglebug.com/4995
434     Feature preferredLargeHeapBlockSize4MB = {
435         "preferredLargeHeapBlockSize4MB", FeatureCategory::VulkanWorkarounds,
436         "Use 4 MB preferred large heap block size with AMD allocator", &members,
437         "http://anglebug.com/4995"};
438 
439     // Manhattan is calling glFlush in the middle of renderpass which breaks renderpass and hurts
440     // performance on tile based GPU. When this is enabled, we will defer the glFlush call made in
441     // the middle of renderpass to the end of renderpass.
442     // https://issuetracker.google.com/issues/166475273
443     Feature deferFlushUntilEndRenderPass = {
444         "deferFlushUntilEndRenderPass", FeatureCategory::VulkanWorkarounds,
445         "Allow glFlush to be deferred until renderpass ends", &members,
446         "https://issuetracker.google.com/issues/166475273"};
447 
448     // Android mistakenly destroys oldSwapchain passed to vkCreateSwapchainKHR, causing crashes on
449     // certain drivers.  http://anglebug.com/5061
450     Feature waitIdleBeforeSwapchainRecreation = {
451         "waitIdleBeforeSwapchainRecreation", FeatureCategory::VulkanWorkarounds,
452         "Before passing an oldSwapchain to VkSwapchainCreateInfoKHR, wait for queue to be idle. "
453         "Works around a bug on platforms which destroy oldSwapchain in vkCreateSwapchainKHR.",
454         &members, "http://anglebug.com/5061"};
455 
456     // Allow forcing an LOD offset on all sampling operations for performance comparisons. ANGLE is
457     // non-conformant if this feature is enabled.
458     std::array<angle::Feature, 4> forceTextureLODOffset = {
459         angle::Feature{"force_texture_lod_offset_1", angle::FeatureCategory::VulkanWorkarounds,
460                        "Increase the minimum texture level-of-detail by 1 when sampling.",
461                        &members},
462         angle::Feature{"force_texture_lod_offset_2", angle::FeatureCategory::VulkanWorkarounds,
463                        "Increase the minimum texture level-of-detail by 2 when sampling.",
464                        &members},
465         angle::Feature{"force_texture_lod_offset_3", angle::FeatureCategory::VulkanWorkarounds,
466                        "Increase the minimum texture level-of-detail by 3 when sampling.",
467                        &members},
468         angle::Feature{"force_texture_lod_offset_4", angle::FeatureCategory::VulkanWorkarounds,
469                        "Increase the minimum texture level-of-detail by 4 when sampling.",
470                        &members},
471     };
472 
473     // Translate non-nearest filtering modes to nearest for all samplers for performance
474     // comparisons. ANGLE is non-conformant if this feature is enabled.
475     Feature forceNearestFiltering = {"force_nearest_filtering", FeatureCategory::VulkanWorkarounds,
476                                      "Force nearest filtering when sampling.", &members};
477 
478     // Translate  non-nearest mip filtering modes to nearest mip for all samplers for performance
479     // comparisons. ANGLE is non-conformant if this feature is enabled.
480     Feature forceNearestMipFiltering = {"forceNearestMipFiltering",
481                                         FeatureCategory::VulkanWorkarounds,
482                                         "Force nearest mip filtering when sampling.", &members};
483 
484     // Compress float32 vertices in static buffers to float16 at draw time. ANGLE is non-conformant
485     // if this feature is enabled.
486     angle::Feature compressVertexData = {"compress_vertex_data",
487                                          angle::FeatureCategory::VulkanWorkarounds,
488                                          "Compress vertex data to smaller data types when "
489                                          "possible. Using this feature makes ANGLE non-conformant.",
490                                          &members};
491 
492     // Qualcomm missynchronizes vkCmdClearAttachments in the middle of render pass.
493     // https://issuetracker.google.com/166809097
494     Feature preferDrawClearOverVkCmdClearAttachments = {
495         "preferDrawClearOverVkCmdClearAttachments", FeatureCategory::VulkanWorkarounds,
496         "On some hardware, clear using a draw call instead of vkCmdClearAttachments in the middle "
497         "of render pass due to bugs",
498         &members, "https://issuetracker.google.com/166809097"};
499 
500     // Whether prerotation is being emulated for testing.  90 degree rotation.
501     Feature emulatedPrerotation90 = {"emulatedPrerotation90", FeatureCategory::VulkanFeatures,
502                                      "Emulate 90-degree prerotation.", &members,
503                                      "http://anglebug.com/4901"};
504 
505     // Whether prerotation is being emulated for testing.  180 degree rotation.
506     Feature emulatedPrerotation180 = {"emulatedPrerotation180", FeatureCategory::VulkanFeatures,
507                                       "Emulate 180-degree prerotation.", &members,
508                                       "http://anglebug.com/4901"};
509 
510     // Whether prerotation is being emulated for testing.  270 degree rotation.
511     Feature emulatedPrerotation270 = {"emulatedPrerotation270", FeatureCategory::VulkanFeatures,
512                                       "Emulate 270-degree prerotation.", &members,
513                                       "http://anglebug.com/4901"};
514 
515     // Whether SPIR-V should be generated through glslang.  Transitory feature while confidence is
516     // built on the SPIR-V generation code.
517     Feature generateSPIRVThroughGlslang = {
518         "generateSPIRVThroughGlslang", FeatureCategory::VulkanFeatures,
519         "Translate SPIR-V through glslang.", &members, "http://anglebug.com/4889"};
520 
521     // Whether we should use driver uniforms over specialization constants for some shader
522     // modifications like yflip and rotation.
523     Feature forceDriverUniformOverSpecConst = {
524         "forceDriverUniformOverSpecConst", FeatureCategory::VulkanWorkarounds,
525         "Forces using driver uniforms instead of specialization constants.", &members,
526         "http://issuetracker.google.com/173636783"};
527 
528     // Whether non-conformant configurations and extensions should be exposed.  When an extension is
529     // in development, or a GLES version is not supported on a device, we may still want to expose
530     // them for partial testing.  This feature is enabled by our test harness.
531     Feature exposeNonConformantExtensionsAndVersions = {
532         "exposeNonConformantExtensionsAndVersions", FeatureCategory::VulkanWorkarounds,
533         "Expose GLES versions and extensions that are not conformant.", &members,
534         "http://anglebug.com/5375"};
535 
536     // imageAtomicExchange is expected to work for r32f formats, but support for atomic operations
537     // for VK_FORMAT_R32_SFLOAT is rare.  This support is emulated by using an r32ui format for such
538     // images instead.
539     Feature emulateR32fImageAtomicExchange = {
540         "emulateR32fImageAtomicExchange", FeatureCategory::VulkanWorkarounds,
541         "Emulate r32f images with r32ui to support imageAtomicExchange.", &members,
542         "http://anglebug.com/5535"};
543 
544     Feature supportsNegativeViewport = {
545         "supportsNegativeViewport", FeatureCategory::VulkanFeatures,
546         "The driver supports inverting the viewport with a negative height.", &members};
547 
548     // Whether we should force any highp precision in the fragment shader to mediump.
549     // ANGLE is non-conformant if this feature is enabled.
550     Feature forceFragmentShaderPrecisionHighpToMediump = {
551         "forceFragmentShaderPrecisionHighpToMediump", FeatureCategory::VulkanWorkarounds,
552         "Forces highp precision in fragment shader to mediump.", &members,
553         "https://issuetracker.google.com/184850002"};
554 
555     // Whether we should submit at each FBO boundary.
556     Feature preferSubmitAtFBOBoundary = {
557         "preferSubmitAtFBOBoundary", FeatureCategory::VulkanWorkarounds,
558         "Submit commands to driver at each FBO boundary for performance improvements.", &members,
559         "https://issuetracker.google.com/187425444"};
560 
561     // Workaround for gap in Vulkan spec related to querying descriptor count for immutable samplers
562     // tied to an external format.
563     Feature useMultipleDescriptorsForExternalFormats = {
564         "useMultipleDescriptorsForExternalFormats", FeatureCategory::VulkanWorkarounds,
565         "Return a default descriptor count for external formats.", &members,
566         "http://anglebug.com/6141"};
567 
568     // Whether the VkDevice can support Protected Memory.
569     Feature supportsProtectedMemory = {"supports_protected_memory", FeatureCategory::VulkanFeatures,
570                                        "VkDevice supports protected memory", &members,
571                                        "http://anglebug.com/3965"};
572 
573     // Whether the VkDevice supports the VK_EXT_host_query_reset extension
574     // http://anglebug.com/6692
575     Feature supportsHostQueryReset = {"supportsHostQueryReset", FeatureCategory::VulkanFeatures,
576                                       "VkDevice supports VK_EXT_host_query_reset extension",
577                                       &members, "http://anglebug.com/6692"};
578 
579     // Whether the VkInstance supports the VK_KHR_get_surface_capabilities2 extension.
580     Feature supportsSurfaceCapabilities2Extension = {
581         "supportsSurfaceCapabilities2Extension", FeatureCategory::VulkanFeatures,
582         "VkInstance supports the VK_KHR_get_surface_capabilities2 extension", &members};
583 
584     // Whether the VkInstance supports the VK_KHR_surface_protected_capabilities extension.
585     Feature supportsSurfaceProtectedCapabilitiesExtension = {
586         "supportsSurfaceProtectedCapabilitiesExtension", FeatureCategory::VulkanFeatures,
587         "VkInstance supports the VK_KHR_surface_protected_capabilities extension", &members};
588 
589     // Whether the VkSurface supports protected swapchains from
590     // supportsSurfaceProtectedCapabilitiesExtension.
591     Feature supportsSurfaceProtectedSwapchains = {
592         "supportsSurfaceProtectedSwapchains", FeatureCategory::VulkanFeatures,
593         "VkSurface supportsProtected for protected swapchains", &members};
594 
595     // Whether surface format GL_RGB8 should be overridden to GL_RGBA8.
596     Feature overrideSurfaceFormatRGB8toRGBA8 = {
597         "overrideSurfaceFormatRGB8toRGBA8", FeatureCategory::VulkanWorkarounds,
598         "Override surface format GL_RGB8 to GL_RGBA8", &members, "http://anglebug.com/6651"};
599 
600     // Whether the VkSurface supports VK_KHR_shared_presentable_images.
601     Feature supportsSharedPresentableImageExtension = {
602         "supportsSharedPresentableImageExtension", FeatureCategory::VulkanFeatures,
603         "VkSurface supports the VK_KHR_shared_presentable_images extension", &members};
604 };
605 
606 inline FeaturesVk::FeaturesVk()  = default;
607 inline FeaturesVk::~FeaturesVk() = default;
608 
609 }  // namespace angle
610 
611 #endif  // ANGLE_PLATFORM_FEATURESVK_H_
612