0031596: Visualization, OpenGl_Context - take GL_OES_texture_float extension into...
[occt.git] / src / OpenGl / OpenGl_Context.cxx
CommitLineData
6aca4d39 1// Created on: 2012-01-26
b311480e 2// Created by: Kirill GAVRILOV
6aca4d39 3// Copyright (c) 2012-2014 OPEN CASCADE SAS
b311480e 4//
973c2be1 5// This file is part of Open CASCADE Technology software library.
b311480e 6//
d5f74e42 7// This library is free software; you can redistribute it and/or modify it under
8// the terms of the GNU Lesser General Public License version 2.1 as published
973c2be1 9// by the Free Software Foundation, with special exception defined in the file
10// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
11// distribution for complete text of the license and disclaimer of any warranty.
b311480e 12//
973c2be1 13// Alternatively, this file may be used under the terms of Open CASCADE
14// commercial license or contractual agreement.
b311480e 15
58655684 16#if defined(_WIN32)
5f8b738e 17 #include <windows.h>
18#endif
19
2166f0fa
SK
20#include <OpenGl_Context.hxx>
21
5e27df78 22#include <OpenGl_ArbTBO.hxx>
23#include <OpenGl_ArbIns.hxx>
58655684 24#include <OpenGl_ArbDbg.hxx>
01ca42b2 25#include <OpenGl_ArbFBO.hxx>
37eb4787 26#include <OpenGl_ExtGS.hxx>
cc8cbabe 27#include <OpenGl_ArbSamplerObject.hxx>
25ef750e 28#include <OpenGl_ArbTexBindless.hxx>
9491df8c 29#include <OpenGl_GlCore45.hxx>
a2e4f780 30#include <OpenGl_FrameBuffer.hxx>
15669413 31#include <OpenGl_FrameStats.hxx>
25ef750e 32#include <OpenGl_Sampler.hxx>
30f0ad28 33#include <OpenGl_ShaderManager.hxx>
d850414a 34#include <OpenGl_TextureSetPairIterator.hxx>
299e0ab9 35#include <OpenGl_Workspace.hxx>
bf5f0ca2 36#include <OpenGl_Aspects.hxx>
158f2931 37
79f4f036 38#include <Graphic3d_TransformUtils.hxx>
56689b27 39#include <Graphic3d_RenderingParams.hxx>
faff3767 40#include <Image_SupportedFormats.hxx>
cbf18624 41#include <Message_Messenger.hxx>
a174a3c5 42#include <NCollection_Vector.hxx>
2bd4c032 43#include <Standard_ProgramError.hxx>
158f2931 44#include <Standard_WarningDisableFunctionCast.hxx>
2bd4c032 45
f5f4ebd0 46IMPLEMENT_STANDARD_RTTIEXT(OpenGl_Context,Standard_Transient)
47
da8bb41d 48#if defined(HAVE_EGL)
49 #include <EGL/egl.h>
50 #ifdef _MSC_VER
51 #pragma comment(lib, "libEGL.lib")
52 #endif
53#elif defined(_WIN32)
5f8b738e 54 //
55#elif defined(__APPLE__) && !defined(MACOSX_USE_GLX)
56 #include <dlfcn.h>
f978241f 57 #if defined(TARGET_OS_IPHONE) && TARGET_OS_IPHONE
58 //
59 #else
60 #include <OpenGL/OpenGL.h>
26d9c835 61 #include <CoreGraphics/CoreGraphics.h>
f978241f 62 #endif
5f8b738e 63#else
64 #include <GL/glx.h> // glXGetProcAddress()
65#endif
66
565baee6 67#ifdef __EMSCRIPTEN__
d4cefcc0 68 #include <emscripten.h>
565baee6 69 #include <emscripten/html5.h>
70
71 //! Check if WebGL extension is available and activate it
72 //! (usage of extension without activation will generate errors).
73 static bool checkEnableWebGlExtension (const OpenGl_Context& theCtx,
74 const char* theExtName)
75 {
76 if (!theCtx.CheckExtension (theExtName))
77 {
78 return false;
79 }
80 if (EMSCRIPTEN_WEBGL_CONTEXT_HANDLE aWebGlCtx = emscripten_webgl_get_current_context())
81 {
82 if (emscripten_webgl_enable_extension (aWebGlCtx, theExtName))
83 {
84 return true;
85 }
86 }
87 return false;
88 }
89#endif
90
5e27df78 91namespace
92{
93 static const Handle(OpenGl_Resource) NULL_GL_RESOURCE;
458e3c0d 94 static const OpenGl_Mat4 THE_IDENTITY_MATRIX;
26d9c835 95
96 //! Add key-value pair to the dictionary.
97 static void addInfo (TColStd_IndexedDataMapOfStringString& theDict,
98 const TCollection_AsciiString& theKey,
99 const TCollection_AsciiString& theValue)
100 {
101 theDict.ChangeFromIndex (theDict.Add (theKey, theValue)) = theValue;
102 }
103
104 //! Add key-value pair to the dictionary.
105 static void addInfo (TColStd_IndexedDataMapOfStringString& theDict,
106 const TCollection_AsciiString& theKey,
107 const char* theValue)
108 {
109 TCollection_AsciiString aValue (theValue != NULL ? theValue : "");
110 theDict.ChangeFromIndex (theDict.Add (theKey, aValue)) = aValue;
111 }
01ca42b2 112}
5e27df78 113
2166f0fa
SK
114// =======================================================================
115// function : OpenGl_Context
116// purpose :
117// =======================================================================
58655684 118OpenGl_Context::OpenGl_Context (const Handle(OpenGl_Caps)& theCaps)
01ca42b2 119: core11 (NULL),
120 core11fwd (NULL),
121 core15 (NULL),
122 core15fwd (NULL),
123 core20 (NULL),
124 core20fwd (NULL),
872f98d9 125 core30 (NULL),
126 core30fwd (NULL),
01ca42b2 127 core32 (NULL),
128 core32back (NULL),
25ef750e 129 core33 (NULL),
130 core33back (NULL),
01ca42b2 131 core41 (NULL),
132 core41back (NULL),
133 core42 (NULL),
134 core42back (NULL),
135 core43 (NULL),
136 core43back (NULL),
137 core44 (NULL),
138 core44back (NULL),
9491df8c 139 core45 (NULL),
140 core45back (NULL),
58655684 141 caps (!theCaps.IsNull() ? theCaps : new OpenGl_Caps()),
d4cefcc0 142 hasGetBufferData (Standard_False),
ca3c13d1 143#if defined(GL_ES_VERSION_2_0)
144 hasHighp (Standard_False),
e99a2f7c 145 hasUintIndex(Standard_False),
ca3c13d1 146 hasTexRGBA8(Standard_False),
147#else
148 hasHighp (Standard_True),
e99a2f7c 149 hasUintIndex(Standard_True),
ca3c13d1 150 hasTexRGBA8(Standard_True),
ba00aab7 151#endif
67312b79 152 hasTexFloatLinear (Standard_False),
ba00aab7 153 hasTexSRGB (Standard_False),
154 hasFboSRGB (Standard_False),
155 hasSRGBControl (Standard_False),
156#if defined(GL_ES_VERSION_2_0)
157 hasFlatShading (OpenGl_FeatureNotAvailable),
158#else
c39bb31b 159 hasFlatShading (OpenGl_FeatureInCore),
ca3c13d1 160#endif
59515ca6 161 hasGlslBitwiseOps (OpenGl_FeatureNotAvailable),
a1073ae2 162 hasDrawBuffers (OpenGl_FeatureNotAvailable),
163 hasFloatBuffer (OpenGl_FeatureNotAvailable),
164 hasHalfFloatBuffer (OpenGl_FeatureNotAvailable),
165 hasSampleVariables (OpenGl_FeatureNotAvailable),
2a332745 166 hasGeometryStage (OpenGl_FeatureNotAvailable),
a1073ae2 167 arbDrawBuffers (Standard_False),
25ef750e 168 arbNPTW (Standard_False),
169 arbTexRG (Standard_False),
74fb257d 170 arbTexFloat (Standard_False),
cc8cbabe 171 arbSamplerObject (NULL),
25ef750e 172 arbTexBindless (NULL),
5e27df78 173 arbTBO (NULL),
25ef750e 174 arbTboRGB32 (Standard_False),
5e27df78 175 arbIns (NULL),
58655684 176 arbDbg (NULL),
01ca42b2 177 arbFBO (NULL),
b86bb3df 178 arbFBOBlit (NULL),
a1073ae2 179 arbSampleShading (Standard_False),
1ce0716b 180 extFragDepth (Standard_False),
a1073ae2 181 extDrawBuffers (Standard_False),
37eb4787 182 extGS (NULL),
bf75be98 183 extBgra(Standard_False),
184 extAnis(Standard_False),
30f0ad28 185 extPDS (Standard_False),
f0430952 186 atiMem (Standard_False),
187 nvxMem (Standard_False),
a1073ae2 188 oesSampleVariables (Standard_False),
8c3237d4 189 oesStdDerivatives (Standard_False),
5e27df78 190 mySharedResources (new OpenGl_ResourcesMap()),
a174a3c5 191 myDelayed (new OpenGl_DelayReleaseMap()),
3125ebb6 192 myUnusedResources (new OpenGl_ResourcesStack()),
4269bd1b 193 myClippingState (),
5f8b738e 194 myGlLibHandle (NULL),
01ca42b2 195 myFuncs (new OpenGl_GlFunctions()),
faff3767 196 mySupportedFormats (new Image_SupportedFormats()),
2f6cb3ac 197 myAnisoMax (1),
ca3c13d1 198 myTexClamp (GL_CLAMP_TO_EDGE),
eafb234b 199 myMaxTexDim (1024),
cc8cbabe 200 myMaxTexCombined (1),
5c225e8e 201 myMaxTexUnitsFFP (1),
6997ff1c 202 myMaxDumpSizeX (1024),
203 myMaxDumpSizeY (1024),
4269bd1b 204 myMaxClipPlanes (6),
3c4b62a4 205 myMaxMsaaSamples(0),
a1073ae2 206 myMaxDrawBuffers (1),
207 myMaxColorAttachments (1),
5f8b738e 208 myGlVerMajor (0),
209 myGlVerMinor (0),
b5ac8292 210 myIsInitialized (Standard_False),
211 myIsStereoBuffers (Standard_False),
7d9e854b 212 myIsGlNormalizeEnabled (Standard_False),
72f6dc61 213 mySpriteTexUnit (Graphic3d_TextureUnit_PointSprite),
3a9b5dc8 214 myHasRayTracing (Standard_False),
215 myHasRayTracingTextures (Standard_False),
216 myHasRayTracingAdaptiveSampling (Standard_False),
e084dbbc 217 myHasRayTracingAdaptiveSamplingAtomic (Standard_False),
67312b79 218 myHasPBR (Standard_False),
72f6dc61 219 myPBREnvLUTTexUnit (Graphic3d_TextureUnit_PbrEnvironmentLUT),
220 myPBRDiffIBLMapSHTexUnit (Graphic3d_TextureUnit_PbrIblDiffuseSH),
221 myPBRSpecIBLMapTexUnit (Graphic3d_TextureUnit_PbrIblSpecular),
15669413 222 myFrameStats (new OpenGl_FrameStats()),
72f6dc61 223 myActiveMockTextures (0),
ca3c13d1 224#if !defined(GL_ES_VERSION_2_0)
fd59283a 225 myPointSpriteOrig (GL_UPPER_LEFT),
7d3e64ef 226 myRenderMode (GL_RENDER),
08669adf 227 myShadeModel (GL_SMOOTH),
6d0e6be5 228 myPolygonMode (GL_FILL),
ca3c13d1 229#else
fd59283a 230 myPointSpriteOrig (0),
ca3c13d1 231 myRenderMode (0),
08669adf 232 myShadeModel (0),
6d0e6be5 233 myPolygonMode (0),
ca3c13d1 234#endif
b6472664 235 myToCullBackFaces (false),
38a0206f 236 myReadBuffer (0),
c3487460 237 myDrawBuffers (0, 7),
4e1523ef 238 myDefaultVao (0),
f88457e6 239 myColorMask (true),
c40eb6b9 240 myAlphaToCoverage (false),
ba00aab7 241 myIsGlDebugCtx (false),
242 myIsSRgbWindow (false),
56689b27 243 myResolution (Graphic3d_RenderingParams::THE_DEFAULT_RESOLUTION),
244 myResolutionRatio (1.0f),
245 myLineWidthScale (1.0f),
2a332745 246 myLineFeather (1.0f),
56689b27 247 myRenderScale (1.0f),
248 myRenderScaleInv (1.0f)
2166f0fa 249{
3bffef55 250 myViewport[0] = 0;
251 myViewport[1] = 0;
252 myViewport[2] = 0;
253 myViewport[3] = 0;
56689b27 254 myViewportVirt[0] = 0;
255 myViewportVirt[1] = 0;
256 myViewportVirt[2] = 0;
257 myViewportVirt[3] = 0;
3bffef55 258
8d1a539c 259 myPolygonOffset.Mode = Aspect_POM_Off;
260 myPolygonOffset.Factor = 0.0f;
261 myPolygonOffset.Units = 0.0f;
262
4e1523ef 263 // system-dependent fields
264#if defined(HAVE_EGL)
265 myDisplay = (Aspect_Display )EGL_NO_DISPLAY;
266 myWindow = (Aspect_Drawable )EGL_NO_SURFACE;
458c2c58 267 myGContext = (Aspect_RenderingContext )EGL_NO_CONTEXT;
4e1523ef 268#elif defined(_WIN32)
269 myWindow = NULL;
270 myWindowDC = NULL;
271 myGContext = NULL;
272#elif defined(__APPLE__) && !defined(MACOSX_USE_GLX)
5f8b738e 273 // Vendors can not extend functionality on this system
274 // and developers are limited to OpenGL support provided by Mac OS X SDK.
275 // We retrieve function pointers from system library
276 // to generalize extensions support on all platforms.
277 // In this way we also reach binary compatibility benefit between OS releases
278 // if some newest functionality is optionally used.
279 // Notice that GL version / extension availability checks are required
280 // because function pointers may be available but not functionality itself
281 // (depends on renderer).
a2e4f780 282#if defined(TARGET_OS_IPHONE) && TARGET_OS_IPHONE
283 myGContext = NULL;
284 myGlLibHandle = dlopen ("/System/Library/Frameworks/OpenGLES.framework/OpenGLES", RTLD_LAZY);
285#else
4e1523ef 286 myGContext = NULL;
5f8b738e 287 myGlLibHandle = dlopen ("/System/Library/Frameworks/OpenGL.framework/Versions/Current/OpenGL", RTLD_LAZY);
a2e4f780 288#endif
4e1523ef 289#else
290 myDisplay = NULL;
291 myWindow = 0;
292 myGContext = 0;
5f8b738e 293#endif
a2e4f780 294
01ca42b2 295 memset (myFuncs.operator->(), 0, sizeof(OpenGl_GlFunctions));
30f0ad28 296 myShaderManager = new OpenGl_ShaderManager (this);
2166f0fa
SK
297}
298
299// =======================================================================
300// function : ~OpenGl_Context
301// purpose :
302// =======================================================================
303OpenGl_Context::~OpenGl_Context()
304{
5e27df78 305 // release clean up queue
306 ReleaseDelayed();
307
4e1523ef 308#if !defined(GL_ES_VERSION_2_0)
309 // release default VAO
310 if (myDefaultVao != 0
311 && IsValid()
312 && core32 != NULL)
313 {
314 core32->glDeleteVertexArrays (1, &myDefaultVao);
315 }
316 myDefaultVao = 0;
317#endif
318
72f6dc61 319 // release mock textures
320 if (!myTextureRgbaBlack.IsNull())
321 {
322 myTextureRgbaBlack->Release (this);
323 myTextureRgbaBlack.Nullify();
324 }
325 if (!myTextureRgbaWhite.IsNull())
326 {
327 myTextureRgbaWhite->Release (this);
328 myTextureRgbaWhite.Nullify();
329 }
330
a2e4f780 331 // release default FBO
332 if (!myDefaultFbo.IsNull())
333 {
334 myDefaultFbo->Release (this);
335 myDefaultFbo.Nullify();
336 }
337
5e27df78 338 // release shared resources if any
4796758e 339 if (mySharedResources->GetRefCount() <= 1)
5e27df78 340 {
392ac980 341 myShaderManager.Nullify();
5e27df78 342 for (NCollection_DataMap<TCollection_AsciiString, Handle(OpenGl_Resource)>::Iterator anIter (*mySharedResources);
343 anIter.More(); anIter.Next())
344 {
345 anIter.Value()->Release (this);
346 }
e1c659da 347
348 // release delayed resources added during deletion of shared resources
349 while (!myUnusedResources->IsEmpty())
350 {
351 myUnusedResources->First()->Release (this);
352 myUnusedResources->RemoveFirst();
353 }
5e27df78 354 }
c357e426 355 else if (myShaderManager->IsSameContext (this))
392ac980 356 {
357 myShaderManager->SetContext (NULL);
358 }
5e27df78 359 mySharedResources.Nullify();
a174a3c5 360 myDelayed.Nullify();
5e27df78 361
cbf18624 362 if (arbDbg != NULL
4e1523ef 363 && myIsGlDebugCtx
f8c8ba7a 364 && IsValid())
cbf18624 365 {
366 // reset callback
0deb6f04 367 #if !defined(GL_ES_VERSION_2_0)
cbf18624 368 void* aPtr = NULL;
3b523c4c 369 glGetPointerv (GL_DEBUG_CALLBACK_USER_PARAM, &aPtr);
cbf18624 370 if (aPtr == this)
0deb6f04 371 #endif
cbf18624 372 {
0deb6f04 373 arbDbg->glDebugMessageCallback (NULL, NULL);
cbf18624 374 }
4e1523ef 375 myIsGlDebugCtx = Standard_False;
cbf18624 376 }
5f8b738e 377}
378
379// =======================================================================
05e2200b 380// function : forcedRelease
381// purpose :
382// =======================================================================
383void OpenGl_Context::forcedRelease()
384{
385 ReleaseDelayed();
386 for (NCollection_DataMap<TCollection_AsciiString, Handle(OpenGl_Resource)>::Iterator anIter (*mySharedResources);
387 anIter.More(); anIter.Next())
388 {
389 anIter.Value()->Release (this);
390 }
391 mySharedResources->Clear();
392 myShaderManager->clear();
393 myShaderManager->SetContext (NULL);
e1c659da 394
395 // release delayed resources added during deletion of shared resources
396 while (!myUnusedResources->IsEmpty())
397 {
398 myUnusedResources->First()->Release (this);
399 myUnusedResources->RemoveFirst();
400 }
05e2200b 401}
402
3bffef55 403// =======================================================================
404// function : ResizeViewport
405// purpose :
406// =======================================================================
407void OpenGl_Context::ResizeViewport (const Standard_Integer* theRect)
408{
409 core11fwd->glViewport (theRect[0], theRect[1], theRect[2], theRect[3]);
410 myViewport[0] = theRect[0];
411 myViewport[1] = theRect[1];
412 myViewport[2] = theRect[2];
413 myViewport[3] = theRect[3];
56689b27 414 if (HasRenderScale())
415 {
416 myViewportVirt[0] = Standard_Integer(theRect[0] * myRenderScaleInv);
417 myViewportVirt[1] = Standard_Integer(theRect[1] * myRenderScaleInv);
418 myViewportVirt[2] = Standard_Integer(theRect[2] * myRenderScaleInv);
419 myViewportVirt[3] = Standard_Integer(theRect[3] * myRenderScaleInv);
420 }
421 else
422 {
423 myViewportVirt[0] = theRect[0];
424 myViewportVirt[1] = theRect[1];
425 myViewportVirt[2] = theRect[2];
426 myViewportVirt[3] = theRect[3];
427 }
3bffef55 428}
429
ca3c13d1 430#if !defined(GL_ES_VERSION_2_0)
38a0206f 431inline Standard_Integer stereoToMonoBuffer (const Standard_Integer theBuffer)
432{
433 switch (theBuffer)
b5ac8292 434 {
38a0206f 435 case GL_BACK_LEFT:
436 case GL_BACK_RIGHT:
437 return GL_BACK;
438 case GL_FRONT_LEFT:
439 case GL_FRONT_RIGHT:
440 return GL_FRONT;
441 default:
442 return theBuffer;
b5ac8292 443 }
444}
38a0206f 445#endif
b5ac8292 446
447// =======================================================================
38a0206f 448// function : SetReadBuffer
b5ac8292 449// purpose :
450// =======================================================================
38a0206f 451void OpenGl_Context::SetReadBuffer (const Standard_Integer theReadBuffer)
b5ac8292 452{
ca3c13d1 453#if !defined(GL_ES_VERSION_2_0)
38a0206f 454 myReadBuffer = !myIsStereoBuffers ? stereoToMonoBuffer (theReadBuffer) : theReadBuffer;
455 if (myReadBuffer < GL_COLOR_ATTACHMENT0
456 && arbFBO != NULL)
b5ac8292 457 {
38a0206f 458 arbFBO->glBindFramebuffer (GL_FRAMEBUFFER, OpenGl_FrameBuffer::NO_FRAMEBUFFER);
b5ac8292 459 }
38a0206f 460 ::glReadBuffer (myReadBuffer);
461#else
462 (void )theReadBuffer;
ca3c13d1 463#endif
b5ac8292 464}
465
466// =======================================================================
38a0206f 467// function : SetDrawBuffer
b5ac8292 468// purpose :
469// =======================================================================
38a0206f 470void OpenGl_Context::SetDrawBuffer (const Standard_Integer theDrawBuffer)
b5ac8292 471{
ca3c13d1 472#if !defined(GL_ES_VERSION_2_0)
a1073ae2 473 const Standard_Integer aDrawBuffer = !myIsStereoBuffers ? stereoToMonoBuffer (theDrawBuffer) : theDrawBuffer;
474 if (aDrawBuffer < GL_COLOR_ATTACHMENT0
38a0206f 475 && arbFBO != NULL)
b5ac8292 476 {
38a0206f 477 arbFBO->glBindFramebuffer (GL_FRAMEBUFFER, OpenGl_FrameBuffer::NO_FRAMEBUFFER);
b5ac8292 478 }
a1073ae2 479 ::glDrawBuffer (aDrawBuffer);
480
c3487460 481 myDrawBuffers.Init (GL_NONE);
482 myDrawBuffers.SetValue (0, aDrawBuffer);
38a0206f 483#else
484 (void )theDrawBuffer;
ca3c13d1 485#endif
b5ac8292 486}
487
488// =======================================================================
a1073ae2 489// function : SetDrawBuffers
490// purpose :
491// =======================================================================
492void OpenGl_Context::SetDrawBuffers (const Standard_Integer theNb, const Standard_Integer* theDrawBuffers)
493{
494 Standard_ASSERT_RETURN (hasDrawBuffers, "Multiple draw buffers feature is not supported by the context", Standard_ASSERT_DO_NOTHING());
495
c3487460 496 if (myDrawBuffers.Length() < theNb)
497 {
498 // should actually never happen here
499 myDrawBuffers.Resize (0, theNb - 1, false);
500 }
501 myDrawBuffers.Init (GL_NONE);
a1073ae2 502
503 Standard_Boolean useDefaultFbo = Standard_False;
504 for (Standard_Integer anI = 0; anI < theNb; ++anI)
505 {
b17e5bae 506 if (theDrawBuffers[anI] < GL_COLOR_ATTACHMENT0 && theDrawBuffers[anI] != GL_NONE)
a1073ae2 507 {
508 useDefaultFbo = Standard_True;
509 }
c3487460 510 else
a1073ae2 511 {
b17e5bae 512 myDrawBuffers.SetValue (anI, theDrawBuffers[anI]);
a1073ae2 513 }
514 }
515 if (arbFBO != NULL && useDefaultFbo)
516 {
517 arbFBO->glBindFramebuffer (GL_FRAMEBUFFER, OpenGl_FrameBuffer::NO_FRAMEBUFFER);
518 }
519
520 myFuncs->glDrawBuffers (theNb, (const GLenum*)theDrawBuffers);
521}
522
523// =======================================================================
ba00aab7 524// function : SetFrameBufferSRGB
525// purpose :
526// =======================================================================
e5c11edd 527void OpenGl_Context::SetFrameBufferSRGB (bool theIsFbo, bool theIsFboSRgb)
ba00aab7 528{
529 if (!hasFboSRGB)
530 {
531 myIsSRgbActive = false;
532 return;
533 }
534 myIsSRgbActive = ToRenderSRGB()
e5c11edd 535 && (theIsFbo || myIsSRgbWindow)
536 && theIsFboSRgb;
ba00aab7 537 if (!hasSRGBControl)
538 {
539 return;
540 }
541
542 if (myIsSRgbActive)
543 {
544 core11fwd->glEnable (GL_FRAMEBUFFER_SRGB);
545 }
546 else
547 {
548 core11fwd->glDisable (GL_FRAMEBUFFER_SRGB);
549 }
550}
551
552// =======================================================================
b6472664 553// function : SetCullBackFaces
554// purpose :
555// =======================================================================
556void OpenGl_Context::SetCullBackFaces (bool theToEnable)
557{
558 if (myToCullBackFaces == theToEnable)
559 {
560 return;
561 }
562
563 myToCullBackFaces = theToEnable;
564 if (theToEnable)
565 {
566 //glCullFace (GL_BACK); GL_BACK by default
567 core11fwd->glEnable (GL_CULL_FACE);
568 }
569 else
570 {
571 core11fwd->glDisable (GL_CULL_FACE);
572 }
573}
574
575// =======================================================================
b5ac8292 576// function : FetchState
577// purpose :
578// =======================================================================
579void OpenGl_Context::FetchState()
580{
ca3c13d1 581#if !defined(GL_ES_VERSION_2_0)
b5ac8292 582 // cache feedback mode state
4e1523ef 583 if (core11 != NULL)
584 {
585 ::glGetIntegerv (GL_RENDER_MODE, &myRenderMode);
08669adf 586 ::glGetIntegerv (GL_SHADE_MODEL, &myShadeModel);
4e1523ef 587 }
b5ac8292 588
a1073ae2 589 // cache read buffers state
38a0206f 590 ::glGetIntegerv (GL_READ_BUFFER, &myReadBuffer);
a1073ae2 591
592 // cache draw buffers state
c3487460 593 if (myDrawBuffers.Length() < myMaxDrawBuffers)
594 {
595 myDrawBuffers.Resize (0, myMaxDrawBuffers - 1, false);
596 }
597 myDrawBuffers.Init (GL_NONE);
a1073ae2 598
c3487460 599 Standard_Integer aDrawBuffer = GL_NONE;
a1073ae2 600 if (myMaxDrawBuffers == 1)
601 {
a1073ae2 602 ::glGetIntegerv (GL_DRAW_BUFFER, &aDrawBuffer);
c3487460 603 myDrawBuffers.SetValue (0, aDrawBuffer);
a1073ae2 604 }
605 else
606 {
a1073ae2 607 for (Standard_Integer anI = 0; anI < myMaxDrawBuffers; ++anI)
608 {
609 ::glGetIntegerv (GL_DRAW_BUFFER0 + anI, &aDrawBuffer);
c3487460 610 myDrawBuffers.SetValue (anI, aDrawBuffer);
a1073ae2 611 }
612 }
ca3c13d1 613#endif
b5ac8292 614}
615
616// =======================================================================
5e27df78 617// function : Share
618// purpose :
619// =======================================================================
620void OpenGl_Context::Share (const Handle(OpenGl_Context)& theShareCtx)
621{
622 if (!theShareCtx.IsNull())
623 {
624 mySharedResources = theShareCtx->mySharedResources;
a174a3c5 625 myDelayed = theShareCtx->myDelayed;
3125ebb6 626 myUnusedResources = theShareCtx->myUnusedResources;
392ac980 627 myShaderManager = theShareCtx->myShaderManager;
5e27df78 628 }
629}
630
4fe56619 631#if !defined(__APPLE__) || defined(MACOSX_USE_GLX)
632
5e27df78 633// =======================================================================
86fa64d9 634// function : IsCurrent
635// purpose :
636// =======================================================================
637Standard_Boolean OpenGl_Context::IsCurrent() const
638{
da8bb41d 639#if defined(HAVE_EGL)
640 if ((EGLDisplay )myDisplay == EGL_NO_DISPLAY
da8bb41d 641 || (EGLContext )myGContext == EGL_NO_CONTEXT)
642 {
643 return Standard_False;
644 }
645
646 return (((EGLDisplay )myDisplay == eglGetCurrentDisplay())
647 && ((EGLContext )myGContext == eglGetCurrentContext())
648 && ((EGLSurface )myWindow == eglGetCurrentSurface (EGL_DRAW)));
649#elif defined(_WIN32)
86fa64d9 650 if (myWindowDC == NULL || myGContext == NULL)
651 {
652 return Standard_False;
653 }
654 return (( (HDC )myWindowDC == wglGetCurrentDC())
655 && ((HGLRC )myGContext == wglGetCurrentContext()));
656#else
657 if (myDisplay == NULL || myWindow == 0 || myGContext == 0)
658 {
659 return Standard_False;
660 }
661
662 return ( ((Display* )myDisplay == glXGetCurrentDisplay())
663 && ((GLXContext )myGContext == glXGetCurrentContext())
664 && ((GLXDrawable )myWindow == glXGetCurrentDrawable()));
665#endif
666}
667
668// =======================================================================
2bd4c032 669// function : MakeCurrent
670// purpose :
671// =======================================================================
672Standard_Boolean OpenGl_Context::MakeCurrent()
673{
da8bb41d 674#if defined(HAVE_EGL)
675 if ((EGLDisplay )myDisplay == EGL_NO_DISPLAY
da8bb41d 676 || (EGLContext )myGContext == EGL_NO_CONTEXT)
677 {
678 Standard_ProgramError_Raise_if (myIsInitialized, "OpenGl_Context::Init() should be called before!");
679 return Standard_False;
680 }
681
682 if (eglMakeCurrent ((EGLDisplay )myDisplay, (EGLSurface )myWindow, (EGLSurface )myWindow, (EGLContext )myGContext) != EGL_TRUE)
683 {
684 // if there is no current context it might be impossible to use glGetError() correctly
3b523c4c 685 PushMessage (GL_DEBUG_SOURCE_WINDOW_SYSTEM, GL_DEBUG_TYPE_ERROR, 0, GL_DEBUG_SEVERITY_HIGH,
da8bb41d 686 "eglMakeCurrent() has failed!");
687 myIsInitialized = Standard_False;
688 return Standard_False;
689 }
690#elif defined(_WIN32)
86fa64d9 691 if (myWindowDC == NULL || myGContext == NULL)
2bd4c032 692 {
86fa64d9 693 Standard_ProgramError_Raise_if (myIsInitialized, "OpenGl_Context::Init() should be called before!");
694 return Standard_False;
695 }
696
697 // technically it should be safe to activate already bound GL context
698 // however some drivers (Intel etc.) may FAIL doing this for unknown reason
699 if (IsCurrent())
700 {
392ac980 701 myShaderManager->SetContext (this);
86fa64d9 702 return Standard_True;
703 }
704 else if (wglMakeCurrent ((HDC )myWindowDC, (HGLRC )myGContext) != TRUE)
705 {
706 // notice that glGetError() couldn't be used here!
707 wchar_t* aMsgBuff = NULL;
708 DWORD anErrorCode = GetLastError();
709 FormatMessageW (FORMAT_MESSAGE_ALLOCATE_BUFFER | FORMAT_MESSAGE_FROM_SYSTEM | FORMAT_MESSAGE_IGNORE_INSERTS,
710 NULL, anErrorCode, MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT), (wchar_t* )&aMsgBuff, 0, NULL);
cbf18624 711 TCollection_ExtendedString aMsg ("wglMakeCurrent() has failed. ");
86fa64d9 712 if (aMsgBuff != NULL)
713 {
cbf18624 714 aMsg += (Standard_ExtString )aMsgBuff;
86fa64d9 715 LocalFree (aMsgBuff);
716 }
3b523c4c 717 PushMessage (GL_DEBUG_SOURCE_WINDOW_SYSTEM, GL_DEBUG_TYPE_ERROR, (unsigned int )anErrorCode, GL_DEBUG_SEVERITY_HIGH, aMsg);
fd4a6963 718 myIsInitialized = Standard_False;
2bd4c032 719 return Standard_False;
720 }
721#else
86fa64d9 722 if (myDisplay == NULL || myWindow == 0 || myGContext == 0)
723 {
724 Standard_ProgramError_Raise_if (myIsInitialized, "OpenGl_Context::Init() should be called before!");
725 return Standard_False;
726 }
727
728 if (!glXMakeCurrent ((Display* )myDisplay, (GLXDrawable )myWindow, (GLXContext )myGContext))
2bd4c032 729 {
730 // if there is no current context it might be impossible to use glGetError() correctly
3b523c4c 731 PushMessage (GL_DEBUG_SOURCE_WINDOW_SYSTEM, GL_DEBUG_TYPE_ERROR, 0, GL_DEBUG_SEVERITY_HIGH,
cbf18624 732 "glXMakeCurrent() has failed!");
fd4a6963 733 myIsInitialized = Standard_False;
2bd4c032 734 return Standard_False;
735 }
736#endif
392ac980 737 myShaderManager->SetContext (this);
2bd4c032 738 return Standard_True;
739}
740
741// =======================================================================
5e27df78 742// function : SwapBuffers
743// purpose :
744// =======================================================================
745void OpenGl_Context::SwapBuffers()
746{
da8bb41d 747#if defined(HAVE_EGL)
748 if ((EGLSurface )myWindow != EGL_NO_SURFACE)
749 {
750 eglSwapBuffers ((EGLDisplay )myDisplay, (EGLSurface )myWindow);
751 }
752#elif defined(_WIN32)
5e27df78 753 if ((HDC )myWindowDC != NULL)
754 {
755 ::SwapBuffers ((HDC )myWindowDC);
756 glFlush();
757 }
758#else
759 if ((Display* )myDisplay != NULL)
760 {
761 glXSwapBuffers ((Display* )myDisplay, (GLXDrawable )myWindow);
762 }
763#endif
764}
765
4fe56619 766#endif // __APPLE__
767
5e27df78 768// =======================================================================
f978241f 769// function : SetSwapInterval
770// purpose :
771// =======================================================================
772Standard_Boolean OpenGl_Context::SetSwapInterval (const Standard_Integer theInterval)
773{
774#if defined(HAVE_EGL)
775 if (::eglSwapInterval ((EGLDisplay )myDisplay, theInterval) == EGL_TRUE)
776 {
777 return Standard_True;
778 }
779#elif defined(_WIN32)
780 if (myFuncs->wglSwapIntervalEXT != NULL)
781 {
782 myFuncs->wglSwapIntervalEXT (theInterval);
783 return Standard_True;
784 }
785#elif defined(TARGET_OS_IPHONE) && TARGET_OS_IPHONE
786 //
787#elif defined(__APPLE__)
788 if (::CGLSetParameter (CGLGetCurrentContext(), kCGLCPSwapInterval, &theInterval) == kCGLNoError)
789 {
790 return Standard_True;
791 }
792#else
793 if (theInterval == -1
794 && myFuncs->glXSwapIntervalEXT != NULL)
795 {
796 typedef int (*glXSwapIntervalEXT_t_x)(Display* theDisplay, GLXDrawable theDrawable, int theInterval);
797 glXSwapIntervalEXT_t_x aFuncPtr = (glXSwapIntervalEXT_t_x )myFuncs->glXSwapIntervalEXT;
798 aFuncPtr ((Display* )myDisplay, (GLXDrawable )myWindow, theInterval);
799 return Standard_True;
800 }
801 else if (myFuncs->glXSwapIntervalSGI != NULL)
802 {
803 myFuncs->glXSwapIntervalSGI (theInterval);
804 return Standard_True;
805 }
806#endif
807 return Standard_False;
808}
809
810// =======================================================================
5f8b738e 811// function : findProc
812// purpose :
813// =======================================================================
814void* OpenGl_Context::findProc (const char* theFuncName)
815{
da8bb41d 816#if defined(HAVE_EGL)
817 return (void* )eglGetProcAddress (theFuncName);
818#elif defined(_WIN32)
7c65581d 819 return (void* )wglGetProcAddress (theFuncName);
5f8b738e 820#elif defined(__APPLE__) && !defined(MACOSX_USE_GLX)
821 return (myGlLibHandle != NULL) ? dlsym (myGlLibHandle, theFuncName) : NULL;
822#else
823 return (void* )glXGetProcAddress ((const GLubyte* )theFuncName);
824#endif
2166f0fa
SK
825}
826
827// =======================================================================
828// function : CheckExtension
829// purpose :
830// =======================================================================
2bd4c032 831Standard_Boolean OpenGl_Context::CheckExtension (const char* theExtName) const
2166f0fa 832{
5f8b738e 833 if (theExtName == NULL)
834 {
0797d9d3 835#ifdef OCCT_DEBUG
5f8b738e 836 std::cerr << "CheckExtension called with NULL string!\n";
63c629aa 837#endif
5f8b738e 838 return Standard_False;
839 }
59515ca6 840 else if (caps->contextNoExtensions)
841 {
842 return Standard_False;
843 }
5f8b738e 844
4e1523ef 845#if !defined(GL_ES_VERSION_2_0)
5f8b738e 846 // available since OpenGL 3.0
847 // and the ONLY way to check extensions with OpenGL 3.1+ core profile
4e1523ef 848 if (IsGlGreaterEqual (3, 0)
849 && myFuncs->glGetStringi != NULL)
5f8b738e 850 {
851 GLint anExtNb = 0;
4e1523ef 852 ::glGetIntegerv (GL_NUM_EXTENSIONS, &anExtNb);
853 const size_t anExtNameLen = strlen (theExtName);
5f8b738e 854 for (GLint anIter = 0; anIter < anExtNb; ++anIter)
855 {
4e1523ef 856 const char* anExtension = (const char* )myFuncs->glGetStringi (GL_EXTENSIONS, (GLuint )anIter);
857 const size_t aTestExtNameLen = strlen (anExtension);
858 if (aTestExtNameLen == anExtNameLen
859 && strncmp (anExtension, theExtName, anExtNameLen) == 0)
5f8b738e 860 {
861 return Standard_True;
862 }
863 }
864 return Standard_False;
4e1523ef 865 }
866#endif
5f8b738e 867
868 // use old way with huge string for all extensions
869 const char* anExtString = (const char* )glGetString (GL_EXTENSIONS);
870 if (anExtString == NULL)
871 {
7e7c2f0b 872 Messenger()->Send ("TKOpenGL: glGetString (GL_EXTENSIONS) has returned NULL! No GL context?", Message_Warning);
2166f0fa
SK
873 return Standard_False;
874 }
58655684 875 return CheckExtension (anExtString, theExtName);
876}
877
878// =======================================================================
879// function : CheckExtension
880// purpose :
881// =======================================================================
882Standard_Boolean OpenGl_Context::CheckExtension (const char* theExtString,
883 const char* theExtName)
884{
885 if (theExtString == NULL)
886 {
887 return Standard_False;
888 }
2166f0fa
SK
889
890 // Search for theExtName in the extensions string.
891 // Use of strstr() is not sufficient because extension names can be prefixes of other extension names.
58655684 892 char* aPtrIter = (char* )theExtString;
893 const char* aPtrEnd = aPtrIter + strlen (theExtString);
894 const size_t anExtNameLen = strlen (theExtName);
2166f0fa
SK
895 while (aPtrIter < aPtrEnd)
896 {
6a7d83c4 897 const size_t n = strcspn (aPtrIter, " ");
5f8b738e 898 if ((n == anExtNameLen) && (strncmp (aPtrIter, theExtName, anExtNameLen) == 0))
899 {
2166f0fa 900 return Standard_True;
5f8b738e 901 }
2166f0fa
SK
902 aPtrIter += (n + 1);
903 }
904 return Standard_False;
905}
906
4fe56619 907#if !defined(__APPLE__) || defined(MACOSX_USE_GLX)
908
2166f0fa
SK
909// =======================================================================
910// function : Init
911// purpose :
912// =======================================================================
4e1523ef 913Standard_Boolean OpenGl_Context::Init (const Standard_Boolean theIsCoreProfile)
2166f0fa 914{
2bd4c032 915 if (myIsInitialized)
5f8b738e 916 {
f0430952 917 return Standard_True;
5f8b738e 918 }
2bd4c032 919
da8bb41d 920#if defined(HAVE_EGL)
921 myDisplay = (Aspect_Display )eglGetCurrentDisplay();
922 myGContext = (Aspect_RenderingContext )eglGetCurrentContext();
923 myWindow = (Aspect_Drawable )eglGetCurrentSurface(EGL_DRAW);
924#elif defined(_WIN32)
2bd4c032 925 myWindowDC = (Aspect_Handle )wglGetCurrentDC();
926 myGContext = (Aspect_RenderingContext )wglGetCurrentContext();
927#else
928 myDisplay = (Aspect_Display )glXGetCurrentDisplay();
929 myGContext = (Aspect_RenderingContext )glXGetCurrentContext();
930 myWindow = (Aspect_Drawable )glXGetCurrentDrawable();
931#endif
f0430952 932 if (myGContext == NULL)
933 {
934 return Standard_False;
935 }
2bd4c032 936
4e1523ef 937 init (theIsCoreProfile);
2bd4c032 938 myIsInitialized = Standard_True;
f0430952 939 return Standard_True;
2bd4c032 940}
941
4fe56619 942#endif // __APPLE__
943
2bd4c032 944// =======================================================================
945// function : Init
946// purpose :
947// =======================================================================
da8bb41d 948#if defined(HAVE_EGL)
949Standard_Boolean OpenGl_Context::Init (const Aspect_Drawable theEglSurface,
950 const Aspect_Display theEglDisplay,
4e1523ef 951 const Aspect_RenderingContext theEglContext,
952 const Standard_Boolean theIsCoreProfile)
da8bb41d 953#elif defined(_WIN32)
f0430952 954Standard_Boolean OpenGl_Context::Init (const Aspect_Handle theWindow,
955 const Aspect_Handle theWindowDC,
4e1523ef 956 const Aspect_RenderingContext theGContext,
957 const Standard_Boolean theIsCoreProfile)
4fe56619 958#elif defined(__APPLE__) && !defined(MACOSX_USE_GLX)
a2e4f780 959
960#if defined(TARGET_OS_IPHONE) && TARGET_OS_IPHONE
961Standard_Boolean OpenGl_Context::Init (EAGLContext* theGContext,
4e1523ef 962 const Standard_Boolean theIsCoreProfile)
2bd4c032 963#else
a2e4f780 964Standard_Boolean OpenGl_Context::Init (NSOpenGLContext* theGContext,
965 const Standard_Boolean theIsCoreProfile)
966#endif
967
968#else
f0430952 969Standard_Boolean OpenGl_Context::Init (const Aspect_Drawable theWindow,
970 const Aspect_Display theDisplay,
4e1523ef 971 const Aspect_RenderingContext theGContext,
972 const Standard_Boolean theIsCoreProfile)
2bd4c032 973#endif
974{
975 Standard_ProgramError_Raise_if (myIsInitialized, "OpenGl_Context::Init() should be called only once!");
da8bb41d 976#if defined(HAVE_EGL)
977 myWindow = theEglSurface;
978 myGContext = theEglContext;
979 myDisplay = theEglDisplay;
980#elif defined(_WIN32)
2bd4c032 981 myWindow = theWindow;
982 myGContext = theGContext;
2bd4c032 983 myWindowDC = theWindowDC;
4fe56619 984#elif defined(__APPLE__) && !defined(MACOSX_USE_GLX)
a2e4f780 985 myGContext = theGContext;
2bd4c032 986#else
4fe56619 987 myWindow = theWindow;
988 myGContext = theGContext;
2bd4c032 989 myDisplay = theDisplay;
990#endif
86fa64d9 991 if (myGContext == NULL || !MakeCurrent())
f0430952 992 {
993 return Standard_False;
994 }
2bd4c032 995
4e1523ef 996 init (theIsCoreProfile);
2bd4c032 997 myIsInitialized = Standard_True;
f0430952 998 return Standard_True;
5f8b738e 999}
1000
1001// =======================================================================
1002// function : ResetErrors
1003// purpose :
1004// =======================================================================
f9f740d6 1005bool OpenGl_Context::ResetErrors (const bool theToPrintErrors)
5f8b738e 1006{
3c4b62a4 1007 int aPrevErr = 0;
1008 int anErr = ::glGetError();
f9f740d6 1009 const bool hasError = anErr != GL_NO_ERROR;
3c4b62a4 1010 if (!theToPrintErrors)
5f8b738e 1011 {
3c4b62a4 1012 for (; anErr != GL_NO_ERROR && aPrevErr != anErr; aPrevErr = anErr, anErr = ::glGetError())
1013 {
1014 //
1015 }
f9f740d6 1016 return hasError;
3c4b62a4 1017 }
1018
1019 for (; anErr != GL_NO_ERROR && aPrevErr != anErr; aPrevErr = anErr, anErr = ::glGetError())
1020 {
1021 TCollection_ExtendedString anErrId;
1022 switch (anErr)
1023 {
1024 case GL_INVALID_ENUM: anErrId = "GL_INVALID_ENUM"; break;
1025 case GL_INVALID_VALUE: anErrId = "GL_INVALID_VALUE"; break;
1026 case GL_INVALID_OPERATION: anErrId = "GL_INVALID_OPERATION"; break;
1027 #ifdef GL_STACK_OVERFLOW
1028 case GL_STACK_OVERFLOW: anErrId = "GL_STACK_OVERFLOW"; break;
1029 case GL_STACK_UNDERFLOW: anErrId = "GL_STACK_UNDERFLOW"; break;
1030 #endif
1031 case GL_OUT_OF_MEMORY: anErrId = "GL_OUT_OF_MEMORY"; break;
1032 case GL_INVALID_FRAMEBUFFER_OPERATION:
1033 anErrId = "GL_INVALID_FRAMEBUFFER_OPERATION";
1034 break;
1035 default:
1036 anErrId = TCollection_ExtendedString("#") + anErr;
1037 break;
1038 }
1039
1040 const TCollection_ExtendedString aMsg = TCollection_ExtendedString ("Unhandled GL error: ") + anErrId;
82f443b6 1041 PushMessage (GL_DEBUG_SOURCE_APPLICATION, GL_DEBUG_TYPE_OTHER, 0, GL_DEBUG_SEVERITY_LOW, aMsg);
5f8b738e 1042 }
f9f740d6 1043 return hasError;
5f8b738e 1044}
1045
1046// =======================================================================
4e1523ef 1047// function : ReadGlVersion
5f8b738e 1048// purpose :
1049// =======================================================================
4e1523ef 1050void OpenGl_Context::ReadGlVersion (Standard_Integer& theGlVerMajor,
1051 Standard_Integer& theGlVerMinor)
5f8b738e 1052{
1053 // reset values
4e1523ef 1054 theGlVerMajor = 0;
1055 theGlVerMinor = 0;
5f8b738e 1056
c64efd9e 1057 bool toCheckVer3 = true;
1058#if defined(__EMSCRIPTEN__)
1059 // WebGL 1.0 prints annoying invalid enumeration warnings to console.
1060 toCheckVer3 = false;
1061 if (EMSCRIPTEN_WEBGL_CONTEXT_HANDLE aWebGlCtx = emscripten_webgl_get_current_context())
5f8b738e 1062 {
c64efd9e 1063 EmscriptenWebGLContextAttributes anAttribs = {};
1064 if (emscripten_webgl_get_context_attributes (aWebGlCtx, &anAttribs) == EMSCRIPTEN_RESULT_SUCCESS)
1065 {
1066 toCheckVer3 = anAttribs.majorVersion >= 2;
1067 }
5f8b738e 1068 }
c64efd9e 1069#endif
1070
1071 // Available since OpenGL 3.0 and OpenGL ES 3.0.
1072 if (toCheckVer3)
4e1523ef 1073 {
c64efd9e 1074 GLint aMajor = 0, aMinor = 0;
1075 glGetIntegerv (GL_MAJOR_VERSION, &aMajor);
1076 glGetIntegerv (GL_MINOR_VERSION, &aMinor);
1077 // glGetError() sometimes does not report an error here even if
1078 // GL does not know GL_MAJOR_VERSION and GL_MINOR_VERSION constants.
1079 // This happens on some renderers like e.g. Cygwin MESA.
1080 // Thus checking additionally if GL has put anything to
1081 // the output variables.
1082 if (::glGetError() == GL_NO_ERROR && aMajor != 0 && aMinor != 0)
4e1523ef 1083 {
c64efd9e 1084 theGlVerMajor = aMajor;
1085 theGlVerMinor = aMinor;
1086 return;
1087 }
1088 for (GLenum anErr = ::glGetError(), aPrevErr = GL_NO_ERROR;; aPrevErr = anErr, anErr = ::glGetError())
1089 {
1090 if (anErr == GL_NO_ERROR
1091 || anErr == aPrevErr)
1092 {
1093 break;
1094 }
4e1523ef 1095 }
1096 }
5f8b738e 1097
1098 // Read version string.
ca3c13d1 1099 // Notice that only first two numbers split by point '2.1 XXXXX' are significant.
5f8b738e 1100 // Following trash (after space) is vendor-specific.
1101 // New drivers also returns micro version of GL like '3.3.0' which has no meaning
1102 // and should be considered as vendor-specific too.
1103 const char* aVerStr = (const char* )glGetString (GL_VERSION);
1104 if (aVerStr == NULL || *aVerStr == '\0')
1105 {
1106 // invalid GL context
1107 return;
1108 }
1109
ca3c13d1 1110//#if defined(GL_ES_VERSION_2_0)
1111 // skip "OpenGL ES-** " section
1112 for (; *aVerStr != '\0'; ++aVerStr)
1113 {
1114 if (*aVerStr >= '0' && *aVerStr <= '9')
1115 {
1116 break;
1117 }
1118 }
1119//#endif
1120
5f8b738e 1121 // parse string for major number
1122 char aMajorStr[32];
1123 char aMinorStr[32];
1124 size_t aMajIter = 0;
1125 while (aVerStr[aMajIter] >= '0' && aVerStr[aMajIter] <= '9')
1126 {
1127 ++aMajIter;
1128 }
1129 if (aMajIter == 0 || aMajIter >= sizeof(aMajorStr))
1130 {
1131 return;
1132 }
1133 memcpy (aMajorStr, aVerStr, aMajIter);
1134 aMajorStr[aMajIter] = '\0';
1135
1136 // parse string for minor number
86325709 1137 aVerStr += aMajIter + 1;
1138 size_t aMinIter = 0;
5f8b738e 1139 while (aVerStr[aMinIter] >= '0' && aVerStr[aMinIter] <= '9')
1140 {
1141 ++aMinIter;
1142 }
86325709 1143 if (aMinIter == 0 || aMinIter >= sizeof(aMinorStr))
5f8b738e 1144 {
1145 return;
1146 }
86325709 1147 memcpy (aMinorStr, aVerStr, aMinIter);
1148 aMinorStr[aMinIter] = '\0';
5f8b738e 1149
1150 // read numbers
4e1523ef 1151 theGlVerMajor = atoi (aMajorStr);
1152 theGlVerMinor = atoi (aMinorStr);
5f8b738e 1153
4e1523ef 1154 if (theGlVerMajor <= 0)
5f8b738e 1155 {
4e1523ef 1156 theGlVerMajor = 0;
1157 theGlVerMinor = 0;
5f8b738e 1158 }
1159}
1160
58655684 1161static Standard_CString THE_DBGMSG_UNKNOWN = "UNKNOWN";
1162static Standard_CString THE_DBGMSG_SOURCES[] =
1163{
3b523c4c 1164 ".OpenGL", // GL_DEBUG_SOURCE_API
1165 ".WinSystem", // GL_DEBUG_SOURCE_WINDOW_SYSTEM
1166 ".GLSL", // GL_DEBUG_SOURCE_SHADER_COMPILER
1167 ".3rdParty", // GL_DEBUG_SOURCE_THIRD_PARTY
1168 "", // GL_DEBUG_SOURCE_APPLICATION
1169 ".Other" // GL_DEBUG_SOURCE_OTHER
58655684 1170};
1171
1172static Standard_CString THE_DBGMSG_TYPES[] =
1173{
3b523c4c 1174 "Error", // GL_DEBUG_TYPE_ERROR
1175 "Deprecated", // GL_DEBUG_TYPE_DEPRECATED_BEHAVIOR
1176 "Undef. behavior", // GL_DEBUG_TYPE_UNDEFINED_BEHAVIOR
1177 "Portability", // GL_DEBUG_TYPE_PORTABILITY
1178 "Performance", // GL_DEBUG_TYPE_PERFORMANCE
1179 "Other" // GL_DEBUG_TYPE_OTHER
58655684 1180};
1181
3b523c4c 1182static Standard_CString THE_DBGMSG_SEV_HIGH = "High"; // GL_DEBUG_SEVERITY_HIGH
1183static Standard_CString THE_DBGMSG_SEV_MEDIUM = "Medium"; // GL_DEBUG_SEVERITY_MEDIUM
1184static Standard_CString THE_DBGMSG_SEV_LOW = "Low"; // GL_DEBUG_SEVERITY_LOW
58655684 1185
cbf18624 1186//! Callback for GL_ARB_debug_output extension
58655684 1187static void APIENTRY debugCallbackWrap(unsigned int theSource,
1188 unsigned int theType,
1189 unsigned int theId,
1190 unsigned int theSeverity,
1191 int /*theLength*/,
1192 const char* theMessage,
9293178b 1193 const void* theUserParam)
cbf18624 1194{
1195 OpenGl_Context* aCtx = (OpenGl_Context* )theUserParam;
1196 aCtx->PushMessage (theSource, theType, theId, theSeverity, theMessage);
1197}
1198
1199// =======================================================================
1200// function : PushMessage
1201// purpose :
1202// =======================================================================
1203void OpenGl_Context::PushMessage (const unsigned int theSource,
1204 const unsigned int theType,
1205 const unsigned int theId,
1206 const unsigned int theSeverity,
1207 const TCollection_ExtendedString& theMessage)
58655684 1208{
c87535af 1209 if (caps->suppressExtraMsg
3b523c4c 1210 && theSource >= GL_DEBUG_SOURCE_API
1211 && theSource <= GL_DEBUG_SOURCE_OTHER
1212 && myFilters[theSource - GL_DEBUG_SOURCE_API].Contains (theId))
c87535af 1213 {
1214 return;
1215 }
1216
3b523c4c 1217 Standard_CString& aSrc = (theSource >= GL_DEBUG_SOURCE_API
1218 && theSource <= GL_DEBUG_SOURCE_OTHER)
1219 ? THE_DBGMSG_SOURCES[theSource - GL_DEBUG_SOURCE_API]
58655684 1220 : THE_DBGMSG_UNKNOWN;
3b523c4c 1221 Standard_CString& aType = (theType >= GL_DEBUG_TYPE_ERROR
1222 && theType <= GL_DEBUG_TYPE_OTHER)
1223 ? THE_DBGMSG_TYPES[theType - GL_DEBUG_TYPE_ERROR]
58655684 1224 : THE_DBGMSG_UNKNOWN;
3b523c4c 1225 Standard_CString& aSev = theSeverity == GL_DEBUG_SEVERITY_HIGH
58655684 1226 ? THE_DBGMSG_SEV_HIGH
3b523c4c 1227 : (theSeverity == GL_DEBUG_SEVERITY_MEDIUM
58655684 1228 ? THE_DBGMSG_SEV_MEDIUM
1229 : THE_DBGMSG_SEV_LOW);
3b523c4c 1230 Message_Gravity aGrav = theSeverity == GL_DEBUG_SEVERITY_HIGH
cbf18624 1231 ? Message_Alarm
3b523c4c 1232 : (theSeverity == GL_DEBUG_SEVERITY_MEDIUM
cbf18624 1233 ? Message_Warning
1234 : Message_Info);
1235
1236 TCollection_ExtendedString aMsg;
1237 aMsg += "TKOpenGl"; aMsg += aSrc;
1238 aMsg += " | Type: "; aMsg += aType;
1239 aMsg += " | ID: "; aMsg += (Standard_Integer )theId;
1240 aMsg += " | Severity: "; aMsg += aSev;
1241 aMsg += " | Message:\n ";
1242 aMsg += theMessage;
7e7c2f0b 1243 Messenger()->Send (aMsg, aGrav);
58655684 1244}
1245
5f8b738e 1246// =======================================================================
c87535af 1247// function : ExcludeMessage
1248// purpose :
1249// ======================================================================
1250Standard_Boolean OpenGl_Context::ExcludeMessage (const unsigned int theSource,
1251 const unsigned int theId)
1252{
3b523c4c 1253 return theSource >= GL_DEBUG_SOURCE_API
1254 && theSource <= GL_DEBUG_SOURCE_OTHER
1255 && myFilters[theSource - GL_DEBUG_SOURCE_API].Add (theId);
c87535af 1256}
1257
1258// =======================================================================
1259// function : IncludeMessage
1260// purpose :
1261// ======================================================================
1262Standard_Boolean OpenGl_Context::IncludeMessage (const unsigned int theSource,
1263 const unsigned int theId)
1264{
3b523c4c 1265 return theSource >= GL_DEBUG_SOURCE_API
1266 && theSource <= GL_DEBUG_SOURCE_OTHER
1267 && myFilters[theSource - GL_DEBUG_SOURCE_API].Remove (theId);
c87535af 1268}
1269
1270// =======================================================================
ee51a9fe 1271// function : checkWrongVersion
1272// purpose :
1273// ======================================================================
0ae9ac21 1274void OpenGl_Context::checkWrongVersion (Standard_Integer theGlVerMajor, Standard_Integer theGlVerMinor,
1275 const char* theLastFailedProc)
ee51a9fe 1276{
1277 if (!IsGlGreaterEqual (theGlVerMajor, theGlVerMinor))
1278 {
1279 return;
1280 }
1281
0ae9ac21 1282 PushMessage (GL_DEBUG_SOURCE_APPLICATION, GL_DEBUG_TYPE_ERROR, 0, GL_DEBUG_SEVERITY_HIGH,
1283 TCollection_AsciiString()
1284 + "Error! OpenGL context reports version "
1285 + myGlVerMajor + "." + myGlVerMinor
1286 + " but does not export required functions for " + theGlVerMajor + "." + theGlVerMinor
1287 + " (" + (theLastFailedProc != NULL ? theLastFailedProc : "") + ")\n"
1288 + "Please report this issue to OpenGL driver vendor '" + myVendor + "'");
1289
1290 // lower internal version
1291 if (theGlVerMinor > 0)
1292 {
1293 myGlVerMajor = theGlVerMajor;
1294 myGlVerMinor = theGlVerMinor - 1;
1295 return;
1296 }
1297#if defined(GL_ES_VERSION_2_0)
1298 switch (theGlVerMajor)
1299 {
1300 case 3: myGlVerMajor = 2; myGlVerMinor = 0; return;
1301 }
1302#else
1303 switch (theGlVerMajor)
1304 {
1305 case 2: myGlVerMajor = 1; myGlVerMinor = 5; return;
1306 case 3: myGlVerMajor = 2; myGlVerMinor = 1; return;
1307 case 4: myGlVerMajor = 3; myGlVerMinor = 3; return;
1308 }
1309#endif
ee51a9fe 1310}
1311
1312// =======================================================================
5f8b738e 1313// function : init
1314// purpose :
1315// =======================================================================
4e1523ef 1316void OpenGl_Context::init (const Standard_Boolean theIsCoreProfile)
5f8b738e 1317{
1318 // read version
4e1523ef 1319 myGlVerMajor = 0;
1320 myGlVerMinor = 0;
3c4b62a4 1321 myMaxMsaaSamples = 0;
a1073ae2 1322 myMaxDrawBuffers = 1;
1323 myMaxColorAttachments = 1;
4e1523ef 1324 ReadGlVersion (myGlVerMajor, myGlVerMinor);
c87535af 1325 myVendor = (const char* )::glGetString (GL_VENDOR);
6997ff1c 1326 myVendor.LowerCase();
59515ca6 1327
faff3767 1328 // standard formats
1329 mySupportedFormats->Clear();
1330 mySupportedFormats->Add (Image_PixMap::ImgGray);
1331 mySupportedFormats->Add (Image_PixMap::ImgAlpha);
1332 mySupportedFormats->Add (Image_PixMap::ImgRGB);
1333 mySupportedFormats->Add (Image_PixMap::ImgRGB32);
1334 mySupportedFormats->Add (Image_PixMap::ImgRGBA);
1335
59515ca6 1336 if (caps->contextMajorVersionUpper != -1)
1337 {
1338 // synthetically restrict OpenGL version for testing
1339 Standard_Integer aCtxVer[2] = { myGlVerMajor, myGlVerMinor };
1340 bool isLowered = false;
1341 if (myGlVerMajor > caps->contextMajorVersionUpper)
1342 {
1343 isLowered = true;
1344 myGlVerMajor = caps->contextMajorVersionUpper;
1345 #if defined(GL_ES_VERSION_2_0)
1346 switch (myGlVerMajor)
1347 {
1348 case 2: myGlVerMinor = 0; break;
1349 }
1350 #else
1351 switch (myGlVerMajor)
1352 {
1353 case 1: myGlVerMinor = 5; break;
1354 case 2: myGlVerMinor = 1; break;
1355 case 3: myGlVerMinor = 3; break;
1356 }
1357 #endif
1358 }
1359 if (caps->contextMinorVersionUpper != -1
1360 && myGlVerMinor > caps->contextMinorVersionUpper)
1361 {
1362 isLowered = true;
1363 myGlVerMinor = caps->contextMinorVersionUpper;
1364 }
1365 if (isLowered)
1366 {
1367 PushMessage (GL_DEBUG_SOURCE_APPLICATION, GL_DEBUG_TYPE_PORTABILITY, 0, GL_DEBUG_SEVERITY_MEDIUM,
1368 TCollection_AsciiString ("OpenGL version ") + aCtxVer[0] + "." + aCtxVer[1]
1369 + " has been lowered to " + myGlVerMajor + "." + myGlVerMinor);
1370 }
1371 }
1372
be375252 1373 if (!caps->ffpEnable
1374 && !IsGlGreaterEqual (2, 0))
1375 {
1376 caps->ffpEnable = true;
1377 TCollection_ExtendedString aMsg =
1378 TCollection_ExtendedString("OpenGL driver is too old! Context info:\n")
1379 + " Vendor: " + (const char* )::glGetString (GL_VENDOR) + "\n"
1380 + " Renderer: " + (const char* )::glGetString (GL_RENDERER) + "\n"
1381 + " Version: " + (const char* )::glGetString (GL_VERSION) + "\n"
1382 + " Fallback using deprecated fixed-function pipeline.\n"
1383 + " Visualization might work incorrectly.\n"
1384 " Consider upgrading the graphics driver.";
1385 PushMessage (GL_DEBUG_SOURCE_APPLICATION, GL_DEBUG_TYPE_PORTABILITY, 0, GL_DEBUG_SEVERITY_HIGH, aMsg);
1386 }
4e1523ef 1387
1388#if defined(GL_ES_VERSION_2_0)
1389 (void )theIsCoreProfile;
1390 const bool isCoreProfile = false;
1391#else
c87535af 1392
6997ff1c 1393 if (myVendor.Search ("nvidia") != -1)
c87535af 1394 {
1395 // Buffer detailed info: Buffer object 1 (bound to GL_ARRAY_BUFFER_ARB, usage hint is GL_STATIC_DRAW)
1396 // will use VIDEO memory as the source for buffer object operations.
3b523c4c 1397 ExcludeMessage (GL_DEBUG_SOURCE_API, 131185);
c87535af 1398 }
4e1523ef 1399 if (IsGlGreaterEqual (3, 0))
1400 {
1401 // retrieve auxiliary function in advance
1402 FindProc ("glGetStringi", myFuncs->glGetStringi);
1403 }
1404
d4271fe5 1405 bool isCoreProfile = false;
4e1523ef 1406 if (IsGlGreaterEqual (3, 2))
1407 {
d4271fe5 1408 isCoreProfile = (theIsCoreProfile == Standard_True);
4e1523ef 1409
d4271fe5 1410 // detect Core profile
c6ad5e5f 1411 if (!isCoreProfile)
4e1523ef 1412 {
d4271fe5 1413 GLint aProfile = 0;
1414 ::glGetIntegerv (GL_CONTEXT_PROFILE_MASK, &aProfile);
1415 isCoreProfile = (aProfile & GL_CONTEXT_CORE_PROFILE_BIT) != 0;
4e1523ef 1416 }
1417 }
4e1523ef 1418#endif
1419
1420 core11 = NULL;
1421 if (!isCoreProfile)
1422 {
1423 core11 = (OpenGl_GlCore11* )(&(*myFuncs));
1424 }
01ca42b2 1425 core11fwd = (OpenGl_GlCore11Fwd* )(&(*myFuncs));
1426 core15 = NULL;
1427 core15fwd = NULL;
1428 core20 = NULL;
1429 core20fwd = NULL;
872f98d9 1430 core30 = NULL;
1431 core30fwd = NULL;
01ca42b2 1432 core32 = NULL;
1433 core32back = NULL;
25ef750e 1434 core33 = NULL;
1435 core33back = NULL;
01ca42b2 1436 core41 = NULL;
1437 core41back = NULL;
1438 core42 = NULL;
1439 core42back = NULL;
1440 core43 = NULL;
1441 core43back = NULL;
1442 core44 = NULL;
1443 core44back = NULL;
9491df8c 1444 core45 = NULL;
1445 core45back = NULL;
01ca42b2 1446 arbTBO = NULL;
25ef750e 1447 arbTboRGB32 = Standard_False;
01ca42b2 1448 arbIns = NULL;
1449 arbDbg = NULL;
1450 arbFBO = NULL;
b86bb3df 1451 arbFBOBlit = NULL;
01ca42b2 1452 extGS = NULL;
4e1523ef 1453 myDefaultVao = 0;
01ca42b2 1454
cc8cbabe 1455 //! Make record shorter to retrieve function pointer using variable with same name
0ae9ac21 1456 const char* aLastFailedProc = NULL;
1457 #define FindProcShort(theFunc) FindProcVerbose(aLastFailedProc, #theFunc, myFuncs->theFunc)
cc8cbabe 1458
ca3c13d1 1459#if defined(GL_ES_VERSION_2_0)
1460
1461 hasTexRGBA8 = IsGlGreaterEqual (3, 0)
1462 || CheckExtension ("GL_OES_rgb8_rgba8");
ba00aab7 1463 hasTexSRGB = IsGlGreaterEqual (3, 0);
1464 hasFboSRGB = IsGlGreaterEqual (3, 0);
1465 hasSRGBControl = CheckExtension ("GL_EXT_sRGB_write_control");
05e2200b 1466 // NPOT textures has limited support within OpenGL ES 2.0
1467 // which are relaxed by OpenGL ES 3.0 or some extensions
1468 //arbNPTW = IsGlGreaterEqual (3, 0)
1469 // || CheckExtension ("GL_OES_texture_npot")
1470 // || CheckExtension ("GL_NV_texture_npot_2D_mipmap");
1471 arbNPTW = Standard_True;
ca3c13d1 1472 arbTexRG = IsGlGreaterEqual (3, 0)
1473 || CheckExtension ("GL_EXT_texture_rg");
1474 extBgra = CheckExtension ("GL_EXT_texture_format_BGRA8888");
1475 extAnis = CheckExtension ("GL_EXT_texture_filter_anisotropic");
e473b95f 1476 extPDS = IsGlGreaterEqual (3, 0)
1477 || CheckExtension ("GL_OES_packed_depth_stencil");
565baee6 1478#ifdef __EMSCRIPTEN__
1479 if (!extPDS
1480 && checkEnableWebGlExtension (*this, "GL_WEBGL_depth_texture"))
1481 {
1482 extPDS = true; // WebGL 1.0 extension (in WebGL 2.0 core)
1483 }
1484#endif
ca3c13d1 1485
faff3767 1486 if (extBgra)
1487 {
1488 // no BGR on OpenGL ES - only BGRA as extension
1489 mySupportedFormats->Add (Image_PixMap::ImgBGR32);
1490 mySupportedFormats->Add (Image_PixMap::ImgBGRA);
1491 }
1492
ca3c13d1 1493 core11fwd = (OpenGl_GlCore11Fwd* )(&(*myFuncs));
1494 if (IsGlGreaterEqual (2, 0))
1495 {
1496 // enable compatible functions
1497 core20 = (OpenGl_GlCore20* )(&(*myFuncs));
1498 core20fwd = (OpenGl_GlCore20Fwd* )(&(*myFuncs));
1499 core15fwd = (OpenGl_GlCore15Fwd* )(&(*myFuncs));
b86bb3df 1500 arbFBO = (OpenGl_ArbFBO* )(&(*myFuncs));
1501 }
1502 if (IsGlGreaterEqual (3, 0)
cc8cbabe 1503 && FindProcShort (glBlitFramebuffer))
b86bb3df 1504 {
1505 arbFBOBlit = (OpenGl_ArbFBOBlit* )(&(*myFuncs));
ca3c13d1 1506 }
cc8cbabe 1507 if (IsGlGreaterEqual (3, 0)
1508 && FindProcShort (glGenSamplers)
1509 && FindProcShort (glDeleteSamplers)
1510 && FindProcShort (glIsSampler)
1511 && FindProcShort (glBindSampler)
1512 && FindProcShort (glSamplerParameteri)
1513 && FindProcShort (glSamplerParameteriv)
1514 && FindProcShort (glSamplerParameterf)
1515 && FindProcShort (glSamplerParameterfv)
1516 && FindProcShort (glGetSamplerParameteriv)
1517 && FindProcShort (glGetSamplerParameterfv))
1518 //&& FindProcShort (glSamplerParameterIiv) // only on Desktop or with extensions GL_OES_texture_border_clamp/GL_EXT_texture_border_clamp
1519 //&& FindProcShort (glSamplerParameterIuiv)
1520 //&& FindProcShort (glGetSamplerParameterIiv)
1521 //&& FindProcShort (glGetSamplerParameterIuiv))
1522 {
1523 arbSamplerObject = (OpenGl_ArbSamplerObject* )(&(*myFuncs));
1524 }
1ce0716b 1525 extFragDepth = !IsGlGreaterEqual(3, 0)
1526 && CheckExtension ("GL_EXT_frag_depth");
3c4b62a4 1527 if (IsGlGreaterEqual (3, 1)
0ae9ac21 1528 && FindProcShort (glTexStorage2DMultisample))
3c4b62a4 1529 {
1530 // MSAA RenderBuffers have been defined in OpenGL ES 3.0,
1531 // but MSAA Textures - only in OpenGL ES 3.1+
1532 ::glGetIntegerv (GL_MAX_SAMPLES, &myMaxMsaaSamples);
1533 }
ca3c13d1 1534
e99a2f7c 1535 hasUintIndex = IsGlGreaterEqual (3, 0)
1536 || CheckExtension ("GL_OES_element_index_uint");
1537 hasHighp = CheckExtension ("GL_OES_fragment_precision_high");
ca3c13d1 1538 GLint aRange[2] = {0, 0};
447c4115 1539 GLint aPrec = 0;
1540 ::glGetShaderPrecisionFormat (GL_FRAGMENT_SHADER, GL_HIGH_FLOAT, aRange, &aPrec);
1541 if (aPrec != 0)
ca3c13d1 1542 {
1543 hasHighp = Standard_True;
1544 }
74fb257d 1545
59ec2cce 1546 arbTexFloat = (IsGlGreaterEqual (3, 0)
1547 && FindProcShort (glTexImage3D))
1548 || CheckExtension ("GL_OES_texture_float");
67312b79 1549 hasTexFloatLinear = arbTexFloat
1550 && CheckExtension ("GL_OES_texture_float_linear");
20aeeb7b 1551
872f98d9 1552 const bool hasTexBuffer32 = IsGlGreaterEqual (3, 2) && FindProcShort (glTexBuffer);
1553 const bool hasExtTexBuffer = CheckExtension ("GL_EXT_texture_buffer") && FindProc ("glTexBufferEXT", myFuncs->glTexBuffer);
20aeeb7b 1554 if (hasTexBuffer32 || hasExtTexBuffer)
1555 {
1556 arbTBO = reinterpret_cast<OpenGl_ArbTBO*> (myFuncs.get());
1557 }
0deb6f04 1558
872f98d9 1559 bool hasInstanced = IsGlGreaterEqual (3, 0)
1560 && FindProcShort (glVertexAttribDivisor)
1561 && FindProcShort (glDrawArraysInstanced)
1562 && FindProcShort (glDrawElementsInstanced);
1563 if (!hasInstanced)
1564 {
1565 hasInstanced = CheckExtension ("GL_ANGLE_instanced_arrays")
1566 && FindProc ("glVertexAttribDivisorANGLE", myFuncs->glVertexAttribDivisor)
1567 && FindProc ("glDrawArraysInstancedANGLE", myFuncs->glDrawArraysInstanced)
1568 && FindProc ("glDrawElementsInstancedANGLE", myFuncs->glDrawElementsInstanced);
1569 }
1570 if (hasInstanced)
1571 {
1572 arbIns = (OpenGl_ArbIns* )(&(*myFuncs));
1573 }
1574
1575 const bool hasVAO = IsGlGreaterEqual (3, 0)
1576 && FindProcShort (glBindVertexArray)
1577 && FindProcShort (glDeleteVertexArrays)
1578 && FindProcShort (glGenVertexArrays)
1579 && FindProcShort (glIsVertexArray);
1580 const bool hasMapBufferRange = IsGlGreaterEqual (3, 0)
1581 && FindProcShort (glMapBufferRange)
1582 && FindProcShort (glFlushMappedBufferRange);
1583
1584 // load OpenGL ES 3.0 new functions
1585 const bool has30es = IsGlGreaterEqual (3, 0)
1586 && hasVAO
1587 && hasMapBufferRange
1588 && hasInstanced
1589 && arbSamplerObject != NULL
1590 && arbFBOBlit != NULL
1591 && FindProcShort (glReadBuffer)
1592 && FindProcShort (glDrawRangeElements)
1593 && FindProcShort (glTexImage3D)
1594 && FindProcShort (glTexSubImage3D)
1595 && FindProcShort (glCopyTexSubImage3D)
1596 && FindProcShort (glCompressedTexImage3D)
1597 && FindProcShort (glCompressedTexSubImage3D)
1598 && FindProcShort (glGenQueries)
1599 && FindProcShort (glDeleteQueries)
1600 && FindProcShort (glIsQuery)
1601 && FindProcShort (glBeginQuery)
1602 && FindProcShort (glEndQuery)
1603 && FindProcShort (glGetQueryiv)
1604 && FindProcShort (glGetQueryObjectuiv)
1605 && FindProcShort (glUnmapBuffer)
1606 && FindProcShort (glGetBufferPointerv)
1607 && FindProcShort (glDrawBuffers)
1608 && FindProcShort (glUniformMatrix2x3fv)
1609 && FindProcShort (glUniformMatrix3x2fv)
1610 && FindProcShort (glUniformMatrix2x4fv)
1611 && FindProcShort (glUniformMatrix4x2fv)
1612 && FindProcShort (glUniformMatrix3x4fv)
1613 && FindProcShort (glUniformMatrix4x3fv)
1614 && FindProcShort (glRenderbufferStorageMultisample)
1615 && FindProcShort (glFramebufferTextureLayer)
1616 && FindProcShort (glGetIntegeri_v)
1617 && FindProcShort (glBeginTransformFeedback)
1618 && FindProcShort (glEndTransformFeedback)
1619 && FindProcShort (glBindBufferRange)
1620 && FindProcShort (glBindBufferBase)
1621 && FindProcShort (glTransformFeedbackVaryings)
1622 && FindProcShort (glGetTransformFeedbackVarying)
1623 && FindProcShort (glVertexAttribIPointer)
1624 && FindProcShort (glGetVertexAttribIiv)
1625 && FindProcShort (glGetVertexAttribIuiv)
1626 && FindProcShort (glVertexAttribI4i)
1627 && FindProcShort (glVertexAttribI4ui)
1628 && FindProcShort (glVertexAttribI4iv)
1629 && FindProcShort (glVertexAttribI4uiv)
1630 && FindProcShort (glGetUniformuiv)
1631 && FindProcShort (glGetFragDataLocation)
1632 && FindProcShort (glUniform1ui)
1633 && FindProcShort (glUniform2ui)
1634 && FindProcShort (glUniform3ui)
1635 && FindProcShort (glUniform4ui)
1636 && FindProcShort (glUniform1uiv)
1637 && FindProcShort (glUniform2uiv)
1638 && FindProcShort (glUniform3uiv)
1639 && FindProcShort (glUniform4uiv)
1640 && FindProcShort (glClearBufferiv)
1641 && FindProcShort (glClearBufferuiv)
1642 && FindProcShort (glClearBufferfv)
1643 && FindProcShort (glClearBufferfi)
1644 && FindProcShort (glGetStringi)
1645 && FindProcShort (glCopyBufferSubData)
1646 && FindProcShort (glGetUniformIndices)
1647 && FindProcShort (glGetActiveUniformsiv)
1648 && FindProcShort (glGetUniformBlockIndex)
1649 && FindProcShort (glGetActiveUniformBlockiv)
1650 && FindProcShort (glGetActiveUniformBlockName)
1651 && FindProcShort (glUniformBlockBinding)
1652 && FindProcShort (glFenceSync)
1653 && FindProcShort (glIsSync)
1654 && FindProcShort (glDeleteSync)
1655 && FindProcShort (glClientWaitSync)
1656 && FindProcShort (glWaitSync)
1657 && FindProcShort (glGetInteger64v)
1658 && FindProcShort (glGetSynciv)
1659 && FindProcShort (glGetInteger64i_v)
1660 && FindProcShort (glGetBufferParameteri64v)
1661 && FindProcShort (glBindTransformFeedback)
1662 && FindProcShort (glDeleteTransformFeedbacks)
1663 && FindProcShort (glGenTransformFeedbacks)
1664 && FindProcShort (glIsTransformFeedback)
1665 && FindProcShort (glPauseTransformFeedback)
1666 && FindProcShort (glResumeTransformFeedback)
1667 && FindProcShort (glGetProgramBinary)
1668 && FindProcShort (glProgramBinary)
1669 && FindProcShort (glProgramParameteri)
1670 && FindProcShort (glInvalidateFramebuffer)
1671 && FindProcShort (glInvalidateSubFramebuffer)
1672 && FindProcShort (glTexStorage2D)
1673 && FindProcShort (glTexStorage3D)
1674 && FindProcShort (glGetInternalformativ);
1675 if (!has30es)
1676 {
1677 checkWrongVersion (3, 0, aLastFailedProc);
1678 }
1679 else
1680 {
1681 core30 = (OpenGl_GlCore30* )(&(*myFuncs));
1682 core30fwd = (OpenGl_GlCore30Fwd* )(&(*myFuncs));
d4cefcc0 1683 hasGetBufferData = true;
872f98d9 1684 }
1685
1686 // load OpenGL ES 3.1 new functions
1687 const bool has31es = IsGlGreaterEqual (3, 1)
1688 && has30es
1689 && FindProcShort (glDispatchCompute)
1690 && FindProcShort (glDispatchComputeIndirect)
1691 && FindProcShort (glDrawArraysIndirect)
1692 && FindProcShort (glDrawElementsIndirect)
1693 && FindProcShort (glFramebufferParameteri)
1694 && FindProcShort (glGetFramebufferParameteriv)
1695 && FindProcShort (glGetProgramInterfaceiv)
1696 && FindProcShort (glGetProgramResourceIndex)
1697 && FindProcShort (glGetProgramResourceName)
1698 && FindProcShort (glGetProgramResourceiv)
1699 && FindProcShort (glGetProgramResourceLocation)
1700 && FindProcShort (glUseProgramStages)
1701 && FindProcShort (glActiveShaderProgram)
1702 && FindProcShort (glCreateShaderProgramv)
1703 && FindProcShort (glBindProgramPipeline)
1704 && FindProcShort (glDeleteProgramPipelines)
1705 && FindProcShort (glGenProgramPipelines)
1706 && FindProcShort (glIsProgramPipeline)
1707 && FindProcShort (glGetProgramPipelineiv)
1708 && FindProcShort (glProgramUniform1i)
1709 && FindProcShort (glProgramUniform2i)
1710 && FindProcShort (glProgramUniform3i)
1711 && FindProcShort (glProgramUniform4i)
1712 && FindProcShort (glProgramUniform1ui)
1713 && FindProcShort (glProgramUniform2ui)
1714 && FindProcShort (glProgramUniform3ui)
1715 && FindProcShort (glProgramUniform4ui)
1716 && FindProcShort (glProgramUniform1f)
1717 && FindProcShort (glProgramUniform2f)
1718 && FindProcShort (glProgramUniform3f)
1719 && FindProcShort (glProgramUniform4f)
1720 && FindProcShort (glProgramUniform1iv)
1721 && FindProcShort (glProgramUniform2iv)
1722 && FindProcShort (glProgramUniform3iv)
1723 && FindProcShort (glProgramUniform4iv)
1724 && FindProcShort (glProgramUniform1uiv)
1725 && FindProcShort (glProgramUniform2uiv)
1726 && FindProcShort (glProgramUniform3uiv)
1727 && FindProcShort (glProgramUniform4uiv)
1728 && FindProcShort (glProgramUniform1fv)
1729 && FindProcShort (glProgramUniform2fv)
1730 && FindProcShort (glProgramUniform3fv)
1731 && FindProcShort (glProgramUniform4fv)
1732 && FindProcShort (glProgramUniformMatrix2fv)
1733 && FindProcShort (glProgramUniformMatrix3fv)
1734 && FindProcShort (glProgramUniformMatrix4fv)
1735 && FindProcShort (glProgramUniformMatrix2x3fv)
1736 && FindProcShort (glProgramUniformMatrix3x2fv)
1737 && FindProcShort (glProgramUniformMatrix2x4fv)
1738 && FindProcShort (glProgramUniformMatrix4x2fv)
1739 && FindProcShort (glProgramUniformMatrix3x4fv)
1740 && FindProcShort (glProgramUniformMatrix4x3fv)
1741 && FindProcShort (glValidateProgramPipeline)
1742 && FindProcShort (glGetProgramPipelineInfoLog)
1743 && FindProcShort (glBindImageTexture)
1744 && FindProcShort (glGetBooleani_v)
1745 && FindProcShort (glMemoryBarrier)
1746 && FindProcShort (glMemoryBarrierByRegion)
1747 && FindProcShort (glTexStorage2DMultisample)
1748 && FindProcShort (glGetMultisamplefv)
1749 && FindProcShort (glSampleMaski)
1750 && FindProcShort (glGetTexLevelParameteriv)
1751 && FindProcShort (glGetTexLevelParameterfv)
1752 && FindProcShort (glBindVertexBuffer)
1753 && FindProcShort (glVertexAttribFormat)
1754 && FindProcShort (glVertexAttribIFormat)
1755 && FindProcShort (glVertexAttribBinding)
1756 && FindProcShort (glVertexBindingDivisor);
1757 if (!has31es)
1758 {
1759 checkWrongVersion (3, 1, aLastFailedProc);
1760 }
1761
0deb6f04 1762 // initialize debug context extension
872f98d9 1763 if (IsGlGreaterEqual (3, 2)
1764 || CheckExtension ("GL_KHR_debug"))
0deb6f04 1765 {
1766 // this functionality become a part of OpenGL ES 3.2
1767 arbDbg = NULL;
872f98d9 1768 if (IsGlGreaterEqual (3, 2)
1769 && FindProcShort (glDebugMessageControl)
1770 && FindProcShort (glDebugMessageInsert)
1771 && FindProcShort (glDebugMessageCallback)
1772 && FindProcShort (glGetDebugMessageLog))
1773 {
1774 arbDbg = (OpenGl_ArbDbg* )(&(*myFuncs));
1775 }
0deb6f04 1776 // According to GL_KHR_debug spec, all functions should have KHR suffix.
1777 // However, some implementations can export these functions without suffix.
872f98d9 1778 else if (!IsGlGreaterEqual (3, 2)
1779 && FindProc ("glDebugMessageControlKHR", myFuncs->glDebugMessageControl)
0deb6f04 1780 && FindProc ("glDebugMessageInsertKHR", myFuncs->glDebugMessageInsert)
1781 && FindProc ("glDebugMessageCallbackKHR", myFuncs->glDebugMessageCallback)
1782 && FindProc ("glGetDebugMessageLogKHR", myFuncs->glGetDebugMessageLog))
1783 {
1784 arbDbg = (OpenGl_ArbDbg* )(&(*myFuncs));
1785 }
1786
1787 if (arbDbg != NULL
1788 && caps->contextDebug)
1789 {
1790 // setup default callback
1791 myIsGlDebugCtx = Standard_True;
1792 arbDbg->glDebugMessageCallback (debugCallbackWrap, this);
1793 ::glEnable (GL_DEBUG_OUTPUT);
1794 if (caps->contextSyncDebug)
1795 {
1796 // note that some broken implementations (e.g. simulators) might generate error message on this call
1797 ::glEnable (GL_DEBUG_OUTPUT_SYNCHRONOUS);
1798 }
1799 }
1800 }
1801
872f98d9 1802 // load OpenGL ES 3.2 new functions
1803 const bool has32es = IsGlGreaterEqual (3, 2)
1804 && has31es
1805 && hasTexBuffer32
1806 && arbDbg != NULL
1807 && FindProcShort (glBlendBarrier)
1808 && FindProcShort (glCopyImageSubData)
1809 && FindProcShort (glPushDebugGroup)
1810 && FindProcShort (glPopDebugGroup)
1811 && FindProcShort (glObjectLabel)
1812 && FindProcShort (glGetObjectLabel)
1813 && FindProcShort (glObjectPtrLabel)
1814 && FindProcShort (glGetObjectPtrLabel)
1815 && FindProcShort (glGetPointerv)
1816 && FindProcShort (glEnablei)
1817 && FindProcShort (glDisablei)
1818 && FindProcShort (glBlendEquationi)
1819 && FindProcShort (glBlendEquationSeparatei)
1820 && FindProcShort (glBlendFunci)
1821 && FindProcShort (glBlendFuncSeparatei)
1822 && FindProcShort (glColorMaski)
1823 && FindProcShort (glIsEnabledi)
1824 && FindProcShort (glDrawElementsBaseVertex)
1825 && FindProcShort (glDrawRangeElementsBaseVertex)
1826 && FindProcShort (glDrawElementsInstancedBaseVertex)
1827 && FindProcShort (glFramebufferTexture)
1828 && FindProcShort (glPrimitiveBoundingBox)
1829 && FindProcShort (glGetGraphicsResetStatus)
1830 && FindProcShort (glReadnPixels)
1831 && FindProcShort (glGetnUniformfv)
1832 && FindProcShort (glGetnUniformiv)
1833 && FindProcShort (glGetnUniformuiv)
1834 && FindProcShort (glMinSampleShading)
1835 && FindProcShort (glPatchParameteri)
1836 && FindProcShort (glTexParameterIiv)
1837 && FindProcShort (glTexParameterIuiv)
1838 && FindProcShort (glGetTexParameterIiv)
1839 && FindProcShort (glGetTexParameterIuiv)
1840 && FindProcShort (glSamplerParameterIiv)
1841 && FindProcShort (glSamplerParameterIuiv)
1842 && FindProcShort (glGetSamplerParameterIiv)
1843 && FindProcShort (glGetSamplerParameterIuiv)
1844 && FindProcShort (glTexBufferRange)
1845 && FindProcShort (glTexStorage3DMultisample);
1846 if (!has32es)
1847 {
1848 checkWrongVersion (3, 2, aLastFailedProc);
1849 }
1850
a1073ae2 1851 extDrawBuffers = CheckExtension ("GL_EXT_draw_buffers") && FindProc ("glDrawBuffersEXT", myFuncs->glDrawBuffers);
1852 arbDrawBuffers = CheckExtension ("GL_ARB_draw_buffers") && FindProc ("glDrawBuffersARB", myFuncs->glDrawBuffers);
1853
0ae9ac21 1854 if (IsGlGreaterEqual (3, 0) && FindProcShort (glDrawBuffers))
a1073ae2 1855 {
1856 hasDrawBuffers = OpenGl_FeatureInCore;
1857 }
1858 else if (extDrawBuffers || arbDrawBuffers)
1859 {
1860 hasDrawBuffers = OpenGl_FeatureInExtensions;
1861 }
1862
1863 hasFloatBuffer = IsGlGreaterEqual (3, 2) ? OpenGl_FeatureInCore :
1864 CheckExtension ("GL_EXT_color_buffer_float") ? OpenGl_FeatureInExtensions
1865 : OpenGl_FeatureNotAvailable;
1866 hasHalfFloatBuffer = IsGlGreaterEqual (3, 2) ? OpenGl_FeatureInCore :
1867 CheckExtension ("GL_EXT_color_buffer_half_float") ? OpenGl_FeatureInExtensions
1868 : OpenGl_FeatureNotAvailable;
1869
1870 oesSampleVariables = CheckExtension ("GL_OES_sample_variables");
8c3237d4 1871 oesStdDerivatives = CheckExtension ("GL_OES_standard_derivatives");
a1073ae2 1872 hasSampleVariables = IsGlGreaterEqual (3, 2) ? OpenGl_FeatureInCore :
1873 oesSampleVariables ? OpenGl_FeatureInExtensions
1874 : OpenGl_FeatureNotAvailable;
59515ca6 1875 hasGlslBitwiseOps = IsGlGreaterEqual (3, 0)
1876 ? OpenGl_FeatureInCore
1877 : OpenGl_FeatureNotAvailable;
c39bb31b 1878 // without hasHighp, dFdx/dFdy precision is considered too low for flat shading (visual artifacts)
1879 hasFlatShading = IsGlGreaterEqual (3, 0)
1880 ? OpenGl_FeatureInCore
1881 : (oesStdDerivatives && hasHighp
1882 ? OpenGl_FeatureInExtensions
1883 : OpenGl_FeatureNotAvailable);
1884 if (!IsGlGreaterEqual (3, 1)
6997ff1c 1885 && myVendor.Search("qualcomm") != -1)
c39bb31b 1886 {
1887 // dFdx/dFdy are completely broken on tested Adreno devices with versions below OpenGl ES 3.1
1888 hasFlatShading = OpenGl_FeatureNotAvailable;
1889 }
2a332745 1890
1891 hasGeometryStage = IsGlGreaterEqual (3, 2)
1892 ? OpenGl_FeatureInCore
1893 : (CheckExtension ("GL_EXT_geometry_shader") && CheckExtension ("GL_EXT_shader_io_blocks")
1894 ? OpenGl_FeatureInExtensions
1895 : OpenGl_FeatureNotAvailable);
ca3c13d1 1896#else
1897
1898 myTexClamp = IsGlGreaterEqual (1, 2) ? GL_CLAMP_TO_EDGE : GL_CLAMP;
1899
1900 hasTexRGBA8 = Standard_True;
faff3767 1901 hasTexSRGB = IsGlGreaterEqual (2, 1);
ba00aab7 1902 hasFboSRGB = IsGlGreaterEqual (2, 1);
1903 hasSRGBControl = hasFboSRGB;
a1073ae2 1904 arbDrawBuffers = CheckExtension ("GL_ARB_draw_buffers");
1905 arbNPTW = CheckExtension ("GL_ARB_texture_non_power_of_two");
1906 arbTexFloat = IsGlGreaterEqual (3, 0)
1907 || CheckExtension ("GL_ARB_texture_float");
67312b79 1908 hasTexFloatLinear = arbTexFloat;
a1073ae2 1909 arbSampleShading = CheckExtension ("GL_ARB_sample_shading");
faff3767 1910 extBgra = IsGlGreaterEqual (1, 2)
1911 || CheckExtension ("GL_EXT_bgra");
a1073ae2 1912 extAnis = CheckExtension ("GL_EXT_texture_filter_anisotropic");
1913 extPDS = CheckExtension ("GL_EXT_packed_depth_stencil");
1914 atiMem = CheckExtension ("GL_ATI_meminfo");
1915 nvxMem = CheckExtension ("GL_NVX_gpu_memory_info");
1916
faff3767 1917 if (extBgra)
1918 {
1919 mySupportedFormats->Add (Image_PixMap::ImgBGR);
1920 mySupportedFormats->Add (Image_PixMap::ImgBGR32);
1921 mySupportedFormats->Add (Image_PixMap::ImgBGRA);
1922 }
1923
a1073ae2 1924 hasDrawBuffers = IsGlGreaterEqual (2, 0) ? OpenGl_FeatureInCore :
1925 arbDrawBuffers ? OpenGl_FeatureInExtensions
1926 : OpenGl_FeatureNotAvailable;
1927
59515ca6 1928 hasGlslBitwiseOps = IsGlGreaterEqual (3, 0)
1929 ? OpenGl_FeatureInCore
1930 : CheckExtension ("GL_EXT_gpu_shader4")
1931 ? OpenGl_FeatureInExtensions
1932 : OpenGl_FeatureNotAvailable;
1933
a1073ae2 1934 hasFloatBuffer = hasHalfFloatBuffer = IsGlGreaterEqual (3, 0) ? OpenGl_FeatureInCore :
1935 CheckExtension ("GL_ARB_color_buffer_float") ? OpenGl_FeatureInExtensions
1936 : OpenGl_FeatureNotAvailable;
1937
2a332745 1938 hasGeometryStage = IsGlGreaterEqual (3, 2)
1939 ? OpenGl_FeatureInCore
1940 : OpenGl_FeatureNotAvailable;
1941
a1073ae2 1942 hasSampleVariables = IsGlGreaterEqual (4, 0) ? OpenGl_FeatureInCore :
1943 arbSampleShading ? OpenGl_FeatureInExtensions
1944 : OpenGl_FeatureNotAvailable;
bf75be98 1945
ca3c13d1 1946 GLint aStereo = GL_FALSE;
b5ac8292 1947 glGetIntegerv (GL_STEREO, &aStereo);
1948 myIsStereoBuffers = aStereo == 1;
1949
ca3c13d1 1950 // get number of maximum clipping planes
1951 glGetIntegerv (GL_MAX_CLIP_PLANES, &myMaxClipPlanes);
1952#endif
1953
a1073ae2 1954 if (hasDrawBuffers)
1955 {
1956 glGetIntegerv (GL_MAX_DRAW_BUFFERS, &myMaxDrawBuffers);
1957 glGetIntegerv (GL_MAX_COLOR_ATTACHMENTS, &myMaxColorAttachments);
c3487460 1958 if (myDrawBuffers.Length() < myMaxDrawBuffers)
1959 {
1960 myDrawBuffers.Resize (0, myMaxDrawBuffers - 1, false);
1961 }
a1073ae2 1962 }
1963
ca3c13d1 1964 glGetIntegerv (GL_MAX_TEXTURE_SIZE, &myMaxTexDim);
737e9a8d 1965#if !defined(GL_ES_VERSION_2_0)
5c225e8e 1966 if (IsGlGreaterEqual (1, 3) && core11 != NULL)
737e9a8d 1967 {
1968 // this is a maximum of texture units for FFP functionality,
5c225e8e 1969 // usually smaller than combined texture units available for GLSL
1970 glGetIntegerv (GL_MAX_TEXTURE_UNITS, &myMaxTexUnitsFFP);
1971 myMaxTexCombined = myMaxTexUnitsFFP;
737e9a8d 1972 }
1973#endif
5c225e8e 1974 if (IsGlGreaterEqual (2, 0))
1975 {
1976 glGetIntegerv (GL_MAX_COMBINED_TEXTURE_IMAGE_UNITS, &myMaxTexCombined);
1977 }
737e9a8d 1978 mySpriteTexUnit = myMaxTexCombined >= 2
72f6dc61 1979 ? Graphic3d_TextureUnit_PointSprite
737e9a8d 1980 : Graphic3d_TextureUnit_0;
ca3c13d1 1981
6997ff1c 1982 GLint aMaxVPortSize[2] = {0, 0};
1983 glGetIntegerv (GL_MAX_VIEWPORT_DIMS, aMaxVPortSize);
1984 myMaxDumpSizeX = Min (aMaxVPortSize[0], myMaxTexDim);
1985 myMaxDumpSizeY = Min (aMaxVPortSize[1], myMaxTexDim);
1986 if (myVendor == "intel")
1987 {
1988 // Intel drivers have known bug with empty dump for images with width>=5462
1989 myMaxDumpSizeX = Min (myMaxDumpSizeX, 4096);
1990 }
1991
bf75be98 1992 if (extAnis)
1993 {
1994 glGetIntegerv (GL_MAX_TEXTURE_MAX_ANISOTROPY_EXT, &myAnisoMax);
1995 }
f0430952 1996
25c35042 1997 myClippingState.Init();
4269bd1b 1998
ca3c13d1 1999#if !defined(GL_ES_VERSION_2_0)
2000
01ca42b2 2001 bool has12 = false;
2002 bool has13 = false;
2003 bool has14 = false;
2004 bool has15 = false;
2005 bool has20 = false;
2006 bool has21 = false;
2007 bool has30 = false;
2008 bool has31 = false;
2009 bool has32 = false;
2010 bool has33 = false;
2011 bool has40 = false;
2012 bool has41 = false;
2013 bool has42 = false;
2014 bool has43 = false;
2015 bool has44 = false;
9491df8c 2016 bool has45 = false;
01ca42b2 2017
4e1523ef 2018 // retrieve platform-dependent extensions
f978241f 2019#if defined(HAVE_EGL)
2020 //
2021#elif defined(_WIN32)
01ca42b2 2022 if (FindProcShort (wglGetExtensionsStringARB))
2023 {
2024 const char* aWglExts = myFuncs->wglGetExtensionsStringARB (wglGetCurrentDC());
2025 if (CheckExtension (aWglExts, "WGL_EXT_swap_control"))
2026 {
2027 FindProcShort (wglSwapIntervalEXT);
2028 }
2029 if (CheckExtension (aWglExts, "WGL_ARB_pixel_format"))
2030 {
2031 FindProcShort (wglChoosePixelFormatARB);
2032 }
2033 if (CheckExtension (aWglExts, "WGL_ARB_create_context_profile"))
2034 {
2035 FindProcShort (wglCreateContextAttribsARB);
2036 }
2037 if (CheckExtension (aWglExts, "WGL_NV_DX_interop"))
2038 {
2039 FindProcShort (wglDXSetResourceShareHandleNV);
2040 FindProcShort (wglDXOpenDeviceNV);
2041 FindProcShort (wglDXCloseDeviceNV);
2042 FindProcShort (wglDXRegisterObjectNV);
2043 FindProcShort (wglDXUnregisterObjectNV);
2044 FindProcShort (wglDXObjectAccessNV);
2045 FindProcShort (wglDXLockObjectsNV);
2046 FindProcShort (wglDXUnlockObjectsNV);
2047 }
2eacd0b8 2048 if (CheckExtension (aWglExts, "WGL_AMD_gpu_association"))
2049 {
2050 FindProcShort (wglGetGPUIDsAMD);
2051 FindProcShort (wglGetGPUInfoAMD);
2052 FindProcShort (wglGetContextGPUIDAMD);
2053 }
01ca42b2 2054 }
f978241f 2055#elif defined(__APPLE__)
2056 //
2057#else
2058 const char* aGlxExts = ::glXQueryExtensionsString ((Display* )myDisplay, DefaultScreen ((Display* )myDisplay));
2059 if (CheckExtension (aGlxExts, "GLX_EXT_swap_control"))
2060 {
2061 FindProcShort (glXSwapIntervalEXT);
2062 }
2063 if (CheckExtension (aGlxExts, "GLX_SGI_swap_control"))
2064 {
2065 FindProcShort (glXSwapIntervalSGI);
2066 }
26d9c835 2067 if (CheckExtension (aGlxExts, "GLX_MESA_query_renderer"))
2068 {
2069 FindProcShort (glXQueryRendererIntegerMESA);
2070 FindProcShort (glXQueryCurrentRendererIntegerMESA);
2071 FindProcShort (glXQueryRendererStringMESA);
2072 FindProcShort (glXQueryCurrentRendererStringMESA);
2073 }
f978241f 2074 //extSwapTear = CheckExtension (aGlxExts, "GLX_EXT_swap_control_tear");
01ca42b2 2075#endif
2076
01ca42b2 2077 // load OpenGL 1.2 new functions
2078 has12 = IsGlGreaterEqual (1, 2)
2079 && FindProcShort (glBlendColor)
2080 && FindProcShort (glBlendEquation)
2081 && FindProcShort (glDrawRangeElements)
2082 && FindProcShort (glTexImage3D)
2083 && FindProcShort (glTexSubImage3D)
2084 && FindProcShort (glCopyTexSubImage3D);
0ae9ac21 2085 if (!has12)
2086 {
2087 checkWrongVersion (1, 2, aLastFailedProc);
2088 }
01ca42b2 2089
2090 // load OpenGL 1.3 new functions
2091 has13 = IsGlGreaterEqual (1, 3)
2092 && FindProcShort (glActiveTexture)
2093 && FindProcShort (glSampleCoverage)
2094 && FindProcShort (glCompressedTexImage3D)
2095 && FindProcShort (glCompressedTexImage2D)
2096 && FindProcShort (glCompressedTexImage1D)
2097 && FindProcShort (glCompressedTexSubImage3D)
2098 && FindProcShort (glCompressedTexSubImage2D)
2099 && FindProcShort (glCompressedTexSubImage1D)
4e1523ef 2100 && FindProcShort (glGetCompressedTexImage);
2101
2102 if (!isCoreProfile)
2103 {
2104 has13 = has13
01ca42b2 2105 && FindProcShort (glClientActiveTexture)
2106 && FindProcShort (glMultiTexCoord1d)
2107 && FindProcShort (glMultiTexCoord1dv)
2108 && FindProcShort (glMultiTexCoord1f)
2109 && FindProcShort (glMultiTexCoord1fv)
2110 && FindProcShort (glMultiTexCoord1i)
2111 && FindProcShort (glMultiTexCoord1iv)
2112 && FindProcShort (glMultiTexCoord1s)
2113 && FindProcShort (glMultiTexCoord1sv)
2114 && FindProcShort (glMultiTexCoord2d)
2115 && FindProcShort (glMultiTexCoord2dv)
2116 && FindProcShort (glMultiTexCoord2f)
2117 && FindProcShort (glMultiTexCoord2fv)
2118 && FindProcShort (glMultiTexCoord2i)
2119 && FindProcShort (glMultiTexCoord2iv)
2120 && FindProcShort (glMultiTexCoord2s)
2121 && FindProcShort (glMultiTexCoord2sv)
2122 && FindProcShort (glMultiTexCoord3d)
2123 && FindProcShort (glMultiTexCoord3dv)
2124 && FindProcShort (glMultiTexCoord3f)
2125 && FindProcShort (glMultiTexCoord3fv)
2126 && FindProcShort (glMultiTexCoord3i)
2127 && FindProcShort (glMultiTexCoord3iv)
2128 && FindProcShort (glMultiTexCoord3s)
2129 && FindProcShort (glMultiTexCoord3sv)
2130 && FindProcShort (glMultiTexCoord4d)
2131 && FindProcShort (glMultiTexCoord4dv)
2132 && FindProcShort (glMultiTexCoord4f)
2133 && FindProcShort (glMultiTexCoord4fv)
2134 && FindProcShort (glMultiTexCoord4i)
2135 && FindProcShort (glMultiTexCoord4iv)
2136 && FindProcShort (glMultiTexCoord4s)
2137 && FindProcShort (glMultiTexCoord4sv)
2138 && FindProcShort (glLoadTransposeMatrixf)
2139 && FindProcShort (glLoadTransposeMatrixd)
2140 && FindProcShort (glMultTransposeMatrixf)
2141 && FindProcShort (glMultTransposeMatrixd);
4e1523ef 2142 }
0ae9ac21 2143 if (!has13)
2144 {
2145 checkWrongVersion (1, 3, aLastFailedProc);
2146 }
01ca42b2 2147
2148 // load OpenGL 1.4 new functions
2149 has14 = IsGlGreaterEqual (1, 4)
2150 && FindProcShort (glBlendFuncSeparate)
2151 && FindProcShort (glMultiDrawArrays)
2152 && FindProcShort (glMultiDrawElements)
2153 && FindProcShort (glPointParameterf)
2154 && FindProcShort (glPointParameterfv)
2155 && FindProcShort (glPointParameteri)
2156 && FindProcShort (glPointParameteriv);
0ae9ac21 2157 if (!has14)
2158 {
2159 checkWrongVersion (1, 4, aLastFailedProc);
2160 }
01ca42b2 2161
2162 // load OpenGL 1.5 new functions
2163 has15 = IsGlGreaterEqual (1, 5)
2164 && FindProcShort (glGenQueries)
2165 && FindProcShort (glDeleteQueries)
2166 && FindProcShort (glIsQuery)
2167 && FindProcShort (glBeginQuery)
2168 && FindProcShort (glEndQuery)
2169 && FindProcShort (glGetQueryiv)
2170 && FindProcShort (glGetQueryObjectiv)
2171 && FindProcShort (glGetQueryObjectuiv)
2172 && FindProcShort (glBindBuffer)
2173 && FindProcShort (glDeleteBuffers)
2174 && FindProcShort (glGenBuffers)
2175 && FindProcShort (glIsBuffer)
2176 && FindProcShort (glBufferData)
2177 && FindProcShort (glBufferSubData)
2178 && FindProcShort (glGetBufferSubData)
2179 && FindProcShort (glMapBuffer)
2180 && FindProcShort (glUnmapBuffer)
2181 && FindProcShort (glGetBufferParameteriv)
2182 && FindProcShort (glGetBufferPointerv);
0ae9ac21 2183 if (has15)
2184 {
2185 if (!isCoreProfile)
2186 {
2187 core15 = (OpenGl_GlCore15* )(&(*myFuncs));
2188 }
2189 core15fwd = (OpenGl_GlCore15Fwd* )(&(*myFuncs));
d4cefcc0 2190 hasGetBufferData = true;
0ae9ac21 2191 }
2192 else
2193 {
2194 checkWrongVersion (1, 5, aLastFailedProc);
2195 }
01ca42b2 2196
2197 // load OpenGL 2.0 new functions
2198 has20 = IsGlGreaterEqual (2, 0)
2199 && FindProcShort (glBlendEquationSeparate)
2200 && FindProcShort (glDrawBuffers)
2201 && FindProcShort (glStencilOpSeparate)
2202 && FindProcShort (glStencilFuncSeparate)
2203 && FindProcShort (glStencilMaskSeparate)
2204 && FindProcShort (glAttachShader)
2205 && FindProcShort (glBindAttribLocation)
2206 && FindProcShort (glCompileShader)
2207 && FindProcShort (glCreateProgram)
2208 && FindProcShort (glCreateShader)
2209 && FindProcShort (glDeleteProgram)
2210 && FindProcShort (glDeleteShader)
2211 && FindProcShort (glDetachShader)
2212 && FindProcShort (glDisableVertexAttribArray)
2213 && FindProcShort (glEnableVertexAttribArray)
2214 && FindProcShort (glGetActiveAttrib)
2215 && FindProcShort (glGetActiveUniform)
2216 && FindProcShort (glGetAttachedShaders)
2217 && FindProcShort (glGetAttribLocation)
2218 && FindProcShort (glGetProgramiv)
2219 && FindProcShort (glGetProgramInfoLog)
2220 && FindProcShort (glGetShaderiv)
2221 && FindProcShort (glGetShaderInfoLog)
2222 && FindProcShort (glGetShaderSource)
2223 && FindProcShort (glGetUniformLocation)
2224 && FindProcShort (glGetUniformfv)
2225 && FindProcShort (glGetUniformiv)
2226 && FindProcShort (glGetVertexAttribdv)
2227 && FindProcShort (glGetVertexAttribfv)
2228 && FindProcShort (glGetVertexAttribiv)
2229 && FindProcShort (glGetVertexAttribPointerv)
2230 && FindProcShort (glIsProgram)
2231 && FindProcShort (glIsShader)
2232 && FindProcShort (glLinkProgram)
2233 && FindProcShort (glShaderSource)
2234 && FindProcShort (glUseProgram)
2235 && FindProcShort (glUniform1f)
2236 && FindProcShort (glUniform2f)
2237 && FindProcShort (glUniform3f)
2238 && FindProcShort (glUniform4f)
2239 && FindProcShort (glUniform1i)
2240 && FindProcShort (glUniform2i)
2241 && FindProcShort (glUniform3i)
2242 && FindProcShort (glUniform4i)
2243 && FindProcShort (glUniform1fv)
2244 && FindProcShort (glUniform2fv)
2245 && FindProcShort (glUniform3fv)
2246 && FindProcShort (glUniform4fv)
2247 && FindProcShort (glUniform1iv)
2248 && FindProcShort (glUniform2iv)
2249 && FindProcShort (glUniform3iv)
2250 && FindProcShort (glUniform4iv)
2251 && FindProcShort (glUniformMatrix2fv)
2252 && FindProcShort (glUniformMatrix3fv)
2253 && FindProcShort (glUniformMatrix4fv)
2254 && FindProcShort (glValidateProgram)
2255 && FindProcShort (glVertexAttrib1d)
2256 && FindProcShort (glVertexAttrib1dv)
2257 && FindProcShort (glVertexAttrib1f)
2258 && FindProcShort (glVertexAttrib1fv)
2259 && FindProcShort (glVertexAttrib1s)
2260 && FindProcShort (glVertexAttrib1sv)
2261 && FindProcShort (glVertexAttrib2d)
2262 && FindProcShort (glVertexAttrib2dv)
2263 && FindProcShort (glVertexAttrib2f)
2264 && FindProcShort (glVertexAttrib2fv)
2265 && FindProcShort (glVertexAttrib2s)
2266 && FindProcShort (glVertexAttrib2sv)
2267 && FindProcShort (glVertexAttrib3d)
2268 && FindProcShort (glVertexAttrib3dv)
2269 && FindProcShort (glVertexAttrib3f)
2270 && FindProcShort (glVertexAttrib3fv)
2271 && FindProcShort (glVertexAttrib3s)
2272 && FindProcShort (glVertexAttrib3sv)
2273 && FindProcShort (glVertexAttrib4Nbv)
2274 && FindProcShort (glVertexAttrib4Niv)
2275 && FindProcShort (glVertexAttrib4Nsv)
2276 && FindProcShort (glVertexAttrib4Nub)
2277 && FindProcShort (glVertexAttrib4Nubv)
2278 && FindProcShort (glVertexAttrib4Nuiv)
2279 && FindProcShort (glVertexAttrib4Nusv)
2280 && FindProcShort (glVertexAttrib4bv)
2281 && FindProcShort (glVertexAttrib4d)
2282 && FindProcShort (glVertexAttrib4dv)
2283 && FindProcShort (glVertexAttrib4f)
2284 && FindProcShort (glVertexAttrib4fv)
2285 && FindProcShort (glVertexAttrib4iv)
2286 && FindProcShort (glVertexAttrib4s)
2287 && FindProcShort (glVertexAttrib4sv)
2288 && FindProcShort (glVertexAttrib4ubv)
2289 && FindProcShort (glVertexAttrib4uiv)
2290 && FindProcShort (glVertexAttrib4usv)
2291 && FindProcShort (glVertexAttribPointer);
0ae9ac21 2292 if (has20)
2293 {
2294 const char* aGlslVer = (const char* )::glGetString (GL_SHADING_LANGUAGE_VERSION);
2295 if (aGlslVer == NULL
2296 || *aGlslVer == '\0')
2297 {
2298 // broken context has been detected
2299 PushMessage (GL_DEBUG_SOURCE_APPLICATION, GL_DEBUG_TYPE_ERROR, 0, GL_DEBUG_SEVERITY_HIGH,
2300 TCollection_AsciiString("Error! OpenGL context reports version ")
2301 + myGlVerMajor + "." + myGlVerMinor + " but reports wrong GLSL version");
2302 myGlVerMajor = 1;
2303 myGlVerMinor = 5;
2304 }
2305 else
2306 {
2307 if (!isCoreProfile)
2308 {
2309 core20 = (OpenGl_GlCore20* )(&(*myFuncs));
2310 }
2311 core20fwd = (OpenGl_GlCore20Fwd* )(&(*myFuncs));
2312 }
2313 }
2314 else
2315 {
2316 checkWrongVersion (2, 0, aLastFailedProc);
2317 }
01ca42b2 2318
2319 // load OpenGL 2.1 new functions
2320 has21 = IsGlGreaterEqual (2, 1)
2321 && FindProcShort (glUniformMatrix2x3fv)
2322 && FindProcShort (glUniformMatrix3x2fv)
2323 && FindProcShort (glUniformMatrix2x4fv)
2324 && FindProcShort (glUniformMatrix4x2fv)
2325 && FindProcShort (glUniformMatrix3x4fv)
2326 && FindProcShort (glUniformMatrix4x3fv);
0ae9ac21 2327 if (!has21)
2328 {
2329 checkWrongVersion (2, 1, aLastFailedProc);
2330 }
01ca42b2 2331
2332 // load GL_ARB_framebuffer_object (added to OpenGL 3.0 core)
2333 const bool hasFBO = (IsGlGreaterEqual (3, 0) || CheckExtension ("GL_ARB_framebuffer_object"))
2334 && FindProcShort (glIsRenderbuffer)
2335 && FindProcShort (glBindRenderbuffer)
2336 && FindProcShort (glDeleteRenderbuffers)
2337 && FindProcShort (glGenRenderbuffers)
2338 && FindProcShort (glRenderbufferStorage)
2339 && FindProcShort (glGetRenderbufferParameteriv)
2340 && FindProcShort (glIsFramebuffer)
2341 && FindProcShort (glBindFramebuffer)
2342 && FindProcShort (glDeleteFramebuffers)
2343 && FindProcShort (glGenFramebuffers)
2344 && FindProcShort (glCheckFramebufferStatus)
2345 && FindProcShort (glFramebufferTexture1D)
2346 && FindProcShort (glFramebufferTexture2D)
2347 && FindProcShort (glFramebufferTexture3D)
2348 && FindProcShort (glFramebufferRenderbuffer)
2349 && FindProcShort (glGetFramebufferAttachmentParameteriv)
2350 && FindProcShort (glGenerateMipmap)
2351 && FindProcShort (glBlitFramebuffer)
2352 && FindProcShort (glRenderbufferStorageMultisample)
2353 && FindProcShort (glFramebufferTextureLayer);
2354
2355 // load GL_ARB_vertex_array_object (added to OpenGL 3.0 core)
2356 const bool hasVAO = (IsGlGreaterEqual (3, 0) || CheckExtension ("GL_ARB_vertex_array_object"))
2357 && FindProcShort (glBindVertexArray)
2358 && FindProcShort (glDeleteVertexArrays)
2359 && FindProcShort (glGenVertexArrays)
2360 && FindProcShort (glIsVertexArray);
2361
2362 // load GL_ARB_map_buffer_range (added to OpenGL 3.0 core)
2363 const bool hasMapBufferRange = (IsGlGreaterEqual (3, 0) || CheckExtension ("GL_ARB_map_buffer_range"))
2364 && FindProcShort (glMapBufferRange)
2365 && FindProcShort (glFlushMappedBufferRange);
2366
2367 // load OpenGL 3.0 new functions
2368 has30 = IsGlGreaterEqual (3, 0)
2369 && hasFBO
2370 && hasVAO
2371 && hasMapBufferRange
2372 && FindProcShort (glColorMaski)
2373 && FindProcShort (glGetBooleani_v)
2374 && FindProcShort (glGetIntegeri_v)
2375 && FindProcShort (glEnablei)
2376 && FindProcShort (glDisablei)
2377 && FindProcShort (glIsEnabledi)
2378 && FindProcShort (glBeginTransformFeedback)
2379 && FindProcShort (glEndTransformFeedback)
2380 && FindProcShort (glBindBufferRange)
2381 && FindProcShort (glBindBufferBase)
2382 && FindProcShort (glTransformFeedbackVaryings)
2383 && FindProcShort (glGetTransformFeedbackVarying)
2384 && FindProcShort (glClampColor)
2385 && FindProcShort (glBeginConditionalRender)
2386 && FindProcShort (glEndConditionalRender)
2387 && FindProcShort (glVertexAttribIPointer)
2388 && FindProcShort (glGetVertexAttribIiv)
2389 && FindProcShort (glGetVertexAttribIuiv)
2390 && FindProcShort (glVertexAttribI1i)
2391 && FindProcShort (glVertexAttribI2i)
2392 && FindProcShort (glVertexAttribI3i)
2393 && FindProcShort (glVertexAttribI4i)
2394 && FindProcShort (glVertexAttribI1ui)
2395 && FindProcShort (glVertexAttribI2ui)
2396 && FindProcShort (glVertexAttribI3ui)
2397 && FindProcShort (glVertexAttribI4ui)
2398 && FindProcShort (glVertexAttribI1iv)
2399 && FindProcShort (glVertexAttribI2iv)
2400 && FindProcShort (glVertexAttribI3iv)
2401 && FindProcShort (glVertexAttribI4iv)
2402 && FindProcShort (glVertexAttribI1uiv)
2403 && FindProcShort (glVertexAttribI2uiv)
2404 && FindProcShort (glVertexAttribI3uiv)
2405 && FindProcShort (glVertexAttribI4uiv)
2406 && FindProcShort (glVertexAttribI4bv)
2407 && FindProcShort (glVertexAttribI4sv)
2408 && FindProcShort (glVertexAttribI4ubv)
2409 && FindProcShort (glVertexAttribI4usv)
2410 && FindProcShort (glGetUniformuiv)
2411 && FindProcShort (glBindFragDataLocation)
2412 && FindProcShort (glGetFragDataLocation)
2413 && FindProcShort (glUniform1ui)
2414 && FindProcShort (glUniform2ui)
2415 && FindProcShort (glUniform3ui)
2416 && FindProcShort (glUniform4ui)
2417 && FindProcShort (glUniform1uiv)
2418 && FindProcShort (glUniform2uiv)
2419 && FindProcShort (glUniform3uiv)
2420 && FindProcShort (glUniform4uiv)
2421 && FindProcShort (glTexParameterIiv)
2422 && FindProcShort (glTexParameterIuiv)
2423 && FindProcShort (glGetTexParameterIiv)
2424 && FindProcShort (glGetTexParameterIuiv)
2425 && FindProcShort (glClearBufferiv)
2426 && FindProcShort (glClearBufferuiv)
2427 && FindProcShort (glClearBufferfv)
2428 && FindProcShort (glClearBufferfi)
2429 && FindProcShort (glGetStringi);
0ae9ac21 2430 if (!has30)
2431 {
2432 checkWrongVersion (3, 0, aLastFailedProc);
2433 }
01ca42b2 2434
2435 // load GL_ARB_uniform_buffer_object (added to OpenGL 3.1 core)
2436 const bool hasUBO = (IsGlGreaterEqual (3, 1) || CheckExtension ("GL_ARB_uniform_buffer_object"))
2437 && FindProcShort (glGetUniformIndices)
2438 && FindProcShort (glGetActiveUniformsiv)
2439 && FindProcShort (glGetActiveUniformName)
2440 && FindProcShort (glGetUniformBlockIndex)
2441 && FindProcShort (glGetActiveUniformBlockiv)
2442 && FindProcShort (glGetActiveUniformBlockName)
2443 && FindProcShort (glUniformBlockBinding);
2444
2445 // load GL_ARB_copy_buffer (added to OpenGL 3.1 core)
2446 const bool hasCopyBufSubData = (IsGlGreaterEqual (3, 1) || CheckExtension ("GL_ARB_copy_buffer"))
2447 && FindProcShort (glCopyBufferSubData);
2448
2449 if (has30)
2166f0fa 2450 {
01ca42b2 2451 // NPOT textures are required by OpenGL 2.0 specifications
2452 // but doesn't hardware accelerated by some ancient OpenGL 2.1 hardware (GeForce FX, RadeOn 9700 etc.)
2453 arbNPTW = Standard_True;
2454 arbTexRG = Standard_True;
872f98d9 2455
2456 if (!isCoreProfile)
2457 {
2458 core30 = (OpenGl_GlCore30* )(&(*myFuncs));
2459 }
2460 core30fwd = (OpenGl_GlCore30Fwd* )(&(*myFuncs));
2166f0fa
SK
2461 }
2462
01ca42b2 2463 // load OpenGL 3.1 new functions
2464 has31 = IsGlGreaterEqual (3, 1)
2465 && hasUBO
2466 && hasCopyBufSubData
2467 && FindProcShort (glDrawArraysInstanced)
2468 && FindProcShort (glDrawElementsInstanced)
2469 && FindProcShort (glTexBuffer)
2470 && FindProcShort (glPrimitiveRestartIndex);
0ae9ac21 2471 if (has31)
2472 {
2473 arbTBO = (OpenGl_ArbTBO* )(&(*myFuncs));
2474 arbIns = (OpenGl_ArbIns* )(&(*myFuncs));
2475 }
2476 else
2477 {
2478 checkWrongVersion (3, 1, aLastFailedProc);
2479
2480 // initialize TBO extension (ARB)
2481 if (CheckExtension ("GL_ARB_texture_buffer_object")
2482 && FindProc ("glTexBufferARB", myFuncs->glTexBuffer))
2483 {
2484 arbTBO = (OpenGl_ArbTBO* )(&(*myFuncs));
2485 }
2486
2487 // initialize hardware instancing extension (ARB)
2488 if (CheckExtension ("GL_ARB_draw_instanced")
2489 && FindProc ("glDrawArraysInstancedARB", myFuncs->glDrawArraysInstanced)
2490 && FindProc ("glDrawElementsInstancedARB", myFuncs->glDrawElementsInstanced))
2491 {
2492 arbIns = (OpenGl_ArbIns* )(&(*myFuncs));
2493 }
2494 }
2495
2496 arbTboRGB32 = CheckExtension ("GL_ARB_texture_buffer_object_rgb32");
01ca42b2 2497
2498 // load GL_ARB_draw_elements_base_vertex (added to OpenGL 3.2 core)
2499 const bool hasDrawElemsBaseVert = (IsGlGreaterEqual (3, 2) || CheckExtension ("GL_ARB_draw_elements_base_vertex"))
2500 && FindProcShort (glDrawElementsBaseVertex)
2501 && FindProcShort (glDrawRangeElementsBaseVertex)
2502 && FindProcShort (glDrawElementsInstancedBaseVertex)
2503 && FindProcShort (glMultiDrawElementsBaseVertex);
2504
2505 // load GL_ARB_provoking_vertex (added to OpenGL 3.2 core)
2506 const bool hasProvokingVert = (IsGlGreaterEqual (3, 2) || CheckExtension ("GL_ARB_provoking_vertex"))
2507 && FindProcShort (glProvokingVertex);
2508
2509 // load GL_ARB_sync (added to OpenGL 3.2 core)
2510 const bool hasSync = (IsGlGreaterEqual (3, 2) || CheckExtension ("GL_ARB_sync"))
2511 && FindProcShort (glFenceSync)
2512 && FindProcShort (glIsSync)
2513 && FindProcShort (glDeleteSync)
2514 && FindProcShort (glClientWaitSync)
2515 && FindProcShort (glWaitSync)
2516 && FindProcShort (glGetInteger64v)
2517 && FindProcShort (glGetSynciv);
2518
2519 // load GL_ARB_texture_multisample (added to OpenGL 3.2 core)
2520 const bool hasTextureMultisample = (IsGlGreaterEqual (3, 2) || CheckExtension ("GL_ARB_texture_multisample"))
2521 && FindProcShort (glTexImage2DMultisample)
2522 && FindProcShort (glTexImage3DMultisample)
2523 && FindProcShort (glGetMultisamplefv)
2524 && FindProcShort (glSampleMaski);
2525
2526 // load OpenGL 3.2 new functions
2527 has32 = IsGlGreaterEqual (3, 2)
2528 && hasDrawElemsBaseVert
2529 && hasProvokingVert
2530 && hasSync
2531 && hasTextureMultisample
2532 && FindProcShort (glGetInteger64i_v)
2533 && FindProcShort (glGetBufferParameteri64v)
2534 && FindProcShort (glFramebufferTexture);
0ae9ac21 2535 if (has32)
2536 {
2537 core32 = (OpenGl_GlCore32* )(&(*myFuncs));
2538 if (isCoreProfile)
2539 {
2540 core32->glGenVertexArrays (1, &myDefaultVao);
2541 }
2542 else
2543 {
2544 core32back = (OpenGl_GlCore32Back* )(&(*myFuncs));
2545 }
2546 ::glGetIntegerv (GL_MAX_SAMPLES, &myMaxMsaaSamples);
2547 }
2548 else
2549 {
2550 checkWrongVersion (3, 2, aLastFailedProc);
2551 }
01ca42b2 2552
2553 // load GL_ARB_blend_func_extended (added to OpenGL 3.3 core)
2554 const bool hasBlendFuncExtended = (IsGlGreaterEqual (3, 3) || CheckExtension ("GL_ARB_blend_func_extended"))
2555 && FindProcShort (glBindFragDataLocationIndexed)
2556 && FindProcShort (glGetFragDataIndex);
2557
2558 // load GL_ARB_sampler_objects (added to OpenGL 3.3 core)
2559 const bool hasSamplerObjects = (IsGlGreaterEqual (3, 3) || CheckExtension ("GL_ARB_sampler_objects"))
2560 && FindProcShort (glGenSamplers)
2561 && FindProcShort (glDeleteSamplers)
2562 && FindProcShort (glIsSampler)
2563 && FindProcShort (glBindSampler)
2564 && FindProcShort (glSamplerParameteri)
2565 && FindProcShort (glSamplerParameteriv)
2566 && FindProcShort (glSamplerParameterf)
2567 && FindProcShort (glSamplerParameterfv)
2568 && FindProcShort (glSamplerParameterIiv)
2569 && FindProcShort (glSamplerParameterIuiv)
2570 && FindProcShort (glGetSamplerParameteriv)
2571 && FindProcShort (glGetSamplerParameterIiv)
2572 && FindProcShort (glGetSamplerParameterfv)
2573 && FindProcShort (glGetSamplerParameterIuiv);
cc8cbabe 2574 if (hasSamplerObjects)
2575 {
2576 arbSamplerObject = (OpenGl_ArbSamplerObject* )(&(*myFuncs));
2577 }
01ca42b2 2578
2579 // load GL_ARB_timer_query (added to OpenGL 3.3 core)
2580 const bool hasTimerQuery = (IsGlGreaterEqual (3, 3) || CheckExtension ("GL_ARB_timer_query"))
2581 && FindProcShort (glQueryCounter)
2582 && FindProcShort (glGetQueryObjecti64v)
2583 && FindProcShort (glGetQueryObjectui64v);
2584
2585 // load GL_ARB_vertex_type_2_10_10_10_rev (added to OpenGL 3.3 core)
2586 const bool hasVertType21010101rev = (IsGlGreaterEqual (3, 3) || CheckExtension ("GL_ARB_vertex_type_2_10_10_10_rev"))
0e628baf 2587 && FindProcShort (glVertexAttribP1ui)
2588 && FindProcShort (glVertexAttribP1uiv)
2589 && FindProcShort (glVertexAttribP2ui)
2590 && FindProcShort (glVertexAttribP2uiv)
2591 && FindProcShort (glVertexAttribP3ui)
2592 && FindProcShort (glVertexAttribP3uiv)
2593 && FindProcShort (glVertexAttribP4ui)
2594 && FindProcShort (glVertexAttribP4uiv);
2595
2596 if ( hasVertType21010101rev
2597 && !isCoreProfile)
2598 {
2599 // load deprecated functions
2600 const bool hasVertType21010101revExt =
2601 FindProcShort (glVertexP2ui)
01ca42b2 2602 && FindProcShort (glVertexP2uiv)
2603 && FindProcShort (glVertexP3ui)
2604 && FindProcShort (glVertexP3uiv)
2605 && FindProcShort (glVertexP4ui)
2606 && FindProcShort (glVertexP4uiv)
2607 && FindProcShort (glTexCoordP1ui)
2608 && FindProcShort (glTexCoordP1uiv)
2609 && FindProcShort (glTexCoordP2ui)
2610 && FindProcShort (glTexCoordP2uiv)
2611 && FindProcShort (glTexCoordP3ui)
2612 && FindProcShort (glTexCoordP3uiv)
2613 && FindProcShort (glTexCoordP4ui)
2614 && FindProcShort (glTexCoordP4uiv)
2615 && FindProcShort (glMultiTexCoordP1ui)
2616 && FindProcShort (glMultiTexCoordP1uiv)
2617 && FindProcShort (glMultiTexCoordP2ui)
2618 && FindProcShort (glMultiTexCoordP2uiv)
2619 && FindProcShort (glMultiTexCoordP3ui)
2620 && FindProcShort (glMultiTexCoordP3uiv)
2621 && FindProcShort (glMultiTexCoordP4ui)
2622 && FindProcShort (glMultiTexCoordP4uiv)
2623 && FindProcShort (glNormalP3ui)
2624 && FindProcShort (glNormalP3uiv)
2625 && FindProcShort (glColorP3ui)
2626 && FindProcShort (glColorP3uiv)
2627 && FindProcShort (glColorP4ui)
2628 && FindProcShort (glColorP4uiv)
2629 && FindProcShort (glSecondaryColorP3ui)
0e628baf 2630 && FindProcShort (glSecondaryColorP3uiv);
2631 (void )hasVertType21010101revExt;
2632 }
01ca42b2 2633
2634 // load OpenGL 3.3 extra functions
2635 has33 = IsGlGreaterEqual (3, 3)
2636 && hasBlendFuncExtended
2637 && hasSamplerObjects
2638 && hasTimerQuery
2639 && hasVertType21010101rev
2640 && FindProcShort (glVertexAttribDivisor);
0ae9ac21 2641 if (has33)
2642 {
2643 core33 = (OpenGl_GlCore33* )(&(*myFuncs));
2644 if (!isCoreProfile)
2645 {
2646 core33back = (OpenGl_GlCore33Back* )(&(*myFuncs));
2647 }
2648 }
2649 else
2650 {
2651 checkWrongVersion (3, 3, aLastFailedProc);
2652 }
01ca42b2 2653
2654 // load GL_ARB_draw_indirect (added to OpenGL 4.0 core)
2655 const bool hasDrawIndirect = (IsGlGreaterEqual (4, 0) || CheckExtension ("GL_ARB_draw_indirect"))
2656 && FindProcShort (glDrawArraysIndirect)
2657 && FindProcShort (glDrawElementsIndirect);
2658
2659 // load GL_ARB_gpu_shader_fp64 (added to OpenGL 4.0 core)
2660 const bool hasShaderFP64 = (IsGlGreaterEqual (4, 0) || CheckExtension ("GL_ARB_gpu_shader_fp64"))
2661 && FindProcShort (glUniform1d)
2662 && FindProcShort (glUniform2d)
2663 && FindProcShort (glUniform3d)
2664 && FindProcShort (glUniform4d)
2665 && FindProcShort (glUniform1dv)
2666 && FindProcShort (glUniform2dv)
2667 && FindProcShort (glUniform3dv)
2668 && FindProcShort (glUniform4dv)
2669 && FindProcShort (glUniformMatrix2dv)
2670 && FindProcShort (glUniformMatrix3dv)
2671 && FindProcShort (glUniformMatrix4dv)
2672 && FindProcShort (glUniformMatrix2x3dv)
2673 && FindProcShort (glUniformMatrix2x4dv)
2674 && FindProcShort (glUniformMatrix3x2dv)
2675 && FindProcShort (glUniformMatrix3x4dv)
2676 && FindProcShort (glUniformMatrix4x2dv)
2677 && FindProcShort (glUniformMatrix4x3dv)
2678 && FindProcShort (glGetUniformdv);
2679
2680 // load GL_ARB_shader_subroutine (added to OpenGL 4.0 core)
2681 const bool hasShaderSubroutine = (IsGlGreaterEqual (4, 0) || CheckExtension ("GL_ARB_shader_subroutine"))
2682 && FindProcShort (glGetSubroutineUniformLocation)
2683 && FindProcShort (glGetSubroutineIndex)
2684 && FindProcShort (glGetActiveSubroutineUniformiv)
2685 && FindProcShort (glGetActiveSubroutineUniformName)
2686 && FindProcShort (glGetActiveSubroutineName)
2687 && FindProcShort (glUniformSubroutinesuiv)
2688 && FindProcShort (glGetUniformSubroutineuiv)
2689 && FindProcShort (glGetProgramStageiv);
2690
2691 // load GL_ARB_tessellation_shader (added to OpenGL 4.0 core)
2692 const bool hasTessellationShader = (IsGlGreaterEqual (4, 0) || CheckExtension ("GL_ARB_tessellation_shader"))
2693 && FindProcShort (glPatchParameteri)
2694 && FindProcShort (glPatchParameterfv);
2695
2696 // load GL_ARB_transform_feedback2 (added to OpenGL 4.0 core)
2697 const bool hasTrsfFeedback2 = (IsGlGreaterEqual (4, 0) || CheckExtension ("GL_ARB_transform_feedback2"))
2698 && FindProcShort (glBindTransformFeedback)
2699 && FindProcShort (glDeleteTransformFeedbacks)
2700 && FindProcShort (glGenTransformFeedbacks)
2701 && FindProcShort (glIsTransformFeedback)
2702 && FindProcShort (glPauseTransformFeedback)
2703 && FindProcShort (glResumeTransformFeedback)
2704 && FindProcShort (glDrawTransformFeedback);
2705
2706 // load GL_ARB_transform_feedback3 (added to OpenGL 4.0 core)
2707 const bool hasTrsfFeedback3 = (IsGlGreaterEqual (4, 0) || CheckExtension ("GL_ARB_transform_feedback3"))
2708 && FindProcShort (glDrawTransformFeedbackStream)
2709 && FindProcShort (glBeginQueryIndexed)
2710 && FindProcShort (glEndQueryIndexed)
2711 && FindProcShort (glGetQueryIndexediv);
2712
2713 // load OpenGL 4.0 new functions
2714 has40 = IsGlGreaterEqual (4, 0)
2715 && hasDrawIndirect
2716 && hasShaderFP64
2717 && hasShaderSubroutine
2718 && hasTessellationShader
2719 && hasTrsfFeedback2
2720 && hasTrsfFeedback3
2721 && FindProcShort (glMinSampleShading)
2722 && FindProcShort (glBlendEquationi)
2723 && FindProcShort (glBlendEquationSeparatei)
2724 && FindProcShort (glBlendFunci)
2725 && FindProcShort (glBlendFuncSeparatei);
0ae9ac21 2726 if (has40)
2727 {
2728 arbTboRGB32 = Standard_True; // in core since OpenGL 4.0
2729 }
2730 else
2731 {
2732 checkWrongVersion (4, 0, aLastFailedProc);
2733 }
01ca42b2 2734
2735 // load GL_ARB_ES2_compatibility (added to OpenGL 4.1 core)
2736 const bool hasES2Compatibility = (IsGlGreaterEqual (4, 1) || CheckExtension ("GL_ARB_ES2_compatibility"))
2737 && FindProcShort (glReleaseShaderCompiler)
2738 && FindProcShort (glShaderBinary)
2739 && FindProcShort (glGetShaderPrecisionFormat)
2740 && FindProcShort (glDepthRangef)
2741 && FindProcShort (glClearDepthf);
2742
2743 // load GL_ARB_get_program_binary (added to OpenGL 4.1 core)
2744 const bool hasGetProgramBinary = (IsGlGreaterEqual (4, 1) || CheckExtension ("GL_ARB_get_program_binary"))
2745 && FindProcShort (glGetProgramBinary)
2746 && FindProcShort (glProgramBinary)
2747 && FindProcShort (glProgramParameteri);
2748
2749
2750 // load GL_ARB_separate_shader_objects (added to OpenGL 4.1 core)
2751 const bool hasSeparateShaderObjects = (IsGlGreaterEqual (4, 1) || CheckExtension ("GL_ARB_separate_shader_objects"))
2752 && FindProcShort (glUseProgramStages)
2753 && FindProcShort (glActiveShaderProgram)
2754 && FindProcShort (glCreateShaderProgramv)
2755 && FindProcShort (glBindProgramPipeline)
2756 && FindProcShort (glDeleteProgramPipelines)
2757 && FindProcShort (glGenProgramPipelines)
2758 && FindProcShort (glIsProgramPipeline)
2759 && FindProcShort (glGetProgramPipelineiv)
2760 && FindProcShort (glProgramUniform1i)
2761 && FindProcShort (glProgramUniform1iv)
2762 && FindProcShort (glProgramUniform1f)
2763 && FindProcShort (glProgramUniform1fv)
2764 && FindProcShort (glProgramUniform1d)
2765 && FindProcShort (glProgramUniform1dv)
2766 && FindProcShort (glProgramUniform1ui)
2767 && FindProcShort (glProgramUniform1uiv)
2768 && FindProcShort (glProgramUniform2i)
2769 && FindProcShort (glProgramUniform2iv)
2770 && FindProcShort (glProgramUniform2f)
2771 && FindProcShort (glProgramUniform2fv)
2772 && FindProcShort (glProgramUniform2d)
2773 && FindProcShort (glProgramUniform2dv)
2774 && FindProcShort (glProgramUniform2ui)
2775 && FindProcShort (glProgramUniform2uiv)
2776 && FindProcShort (glProgramUniform3i)
2777 && FindProcShort (glProgramUniform3iv)
2778 && FindProcShort (glProgramUniform3f)
2779 && FindProcShort (glProgramUniform3fv)
2780 && FindProcShort (glProgramUniform3d)
2781 && FindProcShort (glProgramUniform3dv)
2782 && FindProcShort (glProgramUniform3ui)
2783 && FindProcShort (glProgramUniform3uiv)
2784 && FindProcShort (glProgramUniform4i)
2785 && FindProcShort (glProgramUniform4iv)
2786 && FindProcShort (glProgramUniform4f)
2787 && FindProcShort (glProgramUniform4fv)
2788 && FindProcShort (glProgramUniform4d)
2789 && FindProcShort (glProgramUniform4dv)
2790 && FindProcShort (glProgramUniform4ui)
2791 && FindProcShort (glProgramUniform4uiv)
2792 && FindProcShort (glProgramUniformMatrix2fv)
2793 && FindProcShort (glProgramUniformMatrix3fv)
2794 && FindProcShort (glProgramUniformMatrix4fv)
2795 && FindProcShort (glProgramUniformMatrix2dv)
2796 && FindProcShort (glProgramUniformMatrix3dv)
2797 && FindProcShort (glProgramUniformMatrix4dv)
2798 && FindProcShort (glProgramUniformMatrix2x3fv)
2799 && FindProcShort (glProgramUniformMatrix3x2fv)
2800 && FindProcShort (glProgramUniformMatrix2x4fv)
2801 && FindProcShort (glProgramUniformMatrix4x2fv)
2802 && FindProcShort (glProgramUniformMatrix3x4fv)
2803 && FindProcShort (glProgramUniformMatrix4x3fv)
2804 && FindProcShort (glProgramUniformMatrix2x3dv)
2805 && FindProcShort (glProgramUniformMatrix3x2dv)
2806 && FindProcShort (glProgramUniformMatrix2x4dv)
2807 && FindProcShort (glProgramUniformMatrix4x2dv)
2808 && FindProcShort (glProgramUniformMatrix3x4dv)
2809 && FindProcShort (glProgramUniformMatrix4x3dv)
2810 && FindProcShort (glValidateProgramPipeline)
2811 && FindProcShort (glGetProgramPipelineInfoLog);
2812
2813 // load GL_ARB_vertex_attrib_64bit (added to OpenGL 4.1 core)
2814 const bool hasVertAttrib64bit = (IsGlGreaterEqual (4, 1) || CheckExtension ("GL_ARB_vertex_attrib_64bit"))
2815 && FindProcShort (glVertexAttribL1d)
2816 && FindProcShort (glVertexAttribL2d)
2817 && FindProcShort (glVertexAttribL3d)
2818 && FindProcShort (glVertexAttribL4d)
2819 && FindProcShort (glVertexAttribL1dv)
2820 && FindProcShort (glVertexAttribL2dv)
2821 && FindProcShort (glVertexAttribL3dv)
2822 && FindProcShort (glVertexAttribL4dv)
2823 && FindProcShort (glVertexAttribLPointer)
2824 && FindProcShort (glGetVertexAttribLdv);
2825
2826 // load GL_ARB_viewport_array (added to OpenGL 4.1 core)
2827 const bool hasViewportArray = (IsGlGreaterEqual (4, 1) || CheckExtension ("GL_ARB_viewport_array"))
2828 && FindProcShort (glViewportArrayv)
2829 && FindProcShort (glViewportIndexedf)
2830 && FindProcShort (glViewportIndexedfv)
2831 && FindProcShort (glScissorArrayv)
2832 && FindProcShort (glScissorIndexed)
2833 && FindProcShort (glScissorIndexedv)
2834 && FindProcShort (glDepthRangeArrayv)
2835 && FindProcShort (glDepthRangeIndexed)
2836 && FindProcShort (glGetFloati_v)
2837 && FindProcShort (glGetDoublei_v);
2838
2839 has41 = IsGlGreaterEqual (4, 1)
2840 && hasES2Compatibility
2841 && hasGetProgramBinary
2842 && hasSeparateShaderObjects
2843 && hasVertAttrib64bit
2844 && hasViewportArray;
0ae9ac21 2845 if (has41)
2846 {
2847 core41 = (OpenGl_GlCore41* )(&(*myFuncs));
2848 if (!isCoreProfile)
2849 {
2850 core41back = (OpenGl_GlCore41Back* )(&(*myFuncs));
2851 }
2852 }
2853 else
2854 {
2855 checkWrongVersion (4, 1, aLastFailedProc);
2856 }
01ca42b2 2857
2858 // load GL_ARB_base_instance (added to OpenGL 4.2 core)
2859 const bool hasBaseInstance = (IsGlGreaterEqual (4, 2) || CheckExtension ("GL_ARB_base_instance"))
2860 && FindProcShort (glDrawArraysInstancedBaseInstance)
2861 && FindProcShort (glDrawElementsInstancedBaseInstance)
2862 && FindProcShort (glDrawElementsInstancedBaseVertexBaseInstance);
2863
2864 // load GL_ARB_transform_feedback_instanced (added to OpenGL 4.2 core)
2865 const bool hasTrsfFeedbackInstanced = (IsGlGreaterEqual (4, 2) || CheckExtension ("GL_ARB_transform_feedback_instanced"))
2866 && FindProcShort (glDrawTransformFeedbackInstanced)
2867 && FindProcShort (glDrawTransformFeedbackStreamInstanced);
2868
2869 // load GL_ARB_internalformat_query (added to OpenGL 4.2 core)
2870 const bool hasInternalFormatQuery = (IsGlGreaterEqual (4, 2) || CheckExtension ("GL_ARB_internalformat_query"))
2871 && FindProcShort (glGetInternalformativ);
2872
2873 // load GL_ARB_shader_atomic_counters (added to OpenGL 4.2 core)
2874 const bool hasShaderAtomicCounters = (IsGlGreaterEqual (4, 2) || CheckExtension ("GL_ARB_shader_atomic_counters"))
2875 && FindProcShort (glGetActiveAtomicCounterBufferiv);
2876
2877 // load GL_ARB_shader_image_load_store (added to OpenGL 4.2 core)
2878 const bool hasShaderImgLoadStore = (IsGlGreaterEqual (4, 2) || CheckExtension ("GL_ARB_shader_image_load_store"))
2879 && FindProcShort (glBindImageTexture)
2880 && FindProcShort (glMemoryBarrier);
2881
2882 // load GL_ARB_texture_storage (added to OpenGL 4.2 core)
2883 const bool hasTextureStorage = (IsGlGreaterEqual (4, 2) || CheckExtension ("GL_ARB_texture_storage"))
2884 && FindProcShort (glTexStorage1D)
2885 && FindProcShort (glTexStorage2D)
c87535af 2886 && FindProcShort (glTexStorage3D);
01ca42b2 2887
2888 has42 = IsGlGreaterEqual (4, 2)
2889 && hasBaseInstance
2890 && hasTrsfFeedbackInstanced
2891 && hasInternalFormatQuery
2892 && hasShaderAtomicCounters
2893 && hasShaderImgLoadStore
2894 && hasTextureStorage;
0ae9ac21 2895 if (has42)
2896 {
2897 core42 = (OpenGl_GlCore42* )(&(*myFuncs));
2898 if (!isCoreProfile)
2899 {
2900 core42back = (OpenGl_GlCore42Back* )(&(*myFuncs));
2901 }
2902 }
2903 else
2904 {
2905 checkWrongVersion (4, 2, aLastFailedProc);
2906 }
01ca42b2 2907
2908 has43 = IsGlGreaterEqual (4, 3)
2909 && FindProcShort (glClearBufferData)
2910 && FindProcShort (glClearBufferSubData)
2911 && FindProcShort (glDispatchCompute)
2912 && FindProcShort (glDispatchComputeIndirect)
2913 && FindProcShort (glCopyImageSubData)
2914 && FindProcShort (glFramebufferParameteri)
2915 && FindProcShort (glGetFramebufferParameteriv)
2916 && FindProcShort (glGetInternalformati64v)
2917 && FindProcShort (glInvalidateTexSubImage)
2918 && FindProcShort (glInvalidateTexImage)
2919 && FindProcShort (glInvalidateBufferSubData)
2920 && FindProcShort (glInvalidateBufferData)
2921 && FindProcShort (glInvalidateFramebuffer)
2922 && FindProcShort (glInvalidateSubFramebuffer)
2923 && FindProcShort (glMultiDrawArraysIndirect)
2924 && FindProcShort (glMultiDrawElementsIndirect)
2925 && FindProcShort (glGetProgramInterfaceiv)
2926 && FindProcShort (glGetProgramResourceIndex)
2927 && FindProcShort (glGetProgramResourceName)
2928 && FindProcShort (glGetProgramResourceiv)
2929 && FindProcShort (glGetProgramResourceLocation)
2930 && FindProcShort (glGetProgramResourceLocationIndex)
2931 && FindProcShort (glShaderStorageBlockBinding)
2932 && FindProcShort (glTexBufferRange)
2933 && FindProcShort (glTexStorage2DMultisample)
2934 && FindProcShort (glTexStorage3DMultisample)
2935 && FindProcShort (glTextureView)
2936 && FindProcShort (glBindVertexBuffer)
2937 && FindProcShort (glVertexAttribFormat)
2938 && FindProcShort (glVertexAttribIFormat)
2939 && FindProcShort (glVertexAttribLFormat)
2940 && FindProcShort (glVertexAttribBinding)
2941 && FindProcShort (glVertexBindingDivisor)
2942 && FindProcShort (glDebugMessageControl)
2943 && FindProcShort (glDebugMessageInsert)
2944 && FindProcShort (glDebugMessageCallback)
2945 && FindProcShort (glGetDebugMessageLog)
2946 && FindProcShort (glPushDebugGroup)
2947 && FindProcShort (glPopDebugGroup)
2948 && FindProcShort (glObjectLabel)
2949 && FindProcShort (glGetObjectLabel)
2950 && FindProcShort (glObjectPtrLabel)
2951 && FindProcShort (glGetObjectPtrLabel);
0ae9ac21 2952 if (has43)
2953 {
2954 core43 = (OpenGl_GlCore43* )(&(*myFuncs));
2955 if (!isCoreProfile)
2956 {
2957 core43back = (OpenGl_GlCore43Back* )(&(*myFuncs));
2958 }
2959 }
2960 else
2961 {
2962 checkWrongVersion (4, 3, aLastFailedProc);
2963 }
01ca42b2 2964
2965 // load GL_ARB_clear_texture (added to OpenGL 4.4 core)
2966 bool arbTexClear = (IsGlGreaterEqual (4, 4) || CheckExtension ("GL_ARB_clear_texture"))
2967 && FindProcShort (glClearTexImage)
2968 && FindProcShort (glClearTexSubImage);
2969
2970 has44 = IsGlGreaterEqual (4, 4)
2971 && arbTexClear
2972 && FindProcShort (glBufferStorage)
2973 && FindProcShort (glBindBuffersBase)
2974 && FindProcShort (glBindBuffersRange)
2975 && FindProcShort (glBindTextures)
2976 && FindProcShort (glBindSamplers)
2977 && FindProcShort (glBindImageTextures)
2978 && FindProcShort (glBindVertexBuffers);
0ae9ac21 2979 if (has44)
2980 {
2981 core44 = (OpenGl_GlCore44* )(&(*myFuncs));
2982 if (!isCoreProfile)
2983 {
2984 core44back = (OpenGl_GlCore44Back* )(&(*myFuncs));
2985 }
2986 }
2987 else
2988 {
2989 checkWrongVersion (4, 4, aLastFailedProc);
2990 }
01ca42b2 2991
9491df8c 2992 has45 = IsGlGreaterEqual (4, 5)
2993 && FindProcShort (glBindVertexBuffers)
2994 && FindProcShort (glClipControl)
2995 && FindProcShort (glCreateTransformFeedbacks)
2996 && FindProcShort (glTransformFeedbackBufferBase)
2997 && FindProcShort (glTransformFeedbackBufferRange)
2998 && FindProcShort (glGetTransformFeedbackiv)
2999 && FindProcShort (glGetTransformFeedbacki_v)
3000 && FindProcShort (glGetTransformFeedbacki64_v)
3001 && FindProcShort (glCreateBuffers)
3002 && FindProcShort (glNamedBufferStorage)
3003 && FindProcShort (glNamedBufferData)
3004 && FindProcShort (glNamedBufferSubData)
3005 && FindProcShort (glCopyNamedBufferSubData)
3006 && FindProcShort (glClearNamedBufferData)
3007 && FindProcShort (glClearNamedBufferSubData)
3008 && FindProcShort (glMapNamedBuffer)
3009 && FindProcShort (glMapNamedBufferRange)
3010 && FindProcShort (glUnmapNamedBuffer)
3011 && FindProcShort (glFlushMappedNamedBufferRange)
3012 && FindProcShort (glGetNamedBufferParameteriv)
3013 && FindProcShort (glGetNamedBufferParameteri64v)
3014 && FindProcShort (glGetNamedBufferPointerv)
3015 && FindProcShort (glGetNamedBufferSubData)
3016 && FindProcShort (glCreateFramebuffers)
3017 && FindProcShort (glNamedFramebufferRenderbuffer)
3018 && FindProcShort (glNamedFramebufferParameteri)
3019 && FindProcShort (glNamedFramebufferTexture)
3020 && FindProcShort (glNamedFramebufferTextureLayer)
3021 && FindProcShort (glNamedFramebufferDrawBuffer)
3022 && FindProcShort (glNamedFramebufferDrawBuffers)
3023 && FindProcShort (glNamedFramebufferReadBuffer)
3024 && FindProcShort (glInvalidateNamedFramebufferData)
3025 && FindProcShort (glInvalidateNamedFramebufferSubData)
3026 && FindProcShort (glClearNamedFramebufferiv)
3027 && FindProcShort (glClearNamedFramebufferuiv)
3028 && FindProcShort (glClearNamedFramebufferfv)
3029 && FindProcShort (glClearNamedFramebufferfi)
3030 && FindProcShort (glBlitNamedFramebuffer)
3031 && FindProcShort (glCheckNamedFramebufferStatus)
3032 && FindProcShort (glGetNamedFramebufferParameteriv)
3033 && FindProcShort (glGetNamedFramebufferAttachmentParameteriv)
3034 && FindProcShort (glCreateRenderbuffers)
3035 && FindProcShort (glNamedRenderbufferStorage)
3036 && FindProcShort (glNamedRenderbufferStorageMultisample)
3037 && FindProcShort (glGetNamedRenderbufferParameteriv)
3038 && FindProcShort (glCreateTextures)
3039 && FindProcShort (glTextureBuffer)
3040 && FindProcShort (glTextureBufferRange)
3041 && FindProcShort (glTextureStorage1D)
3042 && FindProcShort (glTextureStorage2D)
3043 && FindProcShort (glTextureStorage3D)
3044 && FindProcShort (glTextureStorage2DMultisample)
3045 && FindProcShort (glTextureStorage3DMultisample)
3046 && FindProcShort (glTextureSubImage1D)
3047 && FindProcShort (glTextureSubImage2D)
3048 && FindProcShort (glTextureSubImage3D)
3049 && FindProcShort (glCompressedTextureSubImage1D)
3050 && FindProcShort (glCompressedTextureSubImage2D)
3051 && FindProcShort (glCompressedTextureSubImage3D)
3052 && FindProcShort (glCopyTextureSubImage1D)
3053 && FindProcShort (glCopyTextureSubImage2D)
3054 && FindProcShort (glCopyTextureSubImage3D)
3055 && FindProcShort (glTextureParameterf)
3056 && FindProcShort (glTextureParameterfv)
3057 && FindProcShort (glTextureParameteri)
3058 && FindProcShort (glTextureParameterIiv)
3059 && FindProcShort (glTextureParameterIuiv)
3060 && FindProcShort (glTextureParameteriv)
3061 && FindProcShort (glGenerateTextureMipmap)
3062 && FindProcShort (glBindTextureUnit)
3063 && FindProcShort (glGetTextureImage)
3064 && FindProcShort (glGetCompressedTextureImage)
3065 && FindProcShort (glGetTextureLevelParameterfv)
3066 && FindProcShort (glGetTextureLevelParameteriv)
3067 && FindProcShort (glGetTextureParameterfv)
3068 && FindProcShort (glGetTextureParameterIiv)
3069 && FindProcShort (glGetTextureParameterIuiv)
3070 && FindProcShort (glGetTextureParameteriv)
3071 && FindProcShort (glCreateVertexArrays)
3072 && FindProcShort (glDisableVertexArrayAttrib)
3073 && FindProcShort (glEnableVertexArrayAttrib)
3074 && FindProcShort (glVertexArrayElementBuffer)
3075 && FindProcShort (glVertexArrayVertexBuffer)
3076 && FindProcShort (glVertexArrayVertexBuffers)
3077 && FindProcShort (glVertexArrayAttribBinding)
3078 && FindProcShort (glVertexArrayAttribFormat)
3079 && FindProcShort (glVertexArrayAttribIFormat)
3080 && FindProcShort (glVertexArrayAttribLFormat)
3081 && FindProcShort (glVertexArrayBindingDivisor)
3082 && FindProcShort (glGetVertexArrayiv)
3083 && FindProcShort (glGetVertexArrayIndexediv)
3084 && FindProcShort (glGetVertexArrayIndexed64iv)
3085 && FindProcShort (glCreateSamplers)
3086 && FindProcShort (glCreateProgramPipelines)
3087 && FindProcShort (glCreateQueries)
3088 && FindProcShort (glGetQueryBufferObjecti64v)
3089 && FindProcShort (glGetQueryBufferObjectiv)
3090 && FindProcShort (glGetQueryBufferObjectui64v)
3091 && FindProcShort (glGetQueryBufferObjectuiv)
3092 && FindProcShort (glMemoryBarrierByRegion)
3093 && FindProcShort (glGetTextureSubImage)
3094 && FindProcShort (glGetCompressedTextureSubImage)
3095 && FindProcShort (glGetGraphicsResetStatus)
3096 && FindProcShort (glGetnCompressedTexImage)
3097 && FindProcShort (glGetnTexImage)
3098 && FindProcShort (glGetnUniformdv)
3099 && FindProcShort (glGetnUniformfv)
3100 && FindProcShort (glGetnUniformiv)
3101 && FindProcShort (glGetnUniformuiv)
3102 && FindProcShort (glReadnPixels)
3103 && FindProcShort (glGetnMapdv)
3104 && FindProcShort (glGetnMapfv)
3105 && FindProcShort (glGetnMapiv)
3106 && FindProcShort (glGetnPixelMapfv)
3107 && FindProcShort (glGetnPixelMapuiv)
3108 && FindProcShort (glGetnPixelMapusv)
3109 && FindProcShort (glGetnPolygonStipple)
3110 && FindProcShort (glGetnColorTable)
3111 && FindProcShort (glGetnConvolutionFilter)
3112 && FindProcShort (glGetnSeparableFilter)
3113 && FindProcShort (glGetnHistogram)
3114 && FindProcShort (glGetnMinmax)
3115 && FindProcShort (glTextureBarrier);
0ae9ac21 3116 if (has45)
3117 {
3118 core45 = (OpenGl_GlCore45* )(&(*myFuncs));
3119 if (!isCoreProfile)
3120 {
3121 core45back = (OpenGl_GlCore45Back* )(&(*myFuncs));
3122 }
3123 }
3124 else
3125 {
3126 checkWrongVersion (4, 5, aLastFailedProc);
3127 }
9491df8c 3128
0deb6f04 3129 // initialize debug context extension
3130 if (CheckExtension ("GL_ARB_debug_output"))
3131 {
3132 arbDbg = NULL;
3133 if (has43)
3134 {
3135 arbDbg = (OpenGl_ArbDbg* )(&(*myFuncs));
3136 }
3137 else if (FindProc ("glDebugMessageControlARB", myFuncs->glDebugMessageControl)
3138 && FindProc ("glDebugMessageInsertARB", myFuncs->glDebugMessageInsert)
3139 && FindProc ("glDebugMessageCallbackARB", myFuncs->glDebugMessageCallback)
3140 && FindProc ("glGetDebugMessageLogARB", myFuncs->glGetDebugMessageLog))
3141 {
3142 arbDbg = (OpenGl_ArbDbg* )(&(*myFuncs));
3143 }
3144
3145 if (arbDbg != NULL
3146 && caps->contextDebug)
3147 {
3148 // setup default callback
3149 myIsGlDebugCtx = Standard_True;
3150 arbDbg->glDebugMessageCallback (debugCallbackWrap, this);
3151 if (has43)
3152 {
3153 ::glEnable (GL_DEBUG_OUTPUT);
3154 }
3155 if (caps->contextSyncDebug)
3156 {
3157 ::glEnable (GL_DEBUG_OUTPUT_SYNCHRONOUS);
3158 }
3159 }
3160 }
3161
01ca42b2 3162 // initialize FBO extension (ARB)
3163 if (hasFBO)
2166f0fa 3164 {
b86bb3df 3165 arbFBO = (OpenGl_ArbFBO* )(&(*myFuncs));
3166 arbFBOBlit = (OpenGl_ArbFBOBlit* )(&(*myFuncs));
01ca42b2 3167 extPDS = Standard_True; // extension for EXT, but part of ARB
2166f0fa 3168 }
5f8b738e 3169
37eb4787 3170 // initialize GS extension (EXT)
01ca42b2 3171 if (CheckExtension ("GL_EXT_geometry_shader4")
3172 && FindProcShort (glProgramParameteriEXT))
37eb4787 3173 {
01ca42b2 3174 extGS = (OpenGl_ExtGS* )(&(*myFuncs));
37eb4787 3175 }
3176
25ef750e 3177 // initialize bindless texture extension (ARB)
3178 if (CheckExtension ("GL_ARB_bindless_texture")
3179 && FindProcShort (glGetTextureHandleARB)
3180 && FindProcShort (glGetTextureSamplerHandleARB)
3181 && FindProcShort (glMakeTextureHandleResidentARB)
3182 && FindProcShort (glMakeTextureHandleNonResidentARB)
3183 && FindProcShort (glGetImageHandleARB)
3184 && FindProcShort (glMakeImageHandleResidentARB)
3185 && FindProcShort (glMakeImageHandleNonResidentARB)
3186 && FindProcShort (glUniformHandleui64ARB)
3187 && FindProcShort (glUniformHandleui64vARB)
3188 && FindProcShort (glProgramUniformHandleui64ARB)
3189 && FindProcShort (glProgramUniformHandleui64vARB)
3190 && FindProcShort (glIsTextureHandleResidentARB)
3191 && FindProcShort (glIsImageHandleResidentARB)
3192 && FindProcShort (glVertexAttribL1ui64ARB)
3193 && FindProcShort (glVertexAttribL1ui64vARB)
3194 && FindProcShort (glGetVertexAttribLui64vARB))
3195 {
3196 arbTexBindless = (OpenGl_ArbTexBindless* )(&(*myFuncs));
3197 }
3198
0ae9ac21 3199 if (has30)
01ca42b2 3200 {
0ae9ac21 3201 // MSAA RenderBuffers have been defined in OpenGL 3.0,
3202 // but MSAA Textures - only in OpenGL 3.2+
3203 if (!has32
3204 && CheckExtension ("GL_ARB_texture_multisample")
3205 && FindProcShort (glTexImage2DMultisample))
3206 {
3207 GLint aNbColorSamples = 0, aNbDepthSamples = 0;
3208 ::glGetIntegerv (GL_MAX_COLOR_TEXTURE_SAMPLES, &aNbColorSamples);
3209 ::glGetIntegerv (GL_MAX_DEPTH_TEXTURE_SAMPLES, &aNbDepthSamples);
3210 myMaxMsaaSamples = Min (aNbColorSamples, aNbDepthSamples);
3211 }
3212 if (!has43
3213 && CheckExtension ("GL_ARB_texture_storage_multisample")
3214 && FindProcShort (glTexStorage2DMultisample))
3215 {
3216 //
3217 }
01ca42b2 3218 }
01ca42b2 3219
3a9b5dc8 3220 // check whether ray tracing mode is supported
3221 myHasRayTracing = has31
3222 && arbTboRGB32
3223 && arbFBOBlit != NULL;
3224
3225 // check whether textures in ray tracing mode are supported
3226 myHasRayTracingTextures = myHasRayTracing
3227 && arbTexBindless != NULL;
3228
3229 // check whether adaptive screen sampling in ray tracing mode is supported
3230 myHasRayTracingAdaptiveSampling = myHasRayTracing
e084dbbc 3231 && has44;
3232 myHasRayTracingAdaptiveSamplingAtomic = myHasRayTracingAdaptiveSampling
3233 && CheckExtension ("GL_NV_shader_atomic_float");
ca3c13d1 3234#endif
ba00aab7 3235
3236 if (arbFBO != NULL
3237 && hasFboSRGB)
3238 {
3239 // Detect if window buffer is considered by OpenGL as sRGB-ready
3240 // (linear RGB color written by shader is automatically converted into sRGB)
3241 // or not (offscreen FBO should be blit into window buffer with gamma correction).
3242 const GLenum aDefWinBuffer =
3243 #if !defined(GL_ES_VERSION_2_0)
3244 GL_BACK_LEFT;
3245 #else
3246 GL_BACK;
3247 #endif
3248 GLint aWinColorEncoding = 0; // GL_LINEAR
3249 arbFBO->glGetFramebufferAttachmentParameteriv (GL_FRAMEBUFFER, aDefWinBuffer, GL_FRAMEBUFFER_ATTACHMENT_COLOR_ENCODING, &aWinColorEncoding);
3250 ResetErrors (true);
3251 myIsSRgbWindow = aWinColorEncoding == GL_SRGB;
3252
3253 // On desktop OpenGL, pixel formats are almost always sRGB-ready, even when not requested;
3254 // it is safe behavior on desktop where GL_FRAMEBUFFER_SRGB is disabled by default
3255 // (contrary to OpenGL ES, where it is enabled by default).
3256 // NVIDIA drivers, however, always return GL_LINEAR even for sRGB-ready pixel formats on Windows platform,
3257 // while AMD and Intel report GL_SRGB as expected.
3258 // macOS drivers seems to be also report GL_LINEAR even for [NSColorSpace sRGBColorSpace].
3259 #if !defined(GL_ES_VERSION_2_0)
3260 #ifdef __APPLE__
3261 myIsSRgbWindow = true;
3262 #else
3263 if (!myIsSRgbWindow
3264 && myVendor.Search ("nvidia") != -1)
3265 {
3266 myIsSRgbWindow = true;
3267 }
3268 #endif
3269 #endif
3270 if (!myIsSRgbWindow)
3271 {
a87b1b37 3272 Message::SendTrace ("OpenGl_Context, warning: window buffer is not sRGB-ready.\n"
3273 "Check OpenGL window creation parameters for optimal performance.");
ba00aab7 3274 }
3275 }
67312b79 3276
faff3767 3277 if (arbTexFloat)
3278 {
3279 mySupportedFormats->Add (Image_Format_GrayF);
3280 mySupportedFormats->Add (Image_Format_AlphaF);
3281 mySupportedFormats->Add (Image_Format_RGBF);
3282 mySupportedFormats->Add (Image_Format_RGBAF);
3283 if (arbTexRG)
3284 {
3285 mySupportedFormats->Add (Image_Format_RGF);
3286 }
3287 if (extBgra)
3288 {
3289 #if !defined(GL_ES_VERSION_2_0)
3290 mySupportedFormats->Add (Image_Format_BGRF);
3291 #endif
3292 mySupportedFormats->Add (Image_Format_BGRAF);
3293 }
3294 }
3295
3296#ifdef __EMSCRIPTEN__
3297 if (checkEnableWebGlExtension (*this, "GL_WEBGL_compressed_texture_s3tc")) // GL_WEBGL_compressed_texture_s3tc_srgb for sRGB formats
3298 {
3299 mySupportedFormats->Add (Image_CompressedFormat_RGB_S3TC_DXT1);
3300 mySupportedFormats->Add (Image_CompressedFormat_RGBA_S3TC_DXT1);
3301 mySupportedFormats->Add (Image_CompressedFormat_RGBA_S3TC_DXT3);
3302 mySupportedFormats->Add (Image_CompressedFormat_RGBA_S3TC_DXT5);
3303 }
3304#else
3305 if (CheckExtension ("GL_EXT_texture_compression_s3tc")) // GL_EXT_texture_sRGB for sRGB formats
3306 {
3307 mySupportedFormats->Add (Image_CompressedFormat_RGB_S3TC_DXT1);
3308 mySupportedFormats->Add (Image_CompressedFormat_RGBA_S3TC_DXT1);
3309 mySupportedFormats->Add (Image_CompressedFormat_RGBA_S3TC_DXT3);
3310 mySupportedFormats->Add (Image_CompressedFormat_RGBA_S3TC_DXT5);
3311 }
3312 else
3313 {
3314 if (CheckExtension ("GL_EXT_texture_compression_dxt1"))
3315 {
3316 mySupportedFormats->Add (Image_CompressedFormat_RGB_S3TC_DXT1);
3317 mySupportedFormats->Add (Image_CompressedFormat_RGBA_S3TC_DXT1);
3318 }
3319 if (CheckExtension ("GL_ANGLE_texture_compression_dxt3"))
3320 {
3321 mySupportedFormats->Add (Image_CompressedFormat_RGBA_S3TC_DXT3);
3322 }
3323 if (CheckExtension ("GL_ANGLE_texture_compression_dxt5"))
3324 {
3325 mySupportedFormats->Add (Image_CompressedFormat_RGBA_S3TC_DXT5);
3326 }
3327 }
3328#endif
3329
67312b79 3330 // check whether PBR shading model is supported
3331 myHasPBR = arbFBO != NULL
3332 && myMaxTexCombined >= 4
3333 && arbTexRG
3334 && arbTexFloat
3335 && (IsGlGreaterEqual (3, 0)
3336 #if !defined(GL_ES_VERSION_2_0)
3337 || (IsGlGreaterEqual (2, 1) && CheckExtension ("GL_EXT_gpu_shader4"))
3338 #endif
3339 );
3340 if (myHasPBR)
3341 {
72f6dc61 3342 myPBREnvLUTTexUnit = static_cast<Graphic3d_TextureUnit>(myMaxTexCombined + Graphic3d_TextureUnit_PbrEnvironmentLUT);
3343 myPBRDiffIBLMapSHTexUnit = static_cast<Graphic3d_TextureUnit>(myMaxTexCombined + Graphic3d_TextureUnit_PbrIblDiffuseSH);
3344 myPBRSpecIBLMapTexUnit = static_cast<Graphic3d_TextureUnit>(myMaxTexCombined + Graphic3d_TextureUnit_PbrIblSpecular);
67312b79 3345 }
2166f0fa 3346}
f0430952 3347
3348// =======================================================================
3349// function : MemoryInfo
3350// purpose :
3351// =======================================================================
3352Standard_Size OpenGl_Context::AvailableMemory() const
3353{
ca3c13d1 3354#if !defined(GL_ES_VERSION_2_0)
f0430952 3355 if (atiMem)
3356 {
3357 // this is actually information for VBO pool
3358 // however because pools are mostly shared
3359 // it can be used for total GPU memory estimations
3360 GLint aMemInfo[4];
3361 aMemInfo[0] = 0;
3362 glGetIntegerv (GL_VBO_FREE_MEMORY_ATI, aMemInfo);
3363 // returned value is in KiB, however this maybe changed in future
3364 return Standard_Size(aMemInfo[0]) * 1024;
3365 }
3366 else if (nvxMem)
3367 {
3368 // current available dedicated video memory (in KiB), currently unused GPU memory
3369 GLint aMemInfo = 0;
3370 glGetIntegerv (GL_GPU_MEMORY_INFO_CURRENT_AVAILABLE_VIDMEM_NVX, &aMemInfo);
3371 return Standard_Size(aMemInfo) * 1024;
3372 }
ca3c13d1 3373#endif
f0430952 3374 return 0;
3375}
3376
3377// =======================================================================
3378// function : MemoryInfo
3379// purpose :
3380// =======================================================================
3381TCollection_AsciiString OpenGl_Context::MemoryInfo() const
3382{
26d9c835 3383 TColStd_IndexedDataMapOfStringString aDict;
3384 MemoryInfo (aDict);
3385
3386 TCollection_AsciiString aText;
3387 for (TColStd_IndexedDataMapOfStringString::Iterator anIter (aDict); anIter.More(); anIter.Next())
3388 {
3389 if (!aText.IsEmpty())
3390 {
3391 aText += "\n";
3392 }
3393 aText += TCollection_AsciiString(" ") + anIter.Key() + ": " + anIter.Value();
3394 }
3395 return aText;
3396}
3397
3398// =======================================================================
3399// function : MemoryInfo
3400// purpose :
3401// =======================================================================
3402void OpenGl_Context::MemoryInfo (TColStd_IndexedDataMapOfStringString& theDict) const
3403{
3404#if defined(GL_ES_VERSION_2_0)
3405 (void )theDict;
3406#elif defined(__APPLE__) && !defined(MACOSX_USE_GLX)
3407 GLint aGlRendId = 0;
3408 CGLGetParameter (CGLGetCurrentContext(), kCGLCPCurrentRendererID, &aGlRendId);
3409
3410 CGLRendererInfoObj aRendObj = NULL;
3411 CGOpenGLDisplayMask aDispMask = CGDisplayIDToOpenGLDisplayMask (kCGDirectMainDisplay);
3412 GLint aRendNb = 0;
3413 CGLQueryRendererInfo (aDispMask, &aRendObj, &aRendNb);
3414 for (GLint aRendIter = 0; aRendIter < aRendNb; ++aRendIter)
3415 {
3416 GLint aRendId = 0;
3417 if (CGLDescribeRenderer (aRendObj, aRendIter, kCGLRPRendererID, &aRendId) != kCGLNoError
3418 || aRendId != aGlRendId)
3419 {
3420 continue;
3421 }
3422
3423 //kCGLRPVideoMemoryMegabytes = 131;
3424 //kCGLRPTextureMemoryMegabytes = 132;
3425 GLint aVMem = 0;
3426 #if MAC_OS_X_VERSION_MIN_REQUIRED >= 1070
3427 if (CGLDescribeRenderer(aRendObj, aRendIter, kCGLRPVideoMemoryMegabytes, &aVMem) == kCGLNoError)
3428 {
3429 addInfo (theDict, "GPU memory", TCollection_AsciiString() + aVMem + " MiB");
3430 }
3431 if (CGLDescribeRenderer(aRendObj, aRendIter, kCGLRPTextureMemoryMegabytes, &aVMem) == kCGLNoError)
3432 {
3433 addInfo (theDict, "GPU Texture memory", TCollection_AsciiString() + aVMem + " MiB");
3434 }
3435 #else
3436 if (CGLDescribeRenderer(aRendObj, aRendIter, kCGLRPVideoMemory, &aVMem) == kCGLNoError)
3437 {
3438 addInfo (theDict, "GPU memory", TCollection_AsciiString() + (aVMem / (1024 * 1024)) + " MiB");
3439 }
3440 if (CGLDescribeRenderer(aRendObj, aRendIter, kCGLRPTextureMemory, &aVMem) == kCGLNoError)
3441 {
3442 addInfo (theDict, "GPU Texture memory", TCollection_AsciiString() + (aVMem / (1024 * 1024)) + " MiB");
3443 }
3444 #endif
3445 }
3446#endif
3447
ca3c13d1