1 | /* |
2 | * Copyright 2012 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 | |
9 | #ifndef GrGLCaps_DEFINED |
10 | #define GrGLCaps_DEFINED |
11 | |
12 | #include <functional> |
13 | #include "include/private/GrGLTypesPriv.h" |
14 | #include "include/private/SkChecksum.h" |
15 | #include "include/private/SkTArray.h" |
16 | #include "include/private/SkTHash.h" |
17 | #include "src/gpu/GrCaps.h" |
18 | #include "src/gpu/GrSwizzle.h" |
19 | #include "src/gpu/gl/GrGLStencilAttachment.h" |
20 | #include "src/gpu/gl/GrGLUtil.h" |
21 | |
22 | class GrGLContextInfo; |
23 | class GrGLRenderTarget; |
24 | |
25 | /** |
26 | * Stores some capabilities of a GL context. Most are determined by the GL |
27 | * version and the extensions string. It also tracks formats that have passed |
28 | * the FBO completeness test. |
29 | */ |
30 | class GrGLCaps : public GrCaps { |
31 | public: |
32 | typedef GrGLStencilAttachment::Format StencilFormat; |
33 | |
34 | /** |
35 | * The type of MSAA for FBOs supported. Different extensions have different |
36 | * semantics of how / when a resolve is performed. |
37 | */ |
38 | enum MSFBOType { |
39 | /** |
40 | * no support for MSAA FBOs |
41 | */ |
42 | kNone_MSFBOType = 0, |
43 | /** |
44 | * OpenGL 3.0+, OpenGL ES 3.0+, GL_ARB_framebuffer_object, |
45 | * GL_CHROMIUM_framebuffer_multisample, GL_ANGLE_framebuffer_multisample, |
46 | * or GL_EXT_framebuffer_multisample |
47 | */ |
48 | kStandard_MSFBOType, |
49 | /** |
50 | * GL_APPLE_framebuffer_multisample ES extension |
51 | */ |
52 | kES_Apple_MSFBOType, |
53 | /** |
54 | * GL_IMG_multisampled_render_to_texture. This variation does not have MSAA renderbuffers. |
55 | * Instead the texture is multisampled when bound to the FBO and then resolved automatically |
56 | * when read. It also defines an alternate value for GL_MAX_SAMPLES (which we call |
57 | * GR_GL_MAX_SAMPLES_IMG). |
58 | */ |
59 | kES_IMG_MsToTexture_MSFBOType, |
60 | /** |
61 | * GL_EXT_multisampled_render_to_texture. Same as the IMG one above but uses the standard |
62 | * GL_MAX_SAMPLES value. |
63 | */ |
64 | kES_EXT_MsToTexture_MSFBOType, |
65 | |
66 | kLast_MSFBOType = kES_EXT_MsToTexture_MSFBOType |
67 | }; |
68 | |
69 | enum BlitFramebufferFlags { |
70 | kNoSupport_BlitFramebufferFlag = 1 << 0, |
71 | kNoScalingOrMirroring_BlitFramebufferFlag = 1 << 1, |
72 | kResolveMustBeFull_BlitFrambufferFlag = 1 << 2, |
73 | kNoMSAADst_BlitFramebufferFlag = 1 << 3, |
74 | kNoFormatConversion_BlitFramebufferFlag = 1 << 4, |
75 | kNoFormatConversionForMSAASrc_BlitFramebufferFlag = 1 << 5, |
76 | kRectsMustMatchForMSAASrc_BlitFramebufferFlag = 1 << 6, |
77 | }; |
78 | |
79 | enum InvalidateFBType { |
80 | kNone_InvalidateFBType, |
81 | kDiscard_InvalidateFBType, //<! glDiscardFramebuffer() |
82 | kInvalidate_InvalidateFBType, //<! glInvalidateFramebuffer() |
83 | |
84 | kLast_InvalidateFBType = kInvalidate_InvalidateFBType |
85 | }; |
86 | |
87 | enum MapBufferType { |
88 | kNone_MapBufferType, |
89 | kMapBuffer_MapBufferType, // glMapBuffer() |
90 | kMapBufferRange_MapBufferType, // glMapBufferRange() |
91 | kChromium_MapBufferType, // GL_CHROMIUM_map_sub |
92 | |
93 | kLast_MapBufferType = kChromium_MapBufferType, |
94 | }; |
95 | |
96 | enum class TransferBufferType { |
97 | kNone, |
98 | kNV_PBO, // NV__pixel_buffer_object |
99 | kARB_PBO, // ARB_pixel_buffer_object |
100 | kChromium, // CHROMIUM_pixel_transfer_buffer_object |
101 | }; |
102 | |
103 | enum class FenceType { |
104 | kNone, |
105 | kSyncObject, |
106 | kNVFence |
107 | }; |
108 | |
109 | /** |
110 | * Initializes the GrGLCaps to the set of features supported in the current |
111 | * OpenGL context accessible via ctxInfo. |
112 | */ |
113 | GrGLCaps(const GrContextOptions& contextOptions, const GrGLContextInfo& ctxInfo, |
114 | const GrGLInterface* glInterface); |
115 | |
116 | bool isFormatSRGB(const GrBackendFormat&) const override; |
117 | SkImage::CompressionType compressionType(const GrBackendFormat&) const override; |
118 | |
119 | bool isFormatTexturable(const GrBackendFormat&) const override; |
120 | bool isFormatTexturable(GrGLFormat) const; |
121 | |
122 | bool isFormatAsColorTypeRenderable(GrColorType ct, const GrBackendFormat& format, |
123 | int sampleCount = 1) const override; |
124 | bool isFormatRenderable(const GrBackendFormat& format, int sampleCount) const override; |
125 | bool isFormatRenderable(GrGLFormat format, int sampleCount) const { |
126 | return sampleCount <= this->maxRenderTargetSampleCount(format); |
127 | } |
128 | |
129 | int getRenderTargetSampleCount(int requestedCount, |
130 | const GrBackendFormat& format) const override { |
131 | return this->getRenderTargetSampleCount(requestedCount, format.asGLFormat()); |
132 | } |
133 | int getRenderTargetSampleCount(int requestedCount, GrGLFormat) const; |
134 | |
135 | int maxRenderTargetSampleCount(const GrBackendFormat& format) const override { |
136 | return this->maxRenderTargetSampleCount(format.asGLFormat()); |
137 | } |
138 | int maxRenderTargetSampleCount(GrGLFormat) const; |
139 | |
140 | size_t bytesPerPixel(GrGLFormat) const; |
141 | size_t bytesPerPixel(const GrBackendFormat&) const override; |
142 | |
143 | bool isFormatCopyable(const GrBackendFormat&) const override; |
144 | |
145 | bool canFormatBeFBOColorAttachment(GrGLFormat) const; |
146 | |
147 | GrGLFormat getFormatFromColorType(GrColorType colorType) const { |
148 | int idx = static_cast<int>(colorType); |
149 | return fColorTypeToFormatTable[idx]; |
150 | } |
151 | |
152 | /** |
153 | * Gets the internal format to use with glTexImage...() and glTexStorage...(). May be sized or |
154 | * base depending upon the GL. Not applicable to compressed textures. |
155 | */ |
156 | GrGLenum getTexImageOrStorageInternalFormat(GrGLFormat format) const { |
157 | return this->getFormatInfo(format).fInternalFormatForTexImageOrStorage; |
158 | } |
159 | |
160 | /** |
161 | * Gets the external format and type to pass to glTexImage2D with nullptr to create an |
162 | * uninitialized texture. See getTexImageOrStorageInternalFormat() for the internal format. |
163 | */ |
164 | void getTexImageExternalFormatAndType(GrGLFormat surfaceFormat, GrGLenum* externalFormat, |
165 | GrGLenum* externalType) const; |
166 | |
167 | /** |
168 | * Given a src data color type and a color type interpretation for a texture of a given format |
169 | * this provides the external GL format and type to use with glTexSubImage2d. The color types |
170 | * should originate from supportedWritePixelsColorType(). |
171 | */ |
172 | void getTexSubImageExternalFormatAndType(GrGLFormat surfaceFormat, GrColorType surfaceColorType, |
173 | GrColorType memoryColorType, GrGLenum* externalFormat, |
174 | GrGLenum* externalType) const; |
175 | |
176 | /** |
177 | * Gets the external format, type, and bytes per pixel to use when uploading solid color data |
178 | * via glTexSubImage...() to clear the texture at creation. |
179 | */ |
180 | void getTexSubImageDefaultFormatTypeAndColorType(GrGLFormat format, |
181 | GrGLenum* externalFormat, |
182 | GrGLenum* externalType, |
183 | GrColorType* colorType) const; |
184 | |
185 | void getReadPixelsFormat(GrGLFormat surfaceFormat, GrColorType surfaceColorType, |
186 | GrColorType memoryColorType, GrGLenum* externalFormat, |
187 | GrGLenum* externalType) const; |
188 | |
189 | /** |
190 | * Gets an array of legal stencil formats. These formats are not guaranteed |
191 | * to be supported by the driver but are legal GLenum names given the GL |
192 | * version and extensions supported. |
193 | */ |
194 | const SkTArray<StencilFormat, true>& stencilFormats() const { |
195 | return fStencilFormats; |
196 | } |
197 | |
198 | bool formatSupportsTexStorage(GrGLFormat) const; |
199 | |
200 | /** |
201 | * Would it be useful to check GL_IMPLEMENTATION_READ_FORMAT and _TYPE for this format to |
202 | * detect more efficient glReadPixels arguments? |
203 | */ |
204 | bool shouldQueryImplementationReadSupport(GrGLFormat format) const; |
205 | |
206 | /** |
207 | * Let caps know the result of GL_IMPLEMENTATION_READ_FORMAT and _TYPE query for a format |
208 | * to update supported glReadPixels arguments. |
209 | */ |
210 | void didQueryImplementationReadSupport(GrGLFormat format, |
211 | GrGLenum readFormat, |
212 | GrGLenum readType) const; |
213 | |
214 | /** |
215 | * Gets the internal format to use with glRenderbufferStorageMultisample...(). May be sized or |
216 | * base depending upon the GL. Not applicable to compressed textures. |
217 | */ |
218 | GrGLenum getRenderbufferInternalFormat(GrGLFormat format) const { |
219 | return this->getFormatInfo(format).fInternalFormatForRenderbuffer; |
220 | } |
221 | |
222 | /** |
223 | * Gets the default external type to use with glTex[Sub]Image... when the data pointer is null. |
224 | */ |
225 | GrGLenum getFormatDefaultExternalType(GrGLFormat format) const { |
226 | return this->getFormatInfo(format).fDefaultExternalType; |
227 | } |
228 | |
229 | /** |
230 | * Has a stencil format index been found for the format (or we've found that no format works). |
231 | */ |
232 | bool hasStencilFormatBeenDeterminedForFormat(GrGLFormat format) const { |
233 | return this->getFormatInfo(format).fStencilFormatIndex != FormatInfo::kUnknown_StencilIndex; |
234 | } |
235 | |
236 | /** |
237 | * Gets the stencil format index for the format. This assumes |
238 | * hasStencilFormatBeenDeterminedForFormat has already been checked. Returns a value < 0 if |
239 | * no stencil format is supported with the format. Otherwise, returned index refers to the array |
240 | * returned by stencilFormats(). |
241 | */ |
242 | int getStencilFormatIndexForFormat(GrGLFormat format) const { |
243 | SkASSERT(this->hasStencilFormatBeenDeterminedForFormat(format)); |
244 | return this->getFormatInfo(format).fStencilFormatIndex; |
245 | } |
246 | |
247 | /** |
248 | * If index is >= 0 this records an index into stencilFormats() as the best stencil format for |
249 | * the format. If < 0 it records that the format has no supported stencil format index. |
250 | */ |
251 | void setStencilFormatIndexForFormat(GrGLFormat, int index); |
252 | |
253 | /** |
254 | * Reports the type of MSAA FBO support. |
255 | */ |
256 | MSFBOType msFBOType() const { return fMSFBOType; } |
257 | |
258 | /** |
259 | * Does the preferred MSAA FBO extension have MSAA renderbuffers? |
260 | */ |
261 | bool usesMSAARenderBuffers() const { |
262 | return kNone_MSFBOType != fMSFBOType && |
263 | kES_IMG_MsToTexture_MSFBOType != fMSFBOType && |
264 | kES_EXT_MsToTexture_MSFBOType != fMSFBOType; |
265 | } |
266 | |
267 | /** |
268 | * What functionality is supported by glBlitFramebuffer. |
269 | */ |
270 | uint32_t blitFramebufferSupportFlags() const { return fBlitFramebufferFlags; } |
271 | |
272 | /** |
273 | * Is the MSAA FBO extension one where the texture is multisampled when bound to an FBO and |
274 | * then implicitly resolved when read. |
275 | */ |
276 | bool usesImplicitMSAAResolve() const { |
277 | return kES_IMG_MsToTexture_MSFBOType == fMSFBOType || |
278 | kES_EXT_MsToTexture_MSFBOType == fMSFBOType; |
279 | } |
280 | |
281 | InvalidateFBType invalidateFBType() const { return fInvalidateFBType; } |
282 | |
283 | /// What type of buffer mapping is supported? |
284 | MapBufferType mapBufferType() const { return fMapBufferType; } |
285 | |
286 | /// What type of transfer buffer is supported? |
287 | TransferBufferType transferBufferType() const { return fTransferBufferType; } |
288 | |
289 | /// How are GrFences implemented? |
290 | FenceType fenceType() const { return fFenceType; } |
291 | |
292 | /// The maximum number of fragment uniform vectors (GLES has min. 16). |
293 | int maxFragmentUniformVectors() const { return fMaxFragmentUniformVectors; } |
294 | |
295 | /// Is there support for GL_PACK_REVERSE_ROW_ORDER |
296 | bool packFlipYSupport() const { return fPackFlipYSupport; } |
297 | |
298 | /// Is there support for texture parameter GL_TEXTURE_USAGE |
299 | bool textureUsageSupport() const { return fTextureUsageSupport; } |
300 | |
301 | /// Is GL_ARB_IMAGING supported |
302 | bool imagingSupport() const { return fImagingSupport; } |
303 | |
304 | /// Is there support for Vertex Array Objects? |
305 | bool vertexArrayObjectSupport() const { return fVertexArrayObjectSupport; } |
306 | |
307 | /// Is there support for GL_KHR_debug? |
308 | bool debugSupport() const { return fDebugSupport; } |
309 | |
310 | /// Is there support for ES2 compatability? |
311 | bool ES2CompatibilitySupport() const { return fES2CompatibilitySupport; } |
312 | |
313 | /// Is there support for glMultiDraw*Indirect? Note that the baseInstance fields of indirect |
314 | /// draw commands cannot be used unless we have base instance support. |
315 | bool multiDrawIndirectSupport() const { return fMultiDrawIndirectSupport; } |
316 | |
317 | /// Is there support for glDrawRangeElements? |
318 | bool drawRangeElementsSupport() const { return fDrawRangeElementsSupport; } |
319 | |
320 | /// Are the glDraw*Base(VertexBase)Instance methods, and baseInstance fields in indirect draw |
321 | //commands supported? |
322 | bool baseVertexBaseInstanceSupport() const { return fBaseVertexBaseInstanceSupport; } |
323 | |
324 | /// Use indices or vertices in CPU arrays rather than VBOs for dynamic content. |
325 | bool useNonVBOVertexAndIndexDynamicData() const { return fUseNonVBOVertexAndIndexDynamicData; } |
326 | |
327 | SurfaceReadPixelsSupport surfaceSupportsReadPixels(const GrSurface*) const override; |
328 | |
329 | SupportedWrite supportedWritePixelsColorType(GrColorType surfaceColorType, |
330 | const GrBackendFormat& surfaceFormat, |
331 | GrColorType srcColorType) const override; |
332 | |
333 | bool isCoreProfile() const { return fIsCoreProfile; } |
334 | |
335 | bool bindFragDataLocationSupport() const { return fBindFragDataLocationSupport; } |
336 | |
337 | bool bindUniformLocationSupport() const { return fBindUniformLocationSupport; } |
338 | |
339 | /// Are textures with GL_TEXTURE_RECTANGLE type supported. |
340 | bool rectangleTextureSupport() const { return fRectangleTextureSupport; } |
341 | |
342 | bool mipMapLevelAndLodControlSupport() const { return fMipMapLevelAndLodControlSupport; } |
343 | |
344 | bool doManualMipmapping() const { return fDoManualMipmapping; } |
345 | |
346 | void onDumpJSON(SkJSONWriter*) const override; |
347 | |
348 | bool rgba8888PixelsOpsAreSlow() const { return fRGBA8888PixelsOpsAreSlow; } |
349 | bool partialFBOReadIsSlow() const { return fPartialFBOReadIsSlow; } |
350 | bool rgbaToBgraReadbackConversionsAreSlow() const { |
351 | return fRGBAToBGRAReadbackConversionsAreSlow; |
352 | } |
353 | |
354 | bool useBufferDataNullHint() const { return fUseBufferDataNullHint; } |
355 | |
356 | // Certain Intel GPUs on Mac fail to clear if the glClearColor is made up of only 1s and 0s. |
357 | bool clearToBoundaryValuesIsBroken() const { return fClearToBoundaryValuesIsBroken; } |
358 | |
359 | /// glClearTex(Sub)Image support |
360 | bool clearTextureSupport() const { return fClearTextureSupport; } |
361 | |
362 | // Adreno/MSAA drops a draw on the imagefiltersbase GM if the base vertex param to |
363 | // glDrawArrays is nonzero. |
364 | // https://bugs.chromium.org/p/skia/issues/detail?id=6650 |
365 | bool drawArraysBaseVertexIsBroken() const { return fDrawArraysBaseVertexIsBroken; } |
366 | |
367 | // If true then we must use an intermediate surface to perform partial updates to unorm textures |
368 | // that have ever been bound to a FBO. |
369 | bool disallowTexSubImageForUnormConfigTexturesEverBoundToFBO() const { |
370 | return fDisallowTexSubImageForUnormConfigTexturesEverBoundToFBO; |
371 | } |
372 | |
373 | // Use an intermediate surface to write pixels (full or partial overwrite) to into a texture |
374 | // that is bound to an FBO. |
375 | bool useDrawInsteadOfAllRenderTargetWrites() const { |
376 | return fUseDrawInsteadOfAllRenderTargetWrites; |
377 | } |
378 | |
379 | // At least some Adreno 3xx drivers draw lines incorrectly after drawing non-lines. Toggling |
380 | // face culling on and off seems to resolve this. |
381 | bool requiresCullFaceEnableDisableWhenDrawingLinesAfterNonLines() const { |
382 | return fRequiresCullFaceEnableDisableWhenDrawingLinesAfterNonLines; |
383 | } |
384 | |
385 | // Some Adreno drivers refuse to ReadPixels from an MSAA buffer that has stencil attached. |
386 | bool detachStencilFromMSAABuffersBeforeReadPixels() const { |
387 | return fDetachStencilFromMSAABuffersBeforeReadPixels; |
388 | } |
389 | |
390 | // Older Android versions seem to have an issue with setting GL_TEXTURE_BASE_LEVEL or |
391 | // GL_TEXTURE_MAX_LEVEL for GL_TEXTURE_EXTERNAL_OES textures. |
392 | bool dontSetBaseOrMaxLevelForExternalTextures() const { |
393 | return fDontSetBaseOrMaxLevelForExternalTextures; |
394 | } |
395 | |
396 | // PowerVRGX6250 drops every pixel if we modify the sample mask while color writes are disabled. |
397 | bool neverDisableColorWrites() const { return fNeverDisableColorWrites; } |
398 | |
399 | // Returns the observed maximum number of instances the driver can handle in a single draw call |
400 | // without crashing, or 'pendingInstanceCount' if this workaround is not necessary. |
401 | // NOTE: the return value may be larger than pendingInstanceCount. |
402 | int maxInstancesPerDrawWithoutCrashing(int pendingInstanceCount) const { |
403 | return (fMaxInstancesPerDrawWithoutCrashing) |
404 | ? fMaxInstancesPerDrawWithoutCrashing : pendingInstanceCount; |
405 | } |
406 | |
407 | bool canCopyTexSubImage(GrGLFormat dstFormat, bool dstHasMSAARenderBuffer, |
408 | const GrTextureType* dstTypeIfTexture, |
409 | GrGLFormat srcFormat, bool srcHasMSAARenderBuffer, |
410 | const GrTextureType* srcTypeIfTexture) const; |
411 | bool canCopyAsBlit(GrGLFormat dstFormat, int dstSampleCnt, |
412 | const GrTextureType* dstTypeIfTexture, |
413 | GrGLFormat srcFormat, int srcSampleCnt, |
414 | const GrTextureType* srcTypeIfTexture, |
415 | const SkRect& srcBounds, bool srcBoundsExact, |
416 | const SkIRect& srcRect, const SkIPoint& dstPoint) const; |
417 | bool canCopyAsDraw(GrGLFormat dstFormat, bool srcIsTexturable) const; |
418 | |
419 | DstCopyRestrictions getDstCopyRestrictions(const GrRenderTargetProxy* src, |
420 | GrColorType) const override; |
421 | |
422 | bool programBinarySupport() const { return fProgramBinarySupport; } |
423 | bool programParameterSupport() const { return fProgramParameterSupport; } |
424 | |
425 | bool samplerObjectSupport() const { return fSamplerObjectSupport; } |
426 | |
427 | bool tiledRenderingSupport() const { return fTiledRenderingSupport; } |
428 | |
429 | bool fbFetchRequiresEnablePerSample() const { return fFBFetchRequiresEnablePerSample; } |
430 | |
431 | /* Is there support for enabling/disabling sRGB writes for sRGB-capable color buffers? */ |
432 | bool srgbWriteControl() const { return fSRGBWriteControl; } |
433 | |
434 | /** Skip checks for GL errors, shader compilation success, program link success. */ |
435 | bool skipErrorChecks() const { return fSkipErrorChecks; } |
436 | |
437 | GrBackendFormat getBackendFormatFromCompressionType(SkImage::CompressionType) const override; |
438 | |
439 | GrSwizzle getReadSwizzle(const GrBackendFormat&, GrColorType) const override; |
440 | GrSwizzle getWriteSwizzle(const GrBackendFormat&, GrColorType) const override; |
441 | |
442 | uint64_t computeFormatKey(const GrBackendFormat&) const override; |
443 | |
444 | GrProgramDesc makeDesc(const GrRenderTarget*, const GrProgramInfo&) const override; |
445 | |
446 | #if GR_TEST_UTILS |
447 | GrGLStandard standard() const { return fStandard; } |
448 | |
449 | std::vector<TestFormatColorTypeCombination> getTestingCombinations() const override; |
450 | #endif |
451 | |
452 | private: |
453 | enum ExternalFormatUsage { |
454 | kTexImage_ExternalFormatUsage, |
455 | kReadPixels_ExternalFormatUsage, |
456 | }; |
457 | void getExternalFormat(GrGLFormat surfaceFormat, GrColorType surfaceColorType, |
458 | GrColorType memoryColorType, ExternalFormatUsage usage, |
459 | GrGLenum* externalFormat, GrGLenum* externalType) const; |
460 | |
461 | void init(const GrContextOptions&, const GrGLContextInfo&, const GrGLInterface*); |
462 | void initGLSL(const GrGLContextInfo&, const GrGLInterface*); |
463 | bool hasPathRenderingSupport(const GrGLContextInfo&, const GrGLInterface*); |
464 | |
465 | struct FormatWorkarounds { |
466 | bool fDisableSRGBRenderWithMSAAForMacAMD = false; |
467 | bool fDisableRGBA16FTexStorageForCrBug1008003 = false; |
468 | bool fDisableBGRATextureStorageForIntelWindowsES = false; |
469 | bool fDisableRGB8ForMali400 = false; |
470 | bool fDisableLuminance16F = false; |
471 | bool fDontDisableTexStorageOnAndroid = false; |
472 | bool fDisallowDirectRG8ReadPixels = false; |
473 | bool fDisallowBGRA8ReadPixels = false; |
474 | }; |
475 | |
476 | void applyDriverCorrectnessWorkarounds(const GrGLContextInfo&, const GrContextOptions&, |
477 | const GrGLInterface*, |
478 | GrShaderCaps*, FormatWorkarounds*); |
479 | |
480 | void onApplyOptionsOverrides(const GrContextOptions& options) override; |
481 | |
482 | bool onIsWindowRectanglesSupportedForRT(const GrBackendRenderTarget&) const override; |
483 | |
484 | void initFSAASupport(const GrContextOptions& contextOptions, const GrGLContextInfo&, |
485 | const GrGLInterface*); |
486 | void initBlendEqationSupport(const GrGLContextInfo&); |
487 | void initStencilSupport(const GrGLContextInfo&); |
488 | // This must be called after initFSAASupport(). |
489 | void initFormatTable(const GrGLContextInfo&, const GrGLInterface*, const FormatWorkarounds&); |
490 | void setupSampleCounts(const GrGLContextInfo&, const GrGLInterface*); |
491 | bool onSurfaceSupportsWritePixels(const GrSurface*) const override; |
492 | bool onCanCopySurface(const GrSurfaceProxy* dst, const GrSurfaceProxy* src, |
493 | const SkIRect& srcRect, const SkIPoint& dstPoint) const override; |
494 | GrBackendFormat onGetDefaultBackendFormat(GrColorType) const override; |
495 | bool onAreColorTypeAndFormatCompatible(GrColorType, const GrBackendFormat&) const override; |
496 | |
497 | SupportedRead onSupportedReadPixelsColorType(GrColorType, const GrBackendFormat&, |
498 | GrColorType) const override; |
499 | |
500 | GrGLStandard fStandard = kNone_GrGLStandard; |
501 | |
502 | SkTArray<StencilFormat, true> fStencilFormats; |
503 | |
504 | int fMaxFragmentUniformVectors = 0; |
505 | |
506 | MSFBOType fMSFBOType = kNone_MSFBOType; |
507 | InvalidateFBType fInvalidateFBType = kNone_InvalidateFBType; |
508 | MapBufferType fMapBufferType = kNone_MapBufferType; |
509 | TransferBufferType fTransferBufferType = TransferBufferType::kNone; |
510 | FenceType fFenceType = FenceType::kNone; |
511 | |
512 | bool fPackFlipYSupport : 1; |
513 | bool fTextureUsageSupport : 1; |
514 | bool fImagingSupport : 1; |
515 | bool fVertexArrayObjectSupport : 1; |
516 | bool fDebugSupport : 1; |
517 | bool fES2CompatibilitySupport : 1; |
518 | bool fDrawRangeElementsSupport : 1; |
519 | bool fMultiDrawIndirectSupport : 1; |
520 | bool fBaseVertexBaseInstanceSupport : 1; |
521 | bool fUseNonVBOVertexAndIndexDynamicData : 1; |
522 | bool fIsCoreProfile : 1; |
523 | bool fBindFragDataLocationSupport : 1; |
524 | bool fRGBA8888PixelsOpsAreSlow : 1; |
525 | bool fPartialFBOReadIsSlow : 1; |
526 | bool fBindUniformLocationSupport : 1; |
527 | bool fRectangleTextureSupport : 1; |
528 | bool fMipMapLevelAndLodControlSupport : 1; |
529 | bool fRGBAToBGRAReadbackConversionsAreSlow : 1; |
530 | bool fUseBufferDataNullHint : 1; |
531 | bool fClearTextureSupport : 1; |
532 | bool fProgramBinarySupport : 1; |
533 | bool fProgramParameterSupport : 1; |
534 | bool fSamplerObjectSupport : 1; |
535 | bool fTiledRenderingSupport : 1; |
536 | bool fFBFetchRequiresEnablePerSample : 1; |
537 | bool fSRGBWriteControl : 1; |
538 | bool fSkipErrorChecks : 1; |
539 | |
540 | // Driver workarounds |
541 | bool fDoManualMipmapping : 1; |
542 | bool fClearToBoundaryValuesIsBroken : 1; |
543 | bool fDrawArraysBaseVertexIsBroken : 1; |
544 | bool fDisallowTexSubImageForUnormConfigTexturesEverBoundToFBO : 1; |
545 | bool fUseDrawInsteadOfAllRenderTargetWrites : 1; |
546 | bool fRequiresCullFaceEnableDisableWhenDrawingLinesAfterNonLines : 1; |
547 | bool fDetachStencilFromMSAABuffersBeforeReadPixels : 1; |
548 | bool fDontSetBaseOrMaxLevelForExternalTextures : 1; |
549 | bool fNeverDisableColorWrites : 1; |
550 | int fMaxInstancesPerDrawWithoutCrashing = 0; |
551 | |
552 | uint32_t fBlitFramebufferFlags = kNoSupport_BlitFramebufferFlag; |
553 | |
554 | struct ReadPixelsFormat { |
555 | ReadPixelsFormat() : fFormat(0), fType(0) {} |
556 | GrGLenum fFormat; |
557 | GrGLenum fType; |
558 | }; |
559 | |
560 | /** Number type of the components (with out considering number of bits.) */ |
561 | enum class FormatType { |
562 | kUnknown, |
563 | kNormalizedFixedPoint, |
564 | kFloat, |
565 | }; |
566 | |
567 | // ColorTypeInfo for a specific format |
568 | struct ColorTypeInfo { |
569 | GrColorType fColorType = GrColorType::kUnknown; |
570 | enum { |
571 | kUploadData_Flag = 0x1, |
572 | // Does Ganesh itself support rendering to this colorType & format pair. Renderability |
573 | // still additionally depends on if the format can be an FBO color attachment. |
574 | kRenderable_Flag = 0x2, |
575 | }; |
576 | uint32_t fFlags = 0; |
577 | |
578 | GrSwizzle fReadSwizzle; |
579 | GrSwizzle fWriteSwizzle; |
580 | |
581 | struct ExternalIOFormats { |
582 | GrColorType fColorType = GrColorType::kUnknown; |
583 | |
584 | /** The external format and type are to be used when uploading/downloading data using |
585 | data of fColorType and uploading to a texture of a given GrGLFormat and its |
586 | intended GrColorType. The fExternalTexImageFormat is the format to use for TexImage |
587 | calls. The fExternalReadFormat is used when calling ReadPixels. If either is zero |
588 | that signals that either TexImage or ReadPixels is not supported for the combination |
589 | of format and color types. */ |
590 | GrGLenum fExternalType = 0; |
591 | GrGLenum fExternalTexImageFormat = 0; |
592 | GrGLenum fExternalReadFormat = 0; |
593 | /** |
594 | * Must check whether GL_IMPLEMENTATION_COLOR_READ_FORMAT and _TYPE match |
595 | * fExternalReadFormat and fExternalType before using with glReadPixels. |
596 | */ |
597 | bool fRequiresImplementationReadQuery = false; |
598 | }; |
599 | |
600 | GrGLenum externalFormat(GrColorType externalColorType, ExternalFormatUsage usage, |
601 | bool haveQueriedImplementationReadFormat) const { |
602 | for (int i = 0; i < fExternalIOFormatCount; ++i) { |
603 | if (fExternalIOFormats[i].fColorType == externalColorType) { |
604 | if (usage == kTexImage_ExternalFormatUsage) { |
605 | return fExternalIOFormats[i].fExternalTexImageFormat; |
606 | } else { |
607 | SkASSERT(usage == kReadPixels_ExternalFormatUsage); |
608 | if (!haveQueriedImplementationReadFormat && |
609 | fExternalIOFormats[i].fRequiresImplementationReadQuery) { |
610 | return 0; |
611 | } |
612 | return fExternalIOFormats[i].fExternalReadFormat; |
613 | } |
614 | } |
615 | } |
616 | return 0; |
617 | } |
618 | |
619 | GrGLenum externalType(GrColorType externalColorType) const { |
620 | for (int i = 0; i < fExternalIOFormatCount; ++i) { |
621 | if (fExternalIOFormats[i].fColorType == externalColorType) { |
622 | return fExternalIOFormats[i].fExternalType; |
623 | } |
624 | } |
625 | return 0; |
626 | } |
627 | |
628 | std::unique_ptr<ExternalIOFormats[]> fExternalIOFormats; |
629 | int fExternalIOFormatCount = 0; |
630 | }; |
631 | |
632 | struct FormatInfo { |
633 | uint32_t colorTypeFlags(GrColorType colorType) const { |
634 | for (int i = 0; i < fColorTypeInfoCount; ++i) { |
635 | if (fColorTypeInfos[i].fColorType == colorType) { |
636 | return fColorTypeInfos[i].fFlags; |
637 | } |
638 | } |
639 | return 0; |
640 | } |
641 | |
642 | GrGLenum externalFormat(GrColorType surfaceColorType, GrColorType externalColorType, |
643 | ExternalFormatUsage usage) const { |
644 | for (int i = 0; i < fColorTypeInfoCount; ++i) { |
645 | if (fColorTypeInfos[i].fColorType == surfaceColorType) { |
646 | return fColorTypeInfos[i].externalFormat(externalColorType, usage, |
647 | fHaveQueriedImplementationReadSupport); |
648 | } |
649 | } |
650 | return 0; |
651 | } |
652 | |
653 | GrGLenum externalType(GrColorType surfaceColorType, GrColorType externalColorType) const { |
654 | for (int i = 0; i < fColorTypeInfoCount; ++i) { |
655 | if (fColorTypeInfos[i].fColorType == surfaceColorType) { |
656 | return fColorTypeInfos[i].externalType(externalColorType); |
657 | } |
658 | } |
659 | return 0; |
660 | } |
661 | |
662 | enum { |
663 | kTexturable_Flag = 0x1, |
664 | /** kFBOColorAttachment means that even if the format cannot be a GrRenderTarget, we can |
665 | still attach it to a FBO for blitting or reading pixels. */ |
666 | kFBOColorAttachment_Flag = 0x2, |
667 | kFBOColorAttachmentWithMSAA_Flag = 0x4, |
668 | kUseTexStorage_Flag = 0x8, |
669 | }; |
670 | uint32_t fFlags = 0; |
671 | |
672 | FormatType fFormatType = FormatType::kUnknown; |
673 | |
674 | // Not defined for uncompressed formats. Passed to glCompressedTexImage... |
675 | GrGLenum fCompressedInternalFormat = 0; |
676 | |
677 | // Value to uses as the "internalformat" argument to glTexImage or glTexStorage. It is |
678 | // initialized in coordination with the presence/absence of the kUseTexStorage flag. In |
679 | // other words, it is only guaranteed to be compatible with glTexImage if the flag is not |
680 | // set and or with glTexStorage if the flag is set. |
681 | GrGLenum fInternalFormatForTexImageOrStorage = 0; |
682 | |
683 | // Value to uses as the "internalformat" argument to glRenderbufferStorageMultisample... |
684 | GrGLenum fInternalFormatForRenderbuffer = 0; |
685 | |
686 | // Default values to use along with fInternalFormatForTexImageOrStorage for function |
687 | // glTexImage2D when not input providing data (passing nullptr) or when clearing it by |
688 | // uploading a block of solid color data. Not defined for compressed formats. |
689 | GrGLenum fDefaultExternalFormat = 0; |
690 | GrGLenum fDefaultExternalType = 0; |
691 | // When the above two values are used to initialize a texture by uploading cleared data to |
692 | // it the data should be of this color type. |
693 | GrColorType fDefaultColorType = GrColorType::kUnknown; |
694 | // This value is only valid for regular formats. Compressed formats will be 0. |
695 | GrGLenum fBytesPerPixel = 0; |
696 | |
697 | bool fHaveQueriedImplementationReadSupport = false; |
698 | |
699 | enum { |
700 | // This indicates that a stencil format has not yet been determined for the config. |
701 | kUnknown_StencilIndex = -1, |
702 | // This indicates that there is no supported stencil format for the config. |
703 | kUnsupported_StencilFormatIndex = -2 |
704 | }; |
705 | |
706 | // Index fStencilFormats. |
707 | int fStencilFormatIndex = kUnknown_StencilIndex; |
708 | |
709 | SkTDArray<int> fColorSampleCounts; |
710 | |
711 | std::unique_ptr<ColorTypeInfo[]> fColorTypeInfos; |
712 | int fColorTypeInfoCount = 0; |
713 | }; |
714 | |
715 | FormatInfo fFormatTable[kGrGLFormatCount]; |
716 | |
717 | FormatInfo& getFormatInfo(GrGLFormat format) { return fFormatTable[static_cast<int>(format)]; } |
718 | const FormatInfo& getFormatInfo(GrGLFormat format) const { |
719 | return fFormatTable[static_cast<int>(format)]; |
720 | } |
721 | |
722 | GrGLFormat fColorTypeToFormatTable[kGrColorTypeCnt]; |
723 | void setColorTypeFormat(GrColorType, GrGLFormat); |
724 | |
725 | typedef GrCaps INHERITED; |
726 | }; |
727 | |
728 | #endif |
729 | |