[Libreoffice-commits] core.git: Branch 'libreoffice-4-2' - 4 commits - sc/inc sc/source

Tor Lillqvist tml at collabora.com
Tue Jan 7 04:24:38 PST 2014


 sc/inc/clkernelthread.hxx                |   16 ++++++-
 sc/inc/formulacell.hxx                   |    6 --
 sc/source/core/data/formulacell.cxx      |   58 +++++++++++++--------------
 sc/source/core/opencl/formulagroupcl.cxx |   15 ++-----
 sc/source/core/opencl/opbase.hxx         |   66 ++++++++++++++++++++++++++++++-
 sc/source/core/tool/clkernelthread.cxx   |   16 ++++---
 sc/source/core/tool/formulaopt.cxx       |    4 +
 7 files changed, 127 insertions(+), 54 deletions(-)

New commits:
commit d7f899bc56affad4ddd1672d3bfb354dc5966196
Author: Tor Lillqvist <tml at collabora.com>
Date:   Tue Jan 7 14:08:09 2014 +0200

    Drop the check of the SC_BACKGROUND_COMPILATION env var
    
    Change-Id: Ia33002819023c79160d921fbc1cca7a5c12d143a

diff --git a/sc/source/core/data/formulacell.cxx b/sc/source/core/data/formulacell.cxx
index 531c7e5..721f268 100644
--- a/sc/source/core/data/formulacell.cxx
+++ b/sc/source/core/data/formulacell.cxx
@@ -415,18 +415,14 @@ ScFormulaCellGroup::ScFormulaCellGroup() :
     mbSubTotal(false),
     meCalcState(sc::GroupCalcEnabled)
 {
-    static bool bBackgroundCompilation = getenv("SC_BACKGROUND_COMPILATION") != NULL;
-    if (bBackgroundCompilation)
+    if (ScInterpreter::GetGlobalConfig().mbOpenCLEnabled)
     {
-        if (ScInterpreter::GetGlobalConfig().mbOpenCLEnabled)
+        osl::MutexGuard aGuard(getOpenCLCompilationThreadMutex());
+        if (snCount++ == 0)
         {
-            osl::MutexGuard aGuard(getOpenCLCompilationThreadMutex());
-            if (snCount++ == 0)
-            {
-                assert(!sxCompilationThread.is());
-                sxCompilationThread.set(new sc::CLBuildKernelThread);
-                sxCompilationThread->launch();
-            }
+            assert(!sxCompilationThread.is());
+            sxCompilationThread.set(new sc::CLBuildKernelThread);
+            sxCompilationThread->launch();
         }
     }
 }
diff --git a/sc/source/core/tool/formulaopt.cxx b/sc/source/core/tool/formulaopt.cxx
index ebeece1..e954423 100644
--- a/sc/source/core/tool/formulaopt.cxx
+++ b/sc/source/core/tool/formulaopt.cxx
@@ -412,10 +412,9 @@ void ScFormulaCfg::UpdateFromProperties( const Sequence<OUString>& aNames )
                 {
                     sal_Bool bVal = GetCalcConfig().mbOpenCLEnabled;
                     pValues[nProp] >>= bVal;
-#if 0 // Don't remove please unless the SC_BACKGROUND_COMPILATION env var thing goes away.
+#if 0 // Don't remove please.
       // The intent here is that tml when running CppunitTest_sc_opencl_test turns this on.
-                    if (getenv("SC_BACKGROUND_COMPILATION") != NULL)
-                        bVal = sal_True;
+                    bVal = sal_True;
 #endif
                     GetCalcConfig().mbOpenCLEnabled = bVal;
                 }
commit 0c7309cfa5cbf295aae2917d1ccd73d5ab8ed026
Author: Tor Lillqvist <tml at collabora.com>
Date:   Tue Jan 7 11:53:12 2014 +0200

    Add some more logging
    
    Change-Id: I637c365626242142a0f6fc0ac002fa9dd5f1340a

diff --git a/sc/source/core/data/formulacell.cxx b/sc/source/core/data/formulacell.cxx
index c15710f..531c7e5 100644
--- a/sc/source/core/data/formulacell.cxx
+++ b/sc/source/core/data/formulacell.cxx
@@ -3501,13 +3501,15 @@ bool ScFormulaCell::InterpretFormulaGroup()
         aTopPos.SetRow(mxGroup->mpTopCell->aPos.Row());
         ScGroupTokenConverter aConverter(aCode, *pDocument, *this, mxGroup->mpTopCell->aPos);
         if (!aConverter.convert(*pCode))
-            {
-                mxGroup->meCalcState = sc::GroupCalcDisabled;
-                return false;
-            }
+        {
+            SAL_INFO("sc.opencl", "conversion of group " << this << " failed, disabling");
+            mxGroup->meCalcState = sc::GroupCalcDisabled;
+            return false;
+        }
         mxGroup->meCalcState = sc::GroupCalcRunning;
         if (!sc::FormulaGroupInterpreter::getStatic()->interpret(*pDocument, mxGroup->mpTopCell->aPos, mxGroup, aCode))
         {
+            SAL_INFO("sc.opencl", "interpreting group " << mxGroup << " (state " << mxGroup->meCalcState << ") failed, disabling");
             mxGroup->meCalcState = sc::GroupCalcDisabled;
             return false;
         }
@@ -3517,10 +3519,11 @@ bool ScFormulaCell::InterpretFormulaGroup()
     {
         ScTokenArray aDummy;
         if (!sc::FormulaGroupInterpreter::getStatic()->interpret(*pDocument, mxGroup->mpTopCell->aPos, mxGroup, aDummy))
-            {
-                mxGroup->meCalcState = sc::GroupCalcDisabled;
-                return false;
-            }
+        {
+            SAL_INFO("sc.opencl", "interpreting group " << mxGroup << " (state " << mxGroup->meCalcState << ") failed, disabling");
+            mxGroup->meCalcState = sc::GroupCalcDisabled;
+            return false;
+        }
     }
 
     return true;
commit d90fa180dd76e55f5d480f63ce5e484e31307783
Author: Tor Lillqvist <tml at collabora.com>
Date:   Tue Jan 7 11:33:08 2014 +0200

    Avoid assertion failure if group has been disabled
    
    Change-Id: I918f2716778ddd9ede56b5df731a531f97a3b24d

diff --git a/sc/source/core/tool/clkernelthread.cxx b/sc/source/core/tool/clkernelthread.cxx
index 651d369..2a619c5 100644
--- a/sc/source/core/tool/clkernelthread.cxx
+++ b/sc/source/core/tool/clkernelthread.cxx
@@ -48,7 +48,9 @@ void CLBuildKernelThread::execute()
             switch (aWorkItem.meWhatToDo)
             {
             case CLBuildKernelWorkItem::COMPILE:
-                SAL_INFO("sc.opencl.thread", "told to compile group " << aWorkItem.mxGroup << " to binary");
+                SAL_INFO("sc.opencl.thread", "told to compile group " << aWorkItem.mxGroup << " (state " << aWorkItem.mxGroup->meCalcState << ") to binary");
+                if (aWorkItem.mxGroup->meCalcState == sc::GroupCalcDisabled)
+                    break;
                 assert(aWorkItem.mxGroup->meCalcState == sc::GroupCalcOpenCLKernelCompilationScheduled);
                 aWorkItem.mxGroup->mpCompiledFormula =
                     sc::FormulaGroupInterpreter::getStatic()->createCompiledFormula(*aWorkItem.mxGroup->mpTopCell->GetDocument(),
commit 8e3cb2d536adca7de2acde3cc68f25c32fa2b583
Author: Tor Lillqvist <tml at collabora.com>
Date:   Thu Nov 28 10:59:16 2013 +0200

    Background OpenCL compilation re-factoring
    
    Don't use a mutex and condition in each ScFormulaCellGroup.
    
    Not sure at all if this crack works, and I hate every moment spent on it, but
    at least it is still behind an environment variable.
    
    Change-Id: I70c917d47112e3a2ed010de4d123a4155f71c004

diff --git a/sc/inc/clkernelthread.hxx b/sc/inc/clkernelthread.hxx
index 89ae860..8018d3f 100644
--- a/sc/inc/clkernelthread.hxx
+++ b/sc/inc/clkernelthread.hxx
@@ -7,11 +7,17 @@
  * file, You can obtain one at http://mozilla.org/MPL/2.0/.
  */
 
+#ifndef INCLUDED_SC_INC_CLKERNELTHREAD_HXX
+#define INCLUDED_SC_INC_CLKERNELTHREAD_HXX
+
 #include <queue>
 
 #include <osl/conditn.hxx>
 #include <salhelper/thread.hxx>
 
+#include <boost/noncopyable.hpp>
+
+#include "scdllapi.h"
 #include "formulacell.hxx"
 
 namespace sc {
@@ -22,7 +28,7 @@ struct CLBuildKernelWorkItem
     ScFormulaCellGroupRef mxGroup;
 };
 
-class CLBuildKernelThread : public salhelper::Thread
+class SC_DLLPUBLIC CLBuildKernelThread : public salhelper::Thread, boost::noncopyable
 {
 public:
     CLBuildKernelThread();
@@ -32,12 +38,14 @@ public:
 
     void push(CLBuildKernelWorkItem item);
 
+    osl::Condition maCompilationDoneCondition;
+
 protected:
     virtual void execute();
 
 private:
-    osl::Mutex maMutex;
-    osl::Condition maCondition;
+    osl::Mutex maQueueMutex;
+    osl::Condition maQueueCondition;
     std::queue<CLBuildKernelWorkItem> maQueue;
     void produce();
     void consume();
@@ -45,4 +53,6 @@ private:
 
 }
 
+#endif // INCLUDED_SC_INC_CLKERNELTHREAD_HXX
+
 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
diff --git a/sc/inc/formulacell.hxx b/sc/inc/formulacell.hxx
index 656eebb..dbb52e4 100644
--- a/sc/inc/formulacell.hxx
+++ b/sc/inc/formulacell.hxx
@@ -57,8 +57,6 @@ struct SC_DLLPUBLIC ScFormulaCellGroup : boost::noncopyable
     mutable size_t mnRefCount;
 
     ScTokenArray* mpCode;
-    osl::Mutex maMutex;
-    osl::Condition maCompilationDone;
     sc::CompiledFormula* mpCompiledFormula;
     ScFormulaCell *mpTopCell;
     SCROW mnLength; // How many of these do we have ?
@@ -76,8 +74,8 @@ struct SC_DLLPUBLIC ScFormulaCellGroup : boost::noncopyable
     void compileCode(
         ScDocument& rDoc, const ScAddress& rPos, formula::FormulaGrammar::Grammar eGram );
 
-    static int mnCount;
-    static rtl::Reference<sc::CLBuildKernelThread> mxCLKernelThread;
+    static int snCount;
+    static rtl::Reference<sc::CLBuildKernelThread> sxCompilationThread;
 };
 
 inline void intrusive_ptr_add_ref(const ScFormulaCellGroup *p)
diff --git a/sc/source/core/data/formulacell.cxx b/sc/source/core/data/formulacell.cxx
index 1451f02..c15710f 100644
--- a/sc/source/core/data/formulacell.cxx
+++ b/sc/source/core/data/formulacell.cxx
@@ -401,8 +401,8 @@ static osl::Mutex& getOpenCLCompilationThreadMutex()
     return *pMutex;
 }
 
-int ScFormulaCellGroup::mnCount = 0;
-rtl::Reference<sc::CLBuildKernelThread> ScFormulaCellGroup::mxCLKernelThread;
+int ScFormulaCellGroup::snCount = 0;
+rtl::Reference<sc::CLBuildKernelThread> ScFormulaCellGroup::sxCompilationThread;
 
 ScFormulaCellGroup::ScFormulaCellGroup() :
     mnRefCount(0),
@@ -421,11 +421,11 @@ ScFormulaCellGroup::ScFormulaCellGroup() :
         if (ScInterpreter::GetGlobalConfig().mbOpenCLEnabled)
         {
             osl::MutexGuard aGuard(getOpenCLCompilationThreadMutex());
-            if (mnCount++ == 0)
+            if (snCount++ == 0)
             {
-                assert(!mxCLKernelThread.is());
-                mxCLKernelThread.set(new sc::CLBuildKernelThread);
-                mxCLKernelThread->launch();
+                assert(!sxCompilationThread.is());
+                sxCompilationThread.set(new sc::CLBuildKernelThread);
+                sxCompilationThread->launch();
             }
         }
     }
@@ -436,13 +436,13 @@ ScFormulaCellGroup::~ScFormulaCellGroup()
     if (ScInterpreter::GetGlobalConfig().mbOpenCLEnabled)
     {
         osl::MutexGuard aGuard(getOpenCLCompilationThreadMutex());
-        if (--mnCount == 0 && mxCLKernelThread.is())
+        if (--snCount == 0 && sxCompilationThread.is())
             {
-                assert(mxCLKernelThread.is());
-                mxCLKernelThread->finish();
-                mxCLKernelThread->join();
+                assert(sxCompilationThread.is());
+                sxCompilationThread->finish();
+                sxCompilationThread->join();
                 SAL_INFO("sc.opencl", "OpenCL kernel compilation thread has finished");
-                mxCLKernelThread.clear();
+                sxCompilationThread.clear();
             }
     }
     delete mpCode;
@@ -450,13 +450,11 @@ ScFormulaCellGroup::~ScFormulaCellGroup()
 
 void ScFormulaCellGroup::scheduleCompilation()
 {
-    osl::ResettableMutexGuard aGuard(maMutex);
     meCalcState = sc::GroupCalcOpenCLKernelCompilationScheduled;
     sc::CLBuildKernelWorkItem aWorkItem;
     aWorkItem.meWhatToDo = sc::CLBuildKernelWorkItem::COMPILE;
     aWorkItem.mxGroup = this;
-    aGuard.clear();
-    mxCLKernelThread->push(aWorkItem);
+    sxCompilationThread->push(aWorkItem);
 }
 
 void ScFormulaCellGroup::setCode( const ScTokenArray& rCode )
@@ -1940,6 +1938,9 @@ bool ScFormulaCell::IsMultilineResult()
 
 void ScFormulaCell::MaybeInterpret()
 {
+    if (mxGroup && mxGroup->meCalcState == sc::GroupCalcOpenCLKernelCompilationScheduled)
+        return;
+
     if (!IsDirtyOrInTableOpDirty())
         return;
 
@@ -3348,7 +3349,7 @@ ScFormulaCellGroupRef ScFormulaCell::CreateCellGroup( SCROW nLen, bool bInvarian
     mxGroup->mbInvariant = bInvariant;
     mxGroup->mnLength = nLen;
     mxGroup->mpCode = pCode; // Move this to the shared location.
-    if (mxGroup->mxCLKernelThread.is())
+    if (mxGroup->sxCompilationThread.is())
         mxGroup->scheduleCompilation();
     return mxGroup;
 }
diff --git a/sc/source/core/opencl/formulagroupcl.cxx b/sc/source/core/opencl/formulagroupcl.cxx
index a17c34c..35ba880 100644
--- a/sc/source/core/opencl/formulagroupcl.cxx
+++ b/sc/source/core/opencl/formulagroupcl.cxx
@@ -8,6 +8,7 @@
  */
 
 #include "formulagroup.hxx"
+#include "clkernelthread.hxx"
 #include "grouptokenconverter.hxx"
 #include "document.hxx"
 #include "formulacell.hxx"
@@ -3210,8 +3211,9 @@ CompiledFormula* FormulaGroupInterpreterOpenCL::createCompiledFormula(ScDocument
 {
     ScTokenArray *pCode = new ScTokenArray();
     ScGroupTokenConverter aConverter(*pCode, rDoc, *xGroup->mpTopCell, rTopPos);
-    if (!aConverter.convert(rCode))
+    if (!aConverter.convert(rCode) || pCode->GetLen() == 0)
     {
+        delete pCode;
         return NULL;
     }
 
@@ -3227,19 +3229,13 @@ bool FormulaGroupInterpreterOpenCL::interpret( ScDocument& rDoc,
 {
     DynamicKernel *pKernel;
 
-    osl::ResettableMutexGuard aGuard(xGroup->maMutex);
     if (xGroup->meCalcState == sc::GroupCalcOpenCLKernelCompilationScheduled ||
         xGroup->meCalcState == sc::GroupCalcOpenCLKernelBinaryCreated)
     {
         if (xGroup->meCalcState == sc::GroupCalcOpenCLKernelCompilationScheduled)
         {
-            aGuard.clear();
-            xGroup->maCompilationDone.wait();
-            xGroup->maCompilationDone.reset();
-        }
-        else
-        {
-            aGuard.clear();
+            ScFormulaCellGroup::sxCompilationThread->maCompilationDoneCondition.wait();
+            ScFormulaCellGroup::sxCompilationThread->maCompilationDoneCondition.reset();
         }
 
         pKernel = static_cast<DynamicKernel*>(xGroup->mpCompiledFormula);
@@ -3247,7 +3243,6 @@ bool FormulaGroupInterpreterOpenCL::interpret( ScDocument& rDoc,
     else
     {
         assert(xGroup->meCalcState == sc::GroupCalcRunning);
-        aGuard.clear();
         pKernel = static_cast<DynamicKernel*>(createCompiledFormula(rDoc, rTopPos, xGroup, rCode));
     }
 
diff --git a/sc/source/core/opencl/opbase.hxx b/sc/source/core/opencl/opbase.hxx
index 7c21921..9fd1d5b 100644
--- a/sc/source/core/opencl/opbase.hxx
+++ b/sc/source/core/opencl/opbase.hxx
@@ -10,6 +10,8 @@
 #ifndef SC_OPENCL_OPBASE_HXX
 #define SC_OPENCL_OPBASE_HXX
 
+#include <sal/log.hxx>
+
 #include "clcc/clew.h"
 
 #include "formula/token.hxx"
@@ -41,8 +43,70 @@ public:
 /// Failed in marshaling
 class OpenCLError
 {
+private:
+    const char *strerror(cl_int i)
+    {
+#define CASE(val) case val: return #val
+        switch (i)
+        {
+        CASE(CL_SUCCESS);
+        CASE(CL_DEVICE_NOT_FOUND);
+        CASE(CL_DEVICE_NOT_AVAILABLE);
+        CASE(CL_COMPILER_NOT_AVAILABLE);
+        CASE(CL_MEM_OBJECT_ALLOCATION_FAILURE);
+        CASE(CL_OUT_OF_RESOURCES);
+        CASE(CL_OUT_OF_HOST_MEMORY);
+        CASE(CL_PROFILING_INFO_NOT_AVAILABLE);
+        CASE(CL_MEM_COPY_OVERLAP);
+        CASE(CL_IMAGE_FORMAT_MISMATCH);
+        CASE(CL_IMAGE_FORMAT_NOT_SUPPORTED);
+        CASE(CL_BUILD_PROGRAM_FAILURE);
+        CASE(CL_MAP_FAILURE);
+        CASE(CL_INVALID_VALUE);
+        CASE(CL_INVALID_DEVICE_TYPE);
+        CASE(CL_INVALID_PLATFORM);
+        CASE(CL_INVALID_DEVICE);
+        CASE(CL_INVALID_CONTEXT);
+        CASE(CL_INVALID_QUEUE_PROPERTIES);
+        CASE(CL_INVALID_COMMAND_QUEUE);
+        CASE(CL_INVALID_HOST_PTR);
+        CASE(CL_INVALID_MEM_OBJECT);
+        CASE(CL_INVALID_IMAGE_FORMAT_DESCRIPTOR);
+        CASE(CL_INVALID_IMAGE_SIZE);
+        CASE(CL_INVALID_SAMPLER);
+        CASE(CL_INVALID_BINARY);
+        CASE(CL_INVALID_BUILD_OPTIONS);
+        CASE(CL_INVALID_PROGRAM);
+        CASE(CL_INVALID_PROGRAM_EXECUTABLE);
+        CASE(CL_INVALID_KERNEL_NAME);
+        CASE(CL_INVALID_KERNEL_DEFINITION);
+        CASE(CL_INVALID_KERNEL);
+        CASE(CL_INVALID_ARG_INDEX);
+        CASE(CL_INVALID_ARG_VALUE);
+        CASE(CL_INVALID_ARG_SIZE);
+        CASE(CL_INVALID_KERNEL_ARGS);
+        CASE(CL_INVALID_WORK_DIMENSION);
+        CASE(CL_INVALID_WORK_GROUP_SIZE);
+        CASE(CL_INVALID_WORK_ITEM_SIZE);
+        CASE(CL_INVALID_GLOBAL_OFFSET);
+        CASE(CL_INVALID_EVENT_WAIT_LIST);
+        CASE(CL_INVALID_EVENT);
+        CASE(CL_INVALID_OPERATION);
+        CASE(CL_INVALID_GL_OBJECT);
+        CASE(CL_INVALID_BUFFER_SIZE);
+        CASE(CL_INVALID_MIP_LEVEL);
+        CASE(CL_INVALID_GLOBAL_WORK_SIZE);
+        default:
+            return "Unknown OpenCL error code";
+        }
+#undef CASE
+    }
+
 public:
-    OpenCLError(cl_int err): mError(err) {}
+    OpenCLError(cl_int err): mError(err)
+    {
+        SAL_INFO("sc.opencl", "OpenCLError:" << mError << ": " << strerror(mError));
+    }
     cl_int mError;
 };
 
diff --git a/sc/source/core/tool/clkernelthread.cxx b/sc/source/core/tool/clkernelthread.cxx
index e7bda8a..651d369 100644
--- a/sc/source/core/tool/clkernelthread.cxx
+++ b/sc/source/core/tool/clkernelthread.cxx
@@ -35,10 +35,10 @@ void CLBuildKernelThread::execute()
     while (!done)
     {
         SAL_INFO("sc.opencl.thread", "waiting for condition");
-        maCondition.wait();
+        maQueueCondition.wait();
         SAL_INFO("sc.opencl.thread", "got condition");
-        osl::ResettableMutexGuard aGuard(maMutex);
-        maCondition.reset();
+        osl::ResettableMutexGuard aGuard(maQueueMutex);
+        maQueueCondition.reset();
         while (!maQueue.empty())
         {
             CLBuildKernelWorkItem aWorkItem = maQueue.front();
@@ -57,7 +57,7 @@ void CLBuildKernelThread::execute()
                                                                                     *aWorkItem.mxGroup->mpCode);
                 aWorkItem.mxGroup->meCalcState = sc::GroupCalcOpenCLKernelBinaryCreated;
                 SAL_INFO("sc.opencl.thread", "group " << aWorkItem.mxGroup << " compilation done");
-                aWorkItem.mxGroup->maCompilationDone.set();
+                maCompilationDoneCondition.set();
                 break;
             case CLBuildKernelWorkItem::FINISH:
                 SAL_INFO("sc.opencl.thread", "told to finish");
@@ -72,9 +72,9 @@ void CLBuildKernelThread::execute()
 
 void CLBuildKernelThread::push(CLBuildKernelWorkItem item)
 {
-    osl::MutexGuard guard(maMutex);
+    osl::MutexGuard guard(maQueueMutex);
     maQueue.push(item);
-    maCondition.set();
+    maQueueCondition.set();
 }
 
 void CLBuildKernelThread::produce()
diff --git a/sc/source/core/tool/formulaopt.cxx b/sc/source/core/tool/formulaopt.cxx
index d5a7dd9..ebeece1 100644
--- a/sc/source/core/tool/formulaopt.cxx
+++ b/sc/source/core/tool/formulaopt.cxx
@@ -412,6 +412,11 @@ void ScFormulaCfg::UpdateFromProperties( const Sequence<OUString>& aNames )
                 {
                     sal_Bool bVal = GetCalcConfig().mbOpenCLEnabled;
                     pValues[nProp] >>= bVal;
+#if 0 // Don't remove please unless the SC_BACKGROUND_COMPILATION env var thing goes away.
+      // The intent here is that tml when running CppunitTest_sc_opencl_test turns this on.
+                    if (getenv("SC_BACKGROUND_COMPILATION") != NULL)
+                        bVal = sal_True;
+#endif
                     GetCalcConfig().mbOpenCLEnabled = bVal;
                 }
                 break;


More information about the Libreoffice-commits mailing list