1 /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
2 /* vim: set ts=8 sts=2 et sw=2 tw=80: */
3 /* This Source Code Form is subject to the terms of the Mozilla Public
4 * License, v. 2.0. If a copy of the MPL was not distributed with this
5 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
24 // Define MOZ_GL_DEBUG unconditionally to enable GL debugging in opt
27 # define MOZ_GL_DEBUG 1
30 #include "mozilla/IntegerRange.h"
31 #include "mozilla/RefPtr.h"
32 #include "mozilla/UniquePtr.h"
33 #include "mozilla/ThreadLocal.h"
35 #include "MozFramebuffer.h"
40 #include "nsRegionFwd.h"
42 #include "GLContextTypes.h"
43 #include "GLContextSymbols.h"
44 #include "base/platform_thread.h" // for PlatformThreadId
45 #include "mozilla/GenericRefCounted.h"
46 #include "mozilla/WeakPtr.h"
48 #ifdef MOZ_WIDGET_ANDROID
49 # include "mozilla/ProfilerLabels.h"
57 class GLReadTexImageHelper
;
64 class ColorTextureLayerProgram
;
68 class CompositorWidget
;
70 } // namespace mozilla
75 enum class GLFeature
{
87 EXT_color_buffer_float
,
91 framebuffer_multisample
,
93 framebuffer_object_EXT_OES
,
95 get_integer64_indexed
,
96 get_query_object_i64v
,
100 instanced_non_arrays
,
101 internalformat_query
,
102 invalidate_framebuffer
,
106 occlusion_query_boolean
,
108 packed_depth_stencil
,
115 renderbuffer_color_float
,
116 renderbuffer_color_half_float
,
117 robust_buffer_access_behavior
,
121 seamless_cube_map_opt_in
,
124 standard_derivatives
,
127 texture_3D_compressed
,
129 texture_compression_bptc
,
130 texture_compression_rgtc
,
132 texture_float_linear
,
134 texture_half_float_linear
,
135 texture_non_power_of_two
,
141 uniform_buffer_object
,
142 uniform_matrix_nonsquare
,
147 enum class ContextProfile
: uint8_t {
154 enum class GLVendor
{
167 enum class GLRenderer
{
185 MicrosoftBasicRenderDriver
,
189 class GLContext
: public GenericAtomicRefCounted
, public SupportsWeakPtr
{
191 static MOZ_THREAD_LOCAL(uintptr_t) sCurrentContext
;
193 const GLContextDesc mDesc
;
195 bool mImplicitMakeCurrent
= false;
196 bool mUseTLSIsCurrent
;
198 class TlsScope final
{
199 const WeakPtr
<GLContext
> mGL
;
200 const bool mWasTlsOk
;
203 explicit TlsScope(GLContext
* const gl
)
204 : mGL(gl
), mWasTlsOk(gl
&& gl
->mUseTLSIsCurrent
) {
206 mGL
->mUseTLSIsCurrent
= true;
212 mGL
->mUseTLSIsCurrent
= mWasTlsOk
;
217 // -----------------------------------------------------------------------------
221 * Returns true if the context is using ANGLE. This should only be overridden
222 * for an ANGLE implementation.
224 virtual bool IsANGLE() const { return false; }
227 * Returns true if the context is using WARP. This should only be overridden
228 * for an ANGLE implementation.
230 virtual bool IsWARP() const { return false; }
232 virtual void GetWSIInfo(nsCString
* const out
) const = 0;
235 * Return true if we are running on a OpenGL core profile context
237 inline bool IsCoreProfile() const {
238 MOZ_ASSERT(mProfile
!= ContextProfile::Unknown
, "unknown context profile");
240 return mProfile
== ContextProfile::OpenGLCore
;
244 * Return true if we are running on a OpenGL compatibility profile context
245 * (legacy profile 2.1 on Max OS X)
247 inline bool IsCompatibilityProfile() const {
248 MOZ_ASSERT(mProfile
!= ContextProfile::Unknown
, "unknown context profile");
250 return mProfile
== ContextProfile::OpenGLCompatibility
;
253 inline bool IsGLES() const {
254 MOZ_ASSERT(mProfile
!= ContextProfile::Unknown
, "unknown context profile");
256 return mProfile
== ContextProfile::OpenGLES
;
259 inline bool IsAtLeast(ContextProfile profile
, unsigned int version
) const {
260 MOZ_ASSERT(profile
!= ContextProfile::Unknown
,
261 "IsAtLeast: bad <profile> parameter");
262 MOZ_ASSERT(mProfile
!= ContextProfile::Unknown
, "unknown context profile");
263 MOZ_ASSERT(mVersion
!= 0, "unknown context version");
265 if (version
> mVersion
) {
269 return profile
== mProfile
;
273 * Return the version of the context.
275 * If this a OpenGL 2.1, that will return 210
277 inline uint32_t Version() const { return mVersion
; }
279 inline uint32_t ShadingLanguageVersion() const {
280 return mShadingLanguageVersion
;
283 GLVendor
Vendor() const { return mVendor
; }
284 GLRenderer
Renderer() const { return mRenderer
; }
285 bool IsMesa() const { return mIsMesa
; }
287 bool IsContextLost() const { return mContextLost
; }
289 bool CheckContextLost() const {
290 mTopError
= GetError();
291 return IsContextLost();
294 bool HasPBOState() const { return (!IsGLES() || Version() >= 300); }
297 * If this context is double-buffered, returns TRUE.
299 virtual bool IsDoubleBuffered() const { return false; }
301 virtual GLContextType
GetContextType() const = 0;
303 virtual bool IsCurrentImpl() const = 0;
304 virtual bool MakeCurrentImpl() const = 0;
306 bool IsCurrent() const {
307 if (mImplicitMakeCurrent
) return MakeCurrent();
309 return IsCurrentImpl();
312 bool MakeCurrent(bool aForce
= false) const;
315 * Get the default framebuffer for this context.
317 UniquePtr
<MozFramebuffer
> mOffscreenDefaultFb
;
319 bool CreateOffscreenDefaultFb(const gfx::IntSize
& size
);
321 virtual GLuint
GetDefaultFramebuffer() {
322 if (mOffscreenDefaultFb
) {
323 return mOffscreenDefaultFb
->mFB
;
329 * mVersion store the OpenGL's version, multiplied by 100. For example, if
330 * the context is an OpenGL 2.1 context, mVersion value will be 210.
332 uint32_t mVersion
= 0;
333 ContextProfile mProfile
= ContextProfile::Unknown
;
335 uint32_t mShadingLanguageVersion
= 0;
337 GLVendor mVendor
= GLVendor::Other
;
338 GLRenderer mRenderer
= GLRenderer::Other
;
339 bool mIsMesa
= false;
341 // -----------------------------------------------------------------------------
342 // Extensions management
344 * This mechanism is designed to know if an extension is supported. In the
345 * long term, we would like to only use the extension group queries XXX_* to
346 * have full compatibility with context version and profiles (especialy the
347 * core that officialy don't bring any extensions).
351 * Known GL extensions that can be queried by
352 * IsExtensionSupported. The results of this are cached, and as
353 * such it's safe to use this even in performance critical code.
354 * If you add to this array, remember to add to the string names
359 AMD_compressed_ATC_texture
,
361 ANGLE_framebuffer_blit
,
362 ANGLE_framebuffer_multisample
,
363 ANGLE_instanced_arrays
,
365 ANGLE_texture_compression_dxt3
,
366 ANGLE_texture_compression_dxt5
,
368 APPLE_client_storage
,
370 APPLE_framebuffer_multisample
,
373 APPLE_vertex_array_object
,
374 ARB_ES2_compatibility
,
375 ARB_ES3_compatibility
,
376 ARB_color_buffer_float
,
382 ARB_framebuffer_object
,
383 ARB_framebuffer_sRGB
,
384 ARB_geometry_shader4
,
385 ARB_half_float_pixel
,
386 ARB_instanced_arrays
,
387 ARB_internalformat_query
,
388 ARB_invalidate_subdata
,
389 ARB_map_buffer_range
,
390 ARB_occlusion_query2
,
391 ARB_pixel_buffer_object
,
392 ARB_robust_buffer_access_behavior
,
395 ARB_seamless_cube_map
,
396 ARB_shader_texture_lod
,
398 ARB_texture_compression
,
399 ARB_texture_compression_bptc
,
400 ARB_texture_compression_rgtc
,
402 ARB_texture_non_power_of_two
,
403 ARB_texture_rectangle
,
408 ARB_transform_feedback2
,
409 ARB_uniform_buffer_object
,
410 ARB_vertex_array_object
,
411 CHROMIUM_color_buffer_float_rgb
,
412 CHROMIUM_color_buffer_float_rgba
,
415 EXT_color_buffer_float
,
416 EXT_color_buffer_half_float
,
418 EXT_disjoint_timer_query
,
424 EXT_framebuffer_blit
,
425 EXT_framebuffer_multisample
,
426 EXT_framebuffer_object
,
427 EXT_framebuffer_sRGB
,
429 EXT_map_buffer_range
,
430 EXT_multisampled_render_to_texture
,
431 EXT_occlusion_query_boolean
,
432 EXT_packed_depth_stencil
,
433 EXT_read_format_bgra
,
436 EXT_sRGB_write_control
,
437 EXT_shader_texture_lod
,
438 EXT_texture_compression_bptc
,
439 EXT_texture_compression_dxt1
,
440 EXT_texture_compression_rgtc
,
441 EXT_texture_compression_s3tc
,
442 EXT_texture_compression_s3tc_srgb
,
443 EXT_texture_filter_anisotropic
,
444 EXT_texture_format_BGRA8888
,
449 EXT_transform_feedback
,
452 IMG_texture_compression_pvrtc
,
455 KHR_parallel_shader_compile
,
456 KHR_robust_buffer_access_behavior
,
458 KHR_texture_compression_astc_hdr
,
459 KHR_texture_compression_astc_ldr
,
463 NV_geometry_program4
,
466 NV_primitive_restart
,
468 NV_transform_feedback
,
469 NV_transform_feedback2
,
471 OES_EGL_image_external
,
473 OES_compressed_ETC1_RGB8_texture
,
477 OES_draw_buffers_indexed
,
478 OES_element_index_uint
,
479 OES_fbo_render_mipmap
,
480 OES_framebuffer_object
,
481 OES_packed_depth_stencil
,
483 OES_standard_derivatives
,
487 OES_texture_float_linear
,
488 OES_texture_half_float
,
489 OES_texture_half_float_linear
,
491 OES_vertex_array_object
,
497 bool IsExtensionSupported(GLExtensions aKnownExtension
) const {
498 return mAvailableExtensions
[aKnownExtension
];
502 void MarkExtensionUnsupported(GLExtensions aKnownExtension
) {
503 mAvailableExtensions
[aKnownExtension
] = 0;
506 void MarkExtensionSupported(GLExtensions aKnownExtension
) {
507 mAvailableExtensions
[aKnownExtension
] = 1;
510 std::bitset
<Extensions_Max
> mAvailableExtensions
;
512 // -----------------------------------------------------------------------------
515 * This mecahnism introduces a new way to check if a OpenGL feature is
516 * supported, regardless of whether it is supported by an extension or
517 * natively by the context version/profile
520 bool IsSupported(GLFeature feature
) const {
521 return mAvailableFeatures
[size_t(feature
)];
524 static const char* GetFeatureName(GLFeature feature
);
527 std::bitset
<size_t(GLFeature::EnumMax
)> mAvailableFeatures
;
530 * Init features regarding OpenGL extension and context version and profile
535 * Mark the feature and associated extensions as unsupported
537 void MarkUnsupported(GLFeature feature
);
540 * Is this feature supported using the core (unsuffixed) symbols?
542 bool IsFeatureProvidedByCoreSymbols(GLFeature feature
);
544 // -----------------------------------------------------------------------------
548 mutable bool mContextLost
= false;
549 mutable GLenum mTopError
= 0;
552 void OnContextLostError() const;
555 static std::string
GLErrorToString(GLenum aError
);
557 static bool IsBadCallError(const GLenum err
) {
558 return !(err
== 0 || err
== LOCAL_GL_CONTEXT_LOST
);
561 class LocalErrorScope
;
564 mutable std::stack
<const LocalErrorScope
*> mLocalErrorScopeStack
;
565 mutable UniquePtr
<LocalErrorScope
> mDebugErrorScope
;
567 ////////////////////////////////////
568 // Use this safer option.
571 class LocalErrorScope
{
572 const GLContext
& mGL
;
574 bool mHasBeenChecked
;
577 explicit LocalErrorScope(const GLContext
& gl
)
578 : mGL(gl
), mHasBeenChecked(false) {
579 mGL
.mLocalErrorScopeStack
.push(this);
580 mOldTop
= mGL
.GetError();
583 /// Never returns CONTEXT_LOST.
585 MOZ_ASSERT(!mHasBeenChecked
);
586 mHasBeenChecked
= true;
588 const auto ret
= mGL
.GetError();
589 if (ret
== LOCAL_GL_CONTEXT_LOST
) return 0;
594 MOZ_ASSERT(mHasBeenChecked
);
596 MOZ_ASSERT(!IsBadCallError(mGL
.GetError()));
598 MOZ_ASSERT(mGL
.mLocalErrorScopeStack
.top() == this);
599 mGL
.mLocalErrorScopeStack
.pop();
601 mGL
.mTopError
= mOldTop
;
607 bool GetPotentialInteger(GLenum pname
, GLint
* param
) {
608 LocalErrorScope
localError(*this);
610 fGetIntegerv(pname
, param
);
612 GLenum err
= localError
.GetError();
613 MOZ_ASSERT_IF(err
!= LOCAL_GL_NO_ERROR
, err
== LOCAL_GL_INVALID_ENUM
);
614 return err
== LOCAL_GL_NO_ERROR
;
617 void DebugCallback(GLenum source
, GLenum type
, GLuint id
, GLenum severity
,
618 GLsizei length
, const GLchar
* message
);
621 static void GLAPIENTRY
StaticDebugCallback(GLenum source
, GLenum type
,
622 GLuint id
, GLenum severity
,
624 const GLchar
* message
,
625 const GLvoid
* userParam
);
627 // -----------------------------------------------------------------------------
628 // MOZ_GL_DEBUG implementation
630 #ifndef MOZ_FUNCTION_NAME
632 # define MOZ_FUNCTION_NAME __PRETTY_FUNCTION__
633 # elif defined(_MSC_VER)
634 # define MOZ_FUNCTION_NAME __FUNCTION__
636 # define MOZ_FUNCTION_NAME \
637 __func__ // defined in C99, supported in various C++ compilers. Just raw
642 #ifdef MOZ_WIDGET_ANDROID
643 // Record the name of the GL call for better hang stacks on Android.
644 # define ANDROID_ONLY_PROFILER_LABEL AUTO_PROFILER_LABEL(__func__, GRAPHICS);
646 # define ANDROID_ONLY_PROFILER_LABEL
649 #define BEFORE_GL_CALL \
650 ANDROID_ONLY_PROFILER_LABEL \
651 if (MOZ_LIKELY(BeforeGLCall(MOZ_FUNCTION_NAME))) { \
655 #define AFTER_GL_CALL \
656 AfterGLCall(MOZ_FUNCTION_NAME); \
661 void BeforeGLCall_Debug(const char* funcName
) const;
662 void AfterGLCall_Debug(const char* funcName
) const;
663 static void OnImplicitMakeCurrentFailure(const char* funcName
);
665 bool BeforeGLCall(const char* const funcName
) const {
666 if (mImplicitMakeCurrent
) {
667 if (MOZ_UNLIKELY(!MakeCurrent())) {
669 OnImplicitMakeCurrentFailure(funcName
);
674 MOZ_GL_ASSERT(this, IsCurrentImpl());
676 if (MOZ_UNLIKELY(mDebugFlags
)) {
677 BeforeGLCall_Debug(funcName
);
682 void AfterGLCall(const char* const funcName
) const {
683 if (MOZ_UNLIKELY(mDebugFlags
)) {
684 AfterGLCall_Debug(funcName
);
688 GLContext
* TrackingContext() {
689 GLContext
* tip
= this;
690 while (tip
->mSharedContext
) tip
= tip
->mSharedContext
;
694 static void AssertNotPassingStackBufferToTheGL(const void* ptr
);
698 # define TRACKING_CONTEXT(a) \
700 TrackingContext()->a; \
703 # define ASSERT_NOT_PASSING_STACK_BUFFER_TO_GL(ptr) \
704 AssertNotPassingStackBufferToTheGL(ptr)
706 # define ASSERT_SYMBOL_PRESENT(func) \
708 MOZ_ASSERT(strstr(MOZ_FUNCTION_NAME, #func) != nullptr, \
709 "Mismatched symbol check."); \
710 if (MOZ_UNLIKELY(!mSymbols.func)) { \
711 printf_stderr("RUNTIME ASSERT: Uninitialized GL function: %s\n", \
713 MOZ_CRASH("GFX: Uninitialized GL function"); \
717 #else // ifdef MOZ_GL_DEBUG
719 # define TRACKING_CONTEXT(a) \
722 # define ASSERT_NOT_PASSING_STACK_BUFFER_TO_GL(ptr) \
725 # define ASSERT_SYMBOL_PRESENT(func) \
729 #endif // ifdef MOZ_GL_DEBUG
731 // Do whatever setup is necessary to draw to our offscreen FBO, if it's
733 void BeforeGLDrawCall() {}
735 // Do whatever tear-down is necessary after drawing to our offscreen FBO,
737 void AfterGLDrawCall() { mHeavyGLCallsSinceLastFlush
= true; }
739 // Do whatever setup is necessary to read from our offscreen FBO, if it's
741 void BeforeGLReadCall() {}
743 // Do whatever tear-down is necessary after reading from our offscreen FBO,
745 void AfterGLReadCall() {}
748 void OnSyncCall() const { mSyncGLCallCount
++; }
750 uint64_t GetSyncCallCount() const { return mSyncGLCallCount
; }
752 void ResetSyncCallCount(const char* resetReason
) const;
754 // -----------------------------------------------------------------------------
755 // GL official entry points
757 // We smash all errors together, so you never have to loop on this. We
758 // guarantee that immediately after this call, there are no errors left.
759 // Always returns the top-most error, except if followed by CONTEXT_LOST, then
760 // return that instead.
761 GLenum
GetError() const;
763 GLenum
fGetError() { return GetError(); }
765 GLenum
fGetGraphicsResetStatus() const;
769 void fActiveTexture(GLenum texture
) {
771 mSymbols
.fActiveTexture(texture
);
775 void fAttachShader(GLuint program
, GLuint shader
) {
777 mSymbols
.fAttachShader(program
, shader
);
781 void fBeginQuery(GLenum target
, GLuint id
) {
783 ASSERT_SYMBOL_PRESENT(fBeginQuery
);
784 mSymbols
.fBeginQuery(target
, id
);
788 void fBindAttribLocation(GLuint program
, GLuint index
, const GLchar
* name
) {
790 mSymbols
.fBindAttribLocation(program
, index
, name
);
794 void fBindBuffer(GLenum target
, GLuint buffer
) {
796 mSymbols
.fBindBuffer(target
, buffer
);
800 void fInvalidateFramebuffer(GLenum target
, GLsizei numAttachments
,
801 const GLenum
* attachments
) {
804 ASSERT_SYMBOL_PRESENT(fInvalidateFramebuffer
);
805 mSymbols
.fInvalidateFramebuffer(target
, numAttachments
, attachments
);
810 void fInvalidateSubFramebuffer(GLenum target
, GLsizei numAttachments
,
811 const GLenum
* attachments
, GLint x
, GLint y
,
812 GLsizei width
, GLsizei height
) {
815 ASSERT_SYMBOL_PRESENT(fInvalidateSubFramebuffer
);
816 mSymbols
.fInvalidateSubFramebuffer(target
, numAttachments
, attachments
, x
,
822 void fBindTexture(GLenum target
, GLuint texture
) {
824 mSymbols
.fBindTexture(target
, texture
);
828 void fBlendColor(GLfloat red
, GLfloat green
, GLfloat blue
, GLfloat alpha
) {
830 mSymbols
.fBlendColor(red
, green
, blue
, alpha
);
834 void fBlendEquation(GLenum mode
) {
836 mSymbols
.fBlendEquation(mode
);
840 void fBlendEquationSeparate(GLenum modeRGB
, GLenum modeAlpha
) {
842 mSymbols
.fBlendEquationSeparate(modeRGB
, modeAlpha
);
846 void fBlendFunc(GLenum sfactor
, GLenum dfactor
) {
848 mSymbols
.fBlendFunc(sfactor
, dfactor
);
852 void fBlendFuncSeparate(GLenum sfactorRGB
, GLenum dfactorRGB
,
853 GLenum sfactorAlpha
, GLenum dfactorAlpha
) {
855 mSymbols
.fBlendFuncSeparate(sfactorRGB
, dfactorRGB
, sfactorAlpha
,
861 void raw_fBufferData(GLenum target
, GLsizeiptr size
, const GLvoid
* data
,
863 ASSERT_NOT_PASSING_STACK_BUFFER_TO_GL(data
);
865 mSymbols
.fBufferData(target
, size
, data
, usage
);
868 mHeavyGLCallsSinceLastFlush
= true;
872 void fBufferData(GLenum target
, GLsizeiptr size
, const GLvoid
* data
,
874 raw_fBufferData(target
, size
, data
, usage
);
877 if (WorkAroundDriverBugs() && !data
&& Vendor() == GLVendor::NVIDIA
) {
878 UniquePtr
<char[]> buf
= MakeUnique
<char[]>(1);
880 fBufferSubData(target
, size
- 1, 1, buf
.get());
884 void fBufferSubData(GLenum target
, GLintptr offset
, GLsizeiptr size
,
885 const GLvoid
* data
) {
886 ASSERT_NOT_PASSING_STACK_BUFFER_TO_GL(data
);
888 mSymbols
.fBufferSubData(target
, offset
, size
, data
);
890 mHeavyGLCallsSinceLastFlush
= true;
894 void raw_fClear(GLbitfield mask
) {
896 mSymbols
.fClear(mask
);
901 void fClear(GLbitfield mask
) {
907 void fClearBufferfi(GLenum buffer
, GLint drawbuffer
, GLfloat depth
,
911 mSymbols
.fClearBufferfi(buffer
, drawbuffer
, depth
, stencil
);
916 void fClearBufferfv(GLenum buffer
, GLint drawbuffer
, const GLfloat
* value
) {
919 mSymbols
.fClearBufferfv(buffer
, drawbuffer
, value
);
924 void fClearBufferiv(GLenum buffer
, GLint drawbuffer
, const GLint
* value
) {
927 mSymbols
.fClearBufferiv(buffer
, drawbuffer
, value
);
932 void fClearBufferuiv(GLenum buffer
, GLint drawbuffer
, const GLuint
* value
) {
935 mSymbols
.fClearBufferuiv(buffer
, drawbuffer
, value
);
940 void fClearColor(GLfloat r
, GLfloat g
, GLfloat b
, GLfloat a
) {
942 mSymbols
.fClearColor(r
, g
, b
, a
);
946 void fClearStencil(GLint s
) {
948 mSymbols
.fClearStencil(s
);
952 void fClientActiveTexture(GLenum texture
) {
954 mSymbols
.fClientActiveTexture(texture
);
958 void fColorMask(realGLboolean red
, realGLboolean green
, realGLboolean blue
,
959 realGLboolean alpha
) {
961 mSymbols
.fColorMask(red
, green
, blue
, alpha
);
965 void fCompressedTexImage2D(GLenum target
, GLint level
, GLenum internalformat
,
966 GLsizei width
, GLsizei height
, GLint border
,
967 GLsizei imageSize
, const GLvoid
* pixels
) {
968 ASSERT_NOT_PASSING_STACK_BUFFER_TO_GL(pixels
);
970 mSymbols
.fCompressedTexImage2D(target
, level
, internalformat
, width
, height
,
971 border
, imageSize
, pixels
);
973 mHeavyGLCallsSinceLastFlush
= true;
976 void fCompressedTexSubImage2D(GLenum target
, GLint level
, GLint xoffset
,
977 GLint yoffset
, GLsizei width
, GLsizei height
,
978 GLenum format
, GLsizei imageSize
,
979 const GLvoid
* pixels
) {
980 ASSERT_NOT_PASSING_STACK_BUFFER_TO_GL(pixels
);
982 mSymbols
.fCompressedTexSubImage2D(target
, level
, xoffset
, yoffset
, width
,
983 height
, format
, imageSize
, pixels
);
985 mHeavyGLCallsSinceLastFlush
= true;
988 void fCopyTexImage2D(GLenum target
, GLint level
, GLenum internalformat
,
989 GLint x
, GLint y
, GLsizei width
, GLsizei height
,
992 void fCopyTexSubImage2D(GLenum target
, GLint level
, GLint xoffset
,
993 GLint yoffset
, GLint x
, GLint y
, GLsizei width
,
996 raw_fCopyTexSubImage2D(target
, level
, xoffset
, yoffset
, x
, y
, width
,
1001 void fCullFace(GLenum mode
) {
1003 mSymbols
.fCullFace(mode
);
1007 void fDebugMessageCallback(GLDEBUGPROC callback
, const GLvoid
* userParam
) {
1009 ASSERT_SYMBOL_PRESENT(fDebugMessageCallback
);
1010 mSymbols
.fDebugMessageCallback(callback
, userParam
);
1014 void fDebugMessageControl(GLenum source
, GLenum type
, GLenum severity
,
1015 GLsizei count
, const GLuint
* ids
,
1016 realGLboolean enabled
) {
1018 ASSERT_SYMBOL_PRESENT(fDebugMessageControl
);
1019 mSymbols
.fDebugMessageControl(source
, type
, severity
, count
, ids
, enabled
);
1023 void fDebugMessageInsert(GLenum source
, GLenum type
, GLuint id
,
1024 GLenum severity
, GLsizei length
, const GLchar
* buf
) {
1026 ASSERT_SYMBOL_PRESENT(fDebugMessageInsert
);
1027 mSymbols
.fDebugMessageInsert(source
, type
, id
, severity
, length
, buf
);
1031 void fDetachShader(GLuint program
, GLuint shader
) {
1033 mSymbols
.fDetachShader(program
, shader
);
1037 void fDepthFunc(GLenum func
) {
1039 mSymbols
.fDepthFunc(func
);
1043 void fDepthMask(realGLboolean flag
) {
1045 mSymbols
.fDepthMask(flag
);
1049 void fDisable(GLenum capability
) {
1051 mSymbols
.fDisable(capability
);
1055 void fDisableClientState(GLenum capability
) {
1057 mSymbols
.fDisableClientState(capability
);
1061 void fDisableVertexAttribArray(GLuint index
) {
1063 mSymbols
.fDisableVertexAttribArray(index
);
1067 void fDrawBuffer(GLenum mode
) {
1069 mSymbols
.fDrawBuffer(mode
);
1074 void raw_fDrawArrays(GLenum mode
, GLint first
, GLsizei count
) {
1076 mSymbols
.fDrawArrays(mode
, first
, count
);
1080 void raw_fDrawElements(GLenum mode
, GLsizei count
, GLenum type
,
1081 const GLvoid
* indices
) {
1083 mSymbols
.fDrawElements(mode
, count
, type
, indices
);
1088 void fDrawArrays(GLenum mode
, GLint first
, GLsizei count
) {
1090 raw_fDrawArrays(mode
, first
, count
);
1094 void fDrawElements(GLenum mode
, GLsizei count
, GLenum type
,
1095 const GLvoid
* indices
) {
1097 raw_fDrawElements(mode
, count
, type
, indices
);
1101 void fEnable(GLenum capability
) {
1103 mSymbols
.fEnable(capability
);
1107 void fEnableClientState(GLenum capability
) {
1109 mSymbols
.fEnableClientState(capability
);
1113 void fEnableVertexAttribArray(GLuint index
) {
1115 mSymbols
.fEnableVertexAttribArray(index
);
1119 void fEndQuery(GLenum target
) {
1121 ASSERT_SYMBOL_PRESENT(fEndQuery
);
1122 mSymbols
.fEndQuery(target
);
1131 mHeavyGLCallsSinceLastFlush
= false;
1138 mHeavyGLCallsSinceLastFlush
= false;
1141 void fFrontFace(GLenum face
) {
1143 mSymbols
.fFrontFace(face
);
1147 void fGetActiveAttrib(GLuint program
, GLuint index
, GLsizei maxLength
,
1148 GLsizei
* length
, GLint
* size
, GLenum
* type
,
1151 mSymbols
.fGetActiveAttrib(program
, index
, maxLength
, length
, size
, type
,
1157 void fGetActiveUniform(GLuint program
, GLuint index
, GLsizei maxLength
,
1158 GLsizei
* length
, GLint
* size
, GLenum
* type
,
1161 mSymbols
.fGetActiveUniform(program
, index
, maxLength
, length
, size
, type
,
1167 void fGetAttachedShaders(GLuint program
, GLsizei maxCount
, GLsizei
* count
,
1170 mSymbols
.fGetAttachedShaders(program
, maxCount
, count
, shaders
);
1175 GLint
fGetAttribLocation(GLuint program
, const GLchar
* name
) {
1178 retval
= mSymbols
.fGetAttribLocation(program
, name
);
1185 void raw_fGetIntegerv(GLenum pname
, GLint
* params
) const {
1187 mSymbols
.fGetIntegerv(pname
, params
);
1193 void fGetIntegerv(GLenum pname
, GLint
* params
) const;
1195 template <typename T
>
1196 void GetInt(const GLenum pname
, T
* const params
) const {
1197 static_assert(sizeof(T
) == sizeof(GLint
), "Invalid T.");
1198 fGetIntegerv(pname
, reinterpret_cast<GLint
*>(params
));
1201 void GetUIntegerv(GLenum pname
, GLuint
* params
) const {
1202 GetInt(pname
, params
);
1205 template <typename T
>
1206 T
GetIntAs(GLenum pname
) const {
1207 static_assert(sizeof(T
) == sizeof(GLint
), "Invalid T.");
1209 fGetIntegerv(pname
, (GLint
*)&ret
);
1213 void fGetFloatv(GLenum pname
, GLfloat
* params
) const {
1215 mSymbols
.fGetFloatv(pname
, params
);
1220 void fGetBooleanv(GLenum pname
, realGLboolean
* params
) const {
1222 mSymbols
.fGetBooleanv(pname
, params
);
1227 void fGetBufferParameteriv(GLenum target
, GLenum pname
, GLint
* params
) {
1229 mSymbols
.fGetBufferParameteriv(target
, pname
, params
);
1234 GLuint
fGetDebugMessageLog(GLuint count
, GLsizei bufsize
, GLenum
* sources
,
1235 GLenum
* types
, GLuint
* ids
, GLenum
* severities
,
1236 GLsizei
* lengths
, GLchar
* messageLog
) {
1239 ASSERT_SYMBOL_PRESENT(fGetDebugMessageLog
);
1240 ret
= mSymbols
.fGetDebugMessageLog(count
, bufsize
, sources
, types
, ids
,
1241 severities
, lengths
, messageLog
);
1247 void fGetPointerv(GLenum pname
, GLvoid
** params
) {
1249 ASSERT_SYMBOL_PRESENT(fGetPointerv
);
1250 mSymbols
.fGetPointerv(pname
, params
);
1255 void fGetObjectLabel(GLenum identifier
, GLuint name
, GLsizei bufSize
,
1256 GLsizei
* length
, GLchar
* label
) {
1258 ASSERT_SYMBOL_PRESENT(fGetObjectLabel
);
1259 mSymbols
.fGetObjectLabel(identifier
, name
, bufSize
, length
, label
);
1264 void fGetObjectPtrLabel(const GLvoid
* ptr
, GLsizei bufSize
, GLsizei
* length
,
1267 ASSERT_SYMBOL_PRESENT(fGetObjectPtrLabel
);
1268 mSymbols
.fGetObjectPtrLabel(ptr
, bufSize
, length
, label
);
1273 void fGenerateMipmap(GLenum target
) {
1275 mSymbols
.fGenerateMipmap(target
);
1279 void fGetProgramiv(GLuint program
, GLenum pname
, GLint
* param
) {
1281 mSymbols
.fGetProgramiv(program
, pname
, param
);
1286 void fGetProgramInfoLog(GLuint program
, GLsizei bufSize
, GLsizei
* length
,
1289 mSymbols
.fGetProgramInfoLog(program
, bufSize
, length
, infoLog
);
1294 void fTexParameteri(GLenum target
, GLenum pname
, GLint param
) {
1296 mSymbols
.fTexParameteri(target
, pname
, param
);
1300 void fTexParameteriv(GLenum target
, GLenum pname
, const GLint
* params
) {
1302 mSymbols
.fTexParameteriv(target
, pname
, params
);
1306 void fTexParameterf(GLenum target
, GLenum pname
, GLfloat param
) {
1308 mSymbols
.fTexParameterf(target
, pname
, param
);
1312 const GLubyte
* fGetString(GLenum name
) {
1313 const GLubyte
* result
= nullptr;
1315 result
= mSymbols
.fGetString(name
);
1321 void fGetTexImage(GLenum target
, GLint level
, GLenum format
, GLenum type
,
1324 ASSERT_SYMBOL_PRESENT(fGetTexImage
);
1325 mSymbols
.fGetTexImage(target
, level
, format
, type
, img
);
1330 void fGetTexLevelParameteriv(GLenum target
, GLint level
, GLenum pname
,
1333 ASSERT_SYMBOL_PRESENT(fGetTexLevelParameteriv
);
1334 mSymbols
.fGetTexLevelParameteriv(target
, level
, pname
, params
);
1339 void fGetTexParameterfv(GLenum target
, GLenum pname
, GLfloat
* params
) {
1341 mSymbols
.fGetTexParameterfv(target
, pname
, params
);
1346 void fGetTexParameteriv(GLenum target
, GLenum pname
, GLint
* params
) {
1348 mSymbols
.fGetTexParameteriv(target
, pname
, params
);
1353 void fGetUniformfv(GLuint program
, GLint location
, GLfloat
* params
) {
1355 mSymbols
.fGetUniformfv(program
, location
, params
);
1360 void fGetUniformiv(GLuint program
, GLint location
, GLint
* params
) {
1362 mSymbols
.fGetUniformiv(program
, location
, params
);
1367 void fGetUniformuiv(GLuint program
, GLint location
, GLuint
* params
) {
1369 ASSERT_SYMBOL_PRESENT(fGetUniformuiv
);
1370 mSymbols
.fGetUniformuiv(program
, location
, params
);
1375 GLint
fGetUniformLocation(GLuint programObj
, const GLchar
* name
) {
1378 retval
= mSymbols
.fGetUniformLocation(programObj
, name
);
1384 void fGetVertexAttribfv(GLuint index
, GLenum pname
, GLfloat
* retval
) {
1386 mSymbols
.fGetVertexAttribfv(index
, pname
, retval
);
1391 void fGetVertexAttribiv(GLuint index
, GLenum pname
, GLint
* retval
) {
1393 mSymbols
.fGetVertexAttribiv(index
, pname
, retval
);
1398 void fGetVertexAttribPointerv(GLuint index
, GLenum pname
, GLvoid
** retval
) {
1400 mSymbols
.fGetVertexAttribPointerv(index
, pname
, retval
);
1405 void fHint(GLenum target
, GLenum mode
) {
1407 mSymbols
.fHint(target
, mode
);
1411 realGLboolean
fIsBuffer(GLuint buffer
) {
1412 realGLboolean retval
= false;
1414 retval
= mSymbols
.fIsBuffer(buffer
);
1420 realGLboolean
fIsEnabled(GLenum capability
) {
1421 realGLboolean retval
= false;
1423 retval
= mSymbols
.fIsEnabled(capability
);
1428 void SetEnabled(const GLenum cap
, const bool val
) {
1436 bool PushEnabled(const GLenum cap
, const bool newVal
) {
1437 const bool oldVal
= fIsEnabled(cap
);
1438 if (oldVal
!= newVal
) {
1439 SetEnabled(cap
, newVal
);
1444 realGLboolean
fIsProgram(GLuint program
) {
1445 realGLboolean retval
= false;
1447 retval
= mSymbols
.fIsProgram(program
);
1452 realGLboolean
fIsShader(GLuint shader
) {
1453 realGLboolean retval
= false;
1455 retval
= mSymbols
.fIsShader(shader
);
1460 realGLboolean
fIsTexture(GLuint texture
) {
1461 realGLboolean retval
= false;
1463 retval
= mSymbols
.fIsTexture(texture
);
1468 void fLineWidth(GLfloat width
) {
1470 mSymbols
.fLineWidth(width
);
1474 void fLinkProgram(GLuint program
) {
1476 mSymbols
.fLinkProgram(program
);
1480 void fObjectLabel(GLenum identifier
, GLuint name
, GLsizei length
,
1481 const GLchar
* label
) {
1483 ASSERT_SYMBOL_PRESENT(fObjectLabel
);
1484 mSymbols
.fObjectLabel(identifier
, name
, length
, label
);
1488 void fObjectPtrLabel(const GLvoid
* ptr
, GLsizei length
, const GLchar
* label
) {
1490 ASSERT_SYMBOL_PRESENT(fObjectPtrLabel
);
1491 mSymbols
.fObjectPtrLabel(ptr
, length
, label
);
1495 void fLoadIdentity() {
1497 mSymbols
.fLoadIdentity();
1501 void fLoadMatrixf(const GLfloat
* matrix
) {
1503 mSymbols
.fLoadMatrixf(matrix
);
1507 void fMatrixMode(GLenum mode
) {
1509 mSymbols
.fMatrixMode(mode
);
1513 void fPixelStorei(GLenum pname
, GLint param
) {
1515 mSymbols
.fPixelStorei(pname
, param
);
1519 void fTextureRangeAPPLE(GLenum target
, GLsizei length
, GLvoid
* pointer
) {
1520 ASSERT_NOT_PASSING_STACK_BUFFER_TO_GL(pointer
);
1522 mSymbols
.fTextureRangeAPPLE(target
, length
, pointer
);
1526 void fPointParameterf(GLenum pname
, GLfloat param
) {
1528 mSymbols
.fPointParameterf(pname
, param
);
1532 void fPolygonMode(GLenum face
, GLenum mode
) {
1534 mSymbols
.fPolygonMode(face
, mode
);
1538 void fPolygonOffset(GLfloat factor
, GLfloat bias
) {
1540 mSymbols
.fPolygonOffset(factor
, bias
);
1544 void fPopDebugGroup() {
1546 ASSERT_SYMBOL_PRESENT(fPopDebugGroup
);
1547 mSymbols
.fPopDebugGroup();
1551 void fPushDebugGroup(GLenum source
, GLuint id
, GLsizei length
,
1552 const GLchar
* message
) {
1554 ASSERT_SYMBOL_PRESENT(fPushDebugGroup
);
1555 mSymbols
.fPushDebugGroup(source
, id
, length
, message
);
1559 void fReadBuffer(GLenum mode
) {
1561 mSymbols
.fReadBuffer(mode
);
1565 void raw_fReadPixels(GLint x
, GLint y
, GLsizei width
, GLsizei height
,
1566 GLenum format
, GLenum type
, GLvoid
* pixels
) {
1568 mSymbols
.fReadPixels(x
, y
, width
, height
, format
, type
, pixels
);
1571 mHeavyGLCallsSinceLastFlush
= true;
1574 void fReadPixels(GLint x
, GLint y
, GLsizei width
, GLsizei height
,
1575 GLenum format
, GLenum type
, GLvoid
* pixels
);
1578 void fSampleCoverage(GLclampf value
, realGLboolean invert
) {
1580 mSymbols
.fSampleCoverage(value
, invert
);
1584 void fScissor(GLint x
, GLint y
, GLsizei width
, GLsizei height
) {
1585 if (mScissorRect
[0] == x
&& mScissorRect
[1] == y
&&
1586 mScissorRect
[2] == width
&& mScissorRect
[3] == height
) {
1589 mScissorRect
[0] = x
;
1590 mScissorRect
[1] = y
;
1591 mScissorRect
[2] = width
;
1592 mScissorRect
[3] = height
;
1594 mSymbols
.fScissor(x
, y
, width
, height
);
1598 void fStencilFunc(GLenum func
, GLint reference
, GLuint mask
) {
1600 mSymbols
.fStencilFunc(func
, reference
, mask
);
1604 void fStencilFuncSeparate(GLenum frontfunc
, GLenum backfunc
, GLint reference
,
1607 mSymbols
.fStencilFuncSeparate(frontfunc
, backfunc
, reference
, mask
);
1611 void fStencilMask(GLuint mask
) {
1613 mSymbols
.fStencilMask(mask
);
1617 void fStencilMaskSeparate(GLenum face
, GLuint mask
) {
1619 mSymbols
.fStencilMaskSeparate(face
, mask
);
1623 void fStencilOp(GLenum fail
, GLenum zfail
, GLenum zpass
) {
1625 mSymbols
.fStencilOp(fail
, zfail
, zpass
);
1629 void fStencilOpSeparate(GLenum face
, GLenum sfail
, GLenum dpfail
,
1632 mSymbols
.fStencilOpSeparate(face
, sfail
, dpfail
, dppass
);
1636 void fTexGeni(GLenum coord
, GLenum pname
, GLint param
) {
1638 mSymbols
.fTexGeni(coord
, pname
, param
);
1642 void fTexGenf(GLenum coord
, GLenum pname
, GLfloat param
) {
1644 mSymbols
.fTexGenf(coord
, pname
, param
);
1648 void fTexGenfv(GLenum coord
, GLenum pname
, const GLfloat
* params
) {
1650 mSymbols
.fTexGenfv(coord
, pname
, params
);
1655 void raw_fTexImage2D(GLenum target
, GLint level
, GLint internalformat
,
1656 GLsizei width
, GLsizei height
, GLint border
,
1657 GLenum format
, GLenum type
, const GLvoid
* pixels
) {
1658 ASSERT_NOT_PASSING_STACK_BUFFER_TO_GL(pixels
);
1660 mSymbols
.fTexImage2D(target
, level
, internalformat
, width
, height
, border
,
1661 format
, type
, pixels
);
1663 mHeavyGLCallsSinceLastFlush
= true;
1667 void fTexImage2D(GLenum target
, GLint level
, GLint internalformat
,
1668 GLsizei width
, GLsizei height
, GLint border
, GLenum format
,
1669 GLenum type
, const GLvoid
* pixels
);
1671 void fTexSubImage2D(GLenum target
, GLint level
, GLint xoffset
, GLint yoffset
,
1672 GLsizei width
, GLsizei height
, GLenum format
, GLenum type
,
1673 const GLvoid
* pixels
) {
1674 ASSERT_NOT_PASSING_STACK_BUFFER_TO_GL(pixels
);
1676 mSymbols
.fTexSubImage2D(target
, level
, xoffset
, yoffset
, width
, height
,
1677 format
, type
, pixels
);
1679 mHeavyGLCallsSinceLastFlush
= true;
1682 void fUniform1f(GLint location
, GLfloat v0
) {
1684 mSymbols
.fUniform1f(location
, v0
);
1688 void fUniform1fv(GLint location
, GLsizei count
, const GLfloat
* value
) {
1690 mSymbols
.fUniform1fv(location
, count
, value
);
1694 void fUniform1i(GLint location
, GLint v0
) {
1696 mSymbols
.fUniform1i(location
, v0
);
1700 void fUniform1iv(GLint location
, GLsizei count
, const GLint
* value
) {
1702 mSymbols
.fUniform1iv(location
, count
, value
);
1706 void fUniform2f(GLint location
, GLfloat v0
, GLfloat v1
) {
1708 mSymbols
.fUniform2f(location
, v0
, v1
);
1712 void fUniform2fv(GLint location
, GLsizei count
, const GLfloat
* value
) {
1714 mSymbols
.fUniform2fv(location
, count
, value
);
1718 void fUniform2i(GLint location
, GLint v0
, GLint v1
) {
1720 mSymbols
.fUniform2i(location
, v0
, v1
);
1724 void fUniform2iv(GLint location
, GLsizei count
, const GLint
* value
) {
1726 mSymbols
.fUniform2iv(location
, count
, value
);
1730 void fUniform3f(GLint location
, GLfloat v0
, GLfloat v1
, GLfloat v2
) {
1732 mSymbols
.fUniform3f(location
, v0
, v1
, v2
);
1736 void fUniform3fv(GLint location
, GLsizei count
, const GLfloat
* value
) {
1738 mSymbols
.fUniform3fv(location
, count
, value
);
1742 void fUniform3i(GLint location
, GLint v0
, GLint v1
, GLint v2
) {
1744 mSymbols
.fUniform3i(location
, v0
, v1
, v2
);
1748 void fUniform3iv(GLint location
, GLsizei count
, const GLint
* value
) {
1750 mSymbols
.fUniform3iv(location
, count
, value
);
1754 void fUniform4f(GLint location
, GLfloat v0
, GLfloat v1
, GLfloat v2
,
1757 mSymbols
.fUniform4f(location
, v0
, v1
, v2
, v3
);
1761 void fUniform4fv(GLint location
, GLsizei count
, const GLfloat
* value
) {
1763 mSymbols
.fUniform4fv(location
, count
, value
);
1767 void fUniform4i(GLint location
, GLint v0
, GLint v1
, GLint v2
, GLint v3
) {
1769 mSymbols
.fUniform4i(location
, v0
, v1
, v2
, v3
);
1773 void fUniform4iv(GLint location
, GLsizei count
, const GLint
* value
) {
1775 mSymbols
.fUniform4iv(location
, count
, value
);
1779 void fUniformMatrix2fv(GLint location
, GLsizei count
, realGLboolean transpose
,
1780 const GLfloat
* value
) {
1782 mSymbols
.fUniformMatrix2fv(location
, count
, transpose
, value
);
1786 void fUniformMatrix2x3fv(GLint location
, GLsizei count
,
1787 realGLboolean transpose
, const GLfloat
* value
) {
1789 ASSERT_SYMBOL_PRESENT(fUniformMatrix2x3fv
);
1790 mSymbols
.fUniformMatrix2x3fv(location
, count
, transpose
, value
);
1794 void fUniformMatrix2x4fv(GLint location
, GLsizei count
,
1795 realGLboolean transpose
, const GLfloat
* value
) {
1797 ASSERT_SYMBOL_PRESENT(fUniformMatrix2x4fv
);
1798 mSymbols
.fUniformMatrix2x4fv(location
, count
, transpose
, value
);
1802 void fUniformMatrix3fv(GLint location
, GLsizei count
, realGLboolean transpose
,
1803 const GLfloat
* value
) {
1805 mSymbols
.fUniformMatrix3fv(location
, count
, transpose
, value
);
1809 void fUniformMatrix3x2fv(GLint location
, GLsizei count
,
1810 realGLboolean transpose
, const GLfloat
* value
) {
1812 ASSERT_SYMBOL_PRESENT(fUniformMatrix3x2fv
);
1813 mSymbols
.fUniformMatrix3x2fv(location
, count
, transpose
, value
);
1817 void fUniformMatrix3x4fv(GLint location
, GLsizei count
,
1818 realGLboolean transpose
, const GLfloat
* value
) {
1820 ASSERT_SYMBOL_PRESENT(fUniformMatrix3x4fv
);
1821 mSymbols
.fUniformMatrix3x4fv(location
, count
, transpose
, value
);
1825 void fUniformMatrix4fv(GLint location
, GLsizei count
, realGLboolean transpose
,
1826 const GLfloat
* value
) {
1828 mSymbols
.fUniformMatrix4fv(location
, count
, transpose
, value
);
1832 void fUniformMatrix4x2fv(GLint location
, GLsizei count
,
1833 realGLboolean transpose
, const GLfloat
* value
) {
1835 ASSERT_SYMBOL_PRESENT(fUniformMatrix4x2fv
);
1836 mSymbols
.fUniformMatrix4x2fv(location
, count
, transpose
, value
);
1840 void fUniformMatrix4x3fv(GLint location
, GLsizei count
,
1841 realGLboolean transpose
, const GLfloat
* value
) {
1843 ASSERT_SYMBOL_PRESENT(fUniformMatrix4x3fv
);
1844 mSymbols
.fUniformMatrix4x3fv(location
, count
, transpose
, value
);
1848 void fUseProgram(GLuint program
) {
1850 mSymbols
.fUseProgram(program
);
1854 void fValidateProgram(GLuint program
) {
1856 mSymbols
.fValidateProgram(program
);
1860 void fVertexAttribPointer(GLuint index
, GLint size
, GLenum type
,
1861 realGLboolean normalized
, GLsizei stride
,
1862 const GLvoid
* pointer
) {
1864 mSymbols
.fVertexAttribPointer(index
, size
, type
, normalized
, stride
,
1869 void fVertexAttrib1f(GLuint index
, GLfloat x
) {
1871 mSymbols
.fVertexAttrib1f(index
, x
);
1875 void fVertexAttrib2f(GLuint index
, GLfloat x
, GLfloat y
) {
1877 mSymbols
.fVertexAttrib2f(index
, x
, y
);
1881 void fVertexAttrib3f(GLuint index
, GLfloat x
, GLfloat y
, GLfloat z
) {
1883 mSymbols
.fVertexAttrib3f(index
, x
, y
, z
);
1887 void fVertexAttrib4f(GLuint index
, GLfloat x
, GLfloat y
, GLfloat z
,
1890 mSymbols
.fVertexAttrib4f(index
, x
, y
, z
, w
);
1894 void fVertexAttrib1fv(GLuint index
, const GLfloat
* v
) {
1896 mSymbols
.fVertexAttrib1fv(index
, v
);
1900 void fVertexAttrib2fv(GLuint index
, const GLfloat
* v
) {
1902 mSymbols
.fVertexAttrib2fv(index
, v
);
1906 void fVertexAttrib3fv(GLuint index
, const GLfloat
* v
) {
1908 mSymbols
.fVertexAttrib3fv(index
, v
);
1912 void fVertexAttrib4fv(GLuint index
, const GLfloat
* v
) {
1914 mSymbols
.fVertexAttrib4fv(index
, v
);
1918 void fVertexPointer(GLint size
, GLenum type
, GLsizei stride
,
1919 const GLvoid
* pointer
) {
1921 mSymbols
.fVertexPointer(size
, type
, stride
, pointer
);
1925 void fViewport(GLint x
, GLint y
, GLsizei width
, GLsizei height
) {
1926 if (mViewportRect
[0] == x
&& mViewportRect
[1] == y
&&
1927 mViewportRect
[2] == width
&& mViewportRect
[3] == height
) {
1930 mViewportRect
[0] = x
;
1931 mViewportRect
[1] = y
;
1932 mViewportRect
[2] = width
;
1933 mViewportRect
[3] = height
;
1935 mSymbols
.fViewport(x
, y
, width
, height
);
1939 void fCompileShader(GLuint shader
) {
1941 mSymbols
.fCompileShader(shader
);
1946 friend class SharedSurface_IOSurface
;
1948 void raw_fCopyTexImage2D(GLenum target
, GLint level
, GLenum internalformat
,
1949 GLint x
, GLint y
, GLsizei width
, GLsizei height
,
1952 mSymbols
.fCopyTexImage2D(target
, level
, internalformat
, x
, y
, width
, height
,
1957 void raw_fCopyTexSubImage2D(GLenum target
, GLint level
, GLint xoffset
,
1958 GLint yoffset
, GLint x
, GLint y
, GLsizei width
,
1961 mSymbols
.fCopyTexSubImage2D(target
, level
, xoffset
, yoffset
, x
, y
, width
,
1967 void fGetShaderiv(GLuint shader
, GLenum pname
, GLint
* param
) {
1969 mSymbols
.fGetShaderiv(shader
, pname
, param
);
1974 void fGetShaderInfoLog(GLuint shader
, GLsizei bufSize
, GLsizei
* length
,
1977 mSymbols
.fGetShaderInfoLog(shader
, bufSize
, length
, infoLog
);
1983 void raw_fGetShaderPrecisionFormat(GLenum shadertype
, GLenum precisiontype
,
1984 GLint
* range
, GLint
* precision
) {
1985 MOZ_ASSERT(IsGLES());
1988 ASSERT_SYMBOL_PRESENT(fGetShaderPrecisionFormat
);
1989 mSymbols
.fGetShaderPrecisionFormat(shadertype
, precisiontype
, range
,
1996 void fGetShaderPrecisionFormat(GLenum shadertype
, GLenum precisiontype
,
1997 GLint
* range
, GLint
* precision
) {
1999 raw_fGetShaderPrecisionFormat(shadertype
, precisiontype
, range
,
2002 // Fall back to automatic values because almost all desktop hardware
2003 // supports the OpenGL standard precisions.
2004 GetShaderPrecisionFormatNonES2(shadertype
, precisiontype
, range
,
2009 void fGetShaderSource(GLint obj
, GLsizei maxLength
, GLsizei
* length
,
2012 mSymbols
.fGetShaderSource(obj
, maxLength
, length
, source
);
2017 void fShaderSource(GLuint shader
, GLsizei count
, const GLchar
* const* strings
,
2018 const GLint
* lengths
) {
2020 mSymbols
.fShaderSource(shader
, count
, strings
, lengths
);
2025 mutable GLuint mCachedDrawFb
= 0;
2026 mutable GLuint mCachedReadFb
= 0;
2029 bool mElideDuplicateBindFramebuffers
= false;
2031 void fBindFramebuffer(const GLenum target
, const GLuint fb
) const {
2032 if (mElideDuplicateBindFramebuffers
) {
2033 MOZ_ASSERT(mCachedDrawFb
==
2034 GetIntAs
<GLuint
>(LOCAL_GL_DRAW_FRAMEBUFFER_BINDING
));
2035 MOZ_ASSERT(mCachedReadFb
==
2036 GetIntAs
<GLuint
>(LOCAL_GL_READ_FRAMEBUFFER_BINDING
));
2039 case LOCAL_GL_FRAMEBUFFER
:
2040 if (mCachedDrawFb
== fb
&& mCachedReadFb
== fb
) return;
2042 case LOCAL_GL_DRAW_FRAMEBUFFER
:
2043 if (mCachedDrawFb
== fb
) return;
2045 case LOCAL_GL_READ_FRAMEBUFFER
:
2046 if (mCachedReadFb
== fb
) return;
2052 mSymbols
.fBindFramebuffer(target
, fb
);
2056 case LOCAL_GL_FRAMEBUFFER
:
2060 case LOCAL_GL_DRAW_FRAMEBUFFER
:
2063 case LOCAL_GL_READ_FRAMEBUFFER
:
2069 void fBindRenderbuffer(GLenum target
, GLuint renderbuffer
) {
2071 mSymbols
.fBindRenderbuffer(target
, renderbuffer
);
2075 GLenum
fCheckFramebufferStatus(GLenum target
) {
2078 retval
= mSymbols
.fCheckFramebufferStatus(target
);
2084 void fFramebufferRenderbuffer(GLenum target
, GLenum attachmentPoint
,
2085 GLenum renderbufferTarget
,
2086 GLuint renderbuffer
) {
2088 mSymbols
.fFramebufferRenderbuffer(target
, attachmentPoint
,
2089 renderbufferTarget
, renderbuffer
);
2093 void fFramebufferTexture2D(GLenum target
, GLenum attachmentPoint
,
2094 GLenum textureTarget
, GLuint texture
,
2097 mSymbols
.fFramebufferTexture2D(target
, attachmentPoint
, textureTarget
,
2100 if (mNeedsCheckAfterAttachTextureToFb
) {
2101 fCheckFramebufferStatus(target
);
2105 void fFramebufferTextureLayer(GLenum target
, GLenum attachment
,
2106 GLuint texture
, GLint level
, GLint layer
) {
2108 ASSERT_SYMBOL_PRESENT(fFramebufferTextureLayer
);
2109 mSymbols
.fFramebufferTextureLayer(target
, attachment
, texture
, level
,
2114 void fGetFramebufferAttachmentParameteriv(GLenum target
, GLenum attachment
,
2115 GLenum pname
, GLint
* value
) {
2117 mSymbols
.fGetFramebufferAttachmentParameteriv(target
, attachment
, pname
,
2123 void fGetRenderbufferParameteriv(GLenum target
, GLenum pname
, GLint
* value
) {
2125 mSymbols
.fGetRenderbufferParameteriv(target
, pname
, value
);
2130 realGLboolean
fIsFramebuffer(GLuint framebuffer
) {
2131 realGLboolean retval
= false;
2133 retval
= mSymbols
.fIsFramebuffer(framebuffer
);
2140 realGLboolean
fIsRenderbuffer(GLuint renderbuffer
) {
2141 realGLboolean retval
= false;
2143 retval
= mSymbols
.fIsRenderbuffer(renderbuffer
);
2149 void fRenderbufferStorage(GLenum target
, GLenum internalFormat
, GLsizei width
,
2152 mSymbols
.fRenderbufferStorage(target
, internalFormat
, width
, height
);
2157 void raw_fDepthRange(GLclampf a
, GLclampf b
) {
2158 MOZ_ASSERT(!IsGLES());
2161 ASSERT_SYMBOL_PRESENT(fDepthRange
);
2162 mSymbols
.fDepthRange(a
, b
);
2166 void raw_fDepthRangef(GLclampf a
, GLclampf b
) {
2167 MOZ_ASSERT(IsGLES());
2170 ASSERT_SYMBOL_PRESENT(fDepthRangef
);
2171 mSymbols
.fDepthRangef(a
, b
);
2175 void raw_fClearDepth(GLclampf v
) {
2176 MOZ_ASSERT(!IsGLES());
2179 ASSERT_SYMBOL_PRESENT(fClearDepth
);
2180 mSymbols
.fClearDepth(v
);
2184 void raw_fClearDepthf(GLclampf v
) {
2185 MOZ_ASSERT(IsGLES());
2188 ASSERT_SYMBOL_PRESENT(fClearDepthf
);
2189 mSymbols
.fClearDepthf(v
);
2194 void fDepthRange(GLclampf a
, GLclampf b
) {
2196 raw_fDepthRangef(a
, b
);
2198 raw_fDepthRange(a
, b
);
2202 void fClearDepth(GLclampf v
) {
2204 raw_fClearDepthf(v
);
2210 void* fMapBuffer(GLenum target
, GLenum access
) {
2211 void* ret
= nullptr;
2213 ASSERT_SYMBOL_PRESENT(fMapBuffer
);
2214 ret
= mSymbols
.fMapBuffer(target
, access
);
2220 realGLboolean
fUnmapBuffer(GLenum target
) {
2221 realGLboolean ret
= false;
2223 ASSERT_SYMBOL_PRESENT(fUnmapBuffer
);
2224 ret
= mSymbols
.fUnmapBuffer(target
);
2230 GLuint
raw_fCreateProgram() {
2233 ret
= mSymbols
.fCreateProgram();
2238 GLuint
raw_fCreateShader(GLenum t
) {
2241 ret
= mSymbols
.fCreateShader(t
);
2246 void raw_fGenBuffers(GLsizei n
, GLuint
* names
) {
2248 mSymbols
.fGenBuffers(n
, names
);
2253 void raw_fGenFramebuffers(GLsizei n
, GLuint
* names
) {
2255 mSymbols
.fGenFramebuffers(n
, names
);
2260 void raw_fGenRenderbuffers(GLsizei n
, GLuint
* names
) {
2262 mSymbols
.fGenRenderbuffers(n
, names
);
2267 void raw_fGenTextures(GLsizei n
, GLuint
* names
) {
2269 mSymbols
.fGenTextures(n
, names
);
2275 GLuint
fCreateProgram() {
2276 GLuint ret
= raw_fCreateProgram();
2277 TRACKING_CONTEXT(CreatedProgram(this, ret
));
2281 GLuint
fCreateShader(GLenum t
) {
2282 GLuint ret
= raw_fCreateShader(t
);
2283 TRACKING_CONTEXT(CreatedShader(this, ret
));
2287 void fGenBuffers(GLsizei n
, GLuint
* names
) {
2288 raw_fGenBuffers(n
, names
);
2289 TRACKING_CONTEXT(CreatedBuffers(this, n
, names
));
2292 void fGenFramebuffers(GLsizei n
, GLuint
* names
) {
2293 raw_fGenFramebuffers(n
, names
);
2294 TRACKING_CONTEXT(CreatedFramebuffers(this, n
, names
));
2297 void fGenRenderbuffers(GLsizei n
, GLuint
* names
) {
2298 raw_fGenRenderbuffers(n
, names
);
2299 TRACKING_CONTEXT(CreatedRenderbuffers(this, n
, names
));
2302 void fGenTextures(GLsizei n
, GLuint
* names
) {
2303 raw_fGenTextures(n
, names
);
2304 TRACKING_CONTEXT(CreatedTextures(this, n
, names
));
2308 void raw_fDeleteProgram(GLuint program
) {
2310 mSymbols
.fDeleteProgram(program
);
2314 void raw_fDeleteShader(GLuint shader
) {
2316 mSymbols
.fDeleteShader(shader
);
2320 void raw_fDeleteBuffers(GLsizei n
, const GLuint
* names
) {
2322 mSymbols
.fDeleteBuffers(n
, names
);
2326 void raw_fDeleteFramebuffers(GLsizei n
, const GLuint
* names
) {
2328 mSymbols
.fDeleteFramebuffers(n
, names
);
2331 for (const auto i
: IntegerRange(n
)) {
2332 const auto fb
= names
[i
];
2333 if (mCachedDrawFb
== fb
) {
2336 if (mCachedReadFb
== fb
) {
2342 void raw_fDeleteRenderbuffers(GLsizei n
, const GLuint
* names
) {
2344 mSymbols
.fDeleteRenderbuffers(n
, names
);
2348 void raw_fDeleteTextures(GLsizei n
, const GLuint
* names
) {
2350 mSymbols
.fDeleteTextures(n
, names
);
2355 void fDeleteProgram(GLuint program
) {
2356 raw_fDeleteProgram(program
);
2357 TRACKING_CONTEXT(DeletedProgram(this, program
));
2360 void fDeleteShader(GLuint shader
) {
2361 raw_fDeleteShader(shader
);
2362 TRACKING_CONTEXT(DeletedShader(this, shader
));
2365 void fDeleteBuffers(GLsizei n
, const GLuint
* names
) {
2366 raw_fDeleteBuffers(n
, names
);
2367 TRACKING_CONTEXT(DeletedBuffers(this, n
, names
));
2370 void fDeleteFramebuffers(GLsizei n
, const GLuint
* names
);
2372 void fDeleteRenderbuffers(GLsizei n
, const GLuint
* names
) {
2373 raw_fDeleteRenderbuffers(n
, names
);
2374 TRACKING_CONTEXT(DeletedRenderbuffers(this, n
, names
));
2377 void fDeleteTextures(GLsizei n
, const GLuint
* names
) {
2379 // On the Mac the call to fDeleteTextures() triggers a flush. But it
2380 // happens at the wrong time, which can lead to crashes. To work around
2381 // this we call fFlush() explicitly ourselves, before the call to
2382 // fDeleteTextures(). This fixes bug 1666293.
2385 raw_fDeleteTextures(n
, names
);
2386 TRACKING_CONTEXT(DeletedTextures(this, n
, names
));
2389 // -----------------------------------------------------------------------------
2390 // Extension ARB_sync (GL)
2392 GLsync
fFenceSync(GLenum condition
, GLbitfield flags
) {
2395 ASSERT_SYMBOL_PRESENT(fFenceSync
);
2396 ret
= mSymbols
.fFenceSync(condition
, flags
);
2402 realGLboolean
fIsSync(GLsync sync
) {
2403 realGLboolean ret
= false;
2405 ASSERT_SYMBOL_PRESENT(fIsSync
);
2406 ret
= mSymbols
.fIsSync(sync
);
2412 void fDeleteSync(GLsync sync
) {
2414 ASSERT_SYMBOL_PRESENT(fDeleteSync
);
2415 mSymbols
.fDeleteSync(sync
);
2419 GLenum
fClientWaitSync(GLsync sync
, GLbitfield flags
, GLuint64 timeout
) {
2422 ASSERT_SYMBOL_PRESENT(fClientWaitSync
);
2423 ret
= mSymbols
.fClientWaitSync(sync
, flags
, timeout
);
2429 void fWaitSync(GLsync sync
, GLbitfield flags
, GLuint64 timeout
) {
2431 ASSERT_SYMBOL_PRESENT(fWaitSync
);
2432 mSymbols
.fWaitSync(sync
, flags
, timeout
);
2436 void fGetInteger64v(GLenum pname
, GLint64
* params
) {
2438 ASSERT_SYMBOL_PRESENT(fGetInteger64v
);
2439 mSymbols
.fGetInteger64v(pname
, params
);
2443 void fGetSynciv(GLsync sync
, GLenum pname
, GLsizei bufSize
, GLsizei
* length
,
2446 ASSERT_SYMBOL_PRESENT(fGetSynciv
);
2447 mSymbols
.fGetSynciv(sync
, pname
, bufSize
, length
, values
);
2452 // -----------------------------------------------------------------------------
2453 // Extension OES_EGL_image (GLES)
2455 void fEGLImageTargetTexture2D(GLenum target
, GLeglImage image
) {
2457 ASSERT_SYMBOL_PRESENT(fEGLImageTargetTexture2D
);
2458 mSymbols
.fEGLImageTargetTexture2D(target
, image
);
2460 mHeavyGLCallsSinceLastFlush
= true;
2463 void fEGLImageTargetRenderbufferStorage(GLenum target
, GLeglImage image
) {
2465 ASSERT_SYMBOL_PRESENT(fEGLImageTargetRenderbufferStorage
);
2466 mSymbols
.fEGLImageTargetRenderbufferStorage(target
, image
);
2470 // -----------------------------------------------------------------------------
2471 // Package XXX_bind_buffer_offset
2473 void fBindBufferOffset(GLenum target
, GLuint index
, GLuint buffer
,
2476 ASSERT_SYMBOL_PRESENT(fBindBufferOffset
);
2477 mSymbols
.fBindBufferOffset(target
, index
, buffer
, offset
);
2481 // -----------------------------------------------------------------------------
2482 // Package XXX_draw_buffers
2484 void fDrawBuffers(GLsizei n
, const GLenum
* bufs
) {
2486 ASSERT_SYMBOL_PRESENT(fDrawBuffers
);
2487 mSymbols
.fDrawBuffers(n
, bufs
);
2491 // -----------------------------------------------------------------------------
2492 // Package XXX_draw_instanced
2494 void fDrawArraysInstanced(GLenum mode
, GLint first
, GLsizei count
,
2495 GLsizei primcount
) {
2497 raw_fDrawArraysInstanced(mode
, first
, count
, primcount
);
2501 void fDrawElementsInstanced(GLenum mode
, GLsizei count
, GLenum type
,
2502 const GLvoid
* indices
, GLsizei primcount
) {
2504 raw_fDrawElementsInstanced(mode
, count
, type
, indices
, primcount
);
2509 void raw_fDrawArraysInstanced(GLenum mode
, GLint first
, GLsizei count
,
2510 GLsizei primcount
) {
2512 ASSERT_SYMBOL_PRESENT(fDrawArraysInstanced
);
2513 mSymbols
.fDrawArraysInstanced(mode
, first
, count
, primcount
);
2517 void raw_fDrawElementsInstanced(GLenum mode
, GLsizei count
, GLenum type
,
2518 const GLvoid
* indices
, GLsizei primcount
) {
2520 ASSERT_SYMBOL_PRESENT(fDrawElementsInstanced
);
2521 mSymbols
.fDrawElementsInstanced(mode
, count
, type
, indices
, primcount
);
2525 // -----------------------------------------------------------------------------
2526 // Package XXX_framebuffer_blit
2529 void fBlitFramebuffer(GLint srcX0
, GLint srcY0
, GLint srcX1
, GLint srcY1
,
2530 GLint dstX0
, GLint dstY0
, GLint dstX1
, GLint dstY1
,
2531 GLbitfield mask
, GLenum filter
) {
2534 raw_fBlitFramebuffer(srcX0
, srcY0
, srcX1
, srcY1
, dstX0
, dstY0
, dstX1
, dstY1
,
2541 void raw_fBlitFramebuffer(GLint srcX0
, GLint srcY0
, GLint srcX1
, GLint srcY1
,
2542 GLint dstX0
, GLint dstY0
, GLint dstX1
, GLint dstY1
,
2543 GLbitfield mask
, GLenum filter
) {
2545 ASSERT_SYMBOL_PRESENT(fBlitFramebuffer
);
2546 mSymbols
.fBlitFramebuffer(srcX0
, srcY0
, srcX1
, srcY1
, dstX0
, dstY0
, dstX1
,
2547 dstY1
, mask
, filter
);
2551 // -----------------------------------------------------------------------------
2552 // Package XXX_framebuffer_multisample
2554 void fRenderbufferStorageMultisample(GLenum target
, GLsizei samples
,
2555 GLenum internalFormat
, GLsizei width
,
2558 ASSERT_SYMBOL_PRESENT(fRenderbufferStorageMultisample
);
2559 mSymbols
.fRenderbufferStorageMultisample(target
, samples
, internalFormat
,
2564 // -----------------------------------------------------------------------------
2565 // GL 3.0, GL ES 3.0 & EXT_gpu_shader4
2567 void fGetVertexAttribIiv(GLuint index
, GLenum pname
, GLint
* params
) {
2568 ASSERT_SYMBOL_PRESENT(fGetVertexAttribIiv
);
2570 mSymbols
.fGetVertexAttribIiv(index
, pname
, params
);
2575 void fGetVertexAttribIuiv(GLuint index
, GLenum pname
, GLuint
* params
) {
2576 ASSERT_SYMBOL_PRESENT(fGetVertexAttribIuiv
);
2578 mSymbols
.fGetVertexAttribIuiv(index
, pname
, params
);
2583 void fVertexAttribI4i(GLuint index
, GLint x
, GLint y
, GLint z
, GLint w
) {
2585 ASSERT_SYMBOL_PRESENT(fVertexAttribI4i
);
2586 mSymbols
.fVertexAttribI4i(index
, x
, y
, z
, w
);
2590 void fVertexAttribI4iv(GLuint index
, const GLint
* v
) {
2592 ASSERT_SYMBOL_PRESENT(fVertexAttribI4iv
);
2593 mSymbols
.fVertexAttribI4iv(index
, v
);
2597 void fVertexAttribI4ui(GLuint index
, GLuint x
, GLuint y
, GLuint z
, GLuint w
) {
2599 ASSERT_SYMBOL_PRESENT(fVertexAttribI4ui
);
2600 mSymbols
.fVertexAttribI4ui(index
, x
, y
, z
, w
);
2604 void fVertexAttribI4uiv(GLuint index
, const GLuint
* v
) {
2606 ASSERT_SYMBOL_PRESENT(fVertexAttribI4uiv
);
2607 mSymbols
.fVertexAttribI4uiv(index
, v
);
2611 void fVertexAttribIPointer(GLuint index
, GLint size
, GLenum type
,
2612 GLsizei stride
, const GLvoid
* offset
) {
2614 ASSERT_SYMBOL_PRESENT(fVertexAttribIPointer
);
2615 mSymbols
.fVertexAttribIPointer(index
, size
, type
, stride
, offset
);
2619 void fUniform1ui(GLint location
, GLuint v0
) {
2621 ASSERT_SYMBOL_PRESENT(fUniform1ui
);
2622 mSymbols
.fUniform1ui(location
, v0
);
2626 void fUniform2ui(GLint location
, GLuint v0
, GLuint v1
) {
2628 ASSERT_SYMBOL_PRESENT(fUniform2ui
);
2629 mSymbols
.fUniform2ui(location
, v0
, v1
);
2633 void fUniform3ui(GLint location
, GLuint v0
, GLuint v1
, GLuint v2
) {
2635 ASSERT_SYMBOL_PRESENT(fUniform3ui
);
2636 mSymbols
.fUniform3ui(location
, v0
, v1
, v2
);
2640 void fUniform4ui(GLint location
, GLuint v0
, GLuint v1
, GLuint v2
, GLuint v3
) {
2642 ASSERT_SYMBOL_PRESENT(fUniform4ui
);
2643 mSymbols
.fUniform4ui(location
, v0
, v1
, v2
, v3
);
2647 void fUniform1uiv(GLint location
, GLsizei count
, const GLuint
* value
) {
2649 ASSERT_SYMBOL_PRESENT(fUniform1uiv
);
2650 mSymbols
.fUniform1uiv(location
, count
, value
);
2654 void fUniform2uiv(GLint location
, GLsizei count
, const GLuint
* value
) {
2656 ASSERT_SYMBOL_PRESENT(fUniform2uiv
);
2657 mSymbols
.fUniform2uiv(location
, count
, value
);
2661 void fUniform3uiv(GLint location
, GLsizei count
, const GLuint
* value
) {
2663 ASSERT_SYMBOL_PRESENT(fUniform3uiv
);
2664 mSymbols
.fUniform3uiv(location
, count
, value
);
2668 void fUniform4uiv(GLint location
, GLsizei count
, const GLuint
* value
) {
2670 ASSERT_SYMBOL_PRESENT(fUniform4uiv
);
2671 mSymbols
.fUniform4uiv(location
, count
, value
);
2675 GLint
fGetFragDataLocation(GLuint program
, const GLchar
* name
) {
2678 ASSERT_SYMBOL_PRESENT(fGetFragDataLocation
);
2679 result
= mSymbols
.fGetFragDataLocation(program
, name
);
2685 // -----------------------------------------------------------------------------
2686 // Package XXX_instanced_arrays
2688 void fVertexAttribDivisor(GLuint index
, GLuint divisor
) {
2690 ASSERT_SYMBOL_PRESENT(fVertexAttribDivisor
);
2691 mSymbols
.fVertexAttribDivisor(index
, divisor
);
2695 // -----------------------------------------------------------------------------
2696 // Feature internalformat_query
2698 void fGetInternalformativ(GLenum target
, GLenum internalformat
, GLenum pname
,
2699 GLsizei bufSize
, GLint
* params
) {
2701 ASSERT_SYMBOL_PRESENT(fGetInternalformativ
);
2702 mSymbols
.fGetInternalformativ(target
, internalformat
, pname
, bufSize
,
2708 // -----------------------------------------------------------------------------
2709 // Package XXX_query_counter
2711 * XXX_query_counter:
2712 * - depends on XXX_query_objects
2713 * - provide all followed entry points
2714 * - provide GL_TIMESTAMP
2717 void fQueryCounter(GLuint id
, GLenum target
) {
2719 ASSERT_SYMBOL_PRESENT(fQueryCounter
);
2720 mSymbols
.fQueryCounter(id
, target
);
2724 // -----------------------------------------------------------------------------
2725 // Package XXX_query_objects
2727 * XXX_query_objects:
2728 * - provide all followed entry points
2730 * XXX_occlusion_query2:
2731 * - depends on XXX_query_objects
2732 * - provide ANY_SAMPLES_PASSED
2734 * XXX_occlusion_query_boolean:
2735 * - depends on XXX_occlusion_query2
2736 * - provide ANY_SAMPLES_PASSED_CONSERVATIVE
2739 void fDeleteQueries(GLsizei n
, const GLuint
* names
) {
2741 ASSERT_SYMBOL_PRESENT(fDeleteQueries
);
2742 mSymbols
.fDeleteQueries(n
, names
);
2744 TRACKING_CONTEXT(DeletedQueries(this, n
, names
));
2747 void fGenQueries(GLsizei n
, GLuint
* names
) {
2749 ASSERT_SYMBOL_PRESENT(fGenQueries
);
2750 mSymbols
.fGenQueries(n
, names
);
2752 TRACKING_CONTEXT(CreatedQueries(this, n
, names
));
2755 void fGetQueryiv(GLenum target
, GLenum pname
, GLint
* params
) {
2757 ASSERT_SYMBOL_PRESENT(fGetQueryiv
);
2758 mSymbols
.fGetQueryiv(target
, pname
, params
);
2763 void fGetQueryObjectuiv(GLuint id
, GLenum pname
, GLuint
* params
) {
2765 ASSERT_SYMBOL_PRESENT(fGetQueryObjectuiv
);
2766 mSymbols
.fGetQueryObjectuiv(id
, pname
, params
);
2771 realGLboolean
fIsQuery(GLuint query
) {
2772 realGLboolean retval
= false;
2774 ASSERT_SYMBOL_PRESENT(fIsQuery
);
2775 retval
= mSymbols
.fIsQuery(query
);
2781 // -----------------------------------------------------------------------------
2782 // Package XXX_get_query_object_i64v
2784 * XXX_get_query_object_i64v:
2785 * - depends on XXX_query_objects
2786 * - provide the followed entry point
2789 void fGetQueryObjecti64v(GLuint id
, GLenum pname
, GLint64
* params
) {
2791 ASSERT_SYMBOL_PRESENT(fGetQueryObjecti64v
);
2792 mSymbols
.fGetQueryObjecti64v(id
, pname
, params
);
2797 void fGetQueryObjectui64v(GLuint id
, GLenum pname
, GLuint64
* params
) {
2799 ASSERT_SYMBOL_PRESENT(fGetQueryObjectui64v
);
2800 mSymbols
.fGetQueryObjectui64v(id
, pname
, params
);
2805 // -----------------------------------------------------------------------------
2806 // Package XXX_get_query_object_iv
2808 * XXX_get_query_object_iv:
2809 * - depends on XXX_query_objects
2810 * - provide the followed entry point
2812 * XXX_occlusion_query:
2813 * - depends on XXX_get_query_object_iv
2814 * - provide LOCAL_GL_SAMPLES_PASSED
2817 void fGetQueryObjectiv(GLuint id
, GLenum pname
, GLint
* params
) {
2819 ASSERT_SYMBOL_PRESENT(fGetQueryObjectiv
);
2820 mSymbols
.fGetQueryObjectiv(id
, pname
, params
);
2825 // -----------------------------------------------------------------------------
2826 // GL 4.0, GL ES 3.0, ARB_transform_feedback2, NV_transform_feedback2
2828 void fBindBufferBase(GLenum target
, GLuint index
, GLuint buffer
) {
2830 ASSERT_SYMBOL_PRESENT(fBindBufferBase
);
2831 mSymbols
.fBindBufferBase(target
, index
, buffer
);
2835 void fBindBufferRange(GLenum target
, GLuint index
, GLuint buffer
,
2836 GLintptr offset
, GLsizeiptr size
) {
2838 ASSERT_SYMBOL_PRESENT(fBindBufferRange
);
2839 mSymbols
.fBindBufferRange(target
, index
, buffer
, offset
, size
);
2843 void fGenTransformFeedbacks(GLsizei n
, GLuint
* ids
) {
2845 ASSERT_SYMBOL_PRESENT(fGenTransformFeedbacks
);
2846 mSymbols
.fGenTransformFeedbacks(n
, ids
);
2851 void fDeleteTransformFeedbacks(GLsizei n
, const GLuint
* ids
) {
2853 ASSERT_SYMBOL_PRESENT(fDeleteTransformFeedbacks
);
2854 mSymbols
.fDeleteTransformFeedbacks(n
, ids
);
2858 realGLboolean
fIsTransformFeedback(GLuint id
) {
2859 realGLboolean result
= false;
2861 ASSERT_SYMBOL_PRESENT(fIsTransformFeedback
);
2862 result
= mSymbols
.fIsTransformFeedback(id
);
2868 void fBindTransformFeedback(GLenum target
, GLuint id
) {
2870 ASSERT_SYMBOL_PRESENT(fBindTransformFeedback
);
2871 mSymbols
.fBindTransformFeedback(target
, id
);
2875 void fBeginTransformFeedback(GLenum primitiveMode
) {
2877 ASSERT_SYMBOL_PRESENT(fBeginTransformFeedback
);
2878 mSymbols
.fBeginTransformFeedback(primitiveMode
);
2882 void fEndTransformFeedback() {
2884 ASSERT_SYMBOL_PRESENT(fEndTransformFeedback
);
2885 mSymbols
.fEndTransformFeedback();
2889 void fTransformFeedbackVaryings(GLuint program
, GLsizei count
,
2890 const GLchar
* const* varyings
,
2891 GLenum bufferMode
) {
2893 ASSERT_SYMBOL_PRESENT(fTransformFeedbackVaryings
);
2894 mSymbols
.fTransformFeedbackVaryings(program
, count
, varyings
, bufferMode
);
2898 void fGetTransformFeedbackVarying(GLuint program
, GLuint index
,
2899 GLsizei bufSize
, GLsizei
* length
,
2900 GLsizei
* size
, GLenum
* type
, GLchar
* name
) {
2902 ASSERT_SYMBOL_PRESENT(fGetTransformFeedbackVarying
);
2903 mSymbols
.fGetTransformFeedbackVarying(program
, index
, bufSize
, length
, size
,
2909 void fPauseTransformFeedback() {
2911 ASSERT_SYMBOL_PRESENT(fPauseTransformFeedback
);
2912 mSymbols
.fPauseTransformFeedback();
2916 void fResumeTransformFeedback() {
2918 ASSERT_SYMBOL_PRESENT(fResumeTransformFeedback
);
2919 mSymbols
.fResumeTransformFeedback();
2923 void fGetIntegeri_v(GLenum param
, GLuint index
, GLint
* values
) {
2925 ASSERT_SYMBOL_PRESENT(fGetIntegeri_v
);
2926 mSymbols
.fGetIntegeri_v(param
, index
, values
);
2931 void fGetInteger64i_v(GLenum target
, GLuint index
, GLint64
* data
) {
2932 ASSERT_SYMBOL_PRESENT(fGetInteger64i_v
);
2934 mSymbols
.fGetInteger64i_v(target
, index
, data
);
2939 // -----------------------------------------------------------------------------
2940 // Package XXX_vertex_array_object
2942 void fBindVertexArray(GLuint array
) {
2944 ASSERT_SYMBOL_PRESENT(fBindVertexArray
);
2945 mSymbols
.fBindVertexArray(array
);
2949 void fDeleteVertexArrays(GLsizei n
, const GLuint
* arrays
) {
2951 ASSERT_SYMBOL_PRESENT(fDeleteVertexArrays
);
2952 mSymbols
.fDeleteVertexArrays(n
, arrays
);
2956 void fGenVertexArrays(GLsizei n
, GLuint
* arrays
) {
2958 ASSERT_SYMBOL_PRESENT(fGenVertexArrays
);
2959 mSymbols
.fGenVertexArrays(n
, arrays
);
2963 realGLboolean
fIsVertexArray(GLuint array
) {
2964 realGLboolean ret
= false;
2966 ASSERT_SYMBOL_PRESENT(fIsVertexArray
);
2967 ret
= mSymbols
.fIsVertexArray(array
);
2973 // -----------------------------------------------------------------------------
2974 // Extension NV_fence
2976 void fGenFences(GLsizei n
, GLuint
* fences
) {
2977 ASSERT_SYMBOL_PRESENT(fGenFences
);
2979 mSymbols
.fGenFences(n
, fences
);
2983 void fDeleteFences(GLsizei n
, const GLuint
* fences
) {
2984 ASSERT_SYMBOL_PRESENT(fDeleteFences
);
2986 mSymbols
.fDeleteFences(n
, fences
);
2990 void fSetFence(GLuint fence
, GLenum condition
) {
2991 ASSERT_SYMBOL_PRESENT(fSetFence
);
2993 mSymbols
.fSetFence(fence
, condition
);
2997 realGLboolean
fTestFence(GLuint fence
) {
2998 realGLboolean ret
= false;
2999 ASSERT_SYMBOL_PRESENT(fTestFence
);
3001 ret
= mSymbols
.fTestFence(fence
);
3007 void fFinishFence(GLuint fence
) {
3008 ASSERT_SYMBOL_PRESENT(fFinishFence
);
3010 mSymbols
.fFinishFence(fence
);
3015 realGLboolean
fIsFence(GLuint fence
) {
3016 realGLboolean ret
= false;
3017 ASSERT_SYMBOL_PRESENT(fIsFence
);
3019 ret
= mSymbols
.fIsFence(fence
);
3025 void fGetFenceiv(GLuint fence
, GLenum pname
, GLint
* params
) {
3026 ASSERT_SYMBOL_PRESENT(fGetFenceiv
);
3028 mSymbols
.fGetFenceiv(fence
, pname
, params
);
3033 // -----------------------------------------------------------------------------
3034 // Extension NV_texture_barrier
3036 void fTextureBarrier() {
3037 ASSERT_SYMBOL_PRESENT(fTextureBarrier
);
3039 mSymbols
.fTextureBarrier();
3043 // Core GL & Extension ARB_copy_buffer
3045 void fCopyBufferSubData(GLenum readtarget
, GLenum writetarget
,
3046 GLintptr readoffset
, GLintptr writeoffset
,
3049 ASSERT_SYMBOL_PRESENT(fCopyBufferSubData
);
3050 mSymbols
.fCopyBufferSubData(readtarget
, writetarget
, readoffset
,
3055 // -----------------------------------------------------------------------------
3056 // Core GL & Extension ARB_map_buffer_range
3058 void* fMapBufferRange(GLenum target
, GLintptr offset
, GLsizeiptr length
,
3059 GLbitfield access
) {
3060 void* data
= nullptr;
3061 ASSERT_SYMBOL_PRESENT(fMapBufferRange
);
3063 data
= mSymbols
.fMapBufferRange(target
, offset
, length
, access
);
3069 void fFlushMappedBufferRange(GLenum target
, GLintptr offset
,
3070 GLsizeiptr length
) {
3071 ASSERT_SYMBOL_PRESENT(fFlushMappedBufferRange
);
3073 mSymbols
.fFlushMappedBufferRange(target
, offset
, length
);
3077 // -----------------------------------------------------------------------------
3078 // Core GL & Extension ARB_sampler_objects
3080 void fGenSamplers(GLsizei count
, GLuint
* samplers
) {
3082 ASSERT_SYMBOL_PRESENT(fGenSamplers
);
3083 mSymbols
.fGenSamplers(count
, samplers
);
3087 void fDeleteSamplers(GLsizei count
, const GLuint
* samplers
) {
3089 ASSERT_SYMBOL_PRESENT(fDeleteSamplers
);
3090 mSymbols
.fDeleteSamplers(count
, samplers
);
3094 realGLboolean
fIsSampler(GLuint sampler
) {
3095 realGLboolean result
= false;
3097 ASSERT_SYMBOL_PRESENT(fIsSampler
);
3098 result
= mSymbols
.fIsSampler(sampler
);
3104 void fBindSampler(GLuint unit
, GLuint sampler
) {
3106 ASSERT_SYMBOL_PRESENT(fBindSampler
);
3107 mSymbols
.fBindSampler(unit
, sampler
);
3111 void fSamplerParameteri(GLuint sampler
, GLenum pname
, GLint param
) {
3113 ASSERT_SYMBOL_PRESENT(fSamplerParameteri
);
3114 mSymbols
.fSamplerParameteri(sampler
, pname
, param
);
3118 void fSamplerParameteriv(GLuint sampler
, GLenum pname
, const GLint
* param
) {
3120 ASSERT_SYMBOL_PRESENT(fSamplerParameteriv
);
3121 mSymbols
.fSamplerParameteriv(sampler
, pname
, param
);
3125 void fSamplerParameterf(GLuint sampler
, GLenum pname
, GLfloat param
) {
3127 ASSERT_SYMBOL_PRESENT(fSamplerParameterf
);
3128 mSymbols
.fSamplerParameterf(sampler
, pname
, param
);
3132 void fSamplerParameterfv(GLuint sampler
, GLenum pname
, const GLfloat
* param
) {
3134 ASSERT_SYMBOL_PRESENT(fSamplerParameterfv
);
3135 mSymbols
.fSamplerParameterfv(sampler
, pname
, param
);
3139 void fGetSamplerParameteriv(GLuint sampler
, GLenum pname
, GLint
* params
) {
3141 ASSERT_SYMBOL_PRESENT(fGetSamplerParameteriv
);
3142 mSymbols
.fGetSamplerParameteriv(sampler
, pname
, params
);
3146 void fGetSamplerParameterfv(GLuint sampler
, GLenum pname
, GLfloat
* params
) {
3148 ASSERT_SYMBOL_PRESENT(fGetSamplerParameterfv
);
3149 mSymbols
.fGetSamplerParameterfv(sampler
, pname
, params
);
3153 // -----------------------------------------------------------------------------
3154 // Core GL & Extension ARB_uniform_buffer_object
3156 void fGetUniformIndices(GLuint program
, GLsizei uniformCount
,
3157 const GLchar
* const* uniformNames
,
3158 GLuint
* uniformIndices
) {
3159 ASSERT_SYMBOL_PRESENT(fGetUniformIndices
);
3161 mSymbols
.fGetUniformIndices(program
, uniformCount
, uniformNames
,
3167 void fGetActiveUniformsiv(GLuint program
, GLsizei uniformCount
,
3168 const GLuint
* uniformIndices
, GLenum pname
,
3170 ASSERT_SYMBOL_PRESENT(fGetActiveUniformsiv
);
3172 mSymbols
.fGetActiveUniformsiv(program
, uniformCount
, uniformIndices
, pname
,
3178 GLuint
fGetUniformBlockIndex(GLuint program
, const GLchar
* uniformBlockName
) {
3180 ASSERT_SYMBOL_PRESENT(fGetUniformBlockIndex
);
3182 result
= mSymbols
.fGetUniformBlockIndex(program
, uniformBlockName
);
3188 void fGetActiveUniformBlockiv(GLuint program
, GLuint uniformBlockIndex
,
3189 GLenum pname
, GLint
* params
) {
3190 ASSERT_SYMBOL_PRESENT(fGetActiveUniformBlockiv
);
3192 mSymbols
.fGetActiveUniformBlockiv(program
, uniformBlockIndex
, pname
,
3198 void fGetActiveUniformBlockName(GLuint program
, GLuint uniformBlockIndex
,
3199 GLsizei bufSize
, GLsizei
* length
,
3200 GLchar
* uniformBlockName
) {
3201 ASSERT_SYMBOL_PRESENT(fGetActiveUniformBlockName
);
3203 mSymbols
.fGetActiveUniformBlockName(program
, uniformBlockIndex
, bufSize
,
3204 length
, uniformBlockName
);
3209 void fUniformBlockBinding(GLuint program
, GLuint uniformBlockIndex
,
3210 GLuint uniformBlockBinding
) {
3211 ASSERT_SYMBOL_PRESENT(fUniformBlockBinding
);
3213 mSymbols
.fUniformBlockBinding(program
, uniformBlockIndex
,
3214 uniformBlockBinding
);
3218 // -----------------------------------------------------------------------------
3219 // Core GL 4.2, GL ES 3.0 & Extension ARB_texture_storage/EXT_texture_storage
3220 void fTexStorage2D(GLenum target
, GLsizei levels
, GLenum internalformat
,
3221 GLsizei width
, GLsizei height
) {
3223 ASSERT_SYMBOL_PRESENT(fTexStorage2D
);
3224 mSymbols
.fTexStorage2D(target
, levels
, internalformat
, width
, height
);
3229 void fTexStorage3D(GLenum target
, GLsizei levels
, GLenum internalformat
,
3230 GLsizei width
, GLsizei height
, GLsizei depth
) {
3232 ASSERT_SYMBOL_PRESENT(fTexStorage3D
);
3233 mSymbols
.fTexStorage3D(target
, levels
, internalformat
, width
, height
,
3239 // -----------------------------------------------------------------------------
3241 void fTexImage3D(GLenum target
, GLint level
, GLint internalFormat
,
3242 GLsizei width
, GLsizei height
, GLsizei depth
, GLint border
,
3243 GLenum format
, GLenum type
, const GLvoid
* data
) {
3245 ASSERT_SYMBOL_PRESENT(fTexImage3D
);
3246 mSymbols
.fTexImage3D(target
, level
, internalFormat
, width
, height
, depth
,
3247 border
, format
, type
, data
);
3252 void fTexSubImage3D(GLenum target
, GLint level
, GLint xoffset
, GLint yoffset
,
3253 GLint zoffset
, GLsizei width
, GLsizei height
,
3254 GLsizei depth
, GLenum format
, GLenum type
,
3255 const GLvoid
* pixels
) {
3257 ASSERT_SYMBOL_PRESENT(fTexSubImage3D
);
3258 mSymbols
.fTexSubImage3D(target
, level
, xoffset
, yoffset
, zoffset
, width
,
3259 height
, depth
, format
, type
, pixels
);
3264 void fCopyTexSubImage3D(GLenum target
, GLint level
, GLint xoffset
,
3265 GLint yoffset
, GLint zoffset
, GLint x
, GLint y
,
3266 GLsizei width
, GLsizei height
) {
3269 ASSERT_SYMBOL_PRESENT(fCopyTexSubImage3D
);
3270 mSymbols
.fCopyTexSubImage3D(target
, level
, xoffset
, yoffset
, zoffset
, x
, y
,
3276 void fCompressedTexImage3D(GLenum target
, GLint level
, GLenum internalformat
,
3277 GLsizei width
, GLsizei height
, GLsizei depth
,
3278 GLint border
, GLsizei imageSize
,
3279 const GLvoid
* data
) {
3281 ASSERT_SYMBOL_PRESENT(fCompressedTexImage3D
);
3282 mSymbols
.fCompressedTexImage3D(target
, level
, internalformat
, width
, height
,
3283 depth
, border
, imageSize
, data
);
3287 void fCompressedTexSubImage3D(GLenum target
, GLint level
, GLint xoffset
,
3288 GLint yoffset
, GLint zoffset
, GLsizei width
,
3289 GLsizei height
, GLsizei depth
, GLenum format
,
3290 GLsizei imageSize
, const GLvoid
* data
) {
3292 ASSERT_SYMBOL_PRESENT(fCompressedTexSubImage3D
);
3293 mSymbols
.fCompressedTexSubImage3D(target
, level
, xoffset
, yoffset
, zoffset
,
3294 width
, height
, depth
, format
, imageSize
,
3299 // -----------------------------------------------------------------------------
3302 const GLubyte
* fGetStringi(GLenum name
, GLuint index
) {
3303 const GLubyte
* ret
= nullptr;
3305 ASSERT_SYMBOL_PRESENT(fGetStringi
);
3306 ret
= mSymbols
.fGetStringi(name
, index
);
3312 // -----------------------------------------------------------------------------
3313 // APPLE_framebuffer_multisample
3315 void fResolveMultisampleFramebufferAPPLE() {
3317 ASSERT_SYMBOL_PRESENT(fResolveMultisampleFramebufferAPPLE
);
3318 mSymbols
.fResolveMultisampleFramebufferAPPLE();
3322 // -----------------------------------------------------------------------------
3325 void fFinishObjectAPPLE(GLenum object
, GLint name
) {
3327 ASSERT_SYMBOL_PRESENT(fFinishObjectAPPLE
);
3328 mSymbols
.fFinishObjectAPPLE(object
, name
);
3332 realGLboolean
fTestObjectAPPLE(GLenum object
, GLint name
) {
3333 realGLboolean ret
= false;
3335 ASSERT_SYMBOL_PRESENT(fTestObjectAPPLE
);
3336 ret
= mSymbols
.fTestObjectAPPLE(object
, name
);
3341 // -----------------------------------------------------------------------------
3344 void fPrimitiveRestartIndex(GLuint index
) {
3346 ASSERT_SYMBOL_PRESENT(fPrimitiveRestartIndex
);
3347 mSymbols
.fPrimitiveRestartIndex(index
);
3351 // -----------------------------------------------------------------------------
3354 void fFramebufferTextureMultiview(GLenum target
, GLenum attachment
,
3355 GLuint texture
, GLint level
,
3356 GLint baseViewIndex
,
3357 GLsizei numViews
) const {
3359 ASSERT_SYMBOL_PRESENT(fFramebufferTextureMultiview
);
3360 mSymbols
.fFramebufferTextureMultiview(target
, attachment
, texture
, level
,
3361 baseViewIndex
, numViews
);
3366 // draw_buffers_indexed
3368 void fBlendEquationSeparatei(GLuint i
, GLenum modeRGB
,
3369 GLenum modeAlpha
) const {
3371 mSymbols
.fBlendEquationSeparatei(i
, modeRGB
, modeAlpha
);
3375 void fBlendFuncSeparatei(GLuint i
, GLenum sfactorRGB
, GLenum dfactorRGB
,
3376 GLenum sfactorAlpha
, GLenum dfactorAlpha
) const {
3378 mSymbols
.fBlendFuncSeparatei(i
, sfactorRGB
, dfactorRGB
, sfactorAlpha
,
3383 void fColorMaski(GLuint i
, realGLboolean red
, realGLboolean green
,
3384 realGLboolean blue
, realGLboolean alpha
) const {
3386 mSymbols
.fColorMaski(i
, red
, green
, blue
, alpha
);
3390 void fDisablei(GLenum capability
, GLuint i
) const {
3392 mSymbols
.fDisablei(capability
, i
);
3396 void fEnablei(GLenum capability
, GLuint i
) const {
3398 mSymbols
.fEnablei(capability
, i
);
3402 #undef BEFORE_GL_CALL
3403 #undef AFTER_GL_CALL
3404 #undef ASSERT_SYMBOL_PRESENT
3405 // #undef TRACKING_CONTEXT // Needed in GLContext.cpp
3406 #undef ASSERT_NOT_PASSING_STACK_BUFFER_TO_GL
3408 // -----------------------------------------------------------------------------
3411 explicit GLContext(const GLContextDesc
&, GLContext
* sharedContext
= nullptr,
3412 bool canUseTLSIsCurrent
= false);
3414 // -----------------------------------------------------------------------------
3417 virtual ~GLContext();
3419 // Mark this context as destroyed. This will nullptr out all
3420 // the GL function pointers!
3421 void MarkDestroyed();
3424 virtual void OnMarkDestroyed() {}
3426 // -----------------------------------------------------------------------------
3427 // Everything that isn't standard GL APIs
3429 typedef gfx::SurfaceFormat SurfaceFormat
;
3432 virtual void ReleaseSurface() {}
3434 bool IsDestroyed() const {
3435 // MarkDestroyed will mark all these as null.
3436 return mContextLost
&& mSymbols
.fUseProgram
== nullptr;
3439 GLContext
* GetSharedContext() { return mSharedContext
; }
3442 * Returns true if the thread on which this context was created is the
3443 * currently executing thread.
3445 bool IsOwningThreadCurrent();
3447 static void PlatformStartup();
3451 * If this context wraps a double-buffered target, swap the back
3452 * and front buffers. It should be assumed that after a swap, the
3453 * contents of the new back buffer are undefined.
3455 virtual bool SwapBuffers() { return false; }
3458 * Stores a damage region (in origin bottom left coordinates), which
3459 * makes the next SwapBuffers call do eglSwapBuffersWithDamage if supported.
3461 * Note that even if only part of the context is damaged, the entire buffer
3462 * needs to be filled with up-to-date contents. This region is only a hint
3463 * telling the system compositor which parts of the buffer were updated.
3465 virtual void SetDamage(const nsIntRegion
& aDamageRegion
) {}
3468 * Get the buffer age. If it returns 0, that indicates the buffer state is
3469 * unknown and the entire frame should be redrawn.
3471 virtual GLint
GetBufferAge() const { return 0; }
3474 * Defines a two-dimensional texture image for context target surface
3476 virtual bool BindTexImage() { return false; }
3478 * Releases a color buffer that is being used as a texture
3480 virtual bool ReleaseTexImage() { return false; }
3482 virtual Maybe
<SymbolLoader
> GetSymbolLoader() const = 0;
3484 void BindFB(GLuint fb
) {
3485 fBindFramebuffer(LOCAL_GL_FRAMEBUFFER
, fb
);
3486 MOZ_GL_ASSERT(this, !fb
|| fIsFramebuffer(fb
));
3489 void BindDrawFB(GLuint fb
) {
3490 fBindFramebuffer(LOCAL_GL_DRAW_FRAMEBUFFER_EXT
, fb
);
3493 void BindReadFB(GLuint fb
) {
3494 fBindFramebuffer(LOCAL_GL_READ_FRAMEBUFFER_EXT
, fb
);
3497 GLuint
GetDrawFB() const {
3498 return GetIntAs
<GLuint
>(LOCAL_GL_DRAW_FRAMEBUFFER_BINDING_EXT
);
3501 GLuint
GetReadFB() const {
3502 auto bindEnum
= LOCAL_GL_READ_FRAMEBUFFER_BINDING_EXT
;
3503 if (!IsSupported(GLFeature::split_framebuffer
)) {
3504 bindEnum
= LOCAL_GL_FRAMEBUFFER_BINDING
;
3506 return GetIntAs
<GLuint
>(bindEnum
);
3509 GLuint
GetFB() const {
3510 const auto ret
= GetDrawFB();
3511 MOZ_ASSERT(ret
== GetReadFB());
3516 void GetShaderPrecisionFormatNonES2(GLenum shadertype
, GLenum precisiontype
,
3517 GLint
* range
, GLint
* precision
) {
3518 switch (precisiontype
) {
3519 case LOCAL_GL_LOW_FLOAT
:
3520 case LOCAL_GL_MEDIUM_FLOAT
:
3521 case LOCAL_GL_HIGH_FLOAT
:
3522 // Assume IEEE 754 precision
3527 case LOCAL_GL_LOW_INT
:
3528 case LOCAL_GL_MEDIUM_INT
:
3529 case LOCAL_GL_HIGH_INT
:
3530 // Some (most) hardware only supports single-precision floating-point
3531 // numbers, which can accurately represent integers up to +/-16777216
3540 virtual GLenum
GetPreferredARGB32Format() const { return LOCAL_GL_RGBA
; }
3542 virtual GLenum
GetPreferredEGLImageTextureTarget() const {
3544 return LOCAL_GL_TEXTURE_2D
;
3546 return IsExtensionSupported(OES_EGL_image_external
)
3547 ? LOCAL_GL_TEXTURE_EXTERNAL
3548 : LOCAL_GL_TEXTURE_2D
;
3552 virtual bool RenewSurface(widget::CompositorWidget
* aWidget
) { return false; }
3554 // Shared code for GL extensions and GLX extensions.
3555 static bool ListHasExtension(const GLubyte
* extensions
,
3556 const char* extension
);
3560 DebugFlagEnabled
= 1 << 0,
3561 DebugFlagTrace
= 1 << 1,
3562 DebugFlagAbortOnError
= 1 << 2
3565 const uint8_t mDebugFlags
;
3566 static uint8_t ChooseDebugFlags(CreateContextFlags createFlags
);
3569 RefPtr
<GLContext
> mSharedContext
;
3571 // The thread id which this context was created.
3572 PlatformThreadId mOwningThreadId
;
3574 GLContextSymbols mSymbols
= {};
3576 UniquePtr
<GLBlitHelper
> mBlitHelper
;
3577 UniquePtr
<GLReadTexImageHelper
> mReadTexImageHelper
;
3580 GLBlitHelper
* BlitHelper();
3581 GLReadTexImageHelper
* ReadTexImageHelper();
3583 // Assumes shares are created by all sharing with the same global context.
3584 bool SharesWith(const GLContext
* other
) const {
3585 MOZ_ASSERT(!this->mSharedContext
|| !this->mSharedContext
->mSharedContext
);
3586 MOZ_ASSERT(!other
->mSharedContext
||
3587 !other
->mSharedContext
->mSharedContext
);
3588 MOZ_ASSERT(!this->mSharedContext
|| !other
->mSharedContext
||
3589 this->mSharedContext
== other
->mSharedContext
);
3591 const GLContext
* thisShared
=
3592 this->mSharedContext
? this->mSharedContext
: this;
3593 const GLContext
* otherShared
=
3594 other
->mSharedContext
? other
->mSharedContext
: other
;
3596 return thisShared
== otherShared
;
3599 bool IsFramebufferComplete(GLuint fb
, GLenum
* status
= nullptr);
3601 // Does not check completeness.
3602 void AttachBuffersToFB(GLuint colorTex
, GLuint colorRB
, GLuint depthRB
,
3603 GLuint stencilRB
, GLuint fb
,
3604 GLenum target
= LOCAL_GL_TEXTURE_2D
);
3606 // Passing null is fine if the value you'd get is 0.
3607 bool AssembleOffscreenFBs(const GLuint colorMSRB
, const GLuint depthRB
,
3608 const GLuint stencilRB
, const GLuint texture
,
3609 GLuint
* drawFB
, GLuint
* readFB
);
3612 SharedSurface
* mLockedSurface
= nullptr;
3615 void LockSurface(SharedSurface
* surf
) { mLockedSurface
= surf
; }
3617 void UnlockSurface(SharedSurface
* surf
) {
3618 MOZ_ASSERT(mLockedSurface
== surf
);
3619 mLockedSurface
= nullptr;
3622 SharedSurface
* GetLockedSurface() const { return mLockedSurface
; }
3624 bool IsOffscreen() const { return mDesc
.isOffscreen
; }
3626 bool WorkAroundDriverBugs() const { return mWorkAroundDriverBugs
; }
3628 bool IsOffscreenSizeAllowed(const gfx::IntSize
& aSize
) const;
3630 virtual bool Init();
3634 void LoadMoreSymbols(const SymbolLoader
& loader
);
3635 bool LoadExtSymbols(const SymbolLoader
& loader
, const SymLoadStruct
* list
,
3637 bool LoadFeatureSymbols(const SymbolLoader
& loader
, const SymLoadStruct
* list
,
3641 void InitExtensions();
3643 GLint mViewportRect
[4] = {};
3644 GLint mScissorRect
[4] = {};
3646 uint32_t mMaxTexOrRbSize
= 0;
3647 GLint mMaxTextureSize
= 0;
3648 GLint mMaxCubeMapTextureSize
= 0;
3649 GLint mMaxRenderbufferSize
= 0;
3650 GLint mMaxViewportDims
[2] = {};
3651 GLsizei mMaxSamples
= 0;
3652 bool mNeedsTextureSizeChecks
= false;
3653 bool mNeedsFlushBeforeDeleteFB
= false;
3654 bool mTextureAllocCrashesOnMapFailure
= false;
3655 bool mNeedsCheckAfterAttachTextureToFb
= false;
3656 const bool mWorkAroundDriverBugs
;
3657 mutable uint64_t mSyncGLCallCount
= 0;
3659 bool IsTextureSizeSafeToPassToDriver(GLenum target
, GLsizei width
,
3660 GLsizei height
) const {
3661 if (mNeedsTextureSizeChecks
) {
3662 // some drivers incorrectly handle some large texture sizes that are below
3663 // the max texture size that they report. So we check ourselves against
3664 // our own values (mMax[CubeMap]TextureSize). see bug 737182 for Mac Intel
3665 // 2D textures see bug 684882 for Mac Intel cube map textures see bug
3666 // 814716 for Mesa Nouveau
3668 target
== LOCAL_GL_TEXTURE_CUBE_MAP
||
3669 (target
>= LOCAL_GL_TEXTURE_CUBE_MAP_POSITIVE_X
&&
3670 target
<= LOCAL_GL_TEXTURE_CUBE_MAP_NEGATIVE_Z
)
3671 ? mMaxCubeMapTextureSize
3673 return width
<= maxSize
&& height
<= maxSize
;
3679 auto MaxSamples() const { return uint32_t(mMaxSamples
); }
3680 auto MaxTextureSize() const { return uint32_t(mMaxTextureSize
); }
3681 auto MaxRenderbufferSize() const { return uint32_t(mMaxRenderbufferSize
); }
3682 auto MaxTexOrRbSize() const { return mMaxTexOrRbSize
; }
3685 void CreatedProgram(GLContext
* aOrigin
, GLuint aName
);
3686 void CreatedShader(GLContext
* aOrigin
, GLuint aName
);
3687 void CreatedBuffers(GLContext
* aOrigin
, GLsizei aCount
, GLuint
* aNames
);
3688 void CreatedQueries(GLContext
* aOrigin
, GLsizei aCount
, GLuint
* aNames
);
3689 void CreatedTextures(GLContext
* aOrigin
, GLsizei aCount
, GLuint
* aNames
);
3690 void CreatedFramebuffers(GLContext
* aOrigin
, GLsizei aCount
, GLuint
* aNames
);
3691 void CreatedRenderbuffers(GLContext
* aOrigin
, GLsizei aCount
, GLuint
* aNames
);
3692 void DeletedProgram(GLContext
* aOrigin
, GLuint aName
);
3693 void DeletedShader(GLContext
* aOrigin
, GLuint aName
);
3694 void DeletedBuffers(GLContext
* aOrigin
, GLsizei aCount
, const GLuint
* aNames
);
3695 void DeletedQueries(GLContext
* aOrigin
, GLsizei aCount
, const GLuint
* aNames
);
3696 void DeletedTextures(GLContext
* aOrigin
, GLsizei aCount
,
3697 const GLuint
* aNames
);
3698 void DeletedFramebuffers(GLContext
* aOrigin
, GLsizei aCount
,
3699 const GLuint
* aNames
);
3700 void DeletedRenderbuffers(GLContext
* aOrigin
, GLsizei aCount
,
3701 const GLuint
* aNames
);
3703 void SharedContextDestroyed(GLContext
* aChild
);
3704 void ReportOutstandingNames();
3706 struct NamedResource
{
3707 NamedResource() : origin(nullptr), name(0), originDeleted(false) {}
3709 NamedResource(GLContext
* aOrigin
, GLuint aName
)
3710 : origin(aOrigin
), name(aName
), originDeleted(false) {}
3717 bool operator<(const NamedResource
& aOther
) const {
3718 if (intptr_t(origin
) < intptr_t(aOther
.origin
)) return true;
3719 if (name
< aOther
.name
) return true;
3722 bool operator==(const NamedResource
& aOther
) const {
3723 return origin
== aOther
.origin
&& name
== aOther
.name
&&
3724 originDeleted
== aOther
.originDeleted
;
3728 nsTArray
<NamedResource
> mTrackedPrograms
;
3729 nsTArray
<NamedResource
> mTrackedShaders
;
3730 nsTArray
<NamedResource
> mTrackedTextures
;
3731 nsTArray
<NamedResource
> mTrackedFramebuffers
;
3732 nsTArray
<NamedResource
> mTrackedRenderbuffers
;
3733 nsTArray
<NamedResource
> mTrackedBuffers
;
3734 nsTArray
<NamedResource
> mTrackedQueries
;
3738 bool mHeavyGLCallsSinceLastFlush
= false;
3741 void FlushIfHeavyGLCallsSinceLastFlush();
3742 static bool ShouldSpew();
3743 static bool ShouldDumpExts();
3747 void TexParams_SetClampNoMips(GLenum target
= LOCAL_GL_TEXTURE_2D
) {
3748 fTexParameteri(target
, LOCAL_GL_TEXTURE_WRAP_S
, LOCAL_GL_CLAMP_TO_EDGE
);
3749 fTexParameteri(target
, LOCAL_GL_TEXTURE_WRAP_T
, LOCAL_GL_CLAMP_TO_EDGE
);
3750 fTexParameteri(target
, LOCAL_GL_TEXTURE_MAG_FILTER
, LOCAL_GL_NEAREST
);
3751 fTexParameteri(target
, LOCAL_GL_TEXTURE_MIN_FILTER
, LOCAL_GL_NEAREST
);
3756 GLuint
CreateFramebuffer() {
3758 fGenFramebuffers(1, &x
);
3761 GLuint
CreateRenderbuffer() {
3763 fGenRenderbuffers(1, &x
);
3766 GLuint
CreateTexture() {
3768 fGenTextures(1, &x
);
3772 void DeleteFramebuffer(const GLuint x
) { fDeleteFramebuffers(1, &x
); }
3773 void DeleteRenderbuffer(const GLuint x
) { fDeleteRenderbuffers(1, &x
); }
3774 void DeleteTexture(const GLuint x
) { fDeleteTextures(1, &x
); }
3777 bool DoesStringMatch(const char* aString
, const char* aWantedString
);
3779 void SplitByChar(const nsACString
& str
, const char delim
,
3780 std::vector
<nsCString
>* const out
);
3783 bool MarkBitfieldByString(const nsACString
& str
,
3784 const char* const (&markStrList
)[N
],
3785 std::bitset
<N
>* const out_markList
) {
3786 for (size_t i
= 0; i
< N
; i
++) {
3787 if (str
.Equals(markStrList
[i
])) {
3788 (*out_markList
)[i
] = 1;
3796 void MarkBitfieldByStrings(const std::vector
<nsCString
>& strList
,
3798 const char* const (&markStrList
)[N
],
3799 std::bitset
<N
>* const out_markList
) {
3800 for (auto itr
= strList
.begin(); itr
!= strList
.end(); ++itr
) {
3801 const nsACString
& str
= *itr
;
3802 const bool wasMarked
= MarkBitfieldByString(str
, markStrList
, out_markList
);
3804 printf_stderr(" %s%s\n", str
.BeginReading(), wasMarked
? "(*)" : "");
3810 class Renderbuffer final
{
3812 const WeakPtr
<GLContext
> weakGl
;
3816 static GLuint
Create(GLContext
& gl
) {
3818 gl
.fGenRenderbuffers(1, &ret
);
3823 explicit Renderbuffer(GLContext
& gl
) : weakGl(&gl
), name(Create(gl
)) {}
3826 const RefPtr
<GLContext
> gl
= weakGl
.get();
3827 if (!gl
|| !gl
->MakeCurrent()) return;
3828 gl
->fDeleteRenderbuffers(1, &name
);
3834 class Texture final
{
3836 const WeakPtr
<GLContext
> weakGl
;
3840 static GLuint
Create(GLContext
& gl
) {
3842 gl
.fGenTextures(1, &ret
);
3847 explicit Texture(GLContext
& gl
) : weakGl(&gl
), name(Create(gl
)) {}
3850 const RefPtr
<GLContext
> gl
= weakGl
.get();
3851 if (!gl
|| !gl
->MakeCurrent()) return;
3852 gl
->fDeleteTextures(1, &name
);
3857 * Helper function that creates a 2D texture aSize.width x aSize.height with
3858 * storage type specified by aFormats. Returns GL texture object id.
3860 * See mozilla::gl::CreateTexture.
3862 UniquePtr
<Texture
> CreateTexture(GLContext
&, const gfx::IntSize
& size
);
3865 * Helper function that calculates the number of bytes required per
3866 * texel for a texture from its format and type.
3868 uint32_t GetBytesPerTexel(GLenum format
, GLenum type
);
3870 void MesaMemoryLeakWorkaround();
3872 } /* namespace gl */
3873 } /* namespace mozilla */
3875 #endif /* GLCONTEXT_H_ */