• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 //
2 // Copyright 2012 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 
7 // renderergl_utils.cpp: Conversion functions and other utility routines
8 // specific to the OpenGL renderer.
9 
10 #include "libANGLE/renderer/gl/renderergl_utils.h"
11 
12 #include <array>
13 #include <limits>
14 
15 #include "common/mathutil.h"
16 #include "common/platform.h"
17 #include "libANGLE/Buffer.h"
18 #include "libANGLE/Caps.h"
19 #include "libANGLE/Context.h"
20 #include "libANGLE/formatutils.h"
21 #include "libANGLE/queryconversions.h"
22 #include "libANGLE/renderer/gl/ContextGL.h"
23 #include "libANGLE/renderer/gl/FenceNVGL.h"
24 #include "libANGLE/renderer/gl/FunctionsGL.h"
25 #include "libANGLE/renderer/gl/QueryGL.h"
26 #include "libANGLE/renderer/gl/formatutilsgl.h"
27 #include "platform/FeaturesGL.h"
28 #include "platform/FrontendFeatures.h"
29 
30 #include <EGL/eglext.h>
31 #include <algorithm>
32 #include <sstream>
33 
34 using angle::CheckedNumeric;
35 
36 namespace rx
37 {
38 
SwapControlData()39 SwapControlData::SwapControlData()
40     : targetSwapInterval(0), maxSwapInterval(-1), currentSwapInterval(-1)
41 {}
42 
GetVendorID(const FunctionsGL * functions)43 VendorID GetVendorID(const FunctionsGL *functions)
44 {
45     std::string nativeVendorString(reinterpret_cast<const char *>(functions->getString(GL_VENDOR)));
46     // Concatenate GL_RENDERER to the string being checked because some vendors put their names in
47     // GL_RENDERER
48     nativeVendorString +=
49         " " + std::string(reinterpret_cast<const char *>(functions->getString(GL_RENDERER)));
50     if (nativeVendorString.find("NVIDIA") != std::string::npos)
51     {
52         return VENDOR_ID_NVIDIA;
53     }
54     else if (nativeVendorString.find("ATI") != std::string::npos ||
55              nativeVendorString.find("AMD") != std::string::npos)
56     {
57         return VENDOR_ID_AMD;
58     }
59     else if (nativeVendorString.find("Qualcomm") != std::string::npos)
60     {
61         return VENDOR_ID_QUALCOMM;
62     }
63     else if (nativeVendorString.find("Intel") != std::string::npos)
64     {
65         return VENDOR_ID_INTEL;
66     }
67     else
68     {
69         return VENDOR_ID_UNKNOWN;
70     }
71 }
72 
GetDeviceID(const FunctionsGL * functions)73 uint32_t GetDeviceID(const FunctionsGL *functions)
74 {
75     std::string nativeRendererString(
76         reinterpret_cast<const char *>(functions->getString(GL_RENDERER)));
77     constexpr std::pair<const char *, uint32_t> kKnownDeviceIDs[] = {
78         {"Adreno (TM) 418", ANDROID_DEVICE_ID_NEXUS5X},
79         {"Adreno (TM) 530", ANDROID_DEVICE_ID_PIXEL1XL},
80         {"Adreno (TM) 540", ANDROID_DEVICE_ID_PIXEL2},
81     };
82 
83     for (const auto &knownDeviceID : kKnownDeviceIDs)
84     {
85         if (nativeRendererString.find(knownDeviceID.first) != std::string::npos)
86         {
87             return knownDeviceID.second;
88         }
89     }
90 
91     return 0;
92 }
93 
IsMesa(const FunctionsGL * functions,std::array<int,3> * version)94 bool IsMesa(const FunctionsGL *functions, std::array<int, 3> *version)
95 {
96     ASSERT(version);
97 
98     if (functions->standard != STANDARD_GL_DESKTOP)
99     {
100         return false;
101     }
102 
103     std::string nativeVersionString(
104         reinterpret_cast<const char *>(functions->getString(GL_VERSION)));
105     size_t pos = nativeVersionString.find("Mesa");
106     if (pos == std::string::npos)
107     {
108         return false;
109     }
110 
111     int *data = version->data();
112     data[0] = data[1] = data[2] = 0;
113     std::sscanf(nativeVersionString.c_str() + pos, "Mesa %d.%d.%d", data, data + 1, data + 2);
114 
115     return true;
116 }
117 
118 namespace nativegl_gl
119 {
120 
MeetsRequirements(const FunctionsGL * functions,const nativegl::SupportRequirement & requirements)121 static bool MeetsRequirements(const FunctionsGL *functions,
122                               const nativegl::SupportRequirement &requirements)
123 {
124     bool hasRequiredExtensions = false;
125     for (const std::vector<std::string> &exts : requirements.requiredExtensions)
126     {
127         bool hasAllExtensionsInSet = true;
128         for (const std::string &extension : exts)
129         {
130             if (!functions->hasExtension(extension))
131             {
132                 hasAllExtensionsInSet = false;
133                 break;
134             }
135         }
136         if (hasAllExtensionsInSet)
137         {
138             hasRequiredExtensions = true;
139             break;
140         }
141     }
142     if (!requirements.requiredExtensions.empty() && !hasRequiredExtensions)
143     {
144         return false;
145     }
146 
147     if (functions->version >= requirements.version)
148     {
149         return true;
150     }
151     else if (!requirements.versionExtensions.empty())
152     {
153         for (const std::string &extension : requirements.versionExtensions)
154         {
155             if (!functions->hasExtension(extension))
156             {
157                 return false;
158             }
159         }
160         return true;
161     }
162     else
163     {
164         return false;
165     }
166 }
167 
CheckSizedInternalFormatTextureRenderability(const FunctionsGL * functions,const angle::FeaturesGL & features,GLenum internalFormat)168 static bool CheckSizedInternalFormatTextureRenderability(const FunctionsGL *functions,
169                                                          const angle::FeaturesGL &features,
170                                                          GLenum internalFormat)
171 {
172     const gl::InternalFormat &formatInfo = gl::GetSizedInternalFormatInfo(internalFormat);
173     ASSERT(formatInfo.sized);
174 
175     // Query the current texture so it can be rebound afterwards
176     GLint oldTextureBinding = 0;
177     functions->getIntegerv(GL_TEXTURE_BINDING_2D, &oldTextureBinding);
178 
179     // Create a small texture with the same format and type that gl::Texture would use
180     GLuint texture = 0;
181     functions->genTextures(1, &texture);
182     functions->bindTexture(GL_TEXTURE_2D, texture);
183 
184     // Nearest filter needed for framebuffer completeness on some drivers.
185     functions->texParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
186 
187     nativegl::TexImageFormat texImageFormat = nativegl::GetTexImageFormat(
188         functions, features, formatInfo.internalFormat, formatInfo.format, formatInfo.type);
189     constexpr GLsizei kTextureSize = 16;
190     functions->texImage2D(GL_TEXTURE_2D, 0, texImageFormat.internalFormat, kTextureSize,
191                           kTextureSize, 0, texImageFormat.format, texImageFormat.type, nullptr);
192 
193     // Query the current framebuffer so it can be rebound afterwards
194     GLint oldFramebufferBinding = 0;
195     functions->getIntegerv(GL_FRAMEBUFFER_BINDING, &oldFramebufferBinding);
196 
197     // Bind the texture to the framebuffer and check renderability
198     GLuint fbo = 0;
199     functions->genFramebuffers(1, &fbo);
200     functions->bindFramebuffer(GL_FRAMEBUFFER, fbo);
201     functions->framebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, texture,
202                                     0);
203 
204     bool supported = functions->checkFramebufferStatus(GL_FRAMEBUFFER) == GL_FRAMEBUFFER_COMPLETE;
205 
206     // Delete the framebuffer and restore the previous binding
207     functions->deleteFramebuffers(1, &fbo);
208     functions->bindFramebuffer(GL_FRAMEBUFFER, static_cast<GLuint>(oldFramebufferBinding));
209 
210     // Delete the texture and restore the previous binding
211     functions->deleteTextures(1, &texture);
212     functions->bindTexture(GL_TEXTURE_2D, static_cast<GLuint>(oldTextureBinding));
213 
214     return supported;
215 }
216 
CheckInternalFormatRenderbufferRenderability(const FunctionsGL * functions,const angle::FeaturesGL & features,GLenum internalFormat)217 static bool CheckInternalFormatRenderbufferRenderability(const FunctionsGL *functions,
218                                                          const angle::FeaturesGL &features,
219                                                          GLenum internalFormat)
220 {
221     const gl::InternalFormat &formatInfo = gl::GetSizedInternalFormatInfo(internalFormat);
222     ASSERT(formatInfo.sized);
223 
224     // Query the current renderbuffer so it can be rebound afterwards
225     GLint oldRenderbufferBinding = 0;
226     functions->getIntegerv(GL_RENDERBUFFER_BINDING, &oldRenderbufferBinding);
227 
228     // Create a small renderbuffer with the same format and type that gl::Renderbuffer would use
229     GLuint renderbuffer = 0;
230     functions->genRenderbuffers(1, &renderbuffer);
231     functions->bindRenderbuffer(GL_RENDERBUFFER, renderbuffer);
232 
233     nativegl::RenderbufferFormat renderbufferFormat =
234         nativegl::GetRenderbufferFormat(functions, features, formatInfo.internalFormat);
235     constexpr GLsizei kRenderbufferSize = 16;
236     functions->renderbufferStorage(GL_RENDERBUFFER, renderbufferFormat.internalFormat,
237                                    kRenderbufferSize, kRenderbufferSize);
238 
239     // Query the current framebuffer so it can be rebound afterwards
240     GLint oldFramebufferBinding = 0;
241     functions->getIntegerv(GL_FRAMEBUFFER_BINDING, &oldFramebufferBinding);
242 
243     // Bind the texture to the framebuffer and check renderability
244     GLuint fbo = 0;
245     functions->genFramebuffers(1, &fbo);
246     functions->bindFramebuffer(GL_FRAMEBUFFER, fbo);
247     functions->framebufferRenderbuffer(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_RENDERBUFFER,
248                                        renderbuffer);
249 
250     bool supported = functions->checkFramebufferStatus(GL_FRAMEBUFFER) == GL_FRAMEBUFFER_COMPLETE;
251 
252     // Delete the framebuffer and restore the previous binding
253     functions->deleteFramebuffers(1, &fbo);
254     functions->bindFramebuffer(GL_FRAMEBUFFER, static_cast<GLuint>(oldFramebufferBinding));
255 
256     // Delete the renderbuffer and restore the previous binding
257     functions->deleteRenderbuffers(1, &renderbuffer);
258     functions->bindRenderbuffer(GL_RENDERBUFFER, static_cast<GLuint>(oldRenderbufferBinding));
259 
260     return supported;
261 }
262 
LimitVersion(gl::Version * curVersion,const gl::Version & maxVersion)263 static void LimitVersion(gl::Version *curVersion, const gl::Version &maxVersion)
264 {
265     if (*curVersion >= maxVersion)
266     {
267         *curVersion = maxVersion;
268     }
269 }
270 
GenerateTextureFormatCaps(const FunctionsGL * functions,const angle::FeaturesGL & features,GLenum internalFormat,gl::Version * maxSupportedESVersion)271 static gl::TextureCaps GenerateTextureFormatCaps(const FunctionsGL *functions,
272                                                  const angle::FeaturesGL &features,
273                                                  GLenum internalFormat,
274                                                  gl::Version *maxSupportedESVersion)
275 {
276     ASSERT(functions->getError() == GL_NO_ERROR);
277 
278     gl::TextureCaps textureCaps;
279 
280     const nativegl::InternalFormat &formatInfo =
281         nativegl::GetInternalFormatInfo(internalFormat, functions->standard);
282     textureCaps.texturable = MeetsRequirements(functions, formatInfo.texture);
283     textureCaps.filterable =
284         textureCaps.texturable && MeetsRequirements(functions, formatInfo.filter);
285     textureCaps.textureAttachment = MeetsRequirements(functions, formatInfo.textureAttachment);
286     textureCaps.renderbuffer      = MeetsRequirements(functions, formatInfo.renderbuffer);
287     textureCaps.blendable         = textureCaps.renderbuffer || textureCaps.textureAttachment;
288 
289     // Do extra renderability validation for some formats.
290     // We require GL_RGBA16F is renderable to expose EXT_color_buffer_half_float but we can't know
291     // if the format is supported unless we try to create a framebuffer.
292     if (internalFormat == GL_RGBA16F)
293     {
294         if (textureCaps.textureAttachment)
295         {
296             textureCaps.textureAttachment =
297                 CheckSizedInternalFormatTextureRenderability(functions, features, internalFormat);
298         }
299         if (textureCaps.renderbuffer)
300         {
301             textureCaps.renderbuffer =
302                 CheckInternalFormatRenderbufferRenderability(functions, features, internalFormat);
303         }
304     }
305 
306     // glGetInternalformativ is not available until version 4.2 but may be available through the 3.0
307     // extension GL_ARB_internalformat_query
308     if (textureCaps.renderbuffer && functions->getInternalformativ)
309     {
310         GLenum queryInternalFormat = internalFormat;
311 
312         if (internalFormat == GL_BGRA8_EXT)
313         {
314             // Querying GL_NUM_SAMPLE_COUNTS for GL_BGRA8_EXT generates an INVALID_ENUM on some
315             // drivers.  It seems however that allocating a multisampled renderbuffer of this format
316             // succeeds. To avoid breaking multisampling for this format, query the supported sample
317             // counts for GL_RGBA8 instead.
318             queryInternalFormat = GL_RGBA8;
319         }
320 
321         GLint numSamples = 0;
322         functions->getInternalformativ(GL_RENDERBUFFER, queryInternalFormat, GL_NUM_SAMPLE_COUNTS,
323                                        1, &numSamples);
324 
325         if (numSamples > 0)
326         {
327             std::vector<GLint> samples(numSamples);
328             functions->getInternalformativ(GL_RENDERBUFFER, queryInternalFormat, GL_SAMPLES,
329                                            static_cast<GLsizei>(samples.size()), &samples[0]);
330 
331             if (internalFormat == GL_STENCIL_INDEX8)
332             {
333                 // The query below does generates an error with STENCIL_INDEX8 on NVIDIA driver
334                 // 382.33. So for now we assume that the same sampling modes are conformant for
335                 // STENCIL_INDEX8 as for DEPTH24_STENCIL8. Clean this up once the driver is fixed.
336                 // http://anglebug.com/2059
337                 queryInternalFormat = GL_DEPTH24_STENCIL8;
338             }
339             for (size_t sampleIndex = 0; sampleIndex < samples.size(); sampleIndex++)
340             {
341                 if (features.limitMaxMSAASamplesTo4.enabled && samples[sampleIndex] > 4)
342                 {
343                     continue;
344                 }
345 
346                 // Some NVIDIA drivers expose multisampling modes implemented as a combination of
347                 // multisampling and supersampling. These are non-conformant and should not be
348                 // exposed through ANGLE. Query which formats are conformant from the driver if
349                 // supported.
350                 GLint conformant = GL_TRUE;
351                 if (functions->getInternalformatSampleivNV)
352                 {
353                     ASSERT(functions->getError() == GL_NO_ERROR);
354                     functions->getInternalformatSampleivNV(GL_RENDERBUFFER, queryInternalFormat,
355                                                            samples[sampleIndex], GL_CONFORMANT_NV,
356                                                            1, &conformant);
357                     // getInternalFormatSampleivNV does not work for all formats on NVIDIA Shield TV
358                     // drivers. Assume that formats with large sample counts are non-conformant in
359                     // case the query generates an error.
360                     if (functions->getError() != GL_NO_ERROR)
361                     {
362                         conformant = (samples[sampleIndex] <= 8) ? GL_TRUE : GL_FALSE;
363                     }
364                 }
365                 if (conformant == GL_TRUE)
366                 {
367                     textureCaps.sampleCounts.insert(samples[sampleIndex]);
368                 }
369             }
370         }
371     }
372 
373     // GLES 3.0.5 section 4.4.2.2: "Implementations must support creation of renderbuffers in these
374     // required formats with up to the value of MAX_SAMPLES multisamples, with the exception of
375     // signed and unsigned integer formats."
376     const gl::InternalFormat &glFormatInfo = gl::GetSizedInternalFormatInfo(internalFormat);
377     if (textureCaps.renderbuffer && !glFormatInfo.isInt() &&
378         glFormatInfo.isRequiredRenderbufferFormat(gl::Version(3, 0)) &&
379         textureCaps.getMaxSamples() < 4)
380     {
381         LimitVersion(maxSupportedESVersion, gl::Version(2, 0));
382     }
383 
384     ASSERT(functions->getError() == GL_NO_ERROR);
385     return textureCaps;
386 }
387 
QuerySingleGLInt(const FunctionsGL * functions,GLenum name)388 static GLint QuerySingleGLInt(const FunctionsGL *functions, GLenum name)
389 {
390     GLint result = 0;
391     functions->getIntegerv(name, &result);
392     return result;
393 }
394 
QuerySingleIndexGLInt(const FunctionsGL * functions,GLenum name,GLuint index)395 static GLint QuerySingleIndexGLInt(const FunctionsGL *functions, GLenum name, GLuint index)
396 {
397     GLint result;
398     functions->getIntegeri_v(name, index, &result);
399     return result;
400 }
401 
QueryGLIntRange(const FunctionsGL * functions,GLenum name,size_t index)402 static GLint QueryGLIntRange(const FunctionsGL *functions, GLenum name, size_t index)
403 {
404     GLint result[2] = {};
405     functions->getIntegerv(name, result);
406     return result[index];
407 }
408 
QuerySingleGLInt64(const FunctionsGL * functions,GLenum name)409 static GLint64 QuerySingleGLInt64(const FunctionsGL *functions, GLenum name)
410 {
411     // Fall back to 32-bit int if 64-bit query is not available. This can become relevant for some
412     // caps that are defined as 64-bit values in core spec, but were introduced earlier in
413     // extensions as 32-bit. Triggered in some cases by RenderDoc's emulated OpenGL driver.
414     if (!functions->getInteger64v)
415     {
416         GLint result = 0;
417         functions->getIntegerv(name, &result);
418         return static_cast<GLint64>(result);
419     }
420     else
421     {
422         GLint64 result = 0;
423         functions->getInteger64v(name, &result);
424         return result;
425     }
426 }
427 
QuerySingleGLFloat(const FunctionsGL * functions,GLenum name)428 static GLfloat QuerySingleGLFloat(const FunctionsGL *functions, GLenum name)
429 {
430     GLfloat result = 0.0f;
431     functions->getFloatv(name, &result);
432     return result;
433 }
434 
QueryGLFloatRange(const FunctionsGL * functions,GLenum name,size_t index)435 static GLfloat QueryGLFloatRange(const FunctionsGL *functions, GLenum name, size_t index)
436 {
437     GLfloat result[2] = {};
438     functions->getFloatv(name, result);
439     return result[index];
440 }
441 
QueryTypePrecision(const FunctionsGL * functions,GLenum shaderType,GLenum precisionType)442 static gl::TypePrecision QueryTypePrecision(const FunctionsGL *functions,
443                                             GLenum shaderType,
444                                             GLenum precisionType)
445 {
446     gl::TypePrecision precision;
447     functions->getShaderPrecisionFormat(shaderType, precisionType, precision.range.data(),
448                                         &precision.precision);
449     return precision;
450 }
451 
QueryQueryValue(const FunctionsGL * functions,GLenum target,GLenum name)452 static GLint QueryQueryValue(const FunctionsGL *functions, GLenum target, GLenum name)
453 {
454     GLint result;
455     functions->getQueryiv(target, name, &result);
456     return result;
457 }
458 
CapCombinedLimitToESShaders(GLint * combinedLimit,gl::ShaderMap<GLint> & perShaderLimit)459 void CapCombinedLimitToESShaders(GLint *combinedLimit, gl::ShaderMap<GLint> &perShaderLimit)
460 {
461     GLint combinedESLimit = 0;
462     for (gl::ShaderType shaderType : gl::kAllGraphicsShaderTypes)
463     {
464         combinedESLimit += perShaderLimit[shaderType];
465     }
466 
467     *combinedLimit = std::min(*combinedLimit, combinedESLimit);
468 }
469 
GenerateCaps(const FunctionsGL * functions,const angle::FeaturesGL & features,gl::Caps * caps,gl::TextureCapsMap * textureCapsMap,gl::Extensions * extensions,gl::Version * maxSupportedESVersion,MultiviewImplementationTypeGL * multiviewImplementationType)470 void GenerateCaps(const FunctionsGL *functions,
471                   const angle::FeaturesGL &features,
472                   gl::Caps *caps,
473                   gl::TextureCapsMap *textureCapsMap,
474                   gl::Extensions *extensions,
475                   gl::Version *maxSupportedESVersion,
476                   MultiviewImplementationTypeGL *multiviewImplementationType)
477 {
478     // Start by assuming ES3.1 support and work down
479     *maxSupportedESVersion = gl::Version(3, 1);
480 
481     // Texture format support checks
482     const gl::FormatSet &allFormats = gl::GetAllSizedInternalFormats();
483     for (GLenum internalFormat : allFormats)
484     {
485         gl::TextureCaps textureCaps =
486             GenerateTextureFormatCaps(functions, features, internalFormat, maxSupportedESVersion);
487         textureCapsMap->insert(internalFormat, textureCaps);
488 
489         if (gl::GetSizedInternalFormatInfo(internalFormat).compressed)
490         {
491             caps->compressedTextureFormats.push_back(internalFormat);
492         }
493     }
494 
495     // Table 6.28, implementation dependent values
496     if (functions->isAtLeastGL(gl::Version(4, 3)) ||
497         functions->hasGLExtension("GL_ARB_ES3_compatibility") ||
498         functions->isAtLeastGLES(gl::Version(3, 0)))
499     {
500         caps->maxElementIndex = QuerySingleGLInt64(functions, GL_MAX_ELEMENT_INDEX);
501 
502         // Work around the null driver limitations.
503         if (caps->maxElementIndex == 0)
504         {
505             caps->maxElementIndex = 0xFFFF;
506         }
507     }
508     else
509     {
510         // Doesn't affect ES3 support, can use a pre-defined limit
511         caps->maxElementIndex = static_cast<GLint64>(std::numeric_limits<unsigned int>::max());
512     }
513 
514     GLint textureSizeLimit = std::numeric_limits<GLint>::max();
515     if (features.limitMaxTextureSizeTo4096.enabled)
516     {
517         textureSizeLimit = 4096;
518     }
519 
520     GLint max3dArrayTextureSizeLimit = std::numeric_limits<GLint>::max();
521     if (features.limitMax3dArrayTextureSizeTo1024.enabled)
522     {
523         max3dArrayTextureSizeLimit = 1024;
524     }
525 
526     if (functions->isAtLeastGL(gl::Version(1, 2)) || functions->isAtLeastGLES(gl::Version(3, 0)) ||
527         functions->hasGLESExtension("GL_OES_texture_3D"))
528     {
529         caps->max3DTextureSize = std::min({QuerySingleGLInt(functions, GL_MAX_3D_TEXTURE_SIZE),
530                                            textureSizeLimit, max3dArrayTextureSizeLimit});
531     }
532     else
533     {
534         // Can't support ES3 without 3D textures
535         LimitVersion(maxSupportedESVersion, gl::Version(2, 0));
536     }
537 
538     caps->max2DTextureSize = std::min(QuerySingleGLInt(functions, GL_MAX_TEXTURE_SIZE),
539                                       textureSizeLimit);  // GL 1.0 / ES 2.0
540     caps->maxCubeMapTextureSize =
541         std::min(QuerySingleGLInt(functions, GL_MAX_CUBE_MAP_TEXTURE_SIZE),
542                  textureSizeLimit);  // GL 1.3 / ES 2.0
543 
544     if (functions->isAtLeastGL(gl::Version(3, 0)) ||
545         functions->hasGLExtension("GL_EXT_texture_array") ||
546         functions->isAtLeastGLES(gl::Version(3, 0)))
547     {
548         caps->maxArrayTextureLayers =
549             std::min({QuerySingleGLInt(functions, GL_MAX_ARRAY_TEXTURE_LAYERS), textureSizeLimit,
550                       max3dArrayTextureSizeLimit});
551     }
552     else
553     {
554         // Can't support ES3 without array textures
555         LimitVersion(maxSupportedESVersion, gl::Version(2, 0));
556     }
557 
558     if (functions->isAtLeastGL(gl::Version(1, 5)) ||
559         functions->hasGLExtension("GL_EXT_texture_lod_bias") ||
560         functions->isAtLeastGLES(gl::Version(3, 0)))
561     {
562         caps->maxLODBias = QuerySingleGLFloat(functions, GL_MAX_TEXTURE_LOD_BIAS);
563     }
564     else
565     {
566         LimitVersion(maxSupportedESVersion, gl::Version(2, 0));
567     }
568 
569     if (functions->isAtLeastGL(gl::Version(3, 0)) ||
570         functions->hasGLExtension("GL_EXT_framebuffer_object") ||
571         functions->isAtLeastGLES(gl::Version(2, 0)))
572     {
573         caps->maxRenderbufferSize = QuerySingleGLInt(functions, GL_MAX_RENDERBUFFER_SIZE);
574         caps->maxColorAttachments = QuerySingleGLInt(functions, GL_MAX_COLOR_ATTACHMENTS);
575     }
576     else
577     {
578         // Can't support ES2 without framebuffers and renderbuffers
579         LimitVersion(maxSupportedESVersion, gl::Version(0, 0));
580     }
581 
582     if (functions->isAtLeastGL(gl::Version(2, 0)) ||
583         functions->hasGLExtension("ARB_draw_buffers") ||
584         functions->isAtLeastGLES(gl::Version(3, 0)) ||
585         functions->hasGLESExtension("GL_EXT_draw_buffers"))
586     {
587         caps->maxDrawBuffers = QuerySingleGLInt(functions, GL_MAX_DRAW_BUFFERS);
588     }
589     else
590     {
591         // Framebuffer is required to have at least one drawbuffer even if the extension is not
592         // supported
593         caps->maxDrawBuffers = 1;
594         LimitVersion(maxSupportedESVersion, gl::Version(2, 0));
595     }
596 
597     caps->maxViewportWidth =
598         QueryGLIntRange(functions, GL_MAX_VIEWPORT_DIMS, 0);  // GL 1.0 / ES 2.0
599     caps->maxViewportHeight =
600         QueryGLIntRange(functions, GL_MAX_VIEWPORT_DIMS, 1);  // GL 1.0 / ES 2.0
601 
602     if (functions->standard == STANDARD_GL_DESKTOP &&
603         (functions->profile & GL_CONTEXT_CORE_PROFILE_BIT) != 0)
604     {
605         // Desktop GL core profile deprecated the GL_ALIASED_POINT_SIZE_RANGE query.  Use
606         // GL_POINT_SIZE_RANGE instead.
607         caps->minAliasedPointSize =
608             std::max(1.0f, QueryGLFloatRange(functions, GL_POINT_SIZE_RANGE, 0));
609         caps->maxAliasedPointSize = QueryGLFloatRange(functions, GL_POINT_SIZE_RANGE, 1);
610     }
611     else
612     {
613         caps->minAliasedPointSize =
614             std::max(1.0f, QueryGLFloatRange(functions, GL_ALIASED_POINT_SIZE_RANGE, 0));
615         caps->maxAliasedPointSize = QueryGLFloatRange(functions, GL_ALIASED_POINT_SIZE_RANGE, 1);
616     }
617 
618     caps->minAliasedLineWidth =
619         QueryGLFloatRange(functions, GL_ALIASED_LINE_WIDTH_RANGE, 0);  // GL 1.2 / ES 2.0
620     caps->maxAliasedLineWidth =
621         QueryGLFloatRange(functions, GL_ALIASED_LINE_WIDTH_RANGE, 1);  // GL 1.2 / ES 2.0
622 
623     // Table 6.29, implementation dependent values (cont.)
624     if (functions->isAtLeastGL(gl::Version(1, 2)) || functions->isAtLeastGLES(gl::Version(3, 0)))
625     {
626         caps->maxElementsIndices  = QuerySingleGLInt(functions, GL_MAX_ELEMENTS_INDICES);
627         caps->maxElementsVertices = QuerySingleGLInt(functions, GL_MAX_ELEMENTS_VERTICES);
628     }
629     else
630     {
631         // Doesn't impact supported version
632     }
633 
634     if (functions->isAtLeastGL(gl::Version(4, 1)) ||
635         functions->hasGLExtension("GL_ARB_get_program_binary") ||
636         functions->isAtLeastGLES(gl::Version(3, 0)) ||
637         functions->hasGLESExtension("GL_OES_get_program_binary"))
638     {
639         // Able to support the GL_PROGRAM_BINARY_ANGLE format as long as another program binary
640         // format is available.
641         GLint numBinaryFormats = QuerySingleGLInt(functions, GL_NUM_PROGRAM_BINARY_FORMATS_OES);
642         if (numBinaryFormats > 0)
643         {
644             caps->programBinaryFormats.push_back(GL_PROGRAM_BINARY_ANGLE);
645         }
646     }
647     else
648     {
649         // Doesn't impact supported version
650     }
651 
652     // glGetShaderPrecisionFormat is not available until desktop GL version 4.1 or
653     // GL_ARB_ES2_compatibility exists
654     if (functions->isAtLeastGL(gl::Version(4, 1)) ||
655         functions->hasGLExtension("GL_ARB_ES2_compatibility") ||
656         functions->isAtLeastGLES(gl::Version(2, 0)))
657     {
658         caps->vertexHighpFloat   = QueryTypePrecision(functions, GL_VERTEX_SHADER, GL_HIGH_FLOAT);
659         caps->vertexMediumpFloat = QueryTypePrecision(functions, GL_VERTEX_SHADER, GL_MEDIUM_FLOAT);
660         caps->vertexLowpFloat    = QueryTypePrecision(functions, GL_VERTEX_SHADER, GL_LOW_FLOAT);
661         caps->fragmentHighpFloat = QueryTypePrecision(functions, GL_FRAGMENT_SHADER, GL_HIGH_FLOAT);
662         caps->fragmentMediumpFloat =
663             QueryTypePrecision(functions, GL_FRAGMENT_SHADER, GL_MEDIUM_FLOAT);
664         caps->fragmentLowpFloat  = QueryTypePrecision(functions, GL_FRAGMENT_SHADER, GL_LOW_FLOAT);
665         caps->vertexHighpInt     = QueryTypePrecision(functions, GL_VERTEX_SHADER, GL_HIGH_INT);
666         caps->vertexMediumpInt   = QueryTypePrecision(functions, GL_VERTEX_SHADER, GL_MEDIUM_INT);
667         caps->vertexLowpInt      = QueryTypePrecision(functions, GL_VERTEX_SHADER, GL_LOW_INT);
668         caps->fragmentHighpInt   = QueryTypePrecision(functions, GL_FRAGMENT_SHADER, GL_HIGH_INT);
669         caps->fragmentMediumpInt = QueryTypePrecision(functions, GL_FRAGMENT_SHADER, GL_MEDIUM_INT);
670         caps->fragmentLowpInt    = QueryTypePrecision(functions, GL_FRAGMENT_SHADER, GL_LOW_INT);
671     }
672     else
673     {
674         // Doesn't impact supported version, set some default values
675         caps->vertexHighpFloat.setIEEEFloat();
676         caps->vertexMediumpFloat.setIEEEFloat();
677         caps->vertexLowpFloat.setIEEEFloat();
678         caps->fragmentHighpFloat.setIEEEFloat();
679         caps->fragmentMediumpFloat.setIEEEFloat();
680         caps->fragmentLowpFloat.setIEEEFloat();
681         caps->vertexHighpInt.setTwosComplementInt(32);
682         caps->vertexMediumpInt.setTwosComplementInt(32);
683         caps->vertexLowpInt.setTwosComplementInt(32);
684         caps->fragmentHighpInt.setTwosComplementInt(32);
685         caps->fragmentMediumpInt.setTwosComplementInt(32);
686         caps->fragmentLowpInt.setTwosComplementInt(32);
687     }
688 
689     if (functions->isAtLeastGL(gl::Version(3, 2)) || functions->hasGLExtension("GL_ARB_sync") ||
690         functions->isAtLeastGLES(gl::Version(3, 0)))
691     {
692         // Work around Linux NVIDIA driver bug where GL_TIMEOUT_IGNORED is returned.
693         caps->maxServerWaitTimeout =
694             std::max<GLint64>(QuerySingleGLInt64(functions, GL_MAX_SERVER_WAIT_TIMEOUT), 0);
695     }
696     else
697     {
698         LimitVersion(maxSupportedESVersion, gl::Version(2, 0));
699     }
700 
701     // Table 6.31, implementation dependent vertex shader limits
702     if (functions->isAtLeastGL(gl::Version(2, 0)) || functions->isAtLeastGLES(gl::Version(2, 0)))
703     {
704         caps->maxVertexAttributes = QuerySingleGLInt(functions, GL_MAX_VERTEX_ATTRIBS);
705         caps->maxShaderUniformComponents[gl::ShaderType::Vertex] =
706             QuerySingleGLInt(functions, GL_MAX_VERTEX_UNIFORM_COMPONENTS);
707         caps->maxShaderTextureImageUnits[gl::ShaderType::Vertex] =
708             QuerySingleGLInt(functions, GL_MAX_VERTEX_TEXTURE_IMAGE_UNITS);
709     }
710     else
711     {
712         // Can't support ES2 version without these caps
713         LimitVersion(maxSupportedESVersion, gl::Version(0, 0));
714     }
715 
716     if (functions->isAtLeastGL(gl::Version(4, 1)) ||
717         functions->hasGLExtension("GL_ARB_ES2_compatibility") ||
718         functions->isAtLeastGLES(gl::Version(2, 0)))
719     {
720         caps->maxVertexUniformVectors = QuerySingleGLInt(functions, GL_MAX_VERTEX_UNIFORM_VECTORS);
721         caps->maxFragmentUniformVectors =
722             QuerySingleGLInt(functions, GL_MAX_FRAGMENT_UNIFORM_VECTORS);
723     }
724     else
725     {
726         // Doesn't limit ES version, GL_MAX_VERTEX_UNIFORM_COMPONENTS / 4 is acceptable.
727         caps->maxVertexUniformVectors =
728             caps->maxShaderUniformComponents[gl::ShaderType::Vertex] / 4;
729         // Doesn't limit ES version, GL_MAX_FRAGMENT_UNIFORM_COMPONENTS / 4 is acceptable.
730         caps->maxFragmentUniformVectors =
731             caps->maxShaderUniformComponents[gl::ShaderType::Fragment] / 4;
732     }
733 
734     if (functions->isAtLeastGL(gl::Version(3, 2)) || functions->isAtLeastGLES(gl::Version(3, 0)))
735     {
736         caps->maxVertexOutputComponents =
737             QuerySingleGLInt(functions, GL_MAX_VERTEX_OUTPUT_COMPONENTS);
738     }
739     else
740     {
741         // There doesn't seem, to be a desktop extension to add this cap, maybe it could be given a
742         // safe limit instead of limiting the supported ES version.
743         LimitVersion(maxSupportedESVersion, gl::Version(2, 0));
744     }
745 
746     // Table 6.32, implementation dependent fragment shader limits
747     if (functions->isAtLeastGL(gl::Version(2, 0)) || functions->isAtLeastGLES(gl::Version(2, 0)))
748     {
749         caps->maxShaderUniformComponents[gl::ShaderType::Fragment] =
750             QuerySingleGLInt(functions, GL_MAX_FRAGMENT_UNIFORM_COMPONENTS);
751         caps->maxShaderTextureImageUnits[gl::ShaderType::Fragment] =
752             QuerySingleGLInt(functions, GL_MAX_TEXTURE_IMAGE_UNITS);
753     }
754     else
755     {
756         // Can't support ES2 version without these caps
757         LimitVersion(maxSupportedESVersion, gl::Version(0, 0));
758     }
759 
760     if (functions->isAtLeastGL(gl::Version(3, 2)) || functions->isAtLeastGLES(gl::Version(3, 0)))
761     {
762         caps->maxFragmentInputComponents =
763             QuerySingleGLInt(functions, GL_MAX_FRAGMENT_INPUT_COMPONENTS);
764     }
765     else
766     {
767         // There doesn't seem, to be a desktop extension to add this cap, maybe it could be given a
768         // safe limit instead of limiting the supported ES version.
769         LimitVersion(maxSupportedESVersion, gl::Version(2, 0));
770     }
771 
772     if (functions->isAtLeastGL(gl::Version(3, 0)) || functions->isAtLeastGLES(gl::Version(3, 0)))
773     {
774         caps->minProgramTexelOffset = QuerySingleGLInt(functions, GL_MIN_PROGRAM_TEXEL_OFFSET);
775         caps->maxProgramTexelOffset = QuerySingleGLInt(functions, GL_MAX_PROGRAM_TEXEL_OFFSET);
776     }
777     else
778     {
779         // Can't support ES3 without texel offset, could possibly be emulated in the shader
780         LimitVersion(maxSupportedESVersion, gl::Version(2, 0));
781     }
782 
783     // Table 6.33, implementation dependent aggregate shader limits
784     if (functions->isAtLeastGL(gl::Version(3, 1)) ||
785         functions->hasGLExtension("GL_ARB_uniform_buffer_object") ||
786         functions->isAtLeastGLES(gl::Version(3, 0)))
787     {
788         caps->maxShaderUniformBlocks[gl::ShaderType::Vertex] =
789             QuerySingleGLInt(functions, GL_MAX_VERTEX_UNIFORM_BLOCKS);
790         caps->maxShaderUniformBlocks[gl::ShaderType::Fragment] =
791             QuerySingleGLInt(functions, GL_MAX_FRAGMENT_UNIFORM_BLOCKS);
792         caps->maxUniformBufferBindings =
793             QuerySingleGLInt(functions, GL_MAX_UNIFORM_BUFFER_BINDINGS);
794         caps->maxUniformBlockSize = QuerySingleGLInt64(functions, GL_MAX_UNIFORM_BLOCK_SIZE);
795         caps->uniformBufferOffsetAlignment =
796             QuerySingleGLInt(functions, GL_UNIFORM_BUFFER_OFFSET_ALIGNMENT);
797         caps->maxCombinedUniformBlocks =
798             QuerySingleGLInt(functions, GL_MAX_COMBINED_UNIFORM_BLOCKS);
799         caps->maxCombinedShaderUniformComponents[gl::ShaderType::Vertex] =
800             QuerySingleGLInt64(functions, GL_MAX_COMBINED_VERTEX_UNIFORM_COMPONENTS);
801         caps->maxCombinedShaderUniformComponents[gl::ShaderType::Fragment] =
802             QuerySingleGLInt64(functions, GL_MAX_COMBINED_FRAGMENT_UNIFORM_COMPONENTS);
803     }
804     else
805     {
806         // Can't support ES3 without uniform blocks
807         LimitVersion(maxSupportedESVersion, gl::Version(2, 0));
808     }
809 
810     if (functions->isAtLeastGL(gl::Version(3, 2)) &&
811         (functions->profile & GL_CONTEXT_CORE_PROFILE_BIT) != 0)
812     {
813         caps->maxVaryingComponents = QuerySingleGLInt(functions, GL_MAX_VERTEX_OUTPUT_COMPONENTS);
814     }
815     else if (functions->isAtLeastGL(gl::Version(3, 0)) ||
816              functions->hasGLExtension("GL_ARB_ES2_compatibility") ||
817              functions->isAtLeastGLES(gl::Version(2, 0)))
818     {
819         caps->maxVaryingComponents = QuerySingleGLInt(functions, GL_MAX_VARYING_COMPONENTS);
820     }
821     else if (functions->isAtLeastGL(gl::Version(2, 0)))
822     {
823         caps->maxVaryingComponents = QuerySingleGLInt(functions, GL_MAX_VARYING_FLOATS);
824         LimitVersion(maxSupportedESVersion, gl::Version(2, 0));
825     }
826     else
827     {
828         LimitVersion(maxSupportedESVersion, gl::Version(0, 0));
829     }
830 
831     if (functions->isAtLeastGL(gl::Version(4, 1)) ||
832         functions->hasGLExtension("GL_ARB_ES2_compatibility") ||
833         functions->isAtLeastGLES(gl::Version(2, 0)))
834     {
835         caps->maxVaryingVectors = QuerySingleGLInt(functions, GL_MAX_VARYING_VECTORS);
836     }
837     else
838     {
839         // Doesn't limit ES version, GL_MAX_VARYING_COMPONENTS / 4 is acceptable.
840         caps->maxVaryingVectors = caps->maxVaryingComponents / 4;
841     }
842 
843     // Determine the max combined texture image units by adding the vertex and fragment limits.  If
844     // the real cap is queried, it would contain the limits for shader types that are not available
845     // to ES.
846     caps->maxCombinedTextureImageUnits =
847         QuerySingleGLInt(functions, GL_MAX_COMBINED_TEXTURE_IMAGE_UNITS);
848 
849     // Table 6.34, implementation dependent transform feedback limits
850     if (functions->isAtLeastGL(gl::Version(4, 0)) ||
851         functions->hasGLExtension("GL_ARB_transform_feedback2") ||
852         functions->isAtLeastGLES(gl::Version(3, 0)))
853     {
854         caps->maxTransformFeedbackInterleavedComponents =
855             QuerySingleGLInt(functions, GL_MAX_TRANSFORM_FEEDBACK_INTERLEAVED_COMPONENTS);
856         caps->maxTransformFeedbackSeparateAttributes =
857             QuerySingleGLInt(functions, GL_MAX_TRANSFORM_FEEDBACK_SEPARATE_ATTRIBS);
858         caps->maxTransformFeedbackSeparateComponents =
859             QuerySingleGLInt(functions, GL_MAX_TRANSFORM_FEEDBACK_SEPARATE_COMPONENTS);
860     }
861     else
862     {
863         // Can't support ES3 without transform feedback
864         LimitVersion(maxSupportedESVersion, gl::Version(2, 0));
865     }
866 
867     GLint sampleCountLimit = std::numeric_limits<GLint>::max();
868     if (features.limitMaxMSAASamplesTo4.enabled)
869     {
870         sampleCountLimit = 4;
871     }
872 
873     // Table 6.35, Framebuffer Dependent Values
874     if (functions->isAtLeastGL(gl::Version(3, 0)) ||
875         functions->hasGLExtension("GL_EXT_framebuffer_multisample") ||
876         functions->isAtLeastGLES(gl::Version(3, 0)) ||
877         functions->hasGLESExtension("GL_EXT_multisampled_render_to_texture"))
878     {
879         caps->maxSamples = std::min(QuerySingleGLInt(functions, GL_MAX_SAMPLES), sampleCountLimit);
880     }
881     else
882     {
883         LimitVersion(maxSupportedESVersion, gl::Version(2, 0));
884     }
885 
886     // Non-constant sampler array indexing is required for OpenGL ES 2 and OpenGL ES after 3.2.
887     // However having it available on OpenGL ES 2 is a specification bug, and using this
888     // indexing in WebGL is undefined. Requiring this feature would break WebGL 1 for some users
889     // so we don't check for it. (it is present with ESSL 100, ESSL >= 320, GLSL >= 400 and
890     // GL_ARB_gpu_shader5)
891 
892     // Check if sampler objects are supported
893     if (!functions->isAtLeastGL(gl::Version(3, 3)) &&
894         !functions->hasGLExtension("GL_ARB_sampler_objects") &&
895         !functions->isAtLeastGLES(gl::Version(3, 0)))
896     {
897         // Can't support ES3 without sampler objects
898         LimitVersion(maxSupportedESVersion, gl::Version(2, 0));
899     }
900 
901     // Can't support ES3 without texture swizzling
902     if (!functions->isAtLeastGL(gl::Version(3, 3)) &&
903         !functions->hasGLExtension("GL_ARB_texture_swizzle") &&
904         !functions->hasGLExtension("GL_EXT_texture_swizzle") &&
905         !functions->isAtLeastGLES(gl::Version(3, 0)))
906     {
907         LimitVersion(maxSupportedESVersion, gl::Version(2, 0));
908 
909         // Texture swizzling is required to work around the luminance texture format not being
910         // present in the core profile
911         if (functions->profile & GL_CONTEXT_CORE_PROFILE_BIT)
912         {
913             LimitVersion(maxSupportedESVersion, gl::Version(0, 0));
914         }
915     }
916 
917     // Can't support ES3 without the GLSL packing builtins. We have a workaround for all
918     // desktop OpenGL versions starting from 3.3 with the bit packing extension.
919     if (!functions->isAtLeastGL(gl::Version(4, 2)) &&
920         !(functions->isAtLeastGL(gl::Version(3, 2)) &&
921           functions->hasGLExtension("GL_ARB_shader_bit_encoding")) &&
922         !functions->hasGLExtension("GL_ARB_shading_language_packing") &&
923         !functions->isAtLeastGLES(gl::Version(3, 0)))
924     {
925         LimitVersion(maxSupportedESVersion, gl::Version(2, 0));
926     }
927 
928     // ES3 needs to support explicit layout location qualifiers, while it might be possible to
929     // fake them in our side, we currently don't support that.
930     if (!functions->isAtLeastGL(gl::Version(3, 3)) &&
931         !functions->hasGLExtension("GL_ARB_explicit_attrib_location") &&
932         !functions->isAtLeastGLES(gl::Version(3, 0)))
933     {
934         LimitVersion(maxSupportedESVersion, gl::Version(2, 0));
935     }
936 
937     if (functions->isAtLeastGL(gl::Version(4, 3)) || functions->isAtLeastGLES(gl::Version(3, 1)) ||
938         functions->hasGLExtension("GL_ARB_framebuffer_no_attachments"))
939     {
940         caps->maxFramebufferWidth  = QuerySingleGLInt(functions, GL_MAX_FRAMEBUFFER_WIDTH);
941         caps->maxFramebufferHeight = QuerySingleGLInt(functions, GL_MAX_FRAMEBUFFER_HEIGHT);
942         caps->maxFramebufferSamples =
943             std::min(QuerySingleGLInt(functions, GL_MAX_FRAMEBUFFER_SAMPLES), sampleCountLimit);
944     }
945     else
946     {
947         LimitVersion(maxSupportedESVersion, gl::Version(3, 0));
948     }
949 
950     if (functions->isAtLeastGL(gl::Version(3, 2)) || functions->isAtLeastGLES(gl::Version(3, 1)) ||
951         functions->hasGLExtension("GL_ARB_texture_multisample"))
952     {
953         caps->maxSampleMaskWords = QuerySingleGLInt(functions, GL_MAX_SAMPLE_MASK_WORDS);
954         caps->maxColorTextureSamples =
955             std::min(QuerySingleGLInt(functions, GL_MAX_COLOR_TEXTURE_SAMPLES), sampleCountLimit);
956         caps->maxDepthTextureSamples =
957             std::min(QuerySingleGLInt(functions, GL_MAX_DEPTH_TEXTURE_SAMPLES), sampleCountLimit);
958         caps->maxIntegerSamples =
959             std::min(QuerySingleGLInt(functions, GL_MAX_INTEGER_SAMPLES), sampleCountLimit);
960     }
961     else
962     {
963         LimitVersion(maxSupportedESVersion, gl::Version(3, 0));
964     }
965 
966     if (functions->isAtLeastGL(gl::Version(4, 3)) || functions->isAtLeastGLES(gl::Version(3, 1)) ||
967         functions->hasGLExtension("GL_ARB_vertex_attrib_binding"))
968     {
969         caps->maxVertexAttribRelativeOffset =
970             QuerySingleGLInt(functions, GL_MAX_VERTEX_ATTRIB_RELATIVE_OFFSET);
971         caps->maxVertexAttribBindings = QuerySingleGLInt(functions, GL_MAX_VERTEX_ATTRIB_BINDINGS);
972 
973         // OpenGL 4.3 has no limit on maximum value of stride.
974         // [OpenGL 4.3 (Core Profile) - February 14, 2013] Chapter 10.3.1 Page 298
975         if (features.emulateMaxVertexAttribStride.enabled ||
976             (functions->standard == STANDARD_GL_DESKTOP && functions->version == gl::Version(4, 3)))
977         {
978             caps->maxVertexAttribStride = 2048;
979         }
980         else
981         {
982             caps->maxVertexAttribStride = QuerySingleGLInt(functions, GL_MAX_VERTEX_ATTRIB_STRIDE);
983         }
984     }
985     else
986     {
987         LimitVersion(maxSupportedESVersion, gl::Version(3, 0));
988     }
989 
990     if (functions->isAtLeastGL(gl::Version(4, 3)) || functions->isAtLeastGLES(gl::Version(3, 1)) ||
991         functions->hasGLExtension("GL_ARB_shader_storage_buffer_object"))
992     {
993         caps->maxCombinedShaderOutputResources =
994             QuerySingleGLInt(functions, GL_MAX_COMBINED_SHADER_OUTPUT_RESOURCES);
995         caps->maxShaderStorageBlocks[gl::ShaderType::Fragment] =
996             QuerySingleGLInt(functions, GL_MAX_FRAGMENT_SHADER_STORAGE_BLOCKS);
997         caps->maxShaderStorageBlocks[gl::ShaderType::Vertex] =
998             QuerySingleGLInt(functions, GL_MAX_VERTEX_SHADER_STORAGE_BLOCKS);
999         caps->maxShaderStorageBufferBindings =
1000             QuerySingleGLInt(functions, GL_MAX_SHADER_STORAGE_BUFFER_BINDINGS);
1001         caps->maxShaderStorageBlockSize =
1002             QuerySingleGLInt64(functions, GL_MAX_SHADER_STORAGE_BLOCK_SIZE);
1003         caps->maxCombinedShaderStorageBlocks =
1004             QuerySingleGLInt(functions, GL_MAX_COMBINED_SHADER_STORAGE_BLOCKS);
1005         caps->shaderStorageBufferOffsetAlignment =
1006             QuerySingleGLInt(functions, GL_SHADER_STORAGE_BUFFER_OFFSET_ALIGNMENT);
1007     }
1008     else
1009     {
1010         LimitVersion(maxSupportedESVersion, gl::Version(3, 0));
1011     }
1012 
1013     if (nativegl::SupportsCompute(functions))
1014     {
1015         for (GLuint index = 0u; index < 3u; ++index)
1016         {
1017             caps->maxComputeWorkGroupCount[index] =
1018                 QuerySingleIndexGLInt(functions, GL_MAX_COMPUTE_WORK_GROUP_COUNT, index);
1019 
1020             caps->maxComputeWorkGroupSize[index] =
1021                 QuerySingleIndexGLInt(functions, GL_MAX_COMPUTE_WORK_GROUP_SIZE, index);
1022         }
1023         caps->maxComputeWorkGroupInvocations =
1024             QuerySingleGLInt(functions, GL_MAX_COMPUTE_WORK_GROUP_INVOCATIONS);
1025         caps->maxShaderUniformBlocks[gl::ShaderType::Compute] =
1026             QuerySingleGLInt(functions, GL_MAX_COMPUTE_UNIFORM_BLOCKS);
1027         caps->maxShaderTextureImageUnits[gl::ShaderType::Compute] =
1028             QuerySingleGLInt(functions, GL_MAX_COMPUTE_TEXTURE_IMAGE_UNITS);
1029         caps->maxComputeSharedMemorySize =
1030             QuerySingleGLInt(functions, GL_MAX_COMPUTE_SHARED_MEMORY_SIZE);
1031         caps->maxShaderUniformComponents[gl::ShaderType::Compute] =
1032             QuerySingleGLInt(functions, GL_MAX_COMPUTE_UNIFORM_COMPONENTS);
1033         caps->maxShaderAtomicCounterBuffers[gl::ShaderType::Compute] =
1034             QuerySingleGLInt(functions, GL_MAX_COMPUTE_ATOMIC_COUNTER_BUFFERS);
1035         caps->maxShaderAtomicCounters[gl::ShaderType::Compute] =
1036             QuerySingleGLInt(functions, GL_MAX_COMPUTE_ATOMIC_COUNTERS);
1037         caps->maxShaderImageUniforms[gl::ShaderType::Compute] =
1038             QuerySingleGLInt(functions, GL_MAX_COMPUTE_IMAGE_UNIFORMS);
1039         caps->maxCombinedShaderUniformComponents[gl::ShaderType::Compute] =
1040             QuerySingleGLInt(functions, GL_MAX_COMBINED_COMPUTE_UNIFORM_COMPONENTS);
1041         caps->maxShaderStorageBlocks[gl::ShaderType::Compute] =
1042             QuerySingleGLInt(functions, GL_MAX_COMPUTE_SHADER_STORAGE_BLOCKS);
1043     }
1044     else
1045     {
1046         LimitVersion(maxSupportedESVersion, gl::Version(3, 0));
1047     }
1048 
1049     if (functions->isAtLeastGL(gl::Version(4, 3)) || functions->isAtLeastGLES(gl::Version(3, 1)) ||
1050         functions->hasGLExtension("GL_ARB_explicit_uniform_location"))
1051     {
1052         caps->maxUniformLocations = QuerySingleGLInt(functions, GL_MAX_UNIFORM_LOCATIONS);
1053     }
1054     else
1055     {
1056         LimitVersion(maxSupportedESVersion, gl::Version(3, 0));
1057     }
1058 
1059     if (functions->isAtLeastGL(gl::Version(4, 0)) || functions->isAtLeastGLES(gl::Version(3, 1)) ||
1060         functions->hasGLExtension("GL_ARB_texture_gather"))
1061     {
1062         caps->minProgramTextureGatherOffset =
1063             QuerySingleGLInt(functions, GL_MIN_PROGRAM_TEXTURE_GATHER_OFFSET);
1064         caps->maxProgramTextureGatherOffset =
1065             QuerySingleGLInt(functions, GL_MAX_PROGRAM_TEXTURE_GATHER_OFFSET);
1066     }
1067     else
1068     {
1069         LimitVersion(maxSupportedESVersion, gl::Version(3, 0));
1070     }
1071 
1072     if (functions->isAtLeastGL(gl::Version(4, 2)) || functions->isAtLeastGLES(gl::Version(3, 1)) ||
1073         functions->hasGLExtension("GL_ARB_shader_image_load_store"))
1074     {
1075         caps->maxShaderImageUniforms[gl::ShaderType::Vertex] =
1076             QuerySingleGLInt(functions, GL_MAX_VERTEX_IMAGE_UNIFORMS);
1077         caps->maxShaderImageUniforms[gl::ShaderType::Fragment] =
1078             QuerySingleGLInt(functions, GL_MAX_FRAGMENT_IMAGE_UNIFORMS);
1079         caps->maxImageUnits = QuerySingleGLInt(functions, GL_MAX_IMAGE_UNITS);
1080         caps->maxCombinedImageUniforms =
1081             QuerySingleGLInt(functions, GL_MAX_COMBINED_IMAGE_UNIFORMS);
1082     }
1083     else
1084     {
1085         LimitVersion(maxSupportedESVersion, gl::Version(3, 0));
1086     }
1087 
1088     if (functions->isAtLeastGL(gl::Version(4, 2)) || functions->isAtLeastGLES(gl::Version(3, 1)) ||
1089         functions->hasGLExtension("GL_ARB_shader_atomic_counters"))
1090     {
1091         caps->maxShaderAtomicCounterBuffers[gl::ShaderType::Vertex] =
1092             QuerySingleGLInt(functions, GL_MAX_VERTEX_ATOMIC_COUNTER_BUFFERS);
1093         caps->maxShaderAtomicCounters[gl::ShaderType::Vertex] =
1094             QuerySingleGLInt(functions, GL_MAX_VERTEX_ATOMIC_COUNTERS);
1095         caps->maxShaderAtomicCounterBuffers[gl::ShaderType::Fragment] =
1096             QuerySingleGLInt(functions, GL_MAX_FRAGMENT_ATOMIC_COUNTER_BUFFERS);
1097         caps->maxShaderAtomicCounters[gl::ShaderType::Fragment] =
1098             QuerySingleGLInt(functions, GL_MAX_FRAGMENT_ATOMIC_COUNTERS);
1099         caps->maxAtomicCounterBufferBindings =
1100             QuerySingleGLInt(functions, GL_MAX_ATOMIC_COUNTER_BUFFER_BINDINGS);
1101         caps->maxAtomicCounterBufferSize =
1102             QuerySingleGLInt(functions, GL_MAX_ATOMIC_COUNTER_BUFFER_SIZE);
1103         caps->maxCombinedAtomicCounterBuffers =
1104             QuerySingleGLInt(functions, GL_MAX_COMBINED_ATOMIC_COUNTER_BUFFERS);
1105         caps->maxCombinedAtomicCounters =
1106             QuerySingleGLInt(functions, GL_MAX_COMBINED_ATOMIC_COUNTERS);
1107     }
1108     else
1109     {
1110         LimitVersion(maxSupportedESVersion, gl::Version(3, 0));
1111     }
1112 
1113     // TODO(geofflang): The gl-uniform-arrays WebGL conformance test struggles to complete on time
1114     // if the max uniform vectors is too large.  Artificially limit the maximum until the test is
1115     // updated.
1116     caps->maxVertexUniformVectors = std::min(1024, caps->maxVertexUniformVectors);
1117     caps->maxShaderUniformComponents[gl::ShaderType::Vertex] =
1118         std::min(caps->maxVertexUniformVectors * 4,
1119                  caps->maxShaderUniformComponents[gl::ShaderType::Vertex]);
1120     caps->maxFragmentUniformVectors = std::min(1024, caps->maxFragmentUniformVectors);
1121     caps->maxShaderUniformComponents[gl::ShaderType::Fragment] =
1122         std::min(caps->maxFragmentUniformVectors * 4,
1123                  caps->maxShaderUniformComponents[gl::ShaderType::Fragment]);
1124 
1125     // If it is not possible to support reading buffer data back, a shadow copy of the buffers must
1126     // be held. This disallows writing to buffers indirectly through transform feedback, thus
1127     // disallowing ES3.
1128     if (!CanMapBufferForRead(functions))
1129     {
1130         LimitVersion(maxSupportedESVersion, gl::Version(2, 0));
1131     }
1132 
1133     // GL_OES_texture_cube_map_array
1134     if (functions->isAtLeastGL(gl::Version(4, 0)) ||
1135         functions->hasGLESExtension("GL_OES_texture_cube_map_array") ||
1136         functions->hasGLESExtension("GL_EXT_texture_cube_map_array") ||
1137         functions->hasGLExtension("GL_ARB_texture_cube_map_array") ||
1138         functions->isAtLeastGLES(gl::Version(3, 2)))
1139     {
1140         extensions->textureCubeMapArrayOES = true;
1141         extensions->textureCubeMapArrayEXT = true;
1142     }
1143     else
1144     {
1145         // Can't support ES3.2 without cube map array textures
1146         LimitVersion(maxSupportedESVersion, gl::Version(3, 1));
1147     }
1148 
1149     // Extension support
1150     extensions->setTextureExtensionSupport(*textureCapsMap);
1151     extensions->textureCompressionASTCHDRKHR =
1152         extensions->textureCompressionASTCLDRKHR &&
1153         functions->hasExtension("GL_KHR_texture_compression_astc_hdr");
1154     extensions->textureCompressionSliced3dASTCKHR =
1155         (extensions->textureCompressionASTCLDRKHR &&
1156          functions->hasExtension("GL_KHR_texture_compression_astc_sliced_3d")) ||
1157         extensions->textureCompressionASTCHDRKHR;
1158     extensions->elementIndexUintOES = functions->standard == STANDARD_GL_DESKTOP ||
1159                                       functions->isAtLeastGLES(gl::Version(3, 0)) ||
1160                                       functions->hasGLESExtension("GL_OES_element_index_uint");
1161     extensions->getProgramBinaryOES = caps->programBinaryFormats.size() > 0;
1162     extensions->readFormatBGRA      = functions->isAtLeastGL(gl::Version(1, 2)) ||
1163                                  functions->hasGLExtension("GL_EXT_bgra") ||
1164                                  functions->hasGLESExtension("GL_EXT_read_format_bgra");
1165     extensions->pixelBufferObjectNV = functions->isAtLeastGL(gl::Version(2, 1)) ||
1166                                       functions->isAtLeastGLES(gl::Version(3, 0)) ||
1167                                       functions->hasGLExtension("GL_ARB_pixel_buffer_object") ||
1168                                       functions->hasGLExtension("GL_EXT_pixel_buffer_object") ||
1169                                       functions->hasGLESExtension("GL_NV_pixel_buffer_object");
1170     extensions->glSyncARB    = nativegl::SupportsFenceSync(functions);
1171     extensions->mapBufferOES = functions->isAtLeastGL(gl::Version(1, 5)) ||
1172                                functions->isAtLeastGLES(gl::Version(3, 0)) ||
1173                                functions->hasGLESExtension("GL_OES_mapbuffer");
1174     extensions->mapBufferRange = functions->isAtLeastGL(gl::Version(3, 0)) ||
1175                                  functions->hasGLExtension("GL_ARB_map_buffer_range") ||
1176                                  functions->isAtLeastGLES(gl::Version(3, 0)) ||
1177                                  functions->hasGLESExtension("GL_EXT_map_buffer_range");
1178     extensions->textureNPOTOES = functions->standard == STANDARD_GL_DESKTOP ||
1179                                  functions->isAtLeastGLES(gl::Version(3, 0)) ||
1180                                  functions->hasGLESExtension("GL_OES_texture_npot");
1181     // TODO(jmadill): Investigate emulating EXT_draw_buffers on ES 3.0's core functionality.
1182     extensions->drawBuffers = functions->isAtLeastGL(gl::Version(2, 0)) ||
1183                               functions->hasGLExtension("ARB_draw_buffers") ||
1184                               functions->hasGLESExtension("GL_EXT_draw_buffers");
1185     extensions->drawBuffersIndexedEXT =
1186         !features.disableDrawBuffersIndexed.enabled &&
1187         (functions->isAtLeastGL(gl::Version(4, 0)) ||
1188          (functions->hasGLExtension("GL_EXT_draw_buffers2") &&
1189           functions->hasGLExtension("GL_ARB_draw_buffers_blend")) ||
1190          functions->isAtLeastGLES(gl::Version(3, 2)) ||
1191          functions->hasGLESExtension("GL_OES_draw_buffers_indexed") ||
1192          functions->hasGLESExtension("GL_EXT_draw_buffers_indexed"));
1193     extensions->drawBuffersIndexedOES = extensions->drawBuffersIndexedEXT;
1194     extensions->textureStorage        = functions->standard == STANDARD_GL_DESKTOP ||
1195                                  functions->hasGLESExtension("GL_EXT_texture_storage");
1196     extensions->textureFilterAnisotropic =
1197         functions->hasGLExtension("GL_EXT_texture_filter_anisotropic") ||
1198         functions->hasGLESExtension("GL_EXT_texture_filter_anisotropic");
1199     extensions->occlusionQueryBoolean = nativegl::SupportsOcclusionQueries(functions);
1200     extensions->maxTextureAnisotropy =
1201         extensions->textureFilterAnisotropic
1202             ? QuerySingleGLFloat(functions, GL_MAX_TEXTURE_MAX_ANISOTROPY_EXT)
1203             : 0.0f;
1204     extensions->fenceNV = FenceNVGL::Supported(functions) || FenceNVSyncGL::Supported(functions);
1205     extensions->blendMinMax = functions->isAtLeastGL(gl::Version(1, 5)) ||
1206                               functions->hasGLExtension("GL_EXT_blend_minmax") ||
1207                               functions->isAtLeastGLES(gl::Version(3, 0)) ||
1208                               functions->hasGLESExtension("GL_EXT_blend_minmax");
1209     extensions->framebufferBlit        = (functions->blitFramebuffer != nullptr);
1210     extensions->framebufferMultisample = caps->maxSamples > 0;
1211     extensions->standardDerivativesOES = functions->isAtLeastGL(gl::Version(2, 0)) ||
1212                                          functions->hasGLExtension("GL_ARB_fragment_shader") ||
1213                                          functions->hasGLESExtension("GL_OES_standard_derivatives");
1214     extensions->shaderTextureLOD = functions->isAtLeastGL(gl::Version(3, 0)) ||
1215                                    functions->hasGLExtension("GL_ARB_shader_texture_lod") ||
1216                                    functions->hasGLESExtension("GL_EXT_shader_texture_lod");
1217     extensions->fragDepth = functions->standard == STANDARD_GL_DESKTOP ||
1218                             functions->hasGLESExtension("GL_EXT_frag_depth");
1219 
1220     // Support video texture extension on non Android backends.
1221     // TODO(crbug.com/776222): support Android and Apple devices.
1222     extensions->webglVideoTexture = !IsAndroid() && !IsApple();
1223 
1224     if (functions->hasGLExtension("GL_ARB_shader_viewport_layer_array") ||
1225         functions->hasGLExtension("GL_NV_viewport_array2"))
1226     {
1227         extensions->multiview  = true;
1228         extensions->multiview2 = true;
1229         // GL_MAX_ARRAY_TEXTURE_LAYERS is guaranteed to be at least 256.
1230         const int maxLayers = QuerySingleGLInt(functions, GL_MAX_ARRAY_TEXTURE_LAYERS);
1231         // GL_MAX_VIEWPORTS is guaranteed to be at least 16.
1232         const int maxViewports = QuerySingleGLInt(functions, GL_MAX_VIEWPORTS);
1233         extensions->maxViews   = static_cast<GLuint>(
1234             std::min(static_cast<int>(gl::IMPLEMENTATION_ANGLE_MULTIVIEW_MAX_VIEWS),
1235                      std::min(maxLayers, maxViewports)));
1236         *multiviewImplementationType = MultiviewImplementationTypeGL::NV_VIEWPORT_ARRAY2;
1237     }
1238 
1239     extensions->fboRenderMipmapOES = functions->isAtLeastGL(gl::Version(3, 0)) ||
1240                                      functions->hasGLExtension("GL_EXT_framebuffer_object") ||
1241                                      functions->isAtLeastGLES(gl::Version(3, 0)) ||
1242                                      functions->hasGLESExtension("GL_OES_fbo_render_mipmap");
1243     extensions->textureBorderClampOES =
1244         functions->standard == STANDARD_GL_DESKTOP ||
1245         functions->hasGLESExtension("GL_OES_texture_border_clamp") ||
1246         functions->hasGLESExtension("GL_EXT_texture_border_clamp") ||
1247         functions->hasGLESExtension("GL_NV_texture_border_clamp");
1248     extensions->instancedArraysANGLE = functions->isAtLeastGL(gl::Version(3, 1)) ||
1249                                        (functions->hasGLExtension("GL_ARB_instanced_arrays") &&
1250                                         (functions->hasGLExtension("GL_ARB_draw_instanced") ||
1251                                          functions->hasGLExtension("GL_EXT_draw_instanced"))) ||
1252                                        functions->isAtLeastGLES(gl::Version(3, 0)) ||
1253                                        functions->hasGLESExtension("GL_EXT_instanced_arrays");
1254     extensions->instancedArraysEXT = extensions->instancedArraysANGLE;
1255     extensions->unpackSubimage     = functions->standard == STANDARD_GL_DESKTOP ||
1256                                  functions->isAtLeastGLES(gl::Version(3, 0)) ||
1257                                  functions->hasGLESExtension("GL_EXT_unpack_subimage");
1258     extensions->noperspectiveInterpolationNV = functions->isAtLeastGL(gl::Version(3, 0));
1259     extensions->packSubimage                 = functions->standard == STANDARD_GL_DESKTOP ||
1260                                functions->isAtLeastGLES(gl::Version(3, 0)) ||
1261                                functions->hasGLESExtension("GL_NV_pack_subimage");
1262     extensions->vertexArrayObjectOES = functions->isAtLeastGL(gl::Version(3, 0)) ||
1263                                        functions->hasGLExtension("GL_ARB_vertex_array_object") ||
1264                                        functions->isAtLeastGLES(gl::Version(3, 0)) ||
1265                                        functions->hasGLESExtension("GL_OES_vertex_array_object");
1266     extensions->debugMarker = functions->isAtLeastGL(gl::Version(4, 3)) ||
1267                               functions->hasGLExtension("GL_KHR_debug") ||
1268                               functions->hasGLExtension("GL_EXT_debug_marker") ||
1269                               functions->isAtLeastGLES(gl::Version(3, 2)) ||
1270                               functions->hasGLESExtension("GL_KHR_debug") ||
1271                               functions->hasGLESExtension("GL_EXT_debug_marker");
1272     extensions->eglImageOES         = functions->hasGLESExtension("GL_OES_EGL_image");
1273     extensions->eglImageExternalOES = functions->hasGLESExtension("GL_OES_EGL_image_external");
1274     extensions->eglImageExternalWrapModesEXT =
1275         functions->hasExtension("GL_EXT_EGL_image_external_wrap_modes");
1276     extensions->eglImageExternalEssl3OES =
1277         functions->hasGLESExtension("GL_OES_EGL_image_external_essl3");
1278     extensions->eglImageArray = functions->hasGLESExtension("GL_EXT_EGL_image_array");
1279 
1280     extensions->eglSyncOES = functions->hasGLESExtension("GL_OES_EGL_sync");
1281 
1282     if (!features.disableTimestampQueries.enabled &&
1283         (functions->isAtLeastGL(gl::Version(3, 3)) ||
1284          functions->hasGLExtension("GL_ARB_timer_query") ||
1285          functions->hasGLESExtension("GL_EXT_disjoint_timer_query")))
1286     {
1287         extensions->disjointTimerQuery = true;
1288 
1289         // If we can't query the counter bits, leave them at 0.
1290         if (!features.queryCounterBitsGeneratesErrors.enabled)
1291         {
1292             extensions->queryCounterBitsTimeElapsed =
1293                 QueryQueryValue(functions, GL_TIME_ELAPSED, GL_QUERY_COUNTER_BITS);
1294             extensions->queryCounterBitsTimestamp =
1295                 QueryQueryValue(functions, GL_TIMESTAMP, GL_QUERY_COUNTER_BITS);
1296         }
1297     }
1298 
1299     // the EXT_multisample_compatibility is written against ES3.1 but can apply
1300     // to earlier versions so therefore we're only checking for the extension string
1301     // and not the specific GLES version.
1302     extensions->multisampleCompatibility =
1303         functions->isAtLeastGL(gl::Version(1, 3)) ||
1304         functions->hasGLESExtension("GL_EXT_multisample_compatibility");
1305 
1306     extensions->framebufferMixedSamples =
1307         functions->hasGLExtension("GL_NV_framebuffer_mixed_samples") ||
1308         functions->hasGLESExtension("GL_NV_framebuffer_mixed_samples");
1309 
1310     extensions->robustness = functions->isAtLeastGL(gl::Version(4, 5)) ||
1311                              functions->hasGLExtension("GL_KHR_robustness") ||
1312                              functions->hasGLExtension("GL_ARB_robustness") ||
1313                              functions->isAtLeastGLES(gl::Version(3, 2)) ||
1314                              functions->hasGLESExtension("GL_KHR_robustness") ||
1315                              functions->hasGLESExtension("GL_EXT_robustness");
1316 
1317     extensions->robustBufferAccessBehavior =
1318         extensions->robustness &&
1319         (functions->hasGLExtension("GL_ARB_robust_buffer_access_behavior") ||
1320          functions->hasGLESExtension("GL_KHR_robust_buffer_access_behavior"));
1321 
1322     extensions->copyTexture = true;
1323     extensions->syncQuery   = SyncQueryGL::IsSupported(functions);
1324 
1325     // Note that OES_texture_storage_multisample_2d_array support could be extended down to GL 3.2
1326     // if we emulated texStorage* API on top of texImage*.
1327     extensions->textureStorageMultisample2DArrayOES =
1328         functions->isAtLeastGL(gl::Version(4, 2)) || functions->isAtLeastGLES(gl::Version(3, 2));
1329 
1330     extensions->multiviewMultisample = extensions->textureStorageMultisample2DArrayOES &&
1331                                        (extensions->multiview || extensions->multiview2);
1332 
1333     extensions->textureMultisample = functions->isAtLeastGL(gl::Version(3, 2)) ||
1334                                      functions->hasGLExtension("GL_ARB_texture_multisample");
1335 
1336     extensions->textureSRGBDecode = functions->hasGLExtension("GL_EXT_texture_sRGB_decode") ||
1337                                     functions->hasGLESExtension("GL_EXT_texture_sRGB_decode");
1338 
1339     // ANGLE treats ETC1 as ETC2 for ES 3.0 and higher because it becomes a core format, and they
1340     // are backwards compatible.
1341     extensions->compressedETC1RGB8SubTexture =
1342         functions->isAtLeastGLES(gl::Version(3, 0)) ||
1343         functions->hasGLESExtension("GL_EXT_compressed_ETC1_RGB8_sub_texture");
1344 
1345 #if defined(ANGLE_PLATFORM_MACOS) || defined(ANGLE_PLATFORM_MACCATALYST)
1346     VendorID vendor = GetVendorID(functions);
1347     if ((IsAMD(vendor) || IsIntel(vendor)) && *maxSupportedESVersion >= gl::Version(3, 0))
1348     {
1349         // Apple Intel/AMD drivers do not correctly use the TEXTURE_SRGB_DECODE property of sampler
1350         // states.  Disable this extension when we would advertise any ES version that has samplers.
1351         extensions->textureSRGBDecode = false;
1352     }
1353 #endif
1354 
1355     extensions->sRGBWriteControl = functions->isAtLeastGL(gl::Version(3, 0)) ||
1356                                    functions->hasGLExtension("GL_EXT_framebuffer_sRGB") ||
1357                                    functions->hasGLExtension("GL_ARB_framebuffer_sRGB") ||
1358                                    functions->hasGLESExtension("GL_EXT_sRGB_write_control");
1359 
1360 #if defined(ANGLE_PLATFORM_ANDROID)
1361     // SRGB blending does not appear to work correctly on the Nexus 5. Writing to an SRGB
1362     // framebuffer with GL_FRAMEBUFFER_SRGB enabled and then reading back returns the same value.
1363     // Disabling GL_FRAMEBUFFER_SRGB will then convert in the wrong direction.
1364     extensions->sRGBWriteControl = false;
1365 
1366     // BGRA formats do not appear to be accepted by the Nexus 5X driver dispite the extension being
1367     // exposed.
1368     extensions->textureFormatBGRA8888 = false;
1369 #endif
1370 
1371     // EXT_discard_framebuffer can be implemented as long as glDiscardFramebufferEXT or
1372     // glInvalidateFramebuffer is available
1373     extensions->discardFramebuffer = functions->isAtLeastGL(gl::Version(4, 3)) ||
1374                                      functions->hasGLExtension("GL_ARB_invalidate_subdata") ||
1375                                      functions->isAtLeastGLES(gl::Version(3, 0)) ||
1376                                      functions->hasGLESExtension("GL_EXT_discard_framebuffer") ||
1377                                      functions->hasGLESExtension("GL_ARB_invalidate_subdata");
1378 
1379     extensions->translatedShaderSource = true;
1380 
1381     if (functions->isAtLeastGL(gl::Version(3, 1)) ||
1382         functions->hasGLExtension("GL_ARB_texture_rectangle"))
1383     {
1384         extensions->textureRectangle  = true;
1385         caps->maxRectangleTextureSize = std::min(
1386             QuerySingleGLInt(functions, GL_MAX_RECTANGLE_TEXTURE_SIZE_ANGLE), textureSizeLimit);
1387     }
1388 
1389     // OpenGL 4.3 (and above) can support all features and constants defined in
1390     // GL_EXT_geometry_shader.
1391     if (functions->isAtLeastGL(gl::Version(4, 3)) || functions->isAtLeastGLES(gl::Version(3, 2)) ||
1392         functions->hasGLESExtension("GL_OES_geometry_shader") ||
1393         functions->hasGLESExtension("GL_EXT_geometry_shader") ||
1394         // OpenGL 4.0 adds the support for instanced geometry shader
1395         // GL_ARB_shader_atomic_counters adds atomic counters to geometry shader
1396         // GL_ARB_shader_storage_buffer_object adds shader storage buffers to geometry shader
1397         // GL_ARB_shader_image_load_store adds images to geometry shader
1398         (functions->isAtLeastGL(gl::Version(4, 0)) &&
1399          functions->hasGLExtension("GL_ARB_shader_atomic_counters") &&
1400          functions->hasGLExtension("GL_ARB_shader_storage_buffer_object") &&
1401          functions->hasGLExtension("GL_ARB_shader_image_load_store")))
1402     {
1403         extensions->geometryShader = true;
1404 
1405         caps->maxFramebufferLayers = QuerySingleGLInt(functions, GL_MAX_FRAMEBUFFER_LAYERS_EXT);
1406 
1407         // GL_PROVOKING_VERTEX isn't a valid return value of GL_LAYER_PROVOKING_VERTEX_EXT in
1408         // GL_EXT_geometry_shader SPEC, however it is legal in desktop OpenGL, which means the value
1409         // follows the one set by glProvokingVertex.
1410         // [OpenGL 4.3] Chapter 11.3.4.6
1411         // The vertex conventions followed for gl_Layer and gl_ViewportIndex may be determined by
1412         // calling GetIntegerv with the symbolic constants LAYER_PROVOKING_VERTEX and
1413         // VIEWPORT_INDEX_PROVOKING_VERTEX, respectively. For either query, if the value returned is
1414         // PROVOKING_VERTEX, then vertex selection follows the convention specified by
1415         // ProvokingVertex.
1416         caps->layerProvokingVertex = QuerySingleGLInt(functions, GL_LAYER_PROVOKING_VERTEX_EXT);
1417         if (caps->layerProvokingVertex == GL_PROVOKING_VERTEX)
1418         {
1419             // We should use GL_LAST_VERTEX_CONVENTION_EXT instead because desktop OpenGL SPEC
1420             // requires the initial value of provoking vertex mode is LAST_VERTEX_CONVENTION.
1421             // [OpenGL 4.3] Chapter 13.4
1422             // The initial value of the provoking vertex mode is LAST_VERTEX_CONVENTION.
1423             caps->layerProvokingVertex = GL_LAST_VERTEX_CONVENTION_EXT;
1424         }
1425 
1426         caps->maxShaderUniformComponents[gl::ShaderType::Geometry] =
1427             QuerySingleGLInt(functions, GL_MAX_GEOMETRY_UNIFORM_COMPONENTS_EXT);
1428         caps->maxShaderUniformBlocks[gl::ShaderType::Geometry] =
1429             QuerySingleGLInt(functions, GL_MAX_GEOMETRY_UNIFORM_BLOCKS_EXT);
1430         caps->maxCombinedShaderUniformComponents[gl::ShaderType::Geometry] =
1431             QuerySingleGLInt(functions, GL_MAX_COMBINED_GEOMETRY_UNIFORM_COMPONENTS_EXT);
1432         caps->maxGeometryInputComponents =
1433             QuerySingleGLInt(functions, GL_MAX_GEOMETRY_INPUT_COMPONENTS_EXT);
1434         caps->maxGeometryOutputComponents =
1435             QuerySingleGLInt(functions, GL_MAX_GEOMETRY_OUTPUT_COMPONENTS_EXT);
1436         caps->maxGeometryOutputVertices =
1437             QuerySingleGLInt(functions, GL_MAX_GEOMETRY_OUTPUT_VERTICES_EXT);
1438         caps->maxGeometryTotalOutputComponents =
1439             QuerySingleGLInt(functions, GL_MAX_GEOMETRY_TOTAL_OUTPUT_COMPONENTS_EXT);
1440         caps->maxGeometryShaderInvocations =
1441             QuerySingleGLInt(functions, GL_MAX_GEOMETRY_SHADER_INVOCATIONS_EXT);
1442         caps->maxShaderTextureImageUnits[gl::ShaderType::Geometry] =
1443             QuerySingleGLInt(functions, GL_MAX_GEOMETRY_TEXTURE_IMAGE_UNITS_EXT);
1444         caps->maxShaderAtomicCounterBuffers[gl::ShaderType::Geometry] =
1445             QuerySingleGLInt(functions, GL_MAX_GEOMETRY_ATOMIC_COUNTER_BUFFERS_EXT);
1446         caps->maxShaderAtomicCounters[gl::ShaderType::Geometry] =
1447             QuerySingleGLInt(functions, GL_MAX_GEOMETRY_ATOMIC_COUNTERS_EXT);
1448         caps->maxShaderImageUniforms[gl::ShaderType::Geometry] =
1449             QuerySingleGLInt(functions, GL_MAX_GEOMETRY_IMAGE_UNIFORMS_EXT);
1450         caps->maxShaderStorageBlocks[gl::ShaderType::Geometry] =
1451             QuerySingleGLInt(functions, GL_MAX_GEOMETRY_SHADER_STORAGE_BLOCKS_EXT);
1452     }
1453 
1454     // The real combined caps contain limits for shader types that are not available to ES, so limit
1455     // the caps to the sum of vertex+fragment+geometry shader caps.
1456     CapCombinedLimitToESShaders(&caps->maxCombinedUniformBlocks, caps->maxShaderUniformBlocks);
1457     CapCombinedLimitToESShaders(&caps->maxCombinedTextureImageUnits,
1458                                 caps->maxShaderTextureImageUnits);
1459     CapCombinedLimitToESShaders(&caps->maxCombinedShaderStorageBlocks,
1460                                 caps->maxShaderStorageBlocks);
1461     CapCombinedLimitToESShaders(&caps->maxCombinedImageUniforms, caps->maxShaderImageUniforms);
1462     CapCombinedLimitToESShaders(&caps->maxCombinedAtomicCounterBuffers,
1463                                 caps->maxShaderAtomicCounterBuffers);
1464     CapCombinedLimitToESShaders(&caps->maxCombinedAtomicCounters, caps->maxShaderAtomicCounters);
1465 
1466     // EXT_blend_func_extended.
1467     // Note that this could be implemented also on top of native EXT_blend_func_extended, but it's
1468     // currently not fully implemented.
1469     extensions->blendFuncExtended = !features.disableBlendFuncExtended.enabled &&
1470                                     functions->standard == STANDARD_GL_DESKTOP &&
1471                                     functions->hasGLExtension("GL_ARB_blend_func_extended");
1472     if (extensions->blendFuncExtended)
1473     {
1474         // TODO(http://anglebug.com/1085): Support greater values of
1475         // MAX_DUAL_SOURCE_DRAW_BUFFERS_EXT queried from the driver. See comments in ProgramGL.cpp
1476         // for more information about this limitation.
1477         extensions->maxDualSourceDrawBuffers = 1;
1478     }
1479 
1480     // EXT_float_blend
1481     // Assume all desktop driver supports this by default.
1482     extensions->floatBlend = functions->standard == STANDARD_GL_DESKTOP ||
1483                              functions->hasGLESExtension("GL_EXT_float_blend");
1484 
1485     // ANGLE_base_vertex_base_instance
1486     extensions->baseVertexBaseInstance =
1487         functions->isAtLeastGL(gl::Version(3, 2)) || functions->isAtLeastGLES(gl::Version(3, 2)) ||
1488         functions->hasGLESExtension("GL_OES_draw_elements_base_vertex") ||
1489         functions->hasGLESExtension("GL_EXT_draw_elements_base_vertex");
1490 
1491     // OES_draw_elements_base_vertex
1492     extensions->drawElementsBaseVertexOES =
1493         functions->isAtLeastGL(gl::Version(3, 2)) || functions->isAtLeastGLES(gl::Version(3, 2)) ||
1494         functions->hasGLESExtension("GL_OES_draw_elements_base_vertex");
1495 
1496     // EXT_draw_elements_base_vertex
1497     extensions->drawElementsBaseVertexEXT =
1498         functions->isAtLeastGL(gl::Version(3, 2)) || functions->isAtLeastGLES(gl::Version(3, 2)) ||
1499         functions->hasGLESExtension("GL_EXT_draw_elements_base_vertex");
1500 
1501     // ANGLE_compressed_texture_etc
1502     // Expose this extension only when we support the formats or we're running on top of a native
1503     // ES driver.
1504     extensions->compressedTextureETC = functions->standard == STANDARD_GL_ES &&
1505                                        gl::DetermineCompressedTextureETCSupport(*textureCapsMap);
1506 
1507     // To work around broken unsized sRGB textures, sized sRGB textures are used. Disable EXT_sRGB
1508     // if those formats are not available.
1509     if (features.unsizedsRGBReadPixelsDoesntTransform.enabled &&
1510         !functions->isAtLeastGLES(gl::Version(3, 0)))
1511     {
1512         extensions->sRGB = false;
1513     }
1514 
1515     extensions->provokingVertex = functions->hasGLExtension("GL_ARB_provoking_vertex") ||
1516                                   functions->hasGLExtension("GL_EXT_provoking_vertex") ||
1517                                   functions->isAtLeastGL(gl::Version(3, 2));
1518 
1519     extensions->textureExternalUpdateANGLE = true;
1520     extensions->texture3DOES               = functions->isAtLeastGL(gl::Version(1, 2)) ||
1521                                functions->isAtLeastGLES(gl::Version(3, 0)) ||
1522                                functions->hasGLESExtension("GL_OES_texture_3D");
1523 
1524     extensions->memoryObject = functions->hasGLExtension("GL_EXT_memory_object") ||
1525                                functions->hasGLESExtension("GL_EXT_memory_object");
1526     extensions->semaphore = functions->hasGLExtension("GL_EXT_semaphore") ||
1527                             functions->hasGLESExtension("GL_EXT_semaphore");
1528     extensions->memoryObjectFd = functions->hasGLExtension("GL_EXT_memory_object_fd") ||
1529                                  functions->hasGLESExtension("GL_EXT_memory_object_fd");
1530     extensions->semaphoreFd = !features.disableSemaphoreFd.enabled &&
1531                               (functions->hasGLExtension("GL_EXT_semaphore_fd") ||
1532                                functions->hasGLESExtension("GL_EXT_semaphore_fd"));
1533     extensions->gpuShader5EXT = functions->isAtLeastGL(gl::Version(4, 0)) ||
1534                                 functions->isAtLeastGLES(gl::Version(3, 2)) ||
1535                                 functions->hasGLExtension("GL_ARB_gpu_shader5") ||
1536                                 functions->hasGLESExtension("GL_EXT_gpu_shader5");
1537 
1538     // GL_APPLE_clip_distance
1539     extensions->clipDistanceAPPLE = functions->isAtLeastGL(gl::Version(3, 0));
1540     if (extensions->clipDistanceAPPLE)
1541     {
1542         caps->maxClipDistances = QuerySingleGLInt(functions, GL_MAX_CLIP_DISTANCES_EXT);
1543     }
1544     else
1545     {
1546         caps->maxClipDistances = 0;
1547     }
1548 }
1549 
InitializeFeatures(const FunctionsGL * functions,angle::FeaturesGL * features)1550 void InitializeFeatures(const FunctionsGL *functions, angle::FeaturesGL *features)
1551 {
1552     VendorID vendor = GetVendorID(functions);
1553     uint32_t device = GetDeviceID(functions);
1554     bool isAMD      = IsAMD(vendor);
1555     bool isIntel    = IsIntel(vendor);
1556     bool isNvidia   = IsNvidia(vendor);
1557     bool isQualcomm = IsQualcomm(vendor);
1558     bool isVMWare   = IsVMWare(vendor);
1559 
1560     std::array<int, 3> mesaVersion = {0, 0, 0};
1561     bool isMesa                    = IsMesa(functions, &mesaVersion);
1562 
1563     // Don't use 1-bit alpha formats on desktop GL with AMD drivers.
1564     ANGLE_FEATURE_CONDITION(features, avoid1BitAlphaTextureFormats,
1565                             functions->standard == STANDARD_GL_DESKTOP && isAMD);
1566 
1567     ANGLE_FEATURE_CONDITION(features, rgba4IsNotSupportedForColorRendering,
1568                             functions->standard == STANDARD_GL_DESKTOP && isIntel);
1569 
1570     // Ported from gpu_driver_bug_list.json (#183)
1571     ANGLE_FEATURE_CONDITION(features, emulateAbsIntFunction, IsApple() && isIntel);
1572 
1573     ANGLE_FEATURE_CONDITION(features, addAndTrueToLoopCondition, IsApple() && isIntel);
1574 
1575     // Ported from gpu_driver_bug_list.json (#191)
1576     ANGLE_FEATURE_CONDITION(
1577         features, emulateIsnanFloat,
1578         isIntel && IsApple() && IsSkylake(device) && GetMacOSVersion() < OSVersion(10, 13, 2));
1579 
1580     ANGLE_FEATURE_CONDITION(features, doesSRGBClearsOnLinearFramebufferAttachments,
1581                             functions->standard == STANDARD_GL_DESKTOP && (isIntel || isAMD));
1582 
1583     ANGLE_FEATURE_CONDITION(features, emulateMaxVertexAttribStride,
1584                             IsLinux() && functions->standard == STANDARD_GL_DESKTOP && isAMD);
1585     ANGLE_FEATURE_CONDITION(
1586         features, useUnusedBlocksWithStandardOrSharedLayout,
1587         (IsApple() && functions->standard == STANDARD_GL_DESKTOP) || (IsLinux() && isAMD));
1588 
1589     // Ported from gpu_driver_bug_list.json (#187)
1590     ANGLE_FEATURE_CONDITION(features, doWhileGLSLCausesGPUHang,
1591                             IsApple() && functions->standard == STANDARD_GL_DESKTOP &&
1592                                 GetMacOSVersion() < OSVersion(10, 11, 0));
1593 
1594     // Ported from gpu_driver_bug_list.json (#211)
1595     ANGLE_FEATURE_CONDITION(features, rewriteFloatUnaryMinusOperator,
1596                             IsApple() && isIntel && GetMacOSVersion() < OSVersion(10, 12, 0));
1597 
1598     ANGLE_FEATURE_CONDITION(features, addBaseVertexToVertexID, IsApple() && isAMD);
1599 
1600     // Triggers a bug on Marshmallow Adreno (4xx?) driver.
1601     // http://anglebug.com/2046
1602     ANGLE_FEATURE_CONDITION(features, dontInitializeUninitializedLocals, IsAndroid() && isQualcomm);
1603 
1604     ANGLE_FEATURE_CONDITION(features, finishDoesNotCauseQueriesToBeAvailable,
1605                             functions->standard == STANDARD_GL_DESKTOP && isNvidia);
1606 
1607     // TODO(cwallez): Disable this workaround for MacOSX versions 10.9 or later.
1608     ANGLE_FEATURE_CONDITION(features, alwaysCallUseProgramAfterLink, true);
1609 
1610     ANGLE_FEATURE_CONDITION(features, unpackOverlappingRowsSeparatelyUnpackBuffer, isNvidia);
1611     ANGLE_FEATURE_CONDITION(features, packOverlappingRowsSeparatelyPackBuffer, isNvidia);
1612 
1613     ANGLE_FEATURE_CONDITION(features, initializeCurrentVertexAttributes, isNvidia);
1614 
1615     ANGLE_FEATURE_CONDITION(features, unpackLastRowSeparatelyForPaddingInclusion,
1616                             IsApple() || isNvidia);
1617     ANGLE_FEATURE_CONDITION(features, packLastRowSeparatelyForPaddingInclusion,
1618                             IsApple() || isNvidia);
1619 
1620     ANGLE_FEATURE_CONDITION(features, removeInvariantAndCentroidForESSL3,
1621                             functions->isAtMostGL(gl::Version(4, 1)) ||
1622                                 (functions->standard == STANDARD_GL_DESKTOP && isAMD));
1623 
1624     // TODO(oetuaho): Make this specific to the affected driver versions. Versions that came after
1625     // 364 are known to be affected, at least up to 375.
1626     ANGLE_FEATURE_CONDITION(features, emulateAtan2Float, isNvidia);
1627 
1628     ANGLE_FEATURE_CONDITION(features, reapplyUBOBindingsAfterUsingBinaryProgram,
1629                             isAMD || IsAndroid());
1630 
1631     ANGLE_FEATURE_CONDITION(features, rewriteVectorScalarArithmetic, isNvidia);
1632 
1633     // TODO(oetuaho): Make this specific to the affected driver versions. Versions at least up to
1634     // 390 are known to be affected. Versions after that are expected not to be affected.
1635     ANGLE_FEATURE_CONDITION(features, clampFragDepth, isNvidia);
1636 
1637     // TODO(oetuaho): Make this specific to the affected driver versions. Versions since 397.31 are
1638     // not affected.
1639     ANGLE_FEATURE_CONDITION(features, rewriteRepeatedAssignToSwizzled, isNvidia);
1640 
1641     // TODO(jmadill): Narrow workaround range for specific devices.
1642 
1643     ANGLE_FEATURE_CONDITION(features, clampPointSize, IsAndroid() || isNvidia);
1644 
1645     // Ported from gpu_driver_bug_list.json (#246, #258)
1646     ANGLE_FEATURE_CONDITION(features, dontUseLoopsToInitializeVariables,
1647                             (IsAndroid() && isQualcomm) || (isIntel && IsApple()));
1648 
1649     ANGLE_FEATURE_CONDITION(features, disableBlendFuncExtended, isAMD || isIntel);
1650 
1651     ANGLE_FEATURE_CONDITION(features, unsizedsRGBReadPixelsDoesntTransform,
1652                             IsAndroid() && isQualcomm);
1653 
1654     ANGLE_FEATURE_CONDITION(features, queryCounterBitsGeneratesErrors, IsNexus5X(vendor, device));
1655 
1656     ANGLE_FEATURE_CONDITION(features, dontRelinkProgramsInParallel,
1657                             IsAndroid() || (IsWindows() && isIntel));
1658 
1659     // TODO(jie.a.chen@intel.com): Clean up the bugs.
1660     // anglebug.com/3031
1661     // crbug.com/922936
1662     ANGLE_FEATURE_CONDITION(features, disableWorkerContexts,
1663                             (IsWindows() && (isIntel || isAMD)) || (IsLinux() && isNvidia));
1664 
1665     bool limitMaxTextureSize = isIntel && IsLinux() && GetLinuxOSVersion() < OSVersion(5, 0, 0);
1666     ANGLE_FEATURE_CONDITION(features, limitMaxTextureSizeTo4096,
1667                             IsAndroid() || limitMaxTextureSize);
1668     // On Apple switchable graphics, GL_MAX_SAMPLES may differ between the GPUs.
1669     // 4 is a lowest common denominator that is always supported.
1670     ANGLE_FEATURE_CONDITION(features, limitMaxMSAASamplesTo4,
1671                             IsAndroid() || (IsApple() && (isIntel || isAMD || isNvidia)));
1672     ANGLE_FEATURE_CONDITION(features, limitMax3dArrayTextureSizeTo1024, limitMaxTextureSize);
1673 
1674     ANGLE_FEATURE_CONDITION(features, allowClearForRobustResourceInit, IsApple());
1675 
1676     // The WebGL conformance/uniforms/out-of-bounds-uniform-array-access test has been seen to fail
1677     // on AMD and Android devices.
1678     // This test is also flaky on Linux Nvidia. So we just turn it on everywhere and don't rely on
1679     // driver since security is important.
1680     ANGLE_FEATURE_CONDITION(
1681         features, clampArrayAccess,
1682         IsAndroid() || isAMD || !functions->hasExtension("GL_KHR_robust_buffer_access_behavior"));
1683 
1684     ANGLE_FEATURE_CONDITION(features, resetTexImage2DBaseLevel,
1685                             IsApple() && isIntel && GetMacOSVersion() >= OSVersion(10, 12, 4));
1686 
1687     ANGLE_FEATURE_CONDITION(features, clearToZeroOrOneBroken,
1688                             IsApple() && isIntel && GetMacOSVersion() < OSVersion(10, 12, 6));
1689 
1690     ANGLE_FEATURE_CONDITION(features, adjustSrcDstRegionBlitFramebuffer,
1691                             IsLinux() || (IsAndroid() && isNvidia) || (IsWindows() && isNvidia));
1692 
1693     ANGLE_FEATURE_CONDITION(features, clipSrcRegionBlitFramebuffer,
1694                             IsApple() || (IsLinux() && isAMD));
1695 
1696     ANGLE_FEATURE_CONDITION(features, resettingTexturesGeneratesErrors,
1697                             IsApple() || (IsWindows() && isAMD));
1698 
1699     ANGLE_FEATURE_CONDITION(features, rgbDXT1TexturesSampleZeroAlpha, IsApple());
1700 
1701     ANGLE_FEATURE_CONDITION(features, unfoldShortCircuits, IsApple());
1702 
1703     ANGLE_FEATURE_CONDITION(features, emulatePrimitiveRestartFixedIndex,
1704                             functions->standard == STANDARD_GL_DESKTOP &&
1705                                 functions->isAtLeastGL(gl::Version(3, 1)) &&
1706                                 !functions->isAtLeastGL(gl::Version(4, 3)));
1707     ANGLE_FEATURE_CONDITION(
1708         features, setPrimitiveRestartFixedIndexForDrawArrays,
1709         features->emulatePrimitiveRestartFixedIndex.enabled && IsApple() && isIntel);
1710 
1711     ANGLE_FEATURE_CONDITION(features, removeDynamicIndexingOfSwizzledVector,
1712                             IsApple() || IsAndroid() || IsWindows());
1713 
1714     // Ported from gpu_driver_bug_list.json (#89)
1715     ANGLE_FEATURE_CONDITION(features, regenerateStructNames, IsApple());
1716 
1717     // Ported from gpu_driver_bug_list.json (#184)
1718     ANGLE_FEATURE_CONDITION(features, preAddTexelFetchOffsets, IsApple() && isIntel);
1719 
1720     // Workaround for the widespread OpenGL ES driver implementaion bug
1721     ANGLE_FEATURE_CONDITION(features, readPixelsUsingImplementationColorReadFormatForNorm16,
1722                             functions->standard == STANDARD_GL_ES &&
1723                                 functions->isAtLeastGLES(gl::Version(3, 1)) &&
1724                                 functions->hasGLESExtension("GL_EXT_texture_norm16"));
1725 
1726     // anglebug.com/4267
1727     ANGLE_FEATURE_CONDITION(features, flushBeforeDeleteTextureIfCopiedTo, IsApple() && isIntel);
1728 
1729     // anglebug.com/2273
1730     // Seems to affect both Intel and AMD GPUs. Enable workaround for all GPUs on macOS.
1731     ANGLE_FEATURE_CONDITION(features, rewriteRowMajorMatrices,
1732                             // IsApple() && functions->standard == STANDARD_GL_DESKTOP);
1733                             // TODO(anglebug.com/2273): diagnose crashes with this workaround.
1734                             false);
1735 
1736     // Workaround for incorrect sampling from DXT1 sRGB textures in Intel OpenGL on Windows.
1737     ANGLE_FEATURE_CONDITION(features, avoidDXT1sRGBTextureFormat, IsWindows() && isIntel);
1738 
1739     ANGLE_FEATURE_CONDITION(features, disableDrawBuffersIndexed, IsWindows() && isAMD);
1740 
1741     ANGLE_FEATURE_CONDITION(
1742         features, disableSemaphoreFd,
1743         IsLinux() && isAMD && isMesa && mesaVersion < (std::array<int, 3>{19, 3, 5}));
1744 
1745     ANGLE_FEATURE_CONDITION(features, disableTimestampQueries, IsLinux() && isVMWare);
1746 
1747     ANGLE_FEATURE_CONDITION(features, encodeAndDecodeSRGBForGenerateMipmap,
1748                             IsApple() && functions->standard == STANDARD_GL_DESKTOP);
1749 
1750     // anglebug.com/4674
1751     // The (redundant) explicit exclusion of Windows AMD is because the workaround fails
1752     // Texture2DRGTest.TextureRGUNormTest on that platform, and the test is skipped. If
1753     // you'd like to enable the workaround on Windows AMD, please fix the test first.
1754     ANGLE_FEATURE_CONDITION(
1755         features, emulateCopyTexImage2DFromRenderbuffers,
1756         IsApple() && functions->standard == STANDARD_GL_ES && !(isAMD && IsWindows()));
1757 }
1758 
InitializeFrontendFeatures(const FunctionsGL * functions,angle::FrontendFeatures * features)1759 void InitializeFrontendFeatures(const FunctionsGL *functions, angle::FrontendFeatures *features)
1760 {
1761     VendorID vendor = GetVendorID(functions);
1762     bool isIntel    = IsIntel(vendor);
1763     bool isQualcomm = IsQualcomm(vendor);
1764 
1765     ANGLE_FEATURE_CONDITION(features, disableProgramCachingForTransformFeedback,
1766                             IsAndroid() && isQualcomm);
1767     ANGLE_FEATURE_CONDITION(features, syncFramebufferBindingsOnTexImage, IsWindows() && isIntel);
1768 }
1769 
1770 }  // namespace nativegl_gl
1771 
1772 namespace nativegl
1773 {
SupportsCompute(const FunctionsGL * functions)1774 bool SupportsCompute(const FunctionsGL *functions)
1775 {
1776     // OpenGL 4.2 is required for GL_ARB_compute_shader, some platform drivers have the extension,
1777     // but their maximum supported GL versions are less than 4.2. Explicitly limit the minimum
1778     // GL version to 4.2.
1779     return (functions->isAtLeastGL(gl::Version(4, 3)) ||
1780             functions->isAtLeastGLES(gl::Version(3, 1)) ||
1781             (functions->isAtLeastGL(gl::Version(4, 2)) &&
1782              functions->hasGLExtension("GL_ARB_compute_shader") &&
1783              functions->hasGLExtension("GL_ARB_shader_storage_buffer_object")));
1784 }
1785 
SupportsFenceSync(const FunctionsGL * functions)1786 bool SupportsFenceSync(const FunctionsGL *functions)
1787 {
1788     return functions->isAtLeastGL(gl::Version(3, 2)) || functions->hasGLExtension("GL_ARB_sync") ||
1789            functions->isAtLeastGLES(gl::Version(3, 0));
1790 }
1791 
SupportsOcclusionQueries(const FunctionsGL * functions)1792 bool SupportsOcclusionQueries(const FunctionsGL *functions)
1793 {
1794     return functions->isAtLeastGL(gl::Version(1, 5)) ||
1795            functions->hasGLExtension("GL_ARB_occlusion_query2") ||
1796            functions->isAtLeastGLES(gl::Version(3, 0)) ||
1797            functions->hasGLESExtension("GL_EXT_occlusion_query_boolean");
1798 }
1799 
SupportsNativeRendering(const FunctionsGL * functions,gl::TextureType type,GLenum internalFormat)1800 bool SupportsNativeRendering(const FunctionsGL *functions,
1801                              gl::TextureType type,
1802                              GLenum internalFormat)
1803 {
1804     // Some desktop drivers allow rendering to formats that are not required by the spec, this is
1805     // exposed through the GL_FRAMEBUFFER_RENDERABLE query.
1806     bool hasInternalFormatQuery = functions->isAtLeastGL(gl::Version(4, 3)) ||
1807                                   functions->hasGLExtension("GL_ARB_internalformat_query2");
1808 
1809     // Some Intel drivers have a bug that returns GL_FULL_SUPPORT when asked if they support
1810     // rendering to compressed texture formats yet return framebuffer incomplete when attempting to
1811     // render to the format.  Skip any native queries for compressed formats.
1812     const gl::InternalFormat &internalFormatInfo = gl::GetSizedInternalFormatInfo(internalFormat);
1813 
1814     if (hasInternalFormatQuery && !internalFormatInfo.compressed)
1815     {
1816         GLint framebufferRenderable = GL_NONE;
1817         functions->getInternalformativ(ToGLenum(type), internalFormat, GL_FRAMEBUFFER_RENDERABLE, 1,
1818                                        &framebufferRenderable);
1819         return framebufferRenderable != GL_NONE;
1820     }
1821     else
1822     {
1823         const nativegl::InternalFormat &nativeInfo =
1824             nativegl::GetInternalFormatInfo(internalFormat, functions->standard);
1825         return nativegl_gl::MeetsRequirements(functions, nativeInfo.textureAttachment);
1826     }
1827 }
1828 
SupportsTexImage(gl::TextureType type)1829 bool SupportsTexImage(gl::TextureType type)
1830 {
1831     switch (type)
1832     {
1833             // Multi-sample texture types only support TexStorage data upload
1834         case gl::TextureType::_2DMultisample:
1835         case gl::TextureType::_2DMultisampleArray:
1836             return false;
1837 
1838         default:
1839             return true;
1840     }
1841 }
1842 
UseTexImage2D(gl::TextureType textureType)1843 bool UseTexImage2D(gl::TextureType textureType)
1844 {
1845     return textureType == gl::TextureType::_2D || textureType == gl::TextureType::CubeMap ||
1846            textureType == gl::TextureType::Rectangle ||
1847            textureType == gl::TextureType::_2DMultisample ||
1848            textureType == gl::TextureType::External || textureType == gl::TextureType::VideoImage;
1849 }
1850 
UseTexImage3D(gl::TextureType textureType)1851 bool UseTexImage3D(gl::TextureType textureType)
1852 {
1853     return textureType == gl::TextureType::_2DArray || textureType == gl::TextureType::_3D ||
1854            textureType == gl::TextureType::_2DMultisampleArray ||
1855            textureType == gl::TextureType::CubeMapArray;
1856 }
1857 
GetTextureBindingQuery(gl::TextureType textureType)1858 GLenum GetTextureBindingQuery(gl::TextureType textureType)
1859 {
1860     switch (textureType)
1861     {
1862         case gl::TextureType::_2D:
1863             return GL_TEXTURE_BINDING_2D;
1864         case gl::TextureType::_2DArray:
1865             return GL_TEXTURE_BINDING_2D_ARRAY;
1866         case gl::TextureType::_2DMultisample:
1867             return GL_TEXTURE_BINDING_2D_MULTISAMPLE;
1868         case gl::TextureType::_2DMultisampleArray:
1869             return GL_TEXTURE_BINDING_2D_MULTISAMPLE_ARRAY;
1870         case gl::TextureType::_3D:
1871             return GL_TEXTURE_BINDING_3D;
1872         case gl::TextureType::External:
1873             return GL_TEXTURE_BINDING_EXTERNAL_OES;
1874         case gl::TextureType::Rectangle:
1875             return GL_TEXTURE_BINDING_RECTANGLE;
1876         case gl::TextureType::CubeMap:
1877             return GL_TEXTURE_BINDING_CUBE_MAP;
1878         case gl::TextureType::CubeMapArray:
1879             return GL_TEXTURE_BINDING_CUBE_MAP_ARRAY_OES;
1880         default:
1881             UNREACHABLE();
1882             return 0;
1883     }
1884 }
1885 
GetTextureBindingTarget(gl::TextureType textureType)1886 GLenum GetTextureBindingTarget(gl::TextureType textureType)
1887 {
1888     return ToGLenum(GetNativeTextureType(textureType));
1889 }
1890 
GetTextureBindingTarget(gl::TextureTarget textureTarget)1891 GLenum GetTextureBindingTarget(gl::TextureTarget textureTarget)
1892 {
1893     return ToGLenum(GetNativeTextureTarget(textureTarget));
1894 }
1895 
GetBufferBindingQuery(gl::BufferBinding bufferBinding)1896 GLenum GetBufferBindingQuery(gl::BufferBinding bufferBinding)
1897 {
1898     switch (bufferBinding)
1899     {
1900         case gl::BufferBinding::Array:
1901             return GL_ARRAY_BUFFER_BINDING;
1902         case gl::BufferBinding::AtomicCounter:
1903             return GL_ATOMIC_COUNTER_BUFFER_BINDING;
1904         case gl::BufferBinding::CopyRead:
1905             return GL_COPY_READ_BUFFER_BINDING;
1906         case gl::BufferBinding::CopyWrite:
1907             return GL_COPY_WRITE_BUFFER_BINDING;
1908         case gl::BufferBinding::DispatchIndirect:
1909             return GL_DISPATCH_INDIRECT_BUFFER_BINDING;
1910         case gl::BufferBinding::DrawIndirect:
1911             return GL_DRAW_INDIRECT_BUFFER_BINDING;
1912         case gl::BufferBinding::ElementArray:
1913             return GL_ELEMENT_ARRAY_BUFFER_BINDING;
1914         case gl::BufferBinding::PixelPack:
1915             return GL_PIXEL_PACK_BUFFER_BINDING;
1916         case gl::BufferBinding::PixelUnpack:
1917             return GL_PIXEL_UNPACK_BUFFER_BINDING;
1918         case gl::BufferBinding::ShaderStorage:
1919             return GL_SHADER_STORAGE_BUFFER_BINDING;
1920         case gl::BufferBinding::TransformFeedback:
1921             return GL_TRANSFORM_FEEDBACK_BUFFER_BINDING;
1922         case gl::BufferBinding::Uniform:
1923             return GL_UNIFORM_BUFFER_BINDING;
1924         default:
1925             UNREACHABLE();
1926             return 0;
1927     }
1928 }
1929 
GetBufferBindingString(gl::BufferBinding bufferBinding)1930 std::string GetBufferBindingString(gl::BufferBinding bufferBinding)
1931 {
1932     std::ostringstream os;
1933     os << bufferBinding << "_BINDING";
1934     return os.str();
1935 }
1936 
GetNativeTextureType(gl::TextureType type)1937 gl::TextureType GetNativeTextureType(gl::TextureType type)
1938 {
1939     // VideoImage texture type is a WebGL type. It doesn't have
1940     // directly mapping type in native OpenGL/OpenGLES.
1941     // Actually, it will be translated to different texture type
1942     // (TEXTURE2D, TEXTURE_EXTERNAL_OES and TEXTURE_RECTANGLE)
1943     // based on OS and other conditions.
1944     // This will introduce problem that binding VideoImage may
1945     // unbind native image implicitly. Please make sure state
1946     // manager is aware of this implicit unbind behaviour.
1947     if (type != gl::TextureType::VideoImage)
1948     {
1949         return type;
1950     }
1951 
1952     // TODO(http://anglebug.com/3889): need to figure out rectangle texture and
1953     // external image when these backend are implemented.
1954     return gl::TextureType::_2D;
1955 }
1956 
GetNativeTextureTarget(gl::TextureTarget target)1957 gl::TextureTarget GetNativeTextureTarget(gl::TextureTarget target)
1958 {
1959     // VideoImage texture type is a WebGL type. It doesn't have
1960     // directly mapping type in native OpenGL/OpenGLES.
1961     // Actually, it will be translated to different texture target
1962     // (TEXTURE2D, TEXTURE_EXTERNAL_OES and TEXTURE_RECTANGLE)
1963     // based on OS and other conditions.
1964     // This will introduce problem that binding VideoImage may
1965     // unbind native image implicitly. Please make sure state
1966     // manager is aware of this implicit unbind behaviour.
1967     if (target != gl::TextureTarget::VideoImage)
1968     {
1969         return target;
1970     }
1971 
1972     // TODO(http://anglebug.com/3889): need to figure out rectangle texture and
1973     // external image when these backend are implemented.
1974     return gl::TextureTarget::_2D;
1975 }
1976 
1977 }  // namespace nativegl
1978 
GetFunctionsGL(const gl::Context * context)1979 const FunctionsGL *GetFunctionsGL(const gl::Context *context)
1980 {
1981     return GetImplAs<ContextGL>(context)->getFunctions();
1982 }
1983 
GetStateManagerGL(const gl::Context * context)1984 StateManagerGL *GetStateManagerGL(const gl::Context *context)
1985 {
1986     return GetImplAs<ContextGL>(context)->getStateManager();
1987 }
1988 
GetBlitGL(const gl::Context * context)1989 BlitGL *GetBlitGL(const gl::Context *context)
1990 {
1991     return GetImplAs<ContextGL>(context)->getBlitter();
1992 }
1993 
GetMultiviewClearer(const gl::Context * context)1994 ClearMultiviewGL *GetMultiviewClearer(const gl::Context *context)
1995 {
1996     return GetImplAs<ContextGL>(context)->getMultiviewClearer();
1997 }
1998 
GetFeaturesGL(const gl::Context * context)1999 const angle::FeaturesGL &GetFeaturesGL(const gl::Context *context)
2000 {
2001     return GetImplAs<ContextGL>(context)->getFeaturesGL();
2002 }
2003 
ClearErrors(const gl::Context * context,const char * file,const char * function,unsigned int line)2004 void ClearErrors(const gl::Context *context,
2005                  const char *file,
2006                  const char *function,
2007                  unsigned int line)
2008 {
2009     const FunctionsGL *functions = GetFunctionsGL(context);
2010 
2011     GLenum error = functions->getError();
2012     while (error != GL_NO_ERROR)
2013     {
2014         ERR() << "Preexisting GL error " << gl::FmtHex(error) << " as of " << file << ", "
2015               << function << ":" << line << ". ";
2016         error = functions->getError();
2017     }
2018 }
2019 
CheckError(const gl::Context * context,const char * call,const char * file,const char * function,unsigned int line)2020 angle::Result CheckError(const gl::Context *context,
2021                          const char *call,
2022                          const char *file,
2023                          const char *function,
2024                          unsigned int line)
2025 {
2026     const FunctionsGL *functions = GetFunctionsGL(context);
2027 
2028     GLenum error = functions->getError();
2029     if (ANGLE_UNLIKELY(error != GL_NO_ERROR))
2030     {
2031         ContextGL *contextGL = GetImplAs<ContextGL>(context);
2032         contextGL->handleError(error, "Unexpected driver error.", file, function, line);
2033         ERR() << "GL call " << call << " generated error " << gl::FmtHex(error) << " in " << file
2034               << ", " << function << ":" << line << ". ";
2035 
2036         // Check that only one GL error was generated, ClearErrors should have been called first.
2037         // Skip GL_CONTEXT_LOST errors, they will be generated continuously and result in an
2038         // infinite loop.
2039         GLenum nextError = functions->getError();
2040         while (nextError != GL_NO_ERROR && nextError != GL_CONTEXT_LOST)
2041         {
2042             ERR() << "Additional GL error " << gl::FmtHex(nextError) << " generated.";
2043             nextError = functions->getError();
2044         }
2045 
2046         return angle::Result::Stop;
2047     }
2048 
2049     return angle::Result::Continue;
2050 }
2051 
CanMapBufferForRead(const FunctionsGL * functions)2052 bool CanMapBufferForRead(const FunctionsGL *functions)
2053 {
2054     return (functions->mapBufferRange != nullptr) ||
2055            (functions->mapBuffer != nullptr && functions->standard == STANDARD_GL_DESKTOP);
2056 }
2057 
MapBufferRangeWithFallback(const FunctionsGL * functions,GLenum target,size_t offset,size_t length,GLbitfield access)2058 uint8_t *MapBufferRangeWithFallback(const FunctionsGL *functions,
2059                                     GLenum target,
2060                                     size_t offset,
2061                                     size_t length,
2062                                     GLbitfield access)
2063 {
2064     if (functions->mapBufferRange != nullptr)
2065     {
2066         return static_cast<uint8_t *>(functions->mapBufferRange(target, offset, length, access));
2067     }
2068     else if (functions->mapBuffer != nullptr &&
2069              (functions->standard == STANDARD_GL_DESKTOP || access == GL_MAP_WRITE_BIT))
2070     {
2071         // Only the read and write bits are supported
2072         ASSERT((access & (GL_MAP_READ_BIT | GL_MAP_WRITE_BIT)) != 0);
2073 
2074         GLenum accessEnum = 0;
2075         if (access == (GL_MAP_READ_BIT | GL_MAP_WRITE_BIT))
2076         {
2077             accessEnum = GL_READ_WRITE;
2078         }
2079         else if (access == GL_MAP_READ_BIT)
2080         {
2081             accessEnum = GL_READ_ONLY;
2082         }
2083         else if (access == GL_MAP_WRITE_BIT)
2084         {
2085             accessEnum = GL_WRITE_ONLY;
2086         }
2087         else
2088         {
2089             UNREACHABLE();
2090             return nullptr;
2091         }
2092 
2093         return static_cast<uint8_t *>(functions->mapBuffer(target, accessEnum)) + offset;
2094     }
2095     else
2096     {
2097         // No options available
2098         UNREACHABLE();
2099         return nullptr;
2100     }
2101 }
2102 
ShouldApplyLastRowPaddingWorkaround(ContextGL * contextGL,const gl::Extents & size,const gl::PixelStoreStateBase & state,const gl::Buffer * pixelBuffer,GLenum format,GLenum type,bool is3D,const void * pixels,bool * shouldApplyOut)2103 angle::Result ShouldApplyLastRowPaddingWorkaround(ContextGL *contextGL,
2104                                                   const gl::Extents &size,
2105                                                   const gl::PixelStoreStateBase &state,
2106                                                   const gl::Buffer *pixelBuffer,
2107                                                   GLenum format,
2108                                                   GLenum type,
2109                                                   bool is3D,
2110                                                   const void *pixels,
2111                                                   bool *shouldApplyOut)
2112 {
2113     if (pixelBuffer == nullptr)
2114     {
2115         *shouldApplyOut = false;
2116         return angle::Result::Continue;
2117     }
2118 
2119     // We are using an pack or unpack buffer, compute what the driver thinks is going to be the
2120     // last byte read or written. If it is past the end of the buffer, we will need to use the
2121     // workaround otherwise the driver will generate INVALID_OPERATION and not do the operation.
2122 
2123     const gl::InternalFormat &glFormat = gl::GetInternalFormatInfo(format, type);
2124     GLuint endByte                     = 0;
2125     ANGLE_CHECK_GL_MATH(contextGL,
2126                         glFormat.computePackUnpackEndByte(type, size, state, is3D, &endByte));
2127     GLuint rowPitch = 0;
2128     ANGLE_CHECK_GL_MATH(contextGL, glFormat.computeRowPitch(type, size.width, state.alignment,
2129                                                             state.rowLength, &rowPitch));
2130 
2131     CheckedNumeric<size_t> checkedPixelBytes = glFormat.computePixelBytes(type);
2132     CheckedNumeric<size_t> checkedEndByte =
2133         angle::CheckedNumeric<size_t>(endByte) + reinterpret_cast<intptr_t>(pixels);
2134 
2135     // At this point checkedEndByte is the actual last byte read.
2136     // The driver adds an extra row padding (if any), mimic it.
2137     ANGLE_CHECK_GL_MATH(contextGL, checkedPixelBytes.IsValid());
2138     if (checkedPixelBytes.ValueOrDie() * size.width < rowPitch)
2139     {
2140         checkedEndByte += rowPitch - checkedPixelBytes * size.width;
2141     }
2142 
2143     ANGLE_CHECK_GL_MATH(contextGL, checkedEndByte.IsValid());
2144 
2145     *shouldApplyOut = checkedEndByte.ValueOrDie() > static_cast<size_t>(pixelBuffer->getSize());
2146     return angle::Result::Continue;
2147 }
2148 
GenerateContextCreationToTry(EGLint requestedType,bool isMesaGLX)2149 std::vector<ContextCreationTry> GenerateContextCreationToTry(EGLint requestedType, bool isMesaGLX)
2150 {
2151     using Type                         = ContextCreationTry::Type;
2152     constexpr EGLint kPlatformOpenGL   = EGL_PLATFORM_ANGLE_TYPE_OPENGL_ANGLE;
2153     constexpr EGLint kPlatformOpenGLES = EGL_PLATFORM_ANGLE_TYPE_OPENGLES_ANGLE;
2154 
2155     std::vector<ContextCreationTry> contextsToTry;
2156 
2157     if (requestedType == EGL_PLATFORM_ANGLE_TYPE_DEFAULT_ANGLE || requestedType == kPlatformOpenGL)
2158     {
2159         contextsToTry.emplace_back(kPlatformOpenGL, Type::DESKTOP_CORE, gl::Version(4, 5));
2160         contextsToTry.emplace_back(kPlatformOpenGL, Type::DESKTOP_CORE, gl::Version(4, 4));
2161         contextsToTry.emplace_back(kPlatformOpenGL, Type::DESKTOP_CORE, gl::Version(4, 3));
2162         contextsToTry.emplace_back(kPlatformOpenGL, Type::DESKTOP_CORE, gl::Version(4, 2));
2163         contextsToTry.emplace_back(kPlatformOpenGL, Type::DESKTOP_CORE, gl::Version(4, 1));
2164         contextsToTry.emplace_back(kPlatformOpenGL, Type::DESKTOP_CORE, gl::Version(4, 0));
2165         contextsToTry.emplace_back(kPlatformOpenGL, Type::DESKTOP_CORE, gl::Version(3, 3));
2166         contextsToTry.emplace_back(kPlatformOpenGL, Type::DESKTOP_CORE, gl::Version(3, 2));
2167         contextsToTry.emplace_back(kPlatformOpenGL, Type::DESKTOP_LEGACY, gl::Version(3, 3));
2168 
2169         // On Mesa, do not try to create OpenGL context versions between 3.0 and
2170         // 3.2 because of compatibility problems. See crbug.com/659030
2171         if (!isMesaGLX)
2172         {
2173             contextsToTry.emplace_back(kPlatformOpenGL, Type::DESKTOP_LEGACY, gl::Version(3, 2));
2174             contextsToTry.emplace_back(kPlatformOpenGL, Type::DESKTOP_LEGACY, gl::Version(3, 1));
2175             contextsToTry.emplace_back(kPlatformOpenGL, Type::DESKTOP_LEGACY, gl::Version(3, 0));
2176         }
2177 
2178         contextsToTry.emplace_back(kPlatformOpenGL, Type::DESKTOP_LEGACY, gl::Version(2, 1));
2179         contextsToTry.emplace_back(kPlatformOpenGL, Type::DESKTOP_LEGACY, gl::Version(2, 0));
2180         contextsToTry.emplace_back(kPlatformOpenGL, Type::DESKTOP_LEGACY, gl::Version(1, 5));
2181         contextsToTry.emplace_back(kPlatformOpenGL, Type::DESKTOP_LEGACY, gl::Version(1, 4));
2182         contextsToTry.emplace_back(kPlatformOpenGL, Type::DESKTOP_LEGACY, gl::Version(1, 3));
2183         contextsToTry.emplace_back(kPlatformOpenGL, Type::DESKTOP_LEGACY, gl::Version(1, 2));
2184         contextsToTry.emplace_back(kPlatformOpenGL, Type::DESKTOP_LEGACY, gl::Version(1, 1));
2185         contextsToTry.emplace_back(kPlatformOpenGL, Type::DESKTOP_LEGACY, gl::Version(1, 0));
2186     }
2187 
2188     if (requestedType == EGL_PLATFORM_ANGLE_TYPE_DEFAULT_ANGLE ||
2189         requestedType == kPlatformOpenGLES)
2190     {
2191         contextsToTry.emplace_back(kPlatformOpenGLES, Type::ES, gl::Version(3, 2));
2192         contextsToTry.emplace_back(kPlatformOpenGLES, Type::ES, gl::Version(3, 1));
2193         contextsToTry.emplace_back(kPlatformOpenGLES, Type::ES, gl::Version(3, 0));
2194         contextsToTry.emplace_back(kPlatformOpenGLES, Type::ES, gl::Version(2, 0));
2195     }
2196 
2197     return contextsToTry;
2198 }
2199 }  // namespace rx
2200