• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright 2015 Google Inc.
3  *
4  * Use of this source code is governed by a BSD-style license that can be
5  * found in the LICENSE file.
6  */
7 
8 #ifndef GrVkCaps_DEFINED
9 #define GrVkCaps_DEFINED
10 
11 #include "include/gpu/vk/GrVkTypes.h"
12 #include "src/gpu/GrCaps.h"
13 #include "src/gpu/vk/GrVkStencilAttachment.h"
14 
15 class GrShaderCaps;
16 class GrVkExtensions;
17 struct GrVkInterface;
18 
19 /**
20  * Stores some capabilities of a Vk backend.
21  */
22 class GrVkCaps : public GrCaps {
23 public:
24     typedef GrVkStencilAttachment::Format StencilFormat;
25 
26     /**
27      * Creates a GrVkCaps that is set such that nothing is supported. The init function should
28      * be called to fill out the caps.
29      */
30     GrVkCaps(const GrContextOptions& contextOptions, const GrVkInterface* vkInterface,
31              VkPhysicalDevice device, const VkPhysicalDeviceFeatures2& features,
32              uint32_t instanceVersion, uint32_t physicalDeviceVersion,
33              const GrVkExtensions& extensions, GrProtected isProtected = GrProtected::kNo);
34 
35     bool isFormatSRGB(const GrBackendFormat&) const override;
36     bool isFormatCompressed(const GrBackendFormat&) const override;
37 
38 
39     bool isFormatTexturableAndUploadable(GrColorType, const GrBackendFormat&) const override;
40     bool isFormatTexturable(const GrBackendFormat&) const override;
41     bool isVkFormatTexturable(VkFormat) const;
42 
isFormatCopyable(const GrBackendFormat &)43     bool isFormatCopyable(const GrBackendFormat&) const override { return true; }
44 
45     bool isFormatAsColorTypeRenderable(GrColorType ct, const GrBackendFormat& format,
46                                        int sampleCount = 1) const override;
47     bool isFormatRenderable(const GrBackendFormat& format, int sampleCount) const override;
48     bool isFormatRenderable(VkFormat, int sampleCount) const;
49 
50     int getRenderTargetSampleCount(int requestedCount, const GrBackendFormat&) const override;
51     int getRenderTargetSampleCount(int requestedCount, VkFormat) const;
52 
53     int maxRenderTargetSampleCount(const GrBackendFormat&) const override;
54     int maxRenderTargetSampleCount(VkFormat format) const;
55 
56     SupportedWrite supportedWritePixelsColorType(GrColorType surfaceColorType,
57                                                  const GrBackendFormat& surfaceFormat,
58                                                  GrColorType srcColorType) const override;
59 
60     SurfaceReadPixelsSupport surfaceSupportsReadPixels(const GrSurface*) const override;
61 
isVkFormatTexturableLinearly(VkFormat format)62     bool isVkFormatTexturableLinearly(VkFormat format) const {
63         return SkToBool(FormatInfo::kTexturable_Flag & this->getFormatInfo(format).fLinearFlags);
64     }
65 
formatCanBeDstofBlit(VkFormat format,bool linearTiled)66     bool formatCanBeDstofBlit(VkFormat format, bool linearTiled) const {
67         const FormatInfo& info = this->getFormatInfo(format);
68         const uint16_t& flags = linearTiled ? info.fLinearFlags : info.fOptimalFlags;
69         return SkToBool(FormatInfo::kBlitDst_Flag & flags);
70     }
71 
formatCanBeSrcofBlit(VkFormat format,bool linearTiled)72     bool formatCanBeSrcofBlit(VkFormat format, bool linearTiled) const {
73         const FormatInfo& info = this->getFormatInfo(format);
74         const uint16_t& flags = linearTiled ? info.fLinearFlags : info.fOptimalFlags;
75         return SkToBool(FormatInfo::kBlitSrc_Flag & flags);
76     }
77 
78     // On Adreno vulkan, they do not respect the imageOffset parameter at least in
79     // copyImageToBuffer. This flag says that we must do the copy starting from the origin always.
mustDoCopiesFromOrigin()80     bool mustDoCopiesFromOrigin() const {
81         return fMustDoCopiesFromOrigin;
82     }
83 
84     // Sometimes calls to QueueWaitIdle return before actually signalling the fences
85     // on the command buffers even though they have completed. This causes an assert to fire when
86     // destroying the command buffers. Therefore we add a sleep to make sure the fence signals.
mustSleepOnTearDown()87     bool mustSleepOnTearDown() const {
88         return fMustSleepOnTearDown;
89     }
90 
91     // Returns true if we should always make dedicated allocations for VkImages.
shouldAlwaysUseDedicatedImageMemory()92     bool shouldAlwaysUseDedicatedImageMemory() const {
93         return fShouldAlwaysUseDedicatedImageMemory;
94     }
95 
96     // Always use a transfer buffer instead of vkCmdUpdateBuffer to upload data to a VkBuffer.
avoidUpdateBuffers()97     bool avoidUpdateBuffers() const {
98         return fAvoidUpdateBuffers;
99     }
100 
101     /**
102      * Returns both a supported and most preferred stencil format to use in draws.
103      */
preferredStencilFormat()104     const StencilFormat& preferredStencilFormat() const {
105         return fPreferredStencilFormat;
106     }
107 
108     // Returns whether the device supports VK_KHR_Swapchain. Internally Skia never uses any of the
109     // swapchain functions, but we may need to transition to and from the
110     // VK_IMAGE_LAYOUT_PRESENT_SRC_KHR image layout, so we must know whether that layout is
111     // supported.
supportsSwapchain()112     bool supportsSwapchain() const { return fSupportsSwapchain; }
113 
114     // Returns whether the device supports the ability to extend VkPhysicalDeviceProperties struct.
supportsPhysicalDeviceProperties2()115     bool supportsPhysicalDeviceProperties2() const { return fSupportsPhysicalDeviceProperties2; }
116     // Returns whether the device supports the ability to extend VkMemoryRequirements struct.
supportsMemoryRequirements2()117     bool supportsMemoryRequirements2() const { return fSupportsMemoryRequirements2; }
118 
119     // Returns whether the device supports the ability to extend the vkBindMemory call.
supportsBindMemory2()120     bool supportsBindMemory2() const { return fSupportsBindMemory2; }
121 
122     // Returns whether or not the device suports the various API maintenance fixes to Vulkan 1.0. In
123     // Vulkan 1.1 all these maintenance are part of the core spec.
supportsMaintenance1()124     bool supportsMaintenance1() const { return fSupportsMaintenance1; }
supportsMaintenance2()125     bool supportsMaintenance2() const { return fSupportsMaintenance2; }
supportsMaintenance3()126     bool supportsMaintenance3() const { return fSupportsMaintenance3; }
127 
128     // Returns true if the device supports passing in a flag to say we are using dedicated GPU when
129     // allocating memory. For some devices this allows them to return more optimized memory knowning
130     // they will never need to suballocate amonst multiple objects.
supportsDedicatedAllocation()131     bool supportsDedicatedAllocation() const { return fSupportsDedicatedAllocation; }
132 
133     // Returns true if the device supports importing of external memory into Vulkan memory.
supportsExternalMemory()134     bool supportsExternalMemory() const { return fSupportsExternalMemory; }
135     // Returns true if the device supports importing Android hardware buffers into Vulkan memory.
supportsAndroidHWBExternalMemory()136     bool supportsAndroidHWBExternalMemory() const { return fSupportsAndroidHWBExternalMemory; }
137 
138     // Returns true if it supports ycbcr conversion for samplers
supportsYcbcrConversion()139     bool supportsYcbcrConversion() const { return fSupportsYcbcrConversion; }
140 
141     // Returns true if the device supports protected memory.
supportsProtectedMemory()142     bool supportsProtectedMemory() const { return fSupportsProtectedMemory; }
143 
144     /**
145      * Helpers used by canCopySurface. In all cases if the SampleCnt parameter is zero that means
146      * the surface is not a render target, otherwise it is the number of samples in the render
147      * target.
148      */
149     bool canCopyImage(VkFormat dstFormat, int dstSampleCnt, bool dstHasYcbcr,
150                       VkFormat srcFormat, int srcSamplecnt, bool srcHasYcbcr) const;
151 
152     bool canCopyAsBlit(VkFormat dstConfig, int dstSampleCnt, bool dstIsLinear, bool dstHasYcbcr,
153                        VkFormat srcConfig, int srcSampleCnt, bool srcIsLinear,
154                        bool srcHasYcbcr) const;
155 
156     bool canCopyAsResolve(VkFormat dstConfig, int dstSampleCnt, bool dstHasYcbcr,
157                           VkFormat srcConfig, int srcSamplecnt, bool srcHasYcbcr) const;
158 
159     GrColorType getYUVAColorTypeFromBackendFormat(const GrBackendFormat&,
160                                                   bool isAlphaChannel) const override;
161 
162     GrBackendFormat getBackendFormatFromCompressionType(SkImage::CompressionType) const override;
163 
getFormatFromColorType(GrColorType colorType)164     VkFormat getFormatFromColorType(GrColorType colorType) const {
165         int idx = static_cast<int>(colorType);
166         return fColorTypeToFormatTable[idx];
167     }
168 
169     bool canClearTextureOnCreation() const override;
170 
171     GrSwizzle getTextureSwizzle(const GrBackendFormat&, GrColorType) const override;
172     GrSwizzle getOutputSwizzle(const GrBackendFormat&, GrColorType) const override;
173 
174     int getFragmentUniformBinding() const;
175     int getFragmentUniformSet() const;
176 
177 #if GR_TEST_UTILS
178     std::vector<TestFormatColorTypeCombination> getTestingCombinations() const override;
179 #endif
180 
181 private:
182     enum VkVendor {
183         kAMD_VkVendor = 4098,
184         kARM_VkVendor = 5045,
185         kImagination_VkVendor = 4112,
186         kIntel_VkVendor = 32902,
187         kNvidia_VkVendor = 4318,
188         kQualcomm_VkVendor = 20803,
189     };
190 
191     void init(const GrContextOptions& contextOptions, const GrVkInterface* vkInterface,
192               VkPhysicalDevice device, const VkPhysicalDeviceFeatures2&,
193               uint32_t physicalDeviceVersion, const GrVkExtensions&, GrProtected isProtected);
194     void initGrCaps(const GrVkInterface* vkInterface,
195                     VkPhysicalDevice physDev,
196                     const VkPhysicalDeviceProperties&,
197                     const VkPhysicalDeviceMemoryProperties&,
198                     const VkPhysicalDeviceFeatures2&,
199                     const GrVkExtensions&);
200     void initShaderCaps(const VkPhysicalDeviceProperties&, const VkPhysicalDeviceFeatures2&);
201 
202     void initFormatTable(const GrVkInterface*, VkPhysicalDevice, const VkPhysicalDeviceProperties&);
203     void initStencilFormat(const GrVkInterface* iface, VkPhysicalDevice physDev);
204 
205     void applyDriverCorrectnessWorkarounds(const VkPhysicalDeviceProperties&);
206 
207     bool onSurfaceSupportsWritePixels(const GrSurface*) const override;
208     bool onCanCopySurface(const GrSurfaceProxy* dst, const GrSurfaceProxy* src,
209                           const SkIRect& srcRect, const SkIPoint& dstPoint) const override;
210     GrBackendFormat onGetDefaultBackendFormat(GrColorType, GrRenderable) const override;
211 
212     GrPixelConfig onGetConfigFromBackendFormat(const GrBackendFormat&, GrColorType) const override;
213     bool onAreColorTypeAndFormatCompatible(GrColorType, const GrBackendFormat&) const override;
214 
215     SupportedRead onSupportedReadPixelsColorType(GrColorType, const GrBackendFormat&,
216                                                  GrColorType) const override;
217 
218     // ColorTypeInfo for a specific format
219     struct ColorTypeInfo {
220         GrColorType fColorType = GrColorType::kUnknown;
221         enum {
222             kUploadData_Flag = 0x1,
223             // Does Ganesh itself support rendering to this colorType & format pair. Renderability
224             // still additionally depends on if the format itself is renderable.
225             kRenderable_Flag = 0x2,
226             // Indicates that this colorType is supported only if we are wrapping a texture with
227             // the given format and colorType. We do not allow creation with this pair.
228             kWrappedOnly_Flag = 0x4,
229         };
230         uint32_t fFlags = 0;
231 
232         GrSwizzle fTextureSwizzle;
233         GrSwizzle fOutputSwizzle;
234     };
235 
236     struct FormatInfo {
colorTypeFlagsFormatInfo237         uint32_t colorTypeFlags(GrColorType colorType) const {
238             for (int i = 0; i < fColorTypeInfoCount; ++i) {
239                 if (fColorTypeInfos[i].fColorType == colorType) {
240                     return fColorTypeInfos[i].fFlags;
241                 }
242             }
243             return 0;
244         }
245 
246         void init(const GrVkInterface*, VkPhysicalDevice, const VkPhysicalDeviceProperties&,
247                   VkFormat);
248         static void InitFormatFlags(VkFormatFeatureFlags, uint16_t* flags);
249         void initSampleCounts(const GrVkInterface*, VkPhysicalDevice,
250                               const VkPhysicalDeviceProperties&, VkFormat);
251 
252         enum {
253             kTexturable_Flag = 0x1,
254             kRenderable_Flag = 0x2,
255             kBlitSrc_Flag    = 0x4,
256             kBlitDst_Flag    = 0x8,
257         };
258 
259         uint16_t fOptimalFlags = 0;
260         uint16_t fLinearFlags = 0;
261 
262         SkTDArray<int> fColorSampleCounts;
263 
264         std::unique_ptr<ColorTypeInfo[]> fColorTypeInfos;
265         int fColorTypeInfoCount = 0;
266     };
267     static const size_t kNumVkFormats = 20;
268     FormatInfo fFormatTable[kNumVkFormats];
269 
270     FormatInfo& getFormatInfo(VkFormat);
271     const FormatInfo& getFormatInfo(VkFormat) const;
272 
273     VkFormat fColorTypeToFormatTable[kGrColorTypeCnt];
274     void setColorType(GrColorType, std::initializer_list<VkFormat> formats);
275 
276     StencilFormat fPreferredStencilFormat;
277 
278     SkSTArray<1, GrVkYcbcrConversionInfo> fYcbcrInfos;
279 
280     bool fMustDoCopiesFromOrigin = false;
281     bool fMustSleepOnTearDown = false;
282     bool fShouldAlwaysUseDedicatedImageMemory = false;
283 
284     bool fAvoidUpdateBuffers = false;
285 
286     bool fSupportsSwapchain = false;
287 
288     bool fSupportsPhysicalDeviceProperties2 = false;
289     bool fSupportsMemoryRequirements2 = false;
290     bool fSupportsBindMemory2 = false;
291     bool fSupportsMaintenance1 = false;
292     bool fSupportsMaintenance2 = false;
293     bool fSupportsMaintenance3 = false;
294 
295     bool fSupportsDedicatedAllocation = false;
296     bool fSupportsExternalMemory = false;
297     bool fSupportsAndroidHWBExternalMemory = false;
298 
299     bool fSupportsYcbcrConversion = false;
300 
301     bool fSupportsProtectedMemory = false;
302 
303     typedef GrCaps INHERITED;
304 };
305 
306 #endif
307