diff options
author | Michael Meeks <michael.meeks@collabora.com> | 2015-09-02 11:18:42 +0100 |
---|---|---|
committer | Michael Meeks <michael.meeks@collabora.com> | 2015-09-02 12:12:01 +0100 |
commit | daa869222edc3aded82f0fc3e73f126b6cfd08ad (patch) | |
tree | e1dc897c9d7066c9ee4a453635bdc3eb1ea40109 | |
parent | b25388f9c71804df92582f01dac8e5d9d1d5439e (diff) |
tdf#93850 - Defer watchdog during shader compiles.
Shader compilation can take a while the first time; best not to
disable GL at that point. Have more of a hair trigger at other times.
Also explicitly exit if we appear to have hung in std::abort handling.
Change-Id: I45f0873672f950fb3baba0ca859d854a0bb25064
-rw-r--r-- | vcl/source/opengl/OpenGLHelper.cxx | 70 |
1 files changed, 54 insertions, 16 deletions
diff --git a/vcl/source/opengl/OpenGLHelper.cxx b/vcl/source/opengl/OpenGLHelper.cxx index 9a28438afe83..6288849dda28 100644 --- a/vcl/source/opengl/OpenGLHelper.cxx +++ b/vcl/source/opengl/OpenGLHelper.cxx @@ -28,6 +28,7 @@ #include "svdata.hxx" +#include "salinst.hxx" #include "opengl/zone.hxx" #include "opengl/watchdog.hxx" #include <osl/conditn.h> @@ -38,6 +39,10 @@ #include "opengl/win/WinDeviceInfo.hxx" #endif +static bool volatile gbInShaderCompile = false; +sal_uInt64 volatile OpenGLZone::gnEnterCount = 0; +sal_uInt64 volatile OpenGLZone::gnLeaveCount = 0; + namespace { OUString getShaderFolder() @@ -140,6 +145,8 @@ GLint OpenGLHelper::LoadShaders(const OUString& rVertexShaderName,const OUString { OpenGLZone aZone; + gbInShaderCompile = true; + VCL_GL_INFO("vcl.opengl", "Load shader: vertex " << rVertexShaderName << " fragment " << rFragmentShaderName); // Create the shaders GLuint VertexShaderID = glCreateShader(GL_VERTEX_SHADER); @@ -190,6 +197,11 @@ GLint OpenGLHelper::LoadShaders(const OUString& rVertexShaderName,const OUString return LogCompilerError(ProgramID, "program", "<both>", false); CHECK_GL_ERROR(); + + // Ensure we bump our counts before we leave the shader zone. + { OpenGLZone aMakeProgress; } + gbInShaderCompile = false; + return ProgramID; } @@ -462,9 +474,6 @@ bool OpenGLHelper::supportsVCLOpenGL() return true; } -sal_uInt64 volatile OpenGLZone::gnEnterCount = 0; -sal_uInt64 volatile OpenGLZone::gnLeaveCount = 0; - void OpenGLZone::enter() { gnEnterCount++; } void OpenGLZone::leave() { gnLeaveCount++; } @@ -481,10 +490,13 @@ OpenGLWatchdogThread::OpenGLWatchdogThread() void OpenGLWatchdogThread::execute() { - static const int nDisableEntries = 4; // 2 seconds - disable GL - static const int nAbortAfter = 10; // 5 seconds - not coming back; abort + // delays to take various actions in 1/4 of a second increments. + static const int nDisableEntries[2] = { 6 /* 1.5s */, 20 /* 5s */ }; + static const int nAbortAfter[2] = { 20 /* 10s */, 120 /* 30s */ }; + int nUnchanged = 0; // how many unchanged nEnters - TimeValue aHalfSecond(0, 1000*1000*1000*0.5); + TimeValue aHalfSecond(0, 1000*1000*1000*0.25); + bool bAbortFired = false; do { sal_uInt64 nLastEnters = OpenGLZone::gnEnterCount; @@ -493,28 +505,54 @@ void OpenGLWatchdogThread::execute() if (OpenGLZone::isInZone()) { + int nType = 0; + // The shader compiler can take a long time, first time. + if (gbInShaderCompile) + nType = 1; + if (nLastEnters == OpenGLZone::gnEnterCount) nUnchanged++; else nUnchanged = 0; SAL_INFO("vcl.opengl", "GL watchdog - unchanged " << nUnchanged << " enter count " << - OpenGLZone::gnEnterCount); + OpenGLZone::gnEnterCount << " type " << + (nType ? "in shader" : "normal gl") << + "breakpoints mid: " << nDisableEntries[nType] << + " max " << nAbortAfter[nType]); // Not making progress - if (nUnchanged == nDisableEntries) + if (nUnchanged >= nDisableEntries[nType]) { - gbWatchdogFiring = true; - SAL_WARN("vcl.opengl", "Watchdog triggered: hard disable GL"); - OpenGLZone::hardDisable(); - gbWatchdogFiring = false; + static bool bFired = false; + if (!bFired) + { + gbWatchdogFiring = true; + SAL_WARN("vcl.opengl", "Watchdog triggered: hard disable GL"); + OpenGLZone::hardDisable(); + gbWatchdogFiring = false; + } + bFired = true; + + // we can hang using VCL in the abort handling -> be impatient + if (bAbortFired) + { + SAL_WARN("vcl.opengl", "Watchdog gave up: hard exiting"); + _exit(1); + } } - if (nUnchanged == nAbortAfter) + // Not making even more progress + if (nUnchanged >= nAbortAfter[nType]) { - SAL_WARN("vcl.opengl", "Watchdog gave up: aborting"); - gbWatchdogFiring = true; - std::abort(); + if (!bAbortFired) + { + SAL_WARN("vcl.opengl", "Watchdog gave up: aborting"); + gbWatchdogFiring = true; + nUnchanged = 0; + std::abort(); + } + bAbortFired = true; } } else |