OLD | NEW |
1 /* | 1 /* |
2 * Copyright 2012 Google Inc. | 2 * Copyright 2012 Google Inc. |
3 * | 3 * |
4 * Use of this source code is governed by a BSD-style license that can be | 4 * Use of this source code is governed by a BSD-style license that can be |
5 * found in the LICENSE file. | 5 * found in the LICENSE file. |
6 */ | 6 */ |
7 | 7 |
8 | 8 |
9 #include "GrGLCaps.h" | 9 #include "GrGLCaps.h" |
10 | 10 |
(...skipping 29 matching lines...) Expand all Loading... |
40 fTexStorageSupport = false; | 40 fTexStorageSupport = false; |
41 fTextureRedSupport = false; | 41 fTextureRedSupport = false; |
42 fImagingSupport = false; | 42 fImagingSupport = false; |
43 fTwoFormatLimit = false; | 43 fTwoFormatLimit = false; |
44 fFragCoordsConventionSupport = false; | 44 fFragCoordsConventionSupport = false; |
45 fVertexArrayObjectSupport = false; | 45 fVertexArrayObjectSupport = false; |
46 fES2CompatibilitySupport = false; | 46 fES2CompatibilitySupport = false; |
47 fUseNonVBOVertexAndIndexDynamicData = false; | 47 fUseNonVBOVertexAndIndexDynamicData = false; |
48 fIsCoreProfile = false; | 48 fIsCoreProfile = false; |
49 fFullClearIsFree = false; | 49 fFullClearIsFree = false; |
50 fDropsTileOnZeroDivide = false; | |
51 fFBFetchSupport = false; | |
52 fFBFetchNeedsCustomOutput = false; | |
53 fFBFetchColorName = NULL; | |
54 fFBFetchExtensionString = NULL; | |
55 fFBMixedSamplesSupport = false; | 50 fFBMixedSamplesSupport = false; |
56 | 51 |
57 fReadPixelsSupportedCache.reset(); | 52 fReadPixelsSupportedCache.reset(); |
| 53 |
| 54 fShaderCaps.reset(SkNEW(GrGLSLCaps)); |
| 55 |
58 } | 56 } |
59 | 57 |
60 GrGLCaps::GrGLCaps(const GrGLCaps& caps) : GrDrawTargetCaps() { | 58 GrGLCaps::GrGLCaps(const GrGLCaps& caps) : GrDrawTargetCaps() { |
61 *this = caps; | 59 *this = caps; |
62 } | 60 } |
63 | 61 |
64 GrGLCaps& GrGLCaps::operator= (const GrGLCaps& caps) { | 62 GrGLCaps& GrGLCaps::operator= (const GrGLCaps& caps) { |
65 INHERITED::operator=(caps); | 63 INHERITED::operator=(caps); |
66 fVerifiedColorConfigs = caps.fVerifiedColorConfigs; | 64 fVerifiedColorConfigs = caps.fVerifiedColorConfigs; |
67 fStencilFormats = caps.fStencilFormats; | 65 fStencilFormats = caps.fStencilFormats; |
(...skipping 16 matching lines...) Expand all Loading... |
84 fTexStorageSupport = caps.fTexStorageSupport; | 82 fTexStorageSupport = caps.fTexStorageSupport; |
85 fTextureRedSupport = caps.fTextureRedSupport; | 83 fTextureRedSupport = caps.fTextureRedSupport; |
86 fImagingSupport = caps.fImagingSupport; | 84 fImagingSupport = caps.fImagingSupport; |
87 fTwoFormatLimit = caps.fTwoFormatLimit; | 85 fTwoFormatLimit = caps.fTwoFormatLimit; |
88 fFragCoordsConventionSupport = caps.fFragCoordsConventionSupport; | 86 fFragCoordsConventionSupport = caps.fFragCoordsConventionSupport; |
89 fVertexArrayObjectSupport = caps.fVertexArrayObjectSupport; | 87 fVertexArrayObjectSupport = caps.fVertexArrayObjectSupport; |
90 fES2CompatibilitySupport = caps.fES2CompatibilitySupport; | 88 fES2CompatibilitySupport = caps.fES2CompatibilitySupport; |
91 fUseNonVBOVertexAndIndexDynamicData = caps.fUseNonVBOVertexAndIndexDynamicDa
ta; | 89 fUseNonVBOVertexAndIndexDynamicData = caps.fUseNonVBOVertexAndIndexDynamicDa
ta; |
92 fIsCoreProfile = caps.fIsCoreProfile; | 90 fIsCoreProfile = caps.fIsCoreProfile; |
93 fFullClearIsFree = caps.fFullClearIsFree; | 91 fFullClearIsFree = caps.fFullClearIsFree; |
94 fDropsTileOnZeroDivide = caps.fDropsTileOnZeroDivide; | |
95 fFBFetchSupport = caps.fFBFetchSupport; | |
96 fFBFetchNeedsCustomOutput = caps.fFBFetchNeedsCustomOutput; | |
97 fFBFetchColorName = caps.fFBFetchColorName; | |
98 fFBFetchExtensionString = caps.fFBFetchExtensionString; | |
99 fFBMixedSamplesSupport = caps.fFBMixedSamplesSupport; | 92 fFBMixedSamplesSupport = caps.fFBMixedSamplesSupport; |
100 | 93 |
| 94 *(reinterpret_cast<GrGLSLCaps*>(fShaderCaps.get())) = |
| 95 *(reinterpret_cast<GrGLSLCaps*>(caps.f
ShaderCaps.get())); |
| 96 |
101 return *this; | 97 return *this; |
102 } | 98 } |
103 | 99 |
104 bool GrGLCaps::init(const GrGLContextInfo& ctxInfo, const GrGLInterface* gli) { | 100 bool GrGLCaps::init(const GrGLContextInfo& ctxInfo, const GrGLInterface* gli) { |
105 | 101 |
106 this->reset(); | 102 this->reset(); |
107 if (!ctxInfo.isInitialized()) { | 103 if (!ctxInfo.isInitialized()) { |
108 return false; | 104 return false; |
109 } | 105 } |
110 | 106 |
(...skipping 135 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
246 ctxInfo.hasExtension("GL_OES_vertex_array_ob
ject"); | 242 ctxInfo.hasExtension("GL_OES_vertex_array_ob
ject"); |
247 } | 243 } |
248 | 244 |
249 if (kGL_GrGLStandard == standard) { | 245 if (kGL_GrGLStandard == standard) { |
250 fES2CompatibilitySupport = ctxInfo.hasExtension("GL_ARB_ES2_compatibilit
y"); | 246 fES2CompatibilitySupport = ctxInfo.hasExtension("GL_ARB_ES2_compatibilit
y"); |
251 } | 247 } |
252 else { | 248 else { |
253 fES2CompatibilitySupport = true; | 249 fES2CompatibilitySupport = true; |
254 } | 250 } |
255 | 251 |
256 if (kGLES_GrGLStandard == standard) { | |
257 if (ctxInfo.hasExtension("GL_EXT_shader_framebuffer_fetch")) { | |
258 fFBFetchNeedsCustomOutput = (version >= GR_GL_VER(3, 0)); | |
259 fFBFetchSupport = true; | |
260 fFBFetchColorName = "gl_LastFragData[0]"; | |
261 fFBFetchExtensionString = "GL_EXT_shader_framebuffer_fetch"; | |
262 } else if (ctxInfo.hasExtension("GL_NV_shader_framebuffer_fetch")) { | |
263 // Actually, we haven't seen an ES3.0 device with this extension yet
, so we don't know | |
264 fFBFetchNeedsCustomOutput = false; | |
265 fFBFetchSupport = true; | |
266 fFBFetchColorName = "gl_LastFragData[0]"; | |
267 fFBFetchExtensionString = "GL_NV_shader_framebuffer_fetch"; | |
268 } else if (ctxInfo.hasExtension("GL_ARM_shader_framebuffer_fetch")) { | |
269 // The arm extension also requires an additional flag which we will
set onResetContext | |
270 fFBFetchNeedsCustomOutput = false; | |
271 fFBFetchSupport = true; | |
272 fFBFetchColorName = "gl_LastFragColorARM"; | |
273 fFBFetchExtensionString = "GL_ARM_shader_framebuffer_fetch"; | |
274 } | |
275 } | |
276 | |
277 // Adreno GPUs have a tendency to drop tiles when there is a divide-by-zero
in a shader | |
278 fDropsTileOnZeroDivide = kQualcomm_GrGLVendor == ctxInfo.vendor(); | |
279 | |
280 this->initFSAASupport(ctxInfo, gli); | 252 this->initFSAASupport(ctxInfo, gli); |
281 this->initStencilFormats(ctxInfo); | 253 this->initStencilFormats(ctxInfo); |
282 | 254 |
283 /************************************************************************** | 255 /************************************************************************** |
284 * GrDrawTargetCaps fields | 256 * GrDrawTargetCaps fields |
285 **************************************************************************/ | 257 **************************************************************************/ |
286 if (kGL_GrGLStandard == standard) { | 258 if (kGL_GrGLStandard == standard) { |
287 // we could also look for GL_ATI_separate_stencil extension or | 259 // we could also look for GL_ATI_separate_stencil extension or |
288 // GL_EXT_stencil_two_side but they use different function signatures | 260 // GL_EXT_stencil_two_side but they use different function signatures |
289 // than GL2.0+ (and than each other). | 261 // than GL2.0+ (and than each other). |
(...skipping 47 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
337 // to alllow arbitrary wrap modes, however. | 309 // to alllow arbitrary wrap modes, however. |
338 fMipMapSupport = fNPOTTextureTileSupport || ctxInfo.hasExtension("GL_IMG
_texture_npot"); | 310 fMipMapSupport = fNPOTTextureTileSupport || ctxInfo.hasExtension("GL_IMG
_texture_npot"); |
339 } | 311 } |
340 | 312 |
341 GR_GL_GetIntegerv(gli, GR_GL_MAX_TEXTURE_SIZE, &fMaxTextureSize); | 313 GR_GL_GetIntegerv(gli, GR_GL_MAX_TEXTURE_SIZE, &fMaxTextureSize); |
342 GR_GL_GetIntegerv(gli, GR_GL_MAX_RENDERBUFFER_SIZE, &fMaxRenderTargetSize); | 314 GR_GL_GetIntegerv(gli, GR_GL_MAX_RENDERBUFFER_SIZE, &fMaxRenderTargetSize); |
343 // Our render targets are always created with textures as the color | 315 // Our render targets are always created with textures as the color |
344 // attachment, hence this min: | 316 // attachment, hence this min: |
345 fMaxRenderTargetSize = SkTMin(fMaxTextureSize, fMaxRenderTargetSize); | 317 fMaxRenderTargetSize = SkTMin(fMaxTextureSize, fMaxRenderTargetSize); |
346 | 318 |
347 fPathRenderingSupport = ctxInfo.hasExtension("GL_NV_path_rendering"); | |
348 | |
349 if (fPathRenderingSupport) { | |
350 if (kGL_GrGLStandard == standard) { | |
351 // We only support v1.3+ of GL_NV_path_rendering which allows us to | |
352 // set individual fragment inputs with ProgramPathFragmentInputGen.
The API | |
353 // additions are detected by checking the existence of the function. | |
354 fPathRenderingSupport = ctxInfo.hasExtension("GL_EXT_direct_state_ac
cess") && | |
355 ((ctxInfo.version() >= GR_GL_VER(4,3) || | |
356 ctxInfo.hasExtension("GL_ARB_program_interface_query")) && | |
357 gli->fFunctions.fProgramPathFragmentInputGen); | |
358 } else { | |
359 fPathRenderingSupport = ctxInfo.version() >= GR_GL_VER(3,1); | |
360 } | |
361 } | |
362 | |
363 fFBMixedSamplesSupport = ctxInfo.hasExtension("GL_NV_framebuffer_mixed_sampl
es"); | 319 fFBMixedSamplesSupport = ctxInfo.hasExtension("GL_NV_framebuffer_mixed_sampl
es"); |
364 | 320 |
365 fGpuTracingSupport = ctxInfo.hasExtension("GL_EXT_debug_marker"); | 321 fGpuTracingSupport = ctxInfo.hasExtension("GL_EXT_debug_marker"); |
366 | 322 |
367 // For now these two are equivalent but we could have dst read in shader via
some other method | |
368 fDstReadInShaderSupport = fFBFetchSupport; | |
369 | |
370 // Disable scratch texture reuse on Mali and Adreno devices | 323 // Disable scratch texture reuse on Mali and Adreno devices |
371 fReuseScratchTextures = kARM_GrGLVendor != ctxInfo.vendor() && | 324 fReuseScratchTextures = kARM_GrGLVendor != ctxInfo.vendor() && |
372 kQualcomm_GrGLVendor != ctxInfo.vendor(); | 325 kQualcomm_GrGLVendor != ctxInfo.vendor(); |
373 | 326 |
374 // Enable supported shader-related caps | |
375 if (kGL_GrGLStandard == standard) { | |
376 fDualSourceBlendingSupport = ctxInfo.version() >= GR_GL_VER(3,3) || | |
377 ctxInfo.hasExtension("GL_ARB_blend_func_ext
ended"); | |
378 fShaderDerivativeSupport = true; | |
379 // we don't support GL_ARB_geometry_shader4, just GL 3.2+ GS | |
380 fGeometryShaderSupport = ctxInfo.version() >= GR_GL_VER(3,2) && | |
381 ctxInfo.glslGeneration() >= k150_GrGLSLGenerati
on; | |
382 } else { | |
383 fShaderDerivativeSupport = ctxInfo.version() >= GR_GL_VER(3, 0) || | |
384 ctxInfo.hasExtension("GL_OES_standard_derivat
ives"); | |
385 } | |
386 | |
387 if (GrGLCaps::kES_IMG_MsToTexture_MSFBOType == fMSFBOType) { | 327 if (GrGLCaps::kES_IMG_MsToTexture_MSFBOType == fMSFBOType) { |
388 GR_GL_GetIntegerv(gli, GR_GL_MAX_SAMPLES_IMG, &fMaxSampleCount); | 328 GR_GL_GetIntegerv(gli, GR_GL_MAX_SAMPLES_IMG, &fMaxSampleCount); |
389 } else if (GrGLCaps::kNone_MSFBOType != fMSFBOType) { | 329 } else if (GrGLCaps::kNone_MSFBOType != fMSFBOType) { |
390 GR_GL_GetIntegerv(gli, GR_GL_MAX_SAMPLES, &fMaxSampleCount); | 330 GR_GL_GetIntegerv(gli, GR_GL_MAX_SAMPLES, &fMaxSampleCount); |
391 } | 331 } |
392 | 332 |
393 if (kPowerVR54x_GrGLRenderer == ctxInfo.renderer() || | 333 if (kPowerVR54x_GrGLRenderer == ctxInfo.renderer() || |
394 kPowerVRRogue_GrGLRenderer == ctxInfo.renderer() || | 334 kPowerVRRogue_GrGLRenderer == ctxInfo.renderer() || |
395 kAdreno3xx_GrGLRenderer == ctxInfo.renderer()) { | 335 kAdreno3xx_GrGLRenderer == ctxInfo.renderer()) { |
396 fUseDrawInsteadOfClear = true; | 336 fUseDrawInsteadOfClear = true; |
397 } | 337 } |
398 | 338 |
399 if (kGL_GrGLStandard == standard) { | 339 if (kGL_GrGLStandard == standard) { |
400 // ARB allows mixed size FBO attachments, EXT does not. | 340 // ARB allows mixed size FBO attachments, EXT does not. |
401 if (ctxInfo.version() >= GR_GL_VER(3, 0) || | 341 if (ctxInfo.version() >= GR_GL_VER(3, 0) || |
402 ctxInfo.hasExtension("GL_ARB_framebuffer_object")) { | 342 ctxInfo.hasExtension("GL_ARB_framebuffer_object")) { |
403 fOversizedStencilSupport = true; | 343 fOversizedStencilSupport = true; |
404 } else { | 344 } else { |
405 SkASSERT(ctxInfo.hasExtension("GL_EXT_framebuffer_object")); | 345 SkASSERT(ctxInfo.hasExtension("GL_EXT_framebuffer_object")); |
406 } | 346 } |
407 } else { | 347 } else { |
408 // ES 3.0 supports mixed size FBO attachments, 2.0 does not. | 348 // ES 3.0 supports mixed size FBO attachments, 2.0 does not. |
409 fOversizedStencilSupport = ctxInfo.version() >= GR_GL_VER(3, 0); | 349 fOversizedStencilSupport = ctxInfo.version() >= GR_GL_VER(3, 0); |
410 } | 350 } |
411 | 351 |
412 this->initConfigTexturableTable(ctxInfo, gli); | 352 this->initConfigTexturableTable(ctxInfo, gli); |
413 this->initConfigRenderableTable(ctxInfo); | 353 this->initConfigRenderableTable(ctxInfo); |
414 | 354 |
415 this->initShaderPrecisionTable(ctxInfo, gli); | 355 reinterpret_cast<GrGLSLCaps*>(fShaderCaps.get())->init(ctxInfo, gli); |
416 | 356 |
417 return true; | 357 return true; |
418 } | 358 } |
419 | 359 |
420 void GrGLCaps::initConfigRenderableTable(const GrGLContextInfo& ctxInfo) { | 360 void GrGLCaps::initConfigRenderableTable(const GrGLContextInfo& ctxInfo) { |
421 // OpenGL < 3.0 | 361 // OpenGL < 3.0 |
422 // no support for render targets unless the GL_ARB_framebuffer_object | 362 // no support for render targets unless the GL_ARB_framebuffer_object |
423 // extension is supported (in which case we get ALPHA, RED, RG, RGB, | 363 // extension is supported (in which case we get ALPHA, RED, RG, RGB, |
424 // RGBA (ALPHA8, RGBA4, RGBA8) for OpenGL > 1.1). Note that we | 364 // RGBA (ALPHA8, RGBA4, RGBA8) for OpenGL > 1.1). Note that we |
425 // probably don't get R8 in this case. | 365 // probably don't get R8 in this case. |
(...skipping 402 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
828 fStencilFormats.push_back() = gD24S8; | 768 fStencilFormats.push_back() = gD24S8; |
829 } | 769 } |
830 if (ctxInfo.hasExtension("GL_OES_stencil4")) { | 770 if (ctxInfo.hasExtension("GL_OES_stencil4")) { |
831 fStencilFormats.push_back() = gS4; | 771 fStencilFormats.push_back() = gS4; |
832 } | 772 } |
833 } | 773 } |
834 SkASSERT(0 == fStencilVerifiedColorConfigs.count()); | 774 SkASSERT(0 == fStencilVerifiedColorConfigs.count()); |
835 fStencilVerifiedColorConfigs.push_back_n(fStencilFormats.count()); | 775 fStencilVerifiedColorConfigs.push_back_n(fStencilFormats.count()); |
836 } | 776 } |
837 | 777 |
838 static GrGLenum precision_to_gl_float_type(GrSLPrecision p) { | |
839 switch (p) { | |
840 case kLow_GrSLPrecision: | |
841 return GR_GL_LOW_FLOAT; | |
842 case kMedium_GrSLPrecision: | |
843 return GR_GL_MEDIUM_FLOAT; | |
844 case kHigh_GrSLPrecision: | |
845 return GR_GL_HIGH_FLOAT; | |
846 } | |
847 SkFAIL("Unknown precision."); | |
848 return -1; | |
849 } | |
850 | |
851 static GrGLenum shader_type_to_gl_shader(GrShaderType type) { | |
852 switch (type) { | |
853 case kVertex_GrShaderType: | |
854 return GR_GL_VERTEX_SHADER; | |
855 case kGeometry_GrShaderType: | |
856 return GR_GL_GEOMETRY_SHADER; | |
857 case kFragment_GrShaderType: | |
858 return GR_GL_FRAGMENT_SHADER; | |
859 } | |
860 SkFAIL("Unknown shader type."); | |
861 return -1; | |
862 } | |
863 | |
864 void GrGLCaps::initShaderPrecisionTable(const GrGLContextInfo& ctxInfo, const Gr
GLInterface* intf) { | |
865 if (kGLES_GrGLStandard == ctxInfo.standard() || ctxInfo.version() >= GR_GL_V
ER(4,1) || | |
866 ctxInfo.hasExtension("GL_ARB_ES2_compatibility")) { | |
867 for (int s = 0; s < kGrShaderTypeCount; ++s) { | |
868 if (kGeometry_GrShaderType != s) { | |
869 GrShaderType shaderType = static_cast<GrShaderType>(s); | |
870 GrGLenum glShader = shader_type_to_gl_shader(shaderType); | |
871 PrecisionInfo* first = NULL; | |
872 fShaderPrecisionVaries = false; | |
873 for (int p = 0; p < kGrSLPrecisionCount; ++p) { | |
874 GrSLPrecision precision = static_cast<GrSLPrecision>(p); | |
875 GrGLenum glPrecision = precision_to_gl_float_type(precision)
; | |
876 GrGLint range[2]; | |
877 GrGLint bits; | |
878 GR_GL_GetShaderPrecisionFormat(intf, glShader, glPrecision,
range, &bits); | |
879 if (bits) { | |
880 fFloatPrecisions[s][p].fLogRangeLow = range[0]; | |
881 fFloatPrecisions[s][p].fLogRangeHigh = range[1]; | |
882 fFloatPrecisions[s][p].fBits = bits; | |
883 if (!first) { | |
884 first = &fFloatPrecisions[s][p]; | |
885 } else if (!fShaderPrecisionVaries) { | |
886 fShaderPrecisionVaries = (*first != fFloatPrecisions
[s][p]); | |
887 } | |
888 } | |
889 } | |
890 } | |
891 } | |
892 } else { | |
893 // We're on a desktop GL that doesn't have precision info. Assume they'r
e all 32bit float. | |
894 fShaderPrecisionVaries = false; | |
895 for (int s = 0; s < kGrShaderTypeCount; ++s) { | |
896 if (kGeometry_GrShaderType != s) { | |
897 for (int p = 0; p < kGrSLPrecisionCount; ++p) { | |
898 fFloatPrecisions[s][p].fLogRangeLow = 127; | |
899 fFloatPrecisions[s][p].fLogRangeHigh = 127; | |
900 fFloatPrecisions[s][p].fBits = 23; | |
901 } | |
902 } | |
903 } | |
904 } | |
905 // GetShaderPrecisionFormat doesn't accept GL_GEOMETRY_SHADER as a shader ty
pe. Assume they're | |
906 // the same as the vertex shader. Only fragment shaders were ever allowed to
omit support for | |
907 // highp. GS was added after GetShaderPrecisionFormat was added to the list
of features that | |
908 // are recommended against. | |
909 if (fGeometryShaderSupport) { | |
910 for (int p = 0; p < kGrSLPrecisionCount; ++p) { | |
911 fFloatPrecisions[kGeometry_GrShaderType][p] = fFloatPrecisions[kVert
ex_GrShaderType][p]; | |
912 } | |
913 } | |
914 } | |
915 | |
916 | |
917 void GrGLCaps::markColorConfigAndStencilFormatAsVerified( | 778 void GrGLCaps::markColorConfigAndStencilFormatAsVerified( |
918 GrPixelConfig config, | 779 GrPixelConfig config, |
919 const GrGLStencilAttachment::Format& format)
{ | 780 const GrGLStencilAttachment::Format& format)
{ |
920 #if !GR_GL_CHECK_FBO_STATUS_ONCE_PER_FORMAT | 781 #if !GR_GL_CHECK_FBO_STATUS_ONCE_PER_FORMAT |
921 return; | 782 return; |
922 #endif | 783 #endif |
923 SkASSERT((unsigned)config < (unsigned)kGrPixelConfigCnt); | 784 SkASSERT((unsigned)config < (unsigned)kGrPixelConfigCnt); |
924 SkASSERT(fStencilFormats.count() == fStencilVerifiedColorConfigs.count()); | 785 SkASSERT(fStencilFormats.count() == fStencilVerifiedColorConfigs.count()); |
925 int count = fStencilFormats.count(); | 786 int count = fStencilFormats.count(); |
926 // we expect a really small number of possible formats so linear search | 787 // we expect a really small number of possible formats so linear search |
(...skipping 79 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1006 "Chromium", | 867 "Chromium", |
1007 }; | 868 }; |
1008 GR_STATIC_ASSERT(0 == kNone_MapBufferType); | 869 GR_STATIC_ASSERT(0 == kNone_MapBufferType); |
1009 GR_STATIC_ASSERT(1 == kMapBuffer_MapBufferType); | 870 GR_STATIC_ASSERT(1 == kMapBuffer_MapBufferType); |
1010 GR_STATIC_ASSERT(2 == kMapBufferRange_MapBufferType); | 871 GR_STATIC_ASSERT(2 == kMapBufferRange_MapBufferType); |
1011 GR_STATIC_ASSERT(3 == kChromium_MapBufferType); | 872 GR_STATIC_ASSERT(3 == kChromium_MapBufferType); |
1012 GR_STATIC_ASSERT(SK_ARRAY_COUNT(kMapBufferTypeStr) == kLast_MapBufferType +
1); | 873 GR_STATIC_ASSERT(SK_ARRAY_COUNT(kMapBufferTypeStr) == kLast_MapBufferType +
1); |
1013 | 874 |
1014 r.appendf("Core Profile: %s\n", (fIsCoreProfile ? "YES" : "NO")); | 875 r.appendf("Core Profile: %s\n", (fIsCoreProfile ? "YES" : "NO")); |
1015 r.appendf("MSAA Type: %s\n", kMSFBOExtStr[fMSFBOType]); | 876 r.appendf("MSAA Type: %s\n", kMSFBOExtStr[fMSFBOType]); |
1016 r.appendf("FB Fetch Support: %s\n", (fFBFetchSupport ? "YES" : "NO")); | |
1017 r.appendf("Invalidate FB Type: %s\n", kInvalidateFBTypeStr[fInvalidateFBType
]); | 877 r.appendf("Invalidate FB Type: %s\n", kInvalidateFBTypeStr[fInvalidateFBType
]); |
1018 r.appendf("Map Buffer Type: %s\n", kMapBufferTypeStr[fMapBufferType]); | 878 r.appendf("Map Buffer Type: %s\n", kMapBufferTypeStr[fMapBufferType]); |
1019 r.appendf("Max FS Uniform Vectors: %d\n", fMaxFragmentUniformVectors); | 879 r.appendf("Max FS Uniform Vectors: %d\n", fMaxFragmentUniformVectors); |
1020 r.appendf("Max FS Texture Units: %d\n", fMaxFragmentTextureUnits); | 880 r.appendf("Max FS Texture Units: %d\n", fMaxFragmentTextureUnits); |
1021 r.appendf("Max Vertex Attributes: %d\n", fMaxVertexAttributes); | 881 r.appendf("Max Vertex Attributes: %d\n", fMaxVertexAttributes); |
1022 r.appendf("Support RGBA8 Render Buffer: %s\n", (fRGBA8RenderbufferSupport ?
"YES": "NO")); | 882 r.appendf("Support RGBA8 Render Buffer: %s\n", (fRGBA8RenderbufferSupport ?
"YES": "NO")); |
1023 r.appendf("BGRA is an internal format: %s\n", (fBGRAIsInternalFormat ? "YES"
: "NO")); | 883 r.appendf("BGRA is an internal format: %s\n", (fBGRAIsInternalFormat ? "YES"
: "NO")); |
1024 r.appendf("Support texture swizzle: %s\n", (fTextureSwizzleSupport ? "YES":
"NO")); | 884 r.appendf("Support texture swizzle: %s\n", (fTextureSwizzleSupport ? "YES":
"NO")); |
1025 r.appendf("Unpack Row length support: %s\n", (fUnpackRowLengthSupport ? "YES
": "NO")); | 885 r.appendf("Unpack Row length support: %s\n", (fUnpackRowLengthSupport ? "YES
": "NO")); |
1026 r.appendf("Unpack Flip Y support: %s\n", (fUnpackFlipYSupport ? "YES": "NO")
); | 886 r.appendf("Unpack Flip Y support: %s\n", (fUnpackFlipYSupport ? "YES": "NO")
); |
1027 r.appendf("Pack Row length support: %s\n", (fPackRowLengthSupport ? "YES": "
NO")); | 887 r.appendf("Pack Row length support: %s\n", (fPackRowLengthSupport ? "YES": "
NO")); |
1028 r.appendf("Pack Flip Y support: %s\n", (fPackFlipYSupport ? "YES": "NO")); | 888 r.appendf("Pack Flip Y support: %s\n", (fPackFlipYSupport ? "YES": "NO")); |
1029 | 889 |
1030 r.appendf("Texture Usage support: %s\n", (fTextureUsageSupport ? "YES": "NO"
)); | 890 r.appendf("Texture Usage support: %s\n", (fTextureUsageSupport ? "YES": "NO"
)); |
1031 r.appendf("Texture Storage support: %s\n", (fTexStorageSupport ? "YES": "NO"
)); | 891 r.appendf("Texture Storage support: %s\n", (fTexStorageSupport ? "YES": "NO"
)); |
1032 r.appendf("GL_R support: %s\n", (fTextureRedSupport ? "YES": "NO")); | 892 r.appendf("GL_R support: %s\n", (fTextureRedSupport ? "YES": "NO")); |
1033 r.appendf("GL_ARB_imaging support: %s\n", (fImagingSupport ? "YES": "NO")); | 893 r.appendf("GL_ARB_imaging support: %s\n", (fImagingSupport ? "YES": "NO")); |
1034 r.appendf("Two Format Limit: %s\n", (fTwoFormatLimit ? "YES": "NO")); | 894 r.appendf("Two Format Limit: %s\n", (fTwoFormatLimit ? "YES": "NO")); |
1035 r.appendf("Fragment coord conventions support: %s\n", | 895 r.appendf("Fragment coord conventions support: %s\n", |
1036 (fFragCoordsConventionSupport ? "YES": "NO")); | 896 (fFragCoordsConventionSupport ? "YES": "NO")); |
1037 r.appendf("Vertex array object support: %s\n", (fVertexArrayObjectSupport ?
"YES": "NO")); | 897 r.appendf("Vertex array object support: %s\n", (fVertexArrayObjectSupport ?
"YES": "NO")); |
1038 r.appendf("Use non-VBO for dynamic data: %s\n", | 898 r.appendf("Use non-VBO for dynamic data: %s\n", |
1039 (fUseNonVBOVertexAndIndexDynamicData ? "YES" : "NO")); | 899 (fUseNonVBOVertexAndIndexDynamicData ? "YES" : "NO")); |
1040 r.appendf("Full screen clear is free: %s\n", (fFullClearIsFree ? "YES" : "NO
")); | 900 r.appendf("Full screen clear is free: %s\n", (fFullClearIsFree ? "YES" : "NO
")); |
| 901 return r; |
| 902 } |
| 903 |
| 904 ////////////////////////////////////////////////////////////////////////////////
//////////// |
| 905 |
| 906 GrGLSLCaps::GrGLSLCaps() { |
| 907 this->reset(); |
| 908 } |
| 909 |
| 910 |
| 911 void GrGLSLCaps::reset() { |
| 912 INHERITED::reset(); |
| 913 |
| 914 fDropsTileOnZeroDivide = false; |
| 915 fFBFetchSupport = false; |
| 916 fFBFetchNeedsCustomOutput = false; |
| 917 fFBFetchColorName = NULL; |
| 918 fFBFetchExtensionString = NULL; |
| 919 } |
| 920 |
| 921 GrGLSLCaps::GrGLSLCaps(const GrGLSLCaps& caps) : GrShaderCaps() { |
| 922 *this = caps; |
| 923 } |
| 924 |
| 925 GrGLSLCaps& GrGLSLCaps::operator= (const GrGLSLCaps& caps) { |
| 926 INHERITED::operator=(caps); |
| 927 fDropsTileOnZeroDivide = caps.fDropsTileOnZeroDivide; |
| 928 fFBFetchSupport = caps.fFBFetchSupport; |
| 929 fFBFetchNeedsCustomOutput = caps.fFBFetchNeedsCustomOutput; |
| 930 fFBFetchColorName = caps.fFBFetchColorName; |
| 931 fFBFetchExtensionString = caps.fFBFetchExtensionString; |
| 932 |
| 933 return *this; |
| 934 } |
| 935 |
| 936 bool GrGLSLCaps::init(const GrGLContextInfo& ctxInfo, const GrGLInterface* gli)
{ |
| 937 this->reset(); |
| 938 if (!ctxInfo.isInitialized()) { |
| 939 return false; |
| 940 } |
| 941 |
| 942 GrGLStandard standard = ctxInfo.standard(); |
| 943 GrGLVersion version = ctxInfo.version(); |
| 944 |
| 945 /************************************************************************** |
| 946 * Caps specific to GrGLSLCaps |
| 947 **************************************************************************/ |
| 948 |
| 949 if (kGLES_GrGLStandard == standard) { |
| 950 if (ctxInfo.hasExtension("GL_EXT_shader_framebuffer_fetch")) { |
| 951 fFBFetchNeedsCustomOutput = (version >= GR_GL_VER(3, 0)); |
| 952 fFBFetchSupport = true; |
| 953 fFBFetchColorName = "gl_LastFragData[0]"; |
| 954 fFBFetchExtensionString = "GL_EXT_shader_framebuffer_fetch"; |
| 955 } |
| 956 else if (ctxInfo.hasExtension("GL_NV_shader_framebuffer_fetch")) { |
| 957 // Actually, we haven't seen an ES3.0 device with this extension yet
, so we don't know |
| 958 fFBFetchNeedsCustomOutput = false; |
| 959 fFBFetchSupport = true; |
| 960 fFBFetchColorName = "gl_LastFragData[0]"; |
| 961 fFBFetchExtensionString = "GL_NV_shader_framebuffer_fetch"; |
| 962 } |
| 963 else if (ctxInfo.hasExtension("GL_ARM_shader_framebuffer_fetch")) { |
| 964 // The arm extension also requires an additional flag which we will
set onResetContext |
| 965 fFBFetchNeedsCustomOutput = false; |
| 966 fFBFetchSupport = true; |
| 967 fFBFetchColorName = "gl_LastFragColorARM"; |
| 968 fFBFetchExtensionString = "GL_ARM_shader_framebuffer_fetch"; |
| 969 } |
| 970 } |
| 971 |
| 972 // Adreno GPUs have a tendency to drop tiles when there is a divide-by-zero
in a shader |
| 973 fDropsTileOnZeroDivide = kQualcomm_GrGLVendor == ctxInfo.vendor(); |
| 974 |
| 975 /************************************************************************** |
| 976 * GrShaderCaps fields |
| 977 **************************************************************************/ |
| 978 |
| 979 fPathRenderingSupport = ctxInfo.hasExtension("GL_NV_path_rendering"); |
| 980 |
| 981 if (fPathRenderingSupport) { |
| 982 if (kGL_GrGLStandard == standard) { |
| 983 // We only support v1.3+ of GL_NV_path_rendering which allows us to |
| 984 // set individual fragment inputs with ProgramPathFragmentInputGen.
The API |
| 985 // additions are detected by checking the existence of the function. |
| 986 fPathRenderingSupport = ctxInfo.hasExtension("GL_EXT_direct_state_ac
cess") && |
| 987 ((ctxInfo.version() >= GR_GL_VER(4, 3) || |
| 988 ctxInfo.hasExtension("GL_ARB_program_interface_query")) && |
| 989 gli->fFunctions.fProgramPathFragmentInputGen); |
| 990 } |
| 991 else { |
| 992 fPathRenderingSupport = ctxInfo.version() >= GR_GL_VER(3, 1); |
| 993 } |
| 994 } |
| 995 |
| 996 // For now these two are equivalent but we could have dst read in shader via
some other method |
| 997 fDstReadInShaderSupport = fFBFetchSupport; |
| 998 |
| 999 // Enable supported shader-related caps |
| 1000 if (kGL_GrGLStandard == standard) { |
| 1001 fDualSourceBlendingSupport = ctxInfo.version() >= GR_GL_VER(3, 3) || |
| 1002 ctxInfo.hasExtension("GL_ARB_blend_func_extended"); |
| 1003 fShaderDerivativeSupport = true; |
| 1004 // we don't support GL_ARB_geometry_shader4, just GL 3.2+ GS |
| 1005 fGeometryShaderSupport = ctxInfo.version() >= GR_GL_VER(3, 2) && |
| 1006 ctxInfo.glslGeneration() >= k150_GrGLSLGeneration; |
| 1007 } |
| 1008 else { |
| 1009 fShaderDerivativeSupport = ctxInfo.version() >= GR_GL_VER(3, 0) || |
| 1010 ctxInfo.hasExtension("GL_OES_standard_derivatives"); |
| 1011 } |
| 1012 |
| 1013 this->initShaderPrecisionTable(ctxInfo, gli); |
| 1014 |
| 1015 return true; |
| 1016 } |
| 1017 |
| 1018 SkString GrGLSLCaps::dump() const { |
| 1019 SkString r = INHERITED::dump(); |
| 1020 |
| 1021 r.appendf("--- GLSL-Specific ---\n"); |
| 1022 |
| 1023 r.appendf("FB Fetch Support: %s\n", (fFBFetchSupport ? "YES" : "NO")); |
1041 r.appendf("Drops tile on zero divide: %s\n", (fDropsTileOnZeroDivide ? "YES"
: "NO")); | 1024 r.appendf("Drops tile on zero divide: %s\n", (fDropsTileOnZeroDivide ? "YES"
: "NO")); |
1042 return r; | 1025 return r; |
1043 } | 1026 } |
| 1027 |
| 1028 static GrGLenum precision_to_gl_float_type(GrSLPrecision p) { |
| 1029 switch (p) { |
| 1030 case kLow_GrSLPrecision: |
| 1031 return GR_GL_LOW_FLOAT; |
| 1032 case kMedium_GrSLPrecision: |
| 1033 return GR_GL_MEDIUM_FLOAT; |
| 1034 case kHigh_GrSLPrecision: |
| 1035 return GR_GL_HIGH_FLOAT; |
| 1036 } |
| 1037 SkFAIL("Unknown precision."); |
| 1038 return -1; |
| 1039 } |
| 1040 |
| 1041 static GrGLenum shader_type_to_gl_shader(GrShaderType type) { |
| 1042 switch (type) { |
| 1043 case kVertex_GrShaderType: |
| 1044 return GR_GL_VERTEX_SHADER; |
| 1045 case kGeometry_GrShaderType: |
| 1046 return GR_GL_GEOMETRY_SHADER; |
| 1047 case kFragment_GrShaderType: |
| 1048 return GR_GL_FRAGMENT_SHADER; |
| 1049 } |
| 1050 SkFAIL("Unknown shader type."); |
| 1051 return -1; |
| 1052 } |
| 1053 |
| 1054 void GrGLSLCaps::initShaderPrecisionTable(const GrGLContextInfo& ctxInfo, |
| 1055 const GrGLInterface* intf) { |
| 1056 if (kGLES_GrGLStandard == ctxInfo.standard() || ctxInfo.version() >= GR_GL_V
ER(4, 1) || |
| 1057 ctxInfo.hasExtension("GL_ARB_ES2_compatibility")) { |
| 1058 for (int s = 0; s < kGrShaderTypeCount; ++s) { |
| 1059 if (kGeometry_GrShaderType != s) { |
| 1060 GrShaderType shaderType = static_cast<GrShaderType>(s); |
| 1061 GrGLenum glShader = shader_type_to_gl_shader(shaderType); |
| 1062 PrecisionInfo* first = NULL; |
| 1063 fShaderPrecisionVaries = false; |
| 1064 for (int p = 0; p < kGrSLPrecisionCount; ++p) { |
| 1065 GrSLPrecision precision = static_cast<GrSLPrecision>(p); |
| 1066 GrGLenum glPrecision = precision_to_gl_float_type(precision)
; |
| 1067 GrGLint range[2]; |
| 1068 GrGLint bits; |
| 1069 GR_GL_GetShaderPrecisionFormat(intf, glShader, glPrecision,
range, &bits); |
| 1070 if (bits) { |
| 1071 fFloatPrecisions[s][p].fLogRangeLow = range[0]; |
| 1072 fFloatPrecisions[s][p].fLogRangeHigh = range[1]; |
| 1073 fFloatPrecisions[s][p].fBits = bits; |
| 1074 if (!first) { |
| 1075 first = &fFloatPrecisions[s][p]; |
| 1076 } |
| 1077 else if (!fShaderPrecisionVaries) { |
| 1078 fShaderPrecisionVaries = (*first != fFloatPrecisions
[s][p]); |
| 1079 } |
| 1080 } |
| 1081 } |
| 1082 } |
| 1083 } |
| 1084 } |
| 1085 else { |
| 1086 // We're on a desktop GL that doesn't have precision info. Assume they'r
e all 32bit float. |
| 1087 fShaderPrecisionVaries = false; |
| 1088 for (int s = 0; s < kGrShaderTypeCount; ++s) { |
| 1089 if (kGeometry_GrShaderType != s) { |
| 1090 for (int p = 0; p < kGrSLPrecisionCount; ++p) { |
| 1091 fFloatPrecisions[s][p].fLogRangeLow = 127; |
| 1092 fFloatPrecisions[s][p].fLogRangeHigh = 127; |
| 1093 fFloatPrecisions[s][p].fBits = 23; |
| 1094 } |
| 1095 } |
| 1096 } |
| 1097 } |
| 1098 // GetShaderPrecisionFormat doesn't accept GL_GEOMETRY_SHADER as a shader ty
pe. Assume they're |
| 1099 // the same as the vertex shader. Only fragment shaders were ever allowed to
omit support for |
| 1100 // highp. GS was added after GetShaderPrecisionFormat was added to the list
of features that |
| 1101 // are recommended against. |
| 1102 if (fGeometryShaderSupport) { |
| 1103 for (int p = 0; p < kGrSLPrecisionCount; ++p) { |
| 1104 fFloatPrecisions[kGeometry_GrShaderType][p] = fFloatPrecisions[kVert
ex_GrShaderType][p]; |
| 1105 } |
| 1106 } |
| 1107 } |
| 1108 |
| 1109 |
| 1110 |
| 1111 |
OLD | NEW |