From 7baee176283e713913603f88bdd34567166e0fba Mon Sep 17 00:00:00 2001 From: Jeff Gilbert Date: Thu, 9 Feb 2017 20:31:36 -0800 Subject: [PATCH] Bug 1339256 - Detect robust_buffer_access_behavior. - r=daoshengmu MozReview-Commit-ID: 4w5D9bOQbY8 --- dom/canvas/WebGLContext.h | 2 ++ dom/canvas/WebGLContextValidate.cpp | 5 ++++ gfx/gl/GLContext.cpp | 37 ++++++++++------------------- gfx/gl/GLContext.h | 17 ++++--------- gfx/gl/GLContextCGL.h | 2 -- gfx/gl/GLContextEAGL.h | 2 -- gfx/gl/GLContextEGL.h | 4 ---- gfx/gl/GLContextFeatures.cpp | 12 ++++++++++ gfx/gl/GLContextGLX.h | 2 -- gfx/gl/GLContextProviderEGL.cpp | 35 ++++++++++++++++----------- gfx/gl/GLContextProviderGLX.cpp | 14 ++++------- gfx/gl/GLContextProviderWGL.cpp | 6 ----- gfx/gl/GLContextWGL.h | 2 -- gfx/gl/GLDefs.h | 3 +++ gfx/gl/GLLibraryEGL.cpp | 3 ++- gfx/gl/GLLibraryEGL.h | 5 +--- gfx/thebes/gfxPrefs.h | 1 + modules/libpref/init/all.js | 1 + 18 files changed, 69 insertions(+), 84 deletions(-) diff --git a/dom/canvas/WebGLContext.h b/dom/canvas/WebGLContext.h index f11089d5bcf8..8147a32ff821 100644 --- a/dom/canvas/WebGLContext.h +++ b/dom/canvas/WebGLContext.h @@ -1965,6 +1965,8 @@ protected: bool mNeedsFakeNoStencil; bool mNeedsEmulatedLoneDepthStencil; + bool mNeedsIndexValidation; + const bool mAllowFBInvalidation; bool Has64BitTimestamps() const; diff --git a/dom/canvas/WebGLContextValidate.cpp b/dom/canvas/WebGLContextValidate.cpp index 8d791b1b3f42..9288800c627e 100644 --- a/dom/canvas/WebGLContextValidate.cpp +++ b/dom/canvas/WebGLContextValidate.cpp @@ -725,6 +725,11 @@ WebGLContext::InitAndValidateGL(FailureReason* const out_failReason) mFakeVertexAttrib0BufferObject = 0; + mNeedsIndexValidation = !gl->IsSupported(gl::GLFeature::robust_buffer_access_behavior); + if (gfxPrefs::WebGLForceIndexValidation()) { + mNeedsIndexValidation = true; + } + return true; } diff --git a/gfx/gl/GLContext.cpp b/gfx/gl/GLContext.cpp index 0349965e9691..22d85c1f514e 100644 --- a/gfx/gl/GLContext.cpp +++ b/gfx/gl/GLContext.cpp @@ -103,6 +103,7 @@ static const char* const sExtensionNames[] = { "GL_ARB_map_buffer_range", "GL_ARB_occlusion_query2", "GL_ARB_pixel_buffer_object", + "GL_ARB_robust_buffer_access_behavior", "GL_ARB_robustness", "GL_ARB_sampler_objects", "GL_ARB_seamless_cube_map", @@ -157,6 +158,8 @@ static const char* const sExtensionNames[] = { "GL_IMG_texture_compression_pvrtc", "GL_IMG_texture_npot", "GL_KHR_debug", + "GL_KHR_robust_buffer_access_behavior", + "GL_KHR_robustness", "GL_KHR_texture_compression_astc_hdr", "GL_KHR_texture_compression_astc_ldr", "GL_NV_draw_instanced", @@ -1143,31 +1146,15 @@ GLContext::LoadMoreSymbols(const char* prefix, bool trygl) }; if (IsSupported(GLFeature::robustness)) { - bool hasRobustness = false; - - if (!hasRobustness && IsExtensionSupported(ARB_robustness)) { - const SymLoadStruct symbols[] = { - { (PRFuncPtr*) &mSymbols.fGetGraphicsResetStatus, { "GetGraphicsResetStatusARB", nullptr } }, - END_SYMBOLS - }; - if (fnLoadForExt(symbols, ARB_robustness)) { - hasRobustness = true; - } - } - - if (!hasRobustness && IsExtensionSupported(EXT_robustness)) { - const SymLoadStruct symbols[] = { - { (PRFuncPtr*) &mSymbols.fGetGraphicsResetStatus, { "GetGraphicsResetStatusEXT", nullptr } }, - END_SYMBOLS - }; - if (fnLoadForExt(symbols, EXT_robustness)) { - hasRobustness = true; - } - } - - if (!hasRobustness) { - MarkUnsupported(GLFeature::robustness); - } + const SymLoadStruct symbols[] = { + { (PRFuncPtr*) &mSymbols.fGetGraphicsResetStatus, { "GetGraphicsResetStatus", + "GetGraphicsResetStatusARB", + "GetGraphicsResetStatusKHR", + "GetGraphicsResetStatusEXT", + nullptr } }, + END_SYMBOLS + }; + fnLoadForFeature(symbols, GLFeature::sync); } if (IsSupported(GLFeature::sync)) { diff --git a/gfx/gl/GLContext.h b/gfx/gl/GLContext.h index 9dcf0a4dba8e..8aea80eae066 100644 --- a/gfx/gl/GLContext.h +++ b/gfx/gl/GLContext.h @@ -121,6 +121,7 @@ enum class GLFeature { read_buffer, renderbuffer_color_float, renderbuffer_color_half_float, + robust_buffer_access_behavior, robustness, sRGB_framebuffer, sRGB_texture, @@ -199,10 +200,6 @@ class GLContext public: MOZ_DECLARE_WEAKREFERENCE_TYPENAME(GLContext) -// ----------------------------------------------------------------------------- -// basic enums -public: - // ----------------------------------------------------------------------------- // basic getters public: @@ -434,6 +431,7 @@ public: ARB_map_buffer_range, ARB_occlusion_query2, ARB_pixel_buffer_object, + ARB_robust_buffer_access_behavior, ARB_robustness, ARB_sampler_objects, ARB_seamless_cube_map, @@ -488,6 +486,8 @@ public: IMG_texture_compression_pvrtc, IMG_texture_npot, KHR_debug, + KHR_robust_buffer_access_behavior, + KHR_robustness, KHR_texture_compression_astc_hdr, KHR_texture_compression_astc_ldr, NV_draw_instanced, @@ -571,15 +571,6 @@ private: */ bool IsFeatureProvidedByCoreSymbols(GLFeature feature); -// ----------------------------------------------------------------------------- -// Robustness handling -private: - /** - * The derived class is expected to provide information on whether or not it - * supports robustness. - */ - virtual bool SupportsRobustness() const = 0; - public: // ----------------------------------------------------------------------------- // Error handling diff --git a/gfx/gl/GLContextCGL.h b/gfx/gl/GLContextCGL.h index 1a29f3d15519..eae9f1d75cba 100644 --- a/gfx/gl/GLContextCGL.h +++ b/gfx/gl/GLContextCGL.h @@ -55,8 +55,6 @@ public: virtual bool IsDoubleBuffered() const override; - virtual bool SupportsRobustness() const override { return false; } - virtual bool SwapBuffers() override; virtual void GetWSIInfo(nsCString* const out) const override; diff --git a/gfx/gl/GLContextEAGL.h b/gfx/gl/GLContextEAGL.h index df25d0f1e560..581cd6a3ca9c 100644 --- a/gfx/gl/GLContextEAGL.h +++ b/gfx/gl/GLContextEAGL.h @@ -51,8 +51,6 @@ public: virtual bool IsDoubleBuffered() const override; - virtual bool SupportsRobustness() const override { return false; } - virtual bool SwapBuffers() override; virtual void GetWSIInfo(nsCString* const out) const override; diff --git a/gfx/gl/GLContextEGL.h b/gfx/gl/GLContextEGL.h index 4c1d7a826822..33300dde312b 100644 --- a/gfx/gl/GLContextEGL.h +++ b/gfx/gl/GLContextEGL.h @@ -58,10 +58,6 @@ public: mIsDoubleBuffered = aIsDB; } - virtual bool SupportsRobustness() const override { - return sEGLLibrary.HasRobustness(); - } - virtual bool IsANGLE() const override { return sEGLLibrary.IsANGLE(); } diff --git a/gfx/gl/GLContextFeatures.cpp b/gfx/gl/GLContextFeatures.cpp index 0714d964150d..7307a7e021d3 100644 --- a/gfx/gl/GLContextFeatures.cpp +++ b/gfx/gl/GLContextFeatures.cpp @@ -532,6 +532,17 @@ static const FeatureInfo sFeatureInfoArr[] = { GLContext::Extensions_End } }, + { + "robust_buffer_access_behavior", + GLVersion::NONE, + GLESVersion::NONE, + GLContext::Extension_None, + { + GLContext::ARB_robust_buffer_access_behavior, + GLContext::KHR_robust_buffer_access_behavior, + GLContext::Extensions_End + } + }, { "robustness", GLVersion::NONE, @@ -540,6 +551,7 @@ static const FeatureInfo sFeatureInfoArr[] = { { GLContext::ARB_robustness, GLContext::EXT_robustness, + GLContext::KHR_robustness, GLContext::Extensions_End } }, diff --git a/gfx/gl/GLContextGLX.h b/gfx/gl/GLContextGLX.h index 4be8d500c715..e3cae6d47df7 100644 --- a/gfx/gl/GLContextGLX.h +++ b/gfx/gl/GLContextGLX.h @@ -56,8 +56,6 @@ public: virtual bool IsDoubleBuffered() const override; - virtual bool SupportsRobustness() const override; - virtual bool SwapBuffers() override; virtual void GetWSIInfo(nsCString* const out) const override; diff --git a/gfx/gl/GLContextProviderEGL.cpp b/gfx/gl/GLContextProviderEGL.cpp index d526d89d9be2..dac28446ca6a 100644 --- a/gfx/gl/GLContextProviderEGL.cpp +++ b/gfx/gl/GLContextProviderEGL.cpp @@ -84,7 +84,7 @@ CreateConfig(EGLConfig* aConfig); #define EGL_ATTRIBS_LIST_SAFE_TERMINATION_WORKING_AROUND_BUGS \ LOCAL_EGL_NONE, 0, 0, 0 -static EGLint gTerminationAttribs[] = { +static EGLint kTerminationAttribs[] = { EGL_ATTRIBS_LIST_SAFE_TERMINATION_WORKING_AROUND_BUGS }; @@ -482,31 +482,38 @@ GLContextEGL::CreateGLContext(CreateContextFlags flags, EGLContext eglShareContext = shareContext ? shareContext->mContext : EGL_NO_CONTEXT; - nsTArray contextAttribs; + std::vector contextAttribs; - contextAttribs.AppendElement(LOCAL_EGL_CONTEXT_CLIENT_VERSION); + contextAttribs.push_back(LOCAL_EGL_CONTEXT_CLIENT_VERSION); if (flags & CreateContextFlags::PREFER_ES3) - contextAttribs.AppendElement(3); + contextAttribs.push_back(3); else - contextAttribs.AppendElement(2); + contextAttribs.push_back(2); - if (sEGLLibrary.HasRobustness()) { -// contextAttribs.AppendElement(LOCAL_EGL_CONTEXT_ROBUST_ACCESS_EXT); -// contextAttribs.AppendElement(LOCAL_EGL_TRUE); + if (sEGLLibrary.IsExtensionSupported(GLLibraryEGL::KHR_create_context)) { + contextAttribs.push_back(LOCAL_EGL_CONTEXT_OPENGL_RESET_NOTIFICATION_STRATEGY_KHR); + contextAttribs.push_back(LOCAL_EGL_LOSE_CONTEXT_ON_RESET_KHR); + contextAttribs.push_back(LOCAL_EGL_CONTEXT_FLAGS_KHR); + contextAttribs.push_back(LOCAL_EGL_CONTEXT_OPENGL_ROBUST_ACCESS_BIT_KHR); + } else if (sEGLLibrary.IsExtensionSupported(GLLibraryEGL::EXT_create_context_robustness)) { + contextAttribs.push_back(LOCAL_EGL_CONTEXT_OPENGL_RESET_NOTIFICATION_STRATEGY_EXT); + contextAttribs.push_back(LOCAL_EGL_LOSE_CONTEXT_ON_RESET_EXT); + contextAttribs.push_back(LOCAL_EGL_CONTEXT_OPENGL_ROBUST_ACCESS_EXT); + contextAttribs.push_back(LOCAL_EGL_TRUE); } - for (size_t i = 0; i < MOZ_ARRAY_LENGTH(gTerminationAttribs); i++) { - contextAttribs.AppendElement(gTerminationAttribs[i]); + for (const auto& cur : kTerminationAttribs) { + contextAttribs.push_back(cur); } EGLContext context = sEGLLibrary.fCreateContext(EGL_DISPLAY(), config, eglShareContext, - contextAttribs.Elements()); + contextAttribs.data()); if (!context && shareContext) { shareContext = nullptr; context = sEGLLibrary.fCreateContext(EGL_DISPLAY(), config, EGL_NO_CONTEXT, - contextAttribs.Elements()); + contextAttribs.data()); } if (!context) { *out_failureId = NS_LITERAL_CSTRING("FEATURE_FAILURE_EGL_CREATE"); @@ -547,8 +554,8 @@ TRY_AGAIN_POWER_OF_TWO: pbattrs.AppendElement(bindToTextureFormat); } - for (size_t i = 0; i < MOZ_ARRAY_LENGTH(gTerminationAttribs); i++) { - pbattrs.AppendElement(gTerminationAttribs[i]); + for (const auto& cur : kTerminationAttribs) { + pbattrs.AppendElement(cur); } surface = sEGLLibrary.fCreatePbufferSurface(EGL_DISPLAY(), config, &pbattrs[0]); diff --git a/gfx/gl/GLContextProviderGLX.cpp b/gfx/gl/GLContextProviderGLX.cpp index 32c9f1efcd34..1ecc18abe8c1 100644 --- a/gfx/gl/GLContextProviderGLX.cpp +++ b/gfx/gl/GLContextProviderGLX.cpp @@ -511,9 +511,11 @@ GLContextGLX::CreateGLContext(CreateContextFlags flags, const SurfaceCaps& caps, if (glx.HasCreateContextAttribs()) { AutoTArray attrib_list; if (glx.HasRobustness()) { - int robust_attribs[] = { - LOCAL_GL_CONTEXT_FLAGS_ARB, LOCAL_GL_CONTEXT_ROBUST_ACCESS_BIT_ARB, - LOCAL_GL_CONTEXT_RESET_NOTIFICATION_STRATEGY_ARB, LOCAL_GL_LOSE_CONTEXT_ON_RESET_ARB, + const int robust_attribs[] = { + LOCAL_GLX_CONTEXT_FLAGS_ARB, + LOCAL_GLX_CONTEXT_ROBUST_ACCESS_BIT_ARB, + LOCAL_GLX_CONTEXT_RESET_NOTIFICATION_STRATEGY_ARB, + LOCAL_GLX_LOSE_CONTEXT_ON_RESET_ARB, }; attrib_list.AppendElements(robust_attribs, MOZ_ARRAY_LENGTH(robust_attribs)); } @@ -662,12 +664,6 @@ GLContextGLX::IsDoubleBuffered() const return mDoubleBuffered; } -bool -GLContextGLX::SupportsRobustness() const -{ - return mGLX->HasRobustness(); -} - bool GLContextGLX::SwapBuffers() { diff --git a/gfx/gl/GLContextProviderWGL.cpp b/gfx/gl/GLContextProviderWGL.cpp index 6e5c23537a22..8739fa2115f3 100644 --- a/gfx/gl/GLContextProviderWGL.cpp +++ b/gfx/gl/GLContextProviderWGL.cpp @@ -361,12 +361,6 @@ GLContextWGL::IsDoubleBuffered() const return mIsDoubleBuffered; } -bool -GLContextWGL::SupportsRobustness() const -{ - return sWGLLib.HasRobustness(); -} - bool GLContextWGL::SwapBuffers() { if (!mIsDoubleBuffered) diff --git a/gfx/gl/GLContextWGL.h b/gfx/gl/GLContextWGL.h index 0c2a444ff671..d8a6c8095108 100644 --- a/gfx/gl/GLContextWGL.h +++ b/gfx/gl/GLContextWGL.h @@ -53,8 +53,6 @@ public: virtual bool IsDoubleBuffered() const override; - virtual bool SupportsRobustness() const override; - virtual bool SwapBuffers() override; virtual bool SetupLookupFunction() override; diff --git a/gfx/gl/GLDefs.h b/gfx/gl/GLDefs.h index f580c06703fd..10b6782e192f 100644 --- a/gfx/gl/GLDefs.h +++ b/gfx/gl/GLDefs.h @@ -75,6 +75,9 @@ #define LOCAL_WGL_ACCESS_READ_WRITE 0x0001 #define LOCAL_WGL_ACCESS_WRITE_DISCARD 0x0002 +// GL_KHR_robustness +#define LOCAL_GL_CONTEXT_ROBUST_ACCESS 0x90F3 + // Others #define LOCAL_EGL_PRESERVED_RESOURCES 0x3030 #define LOCAL_EGL_CONTEXT_RESET_NOTIFICATION_STRATEGY_EXT 0x3138 diff --git a/gfx/gl/GLLibraryEGL.cpp b/gfx/gl/GLLibraryEGL.cpp index 54c04b45e361..6cfcf9797ff7 100644 --- a/gfx/gl/GLLibraryEGL.cpp +++ b/gfx/gl/GLLibraryEGL.cpp @@ -52,7 +52,8 @@ static const char* sEGLExtensionNames[] = { "EGL_ANDROID_image_crop", "EGL_ANGLE_platform_angle", "EGL_ANGLE_platform_angle_d3d", - "EGL_ANGLE_d3d_share_handle_client_buffer" + "EGL_ANGLE_d3d_share_handle_client_buffer", + "EGL_KHR_create_context", }; #if defined(ANDROID) diff --git a/gfx/gl/GLLibraryEGL.h b/gfx/gl/GLLibraryEGL.h index 447165e7b727..e10c980fd9ba 100644 --- a/gfx/gl/GLLibraryEGL.h +++ b/gfx/gl/GLLibraryEGL.h @@ -105,6 +105,7 @@ public: ANGLE_platform_angle, ANGLE_platform_angle_d3d, ANGLE_d3d_share_handle_client_buffer, + KHR_create_context, Extensions_Max }; @@ -327,10 +328,6 @@ public: return IsExtensionSupported(ANGLE_surface_d3d_texture_2d_share_handle); } - bool HasRobustness() const { - return IsExtensionSupported(EXT_create_context_robustness); - } - bool ReadbackEGLImage(EGLImage image, gfx::DataSourceSurface* out_surface); bool EnsureInitialized(bool forceAccel, nsACString* const out_failureId); diff --git a/gfx/thebes/gfxPrefs.h b/gfx/thebes/gfxPrefs.h index 42237858ccd2..c0204e0bea45 100644 --- a/gfx/thebes/gfxPrefs.h +++ b/gfx/thebes/gfxPrefs.h @@ -628,6 +628,7 @@ private: DECL_GFX_PREF(Live, "webgl.enable-webgl2", WebGL2Enabled, bool, true); DECL_GFX_PREF(Live, "webgl.force-enabled", WebGLForceEnabled, bool, false); DECL_GFX_PREF(Once, "webgl.force-layers-readback", WebGLForceLayersReadback, bool, false); + DECL_GFX_PREF(Live, "webgl.force-index-validation", WebGLForceIndexValidation, bool, false); DECL_GFX_PREF(Live, "webgl.lose-context-on-memory-pressure", WebGLLoseContextOnMemoryPressure, bool, false); DECL_GFX_PREF(Live, "webgl.max-warnings-per-context", WebGLMaxWarningsPerContext, uint32_t, 32); DECL_GFX_PREF(Live, "webgl.min_capability_mode", WebGLMinCapabilityMode, bool, false); diff --git a/modules/libpref/init/all.js b/modules/libpref/init/all.js index afac60313b55..0de0bf521798 100644 --- a/modules/libpref/init/all.js +++ b/modules/libpref/init/all.js @@ -4540,6 +4540,7 @@ pref("webgl.msaa-force", false); pref("webgl.prefer-16bpp", false); pref("webgl.default-no-alpha", false); pref("webgl.force-layers-readback", false); +pref("webgl.force-index-validation", false); pref("webgl.lose-context-on-memory-pressure", false); pref("webgl.can-lose-context-in-foreground", true); pref("webgl.restore-context-when-visible", true);