[Libreoffice-commits] core.git: Branch 'private/mmeeks/opengl-backbuffer2' - 213 commits - accessibility/inc avmedia/source basctl/source basebmp/inc basebmp/source basebmp/test basic/Library_sb.mk basic/source bin/update_pch chart2/inc chart2/qa chart2/source compilerplugins/clang connectivity/inc connectivity/source cui/source cui/uiconfig dbaccess/source dbaccess/util desktop/qa desktop/README desktop/source editeng/source embeddedobj/source embedserv/Library_inprocserv.mk embedserv/source extensions/source extensions/uiconfig filter/Configuration_filter.mk filter/Library_gie.mk filter/source fpicker/source framework/inc framework/source helpcompiler/source hwpfilter/source icon-themes/breeze include/basebmp include/canvas include/comphelper include/editeng include/filter include/LibreOfficeKit include/oox include/postwin.h include/prewin.h include/registry include/sfx2 include/svx include/unotools include/vcl ios/experimental libreofficekit/Library_libreofficekitgtk.mk libreofficekit/qa libre officekit/README libreofficekit/source lotuswordpro/source mysqlc/source officecfg/registry oox/source qadevOOo/runner reportdesign/uiconfig sal/osl sc/inc sc/qa sc/source sd/inc sd/qa sd/sdi sd/source sd/uiconfig sfx2/inc sfx2/source shell/Library_ooofilt.mk shell/Library_ooofilt_x64.mk shell/Library_propertyhdl.mk shell/Library_propertyhdl_x64.mk shell/Library_shlxthdl.mk shell/Library_shlxthdl_x64.mk shell/source smoketest/README solenv/gdb starmath/inc starmath/source svtools/inc svtools/source svx/source sw/CppunitTest_sw_ww8import.mk sw/inc sw/qa sw/source sw/uiconfig sysui/desktop ucb/source unusedcode.easy vcl/headless vcl/inc vcl/Library_vcl.mk vcl/opengl vcl/osx vcl/qa vcl/README.vars vcl/source vcl/unx vcl/win wizards/source writerfilter/inc writerfilter/Library_writerfilter.mk writerfilter/qa writerfilter/source writerperfect/source xmloff/source xmlsecurity/inc xmlsecurity/source

Michael Meeks michael.meeks at collabora.com
Thu Dec 10 01:39:40 PST 2015


Rebased ref, commits from common ancestor:
commit 95da540c6f9fb257fd40897e1ec5281c645358bb
Author: Michael Meeks <michael.meeks at collabora.com>
Date:   Wed Dec 9 17:43:44 2015 +0000

    writer: Defer update, until after first render to avoid flicker.
    
    Change-Id: Ib16f5b345901adc7036a8a90d0f46aa3499d66ae

diff --git a/sw/source/uibase/inc/conttree.hxx b/sw/source/uibase/inc/conttree.hxx
index 010b347..ca22dc7 100644
--- a/sw/source/uibase/inc/conttree.hxx
+++ b/sw/source/uibase/inc/conttree.hxx
@@ -137,6 +137,7 @@ protected:
                                     SvTreeListEntry*& rpNewParent,
                                     sal_uLong&        rNewChildPos
                                 ) override;
+    virtual void    Paint( vcl::RenderContext& rRenderContext, const Rectangle& rRect ) override;
     virtual void    MouseButtonDown( const MouseEvent& rMEvt ) override;
 
     void            EditEntry( SvTreeListEntry* pEntry, EditEntryMode nMode );
diff --git a/sw/source/uibase/utlui/content.cxx b/sw/source/uibase/utlui/content.cxx
index 8536c4c..3feb1f9 100644
--- a/sw/source/uibase/utlui/content.cxx
+++ b/sw/source/uibase/utlui/content.cxx
@@ -2424,10 +2424,18 @@ void SwContentTree::ExecCommand(sal_uInt16 nCmd, bool bModifier)
 
 void    SwContentTree::ShowTree()
 {
-    m_aUpdTimer.Start();
     SvTreeListBox::Show();
 }
 
+void SwContentTree::Paint( vcl::RenderContext& rRenderContext,
+                           const Rectangle& rRect )
+{
+    // Start the update timer on the first paint; avoids
+    // flicker on the first reveal.
+    m_aUpdTimer.Start();
+    SvTreeListBox::Paint( rRenderContext, rRect );
+}
+
 // folded together will not be glidled
 
 void    SwContentTree::HideTree()
commit 64c083d049b96d875ebd4cf3d03db4fe2946a067
Author: Michael Meeks <michael.meeks at collabora.com>
Date:   Wed Dec 9 17:43:23 2015 +0000

    Calm unit test down for GL row-strides.
    
    Change-Id: Ie4123fc692f4fac33f082bb2d86b949d834f1858

diff --git a/vcl/qa/cppunit/BitmapTest.cxx b/vcl/qa/cppunit/BitmapTest.cxx
index eb393bc..fe8c933 100644
--- a/vcl/qa/cppunit/BitmapTest.cxx
+++ b/vcl/qa/cppunit/BitmapTest.cxx
@@ -55,7 +55,8 @@ void BitmapTest::testConvert()
         //it would be nice to find and change the stride for quartz to be the same as everyone else
         CPPUNIT_ASSERT_EQUAL(static_cast<sal_uLong>(10), pReadAccess->GetScanlineSize());
 #else
-        CPPUNIT_ASSERT_EQUAL(static_cast<sal_uLong>(12), pReadAccess->GetScanlineSize());
+        if (!OpenGLHelper::isVCLOpenGLEnabled())
+            CPPUNIT_ASSERT_EQUAL(static_cast<sal_uLong>(12), pReadAccess->GetScanlineSize());
 #endif
         CPPUNIT_ASSERT(pReadAccess->HasPalette());
         const BitmapColor& rColor = pReadAccess->GetPaletteColor(pReadAccess->GetPixelIndex(1, 1));
commit 562995943e46df76d9ce678396e6fbe5ff715215
Author: Michael Meeks <michael.meeks at collabora.com>
Date:   Fri Nov 13 12:00:59 2015 +0000

    tdf#93529 - move to a Mac-like double-buffered OpenGL model.
    
    This moves us to always rendering to an off-screen texture, and then
    (at idle) blitting this to the screen & swapping buffers. Ideally we
    should never see any rendering, or flicker again with this approach.
    
    Several fixes are included:
       + avoid multiple OpenGL contexts being created for the same window,
         created excessive flicker problems.
       + de-virtualize UseContext - which context we use is less critical.
       + kill 'mbOffscreen' distinction - all VCL rendering is offscreen.
       + implement 'doFlush' and high priority idle flushing.
       + bind stencil buffer for clipping vs. textures - fixing complex
         clopping when rendering to virtual-devices, and off-screen.
       + document environment. variables.
       + use white as default background glClear color, but red for debug.
    
    Change-Id: I6be08595b6c8deb7e6db0dbd81308b2c97d2b4ff

diff --git a/vcl/README.vars b/vcl/README.vars
index 4f62333..bf85485 100644
--- a/vcl/README.vars
+++ b/vcl/README.vars
@@ -21,6 +21,8 @@ EMF_PLUS_DISABLE - use EMF rendering and ignore EMF+ specifics
 OpenGL
 ------
 SAL_FORCEGL - force enable OpenGL
+SAL_GL_NO_SWAP - disable buffer swapping if set (should show nothing)
+SAL_GL_SLEEP_ON_SWAP - sleep for half a second on each swap-buffers.
 SAL_WITHOUT_WIDGET_CACHE - disable LRU caching of native widget texutres
 SAL_DISABLE_GLYPH_CACHING - don't render glyphs through OpenGL textures
 SAL_DISABLE_GL_WATCHDOG - don't start the thread that watches for broken GL drivers
diff --git a/vcl/inc/opengl/texture.hxx b/vcl/inc/opengl/texture.hxx
index f67b334..e57aa9e 100644
--- a/vcl/inc/opengl/texture.hxx
+++ b/vcl/inc/opengl/texture.hxx
@@ -37,6 +37,8 @@ public:
     int    mnWidth;
     int    mnHeight;
     GLenum mnFilter;
+    GLuint mnOptStencil;
+    bool   mbHasOptStencil;
 
     std::unique_ptr<std::vector<int>> mpSlotReferences;
     int mnFreeSlots;
@@ -76,7 +78,8 @@ public:
     }
 
     bool InitializeSlots(int nSlotSize);
-    int FindFreeSlot();
+    int  FindFreeSlot();
+    GLuint AddStencil();
 };
 
 class VCL_DLLPUBLIC OpenGLTexture
@@ -110,6 +113,9 @@ public:
     void            Bind();
     void            Unbind();
     void            Read( GLenum nFormat, GLenum nType, sal_uInt8* pData );
+    GLuint          AddStencil();
+    bool            HasStencil() const;
+    GLuint          StencilId() const;
 
     void            SaveToFile(const OUString& rFileName);
 
diff --git a/vcl/inc/opengl/win/gdiimpl.hxx b/vcl/inc/opengl/win/gdiimpl.hxx
index ecefede..8102d2e 100644
--- a/vcl/inc/opengl/win/gdiimpl.hxx
+++ b/vcl/inc/opengl/win/gdiimpl.hxx
@@ -31,7 +31,6 @@ public:
 
 protected:
     virtual rtl::Reference<OpenGLContext> CreateWinContext() override;
-    virtual bool UseContext( const rtl::Reference<OpenGLContext> &pContext ) override;
 
     bool RenderTextureCombo(TextureCombo& rCombo, int nX, int nY);
 
diff --git a/vcl/inc/opengl/x11/gdiimpl.hxx b/vcl/inc/opengl/x11/gdiimpl.hxx
index f07468d..eccd0ef 100644
--- a/vcl/inc/opengl/x11/gdiimpl.hxx
+++ b/vcl/inc/opengl/x11/gdiimpl.hxx
@@ -29,7 +29,6 @@ public:
 
 protected:
     virtual rtl::Reference<OpenGLContext> CreateWinContext() override;
-    virtual bool UseContext( const rtl::Reference<OpenGLContext> &pContext ) override;
 
     bool RenderPixmap(X11Pixmap* pPixmap, X11Pixmap* pMask, int nX, int nY, TextureCombo& rCombo);
 
diff --git a/vcl/inc/openglgdiimpl.hxx b/vcl/inc/openglgdiimpl.hxx
index 667b2ec..b2969cc 100644
--- a/vcl/inc/openglgdiimpl.hxx
+++ b/vcl/inc/openglgdiimpl.hxx
@@ -52,12 +52,20 @@ struct TextureCombo
     std::unique_ptr<OpenGLTexture> mpMask;
 };
 
+class OpenGLFlushIdle;
+
 class VCL_DLLPUBLIC OpenGLSalGraphicsImpl : public SalGraphicsImpl
 {
     friend class OpenGLTests;
 protected:
 
+    /// This context is solely for blitting @maOffscreenTex
+    rtl::Reference<OpenGLContext> mpWindowContext;
+
+    /// This context is whatever is most convenient to render
+    /// to @maOffscreenTex with.
     rtl::Reference<OpenGLContext> mpContext;
+
     SalGraphics& mrParent;
     /// Pointer to the SalFrame or SalVirtualDevice
     SalGeometryProvider* mpProvider;
@@ -67,18 +75,27 @@ protected:
     /// Is it someone else's context we shouldn't be fiddling with ?
     static bool IsForeignContext(const rtl::Reference<OpenGLContext> &xContext);
 
+    /// This idle handler is used to swap buffers after rendering.
+    OpenGLFlushIdle *mpFlush;
+
     // clipping
     vcl::Region maClipRegion;
     bool mbUseScissor;
     bool mbUseStencil;
 
-    bool mbOffscreen;
+    /**
+     * All rendering happens to this off-screen texture. For
+     * non-virtual devices, ie. windows - we will blit it and
+     * swapBuffers later.
+     */
     OpenGLTexture maOffscreenTex;
 
     SalColor mnLineColor;
     SalColor mnFillColor;
 #ifdef DBG_UTIL
     bool mProgramIsSolidColor;
+    sal_uInt32 mnDrawCount;
+    sal_uInt32 mnDrawCountAtFlush;
 #endif
     SalColor mProgramSolidColor;
     double mProgramSolidTransparency;
@@ -131,7 +148,10 @@ public:
     // get the height of the device
     GLfloat GetHeight() const { return mpProvider ? mpProvider->GetHeight() : 1; }
 
-    // check whether this instance is used for offscreen rendering
+    /**
+     * check whether this instance is used for offscreen (Virtual Device)
+     * rendering ie. does it need its own context.
+     */
     bool IsOffscreen() const { return mpProvider == nullptr || mpProvider->IsOffScreen(); }
 
     // operations to do before painting
@@ -144,14 +164,18 @@ protected:
     bool AcquireContext();
     bool ReleaseContext();
 
-    // retrieve the default context for offscreen rendering
+    /// retrieve the default context for offscreen rendering
     static rtl::Reference<OpenGLContext> GetDefaultContext();
 
-    // create a new context for window rendering
+    /// create a new context for rendering to the underlying window
     virtual rtl::Reference<OpenGLContext> CreateWinContext() = 0;
 
-    // check whether the given context can be used by this instance
-    virtual bool UseContext( const rtl::Reference<OpenGLContext> &pContext ) = 0;
+    /// check whether the given context can be used for off-screen rendering
+    bool UseContext( const rtl::Reference<OpenGLContext> &pContext )
+    {
+        return pContext->isInitialized() &&  // not released by the OS etc.
+               IsForeignContext( pContext ); // a genuine VCL context.
+    }
 
 public:
     OpenGLSalGraphicsImpl(SalGraphics& pParent, SalGeometryProvider *pProvider);
@@ -328,8 +352,12 @@ public:
 
     virtual bool drawGradient(const tools::PolyPolygon& rPolygon, const Gradient& rGradient) override;
 
-    virtual OpenGLContext *beginPaint() override;
-private:
+    /// queue an idle flush of contents of the back-buffer to the screen
+    void flush();
+
+public:
+    /// do flush of contents of the back-buffer to the screen & swap.
+    void doFlush();
 };
 
 #endif
diff --git a/vcl/opengl/framebuffer.cxx b/vcl/opengl/framebuffer.cxx
index c009ccb..464662d 100644
--- a/vcl/opengl/framebuffer.cxx
+++ b/vcl/opengl/framebuffer.cxx
@@ -72,6 +72,16 @@ void OpenGLFramebuffer::AttachTexture( const OpenGLTexture& rTexture )
     mnHeight = rTexture.GetHeight();
     glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, mnAttachedTexture, 0);
     CHECK_GL_ERROR();
+
+    GLuint nStencil = rTexture.StencilId();
+    if( nStencil )
+    {
+        VCL_GL_INFO( "Attaching stencil " << nStencil << " to framebuffer " << (int)mnId );
+        glFramebufferRenderbuffer( GL_FRAMEBUFFER, GL_STENCIL_ATTACHMENT,
+                                   GL_RENDERBUFFER, nStencil );
+        CHECK_GL_ERROR();
+    }
+
     GLenum status = glCheckFramebufferStatus(GL_FRAMEBUFFER);
     CHECK_GL_ERROR();
     if (status != GL_FRAMEBUFFER_COMPLETE)
@@ -87,6 +97,11 @@ void OpenGLFramebuffer::DetachTexture()
         mnAttachedTexture = 0;
         glFramebufferTexture2D( GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, 0, 0 );
         CHECK_GL_ERROR();
+
+        // FIXME: we could make this conditional on having a stencil ?
+        glFramebufferRenderbuffer( GL_FRAMEBUFFER, GL_STENCIL_ATTACHMENT,
+                                   GL_RENDERBUFFER, 0 );
+        CHECK_GL_ERROR();
     }
 }
 
diff --git a/vcl/opengl/gdiimpl.cxx b/vcl/opengl/gdiimpl.cxx
index 3771d3c..05994dd 100644
--- a/vcl/opengl/gdiimpl.cxx
+++ b/vcl/opengl/gdiimpl.cxx
@@ -37,19 +37,43 @@
 
 #include <vector>
 
+#include <stdlib.h>
+
+class OpenGLFlushIdle : public Idle
+{
+    OpenGLSalGraphicsImpl *m_pImpl;
+public:
+    OpenGLFlushIdle( OpenGLSalGraphicsImpl *pImpl )
+        : Idle( "gl idle swap" )
+        , m_pImpl( pImpl )
+    {
+        SetPriority( SchedulerPriority::HIGHEST );
+    }
+    ~OpenGLFlushIdle()
+    {
+    }
+    virtual void Invoke() override
+    {
+        m_pImpl->doFlush();
+        Stop();
+    }
+};
+
 OpenGLSalGraphicsImpl::OpenGLSalGraphicsImpl(SalGraphics& rParent, SalGeometryProvider *pProvider)
     : mpContext(nullptr)
     , mrParent(rParent)
     , mpProvider(pProvider)
     , mpFramebuffer(nullptr)
     , mpProgram(nullptr)
+    , mpFlush(new OpenGLFlushIdle(this))
     , mbUseScissor(false)
     , mbUseStencil(false)
-    , mbOffscreen(false)
     , mnLineColor(SALCOLOR_NONE)
     , mnFillColor(SALCOLOR_NONE)
 #ifdef DBG_UTIL
     , mProgramIsSolidColor(false)
+    , mnDrawCount(0)
+    , mnDrawCountAtFlush(0)
 #endif
     , mProgramSolidColor(SALCOLOR_NONE)
     , mProgramSolidTransparency(0.0)
@@ -58,6 +82,11 @@ OpenGLSalGraphicsImpl::OpenGLSalGraphicsImpl(SalGraphics& rParent, SalGeometryPr
 
 OpenGLSalGraphicsImpl::~OpenGLSalGraphicsImpl()
 {
+    if( !IsOffscreen() && mnDrawCountAtFlush != mnDrawCount )
+        VCL_GL_INFO( "Destroying un-flushed on-screen graphics" );
+
+    delete mpFlush;
+
     ReleaseContext();
 }
 
@@ -79,10 +108,9 @@ bool OpenGLSalGraphicsImpl::AcquireContext( )
 
     // We always prefer to bind our VirtualDevice / offscreen graphics
     // to the current OpenGLContext - to avoid switching contexts.
-    if (mpContext.is() && mbOffscreen)
+    if (mpContext.is() && OpenGLContext::hasCurrent() && !mpContext->isCurrent())
     {
-        if (OpenGLContext::hasCurrent() && !mpContext->isCurrent())
-            mpContext.clear();
+        mpContext.clear();
     }
 
     if( mpContext.is() )
@@ -97,15 +125,17 @@ bool OpenGLSalGraphicsImpl::AcquireContext( )
     while( pContext )
     {
         // check if this context can be used by this SalGraphicsImpl instance
-        if( UseContext( pContext )  )
+        if( UseContext( pContext ) )
             break;
         pContext = pContext->mpPrevContext;
     }
 
-    if( pContext )
+    if( mpContext.is() )
         mpContext = pContext;
+    else if( mpWindowContext.is() )
+        mpContext = mpWindowContext;
     else
-        mpContext = mbOffscreen ? GetDefaultContext() : CreateWinContext();
+        mpContext = GetDefaultContext();
 
     return mpContext.is();
 }
@@ -119,19 +149,20 @@ bool OpenGLSalGraphicsImpl::ReleaseContext()
 
 void OpenGLSalGraphicsImpl::Init()
 {
-    mbOffscreen = IsOffscreen();
+    // Our init phase is strange ::Init is called twice for vdevs.
+    // the first time around with a NULL geometry provider.
+    if( !mpProvider )
+        return;
 
     // check if we can simply re-use the same context
     if( mpContext.is() )
     {
-        if( !mpContext->isInitialized() ||
-            !UseContext( mpContext ) )
+        if( !UseContext( mpContext ) )
             ReleaseContext();
     }
 
-    // reset the offscreen texture
-    if( !mbOffscreen ||
-        maOffscreenTex.GetWidth()  != GetWidth() ||
+    // Always create the offscreen texture
+    if( maOffscreenTex.GetWidth()  != GetWidth() ||
         maOffscreenTex.GetHeight() != GetHeight() )
     {
         if( maOffscreenTex && // don't work to release empty textures
@@ -141,6 +172,14 @@ void OpenGLSalGraphicsImpl::Init()
             mpContext->ReleaseFramebuffer( maOffscreenTex );
         }
         maOffscreenTex = OpenGLTexture();
+        VCL_GL_INFO("::Init - re-size offscreen texture");
+    }
+
+    if( !IsOffscreen() )
+    {
+        if( mpWindowContext.is() )
+            mpWindowContext->reset();
+        mpWindowContext = CreateWinContext();
     }
 }
 
@@ -155,12 +194,15 @@ void OpenGLSalGraphicsImpl::DeInit()
     // get a shiny new context in AcquireContext:: next PreDraw.
     if( mpContext.is() && !IsOffscreen() )
         mpContext->reset();
+    mpContext.clear();
 }
 
 void OpenGLSalGraphicsImpl::PreDraw()
 {
     OpenGLZone::enter();
 
+    mnDrawCount++;
+
     if( !AcquireContext() )
     {
         SAL_WARN( "vcl.opengl", "Couldn't acquire context" );
@@ -170,10 +212,7 @@ void OpenGLSalGraphicsImpl::PreDraw()
     mpContext->makeCurrent();
     CHECK_GL_ERROR();
 
-    if( !mbOffscreen )
-        mpContext->AcquireDefaultFramebuffer();
-    else
-        CheckOffscreenTexture();
+    CheckOffscreenTexture();
     CHECK_GL_ERROR();
 
     glViewport( 0, 0, GetWidth(), GetHeight() );
@@ -185,15 +224,13 @@ void OpenGLSalGraphicsImpl::PreDraw()
 
 void OpenGLSalGraphicsImpl::PostDraw()
 {
-    if( !mbOffscreen && mpContext->mnPainting == 0 )
-        glFlush();
     if( mbUseScissor )
     {
         glDisable( GL_SCISSOR_TEST );
         CHECK_GL_ERROR();
     }
-   if( mbUseStencil )
-   {
+    if( mbUseStencil )
+    {
         glDisable( GL_STENCIL_TEST );
         CHECK_GL_ERROR();
     }
@@ -205,6 +242,18 @@ void OpenGLSalGraphicsImpl::PostDraw()
         mProgramIsSolidColor = false;
 #endif
     }
+
+    assert (maOffscreenTex);
+
+    if( IsOffscreen() )
+        assert( !mpWindowContext.is() );
+    else
+        assert( mpWindowContext.is() );
+
+    // Always queue the flush.
+    if( !IsOffscreen() )
+        flush();
+
     OpenGLZone::leave();
 }
 
@@ -216,8 +265,9 @@ void OpenGLSalGraphicsImpl::ApplyProgramMatrices(float fPixelOffset)
 void OpenGLSalGraphicsImpl::freeResources()
 {
     // TODO Delete shaders, programs and textures if not shared
-    if( mbOffscreen && mpContext.is() && mpContext->isInitialized() )
+    if( mpContext.is() && mpContext->isInitialized() )
     {
+        VCL_GL_INFO( "freeResources" );
         mpContext->makeCurrent();
         mpContext->ReleaseFramebuffer( maOffscreenTex );
     }
@@ -227,6 +277,20 @@ void OpenGLSalGraphicsImpl::freeResources()
 void OpenGLSalGraphicsImpl::ImplSetClipBit( const vcl::Region& rClip, GLuint nMask )
 {
     glEnable( GL_STENCIL_TEST );
+
+    VCL_GL_INFO( "Adding complex clip / stencil" );
+    GLuint nStencil = maOffscreenTex.StencilId();
+    if( nStencil == 0 )
+    {
+        nStencil = maOffscreenTex.AddStencil();
+        glFramebufferRenderbuffer(
+            GL_FRAMEBUFFER, GL_STENCIL_ATTACHMENT,
+            GL_RENDERBUFFER, nStencil );
+        CHECK_GL_ERROR();
+    }
+    // else - we associated the stencil in
+    //        AcquireFrameBuffer / AttachTexture
+
     CHECK_GL_ERROR();
     glColorMask( GL_FALSE, GL_FALSE, GL_FALSE, GL_FALSE );
     CHECK_GL_ERROR();
@@ -261,7 +325,7 @@ void OpenGLSalGraphicsImpl::ImplInitClipRegion()
     if( maClipRegion != mpContext->maClipRegion )
     {
         mpContext->maClipRegion = maClipRegion;
-        if( maClipRegion.IsRectangle() )
+        if( mbUseScissor )
         {
             Rectangle aRect( maClipRegion.GetBoundRect() );
             glScissor( aRect.Left(), GetHeight() - aRect.Bottom() - 1, aRect.GetWidth() + 1, aRect.GetHeight() + 1 );
@@ -382,8 +446,29 @@ void OpenGLSalGraphicsImpl::SetROPFillColor( SalROPColor /*nROPColor*/ )
 
 bool OpenGLSalGraphicsImpl::CheckOffscreenTexture()
 {
+    bool bClearTexture = false;
+
+    VCL_GL_INFO( "Check Offscreen texture" );
+
+    // Always create the offscreen texture
+    if( maOffscreenTex )
+    {
+        if( maOffscreenTex.GetWidth()  != GetWidth() ||
+            maOffscreenTex.GetHeight() != GetHeight() )
+        {
+            mpContext->ReleaseFramebuffer( maOffscreenTex );
+            maOffscreenTex = OpenGLTexture();
+            VCL_GL_INFO( "re-size offscreen texture" );
+        }
+    }
+
     if( !maOffscreenTex )
+    {
+        VCL_GL_INFO( "create texture of size "
+                     << GetWidth() << " x " << GetHeight() );
         maOffscreenTex = OpenGLTexture( GetWidth(), GetHeight() );
+        bClearTexture = true;
+    }
 
     if( !maOffscreenTex.IsUnique() )
     {
@@ -400,8 +485,23 @@ bool OpenGLSalGraphicsImpl::CheckOffscreenTexture()
     else
     {
         mpFramebuffer = mpContext->AcquireFramebuffer( maOffscreenTex );
+        CHECK_GL_ERROR();
+
+        if( bClearTexture )
+        {
+            glDrawBuffer( GL_COLOR_ATTACHMENT0 );
+#if OSL_DEBUG_LEVEL > 0 // lets have some red debugging background.
+            GLfloat clearColor[4] = { 1.0, 0, 0, 0 };
+#else
+            GLfloat clearColor[4] = { 1.0, 1.0, 1.0, 0 };
+#endif
+            glClearBufferfv( GL_COLOR, 0, clearColor );
+            // FIXME: use glClearTexImage if we have it ?
+        }
     }
 
+    assert( maOffscreenTex );
+
     CHECK_GL_ERROR();
     return true;
 }
@@ -1541,17 +1641,9 @@ void OpenGLSalGraphicsImpl::DoCopyBits( const SalTwoRect& rPosAry, OpenGLSalGrap
         return;
     }
 
-    if( rImpl.mbOffscreen )
-    {
-        PreDraw();
-        DrawTexture( rImpl.maOffscreenTex, rPosAry );
-        PostDraw();
-        return;
-    }
-
-    SAL_WARN( "vcl.opengl", "*** NOT IMPLEMENTED *** copyBits" );
-    // TODO: Copy from one FBO to the other (glBlitFramebuffer)
-    //       ie. copying from one visible window to another visible window
+    PreDraw();
+    DrawTexture( rImpl.maOffscreenTex, rPosAry );
+    PostDraw();
 }
 
 void OpenGLSalGraphicsImpl::drawBitmap( const SalTwoRect& rPosAry, const SalBitmap& rSalBitmap )
@@ -1878,12 +1970,122 @@ bool OpenGLSalGraphicsImpl::drawGradient(const tools::PolyPolygon& rPolyPoly,
     return true;
 }
 
-OpenGLContext *OpenGLSalGraphicsImpl::beginPaint()
+void OpenGLSalGraphicsImpl::flush()
 {
-    if( mbOffscreen || !AcquireContext() )
-        return nullptr;
+    if( IsOffscreen() )
+        return;
+
+    if( !Application::IsInExecute() )
+    {
+        // otherwise nothing would trigger idle rendering
+        doFlush();
+    }
+    else if( !mpFlush->IsActive() )
+        mpFlush->Start();
+}
+
+void OpenGLSalGraphicsImpl::doFlush()
+{
+    if( IsOffscreen() )
+        return;
+
+    assert( mpWindowContext.is() );
+
+    if( !maOffscreenTex )
+    {
+        VCL_GL_INFO( "flushAndSwap - odd no texture !" );
+        return;
+    }
+
+    if (mnDrawCountAtFlush == mnDrawCount)
+    {
+        VCL_GL_INFO( "eliding redundant flushAndSwap, no drawing since last!" );
+        return;
+    }
+
+    mnDrawCountAtFlush = mnDrawCount;
+
+    OpenGLZone aZone;
+
+    VCL_GL_INFO( "flushAndSwap" );
+
+    // Interesting ! -> this destroys a context [ somehow ] ...
+    mpWindowContext->makeCurrent();
+    CHECK_GL_ERROR();
+
+    VCL_GL_INFO( "flushAndSwap - acquire default frame buffer" );
+
+    mpWindowContext->AcquireDefaultFramebuffer();
+    glBindFramebuffer( GL_FRAMEBUFFER, 0 ); // FIXME: paranoid double check.
+    CHECK_GL_ERROR();
+
+    VCL_GL_INFO( "flushAndSwap - acquired default frame buffer" );
+
+    glDisable( GL_SCISSOR_TEST ); // FIXME: paranoia ...
+    CHECK_GL_ERROR();
+    glDisable( GL_STENCIL_TEST ); // FIXME: paranoia ...
+    CHECK_GL_ERROR();
+
+    glViewport( 0, 0, GetWidth(), GetHeight() );
+    CHECK_GL_ERROR();
+
+    glClearColor((float)rand()/RAND_MAX, (float)rand()/RAND_MAX,
+                 (float)rand()/RAND_MAX, 1.0);
+    glClear( GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT | GL_STENCIL_BUFFER_BIT );
+    CHECK_GL_ERROR();
+
+    SalTwoRect aPosAry( 0, 0, maOffscreenTex.GetWidth(), maOffscreenTex.GetHeight(),
+                        0, 0, maOffscreenTex.GetWidth(), maOffscreenTex.GetHeight() );
+    VCL_GL_INFO( "Texture height " << maOffscreenTex.GetHeight() << " vs. window height " << GetHeight() );
+
+    OpenGLProgram *pProgram =
+        mpWindowContext->UseProgram( "textureVertexShader", "textureFragmentShader", "" );
+    if( !pProgram )
+        VCL_GL_INFO( "Can't compile simple copying shader !" );
     else
-        return mpContext.get();
+    {
+        pProgram->Use(); // FIXME: paranoia ...
+        VCL_GL_INFO( "done paranoid re-use." );
+        pProgram->SetTexture( "sampler", maOffscreenTex );
+        maOffscreenTex.Bind(); // FIXME: paranoia ...
+
+        VCL_GL_INFO( "bound bits etc." );
+
+        GLfloat aTexCoord[8];
+        maOffscreenTex.GetCoord( aTexCoord, aPosAry, false );
+        pProgram->SetTextureCoord( aTexCoord );
+
+        long nX1( aPosAry.mnDestX );
+        long nY1( aPosAry.mnDestY );
+        long nX2( nX1 + aPosAry.mnDestWidth );
+        long nY2( nY1 + aPosAry.mnDestHeight );
+        const SalPoint aPoints[] = { { nX1, nY2 }, { nX1, nY1 },
+                                     { nX2, nY1 }, { nX2, nY2 }};
+
+        sal_uInt32 nPoints = 4;
+        std::vector<GLfloat> aVertices(nPoints * 2);
+        sal_uInt32 i, j;
+
+        for( i = 0, j = 0; i < nPoints; i++, j += 2 )
+        {
+            aVertices[j]   = GLfloat(aPoints[i].mnX);
+            aVertices[j+1] = GLfloat(aPoints[i].mnY);
+        }
+
+        pProgram->ApplyMatrix(GetWidth(), GetHeight(), 0.0);
+        pProgram->SetVertices( &aVertices[0] );
+        glDrawArrays( GL_TRIANGLE_FAN, 0, nPoints );
+
+        pProgram->Clean();
+
+        glBindTexture( GL_TEXTURE_2D, 0 );
+
+        static bool bNoSwap = getenv("SAL_GL_NO_SWAP");
+        if (!bNoSwap)
+            mpWindowContext->swapBuffers();
+    }
+
+    VCL_GL_INFO( "flushAndSwap - end." );
 }
 
 bool OpenGLSalGraphicsImpl::IsForeignContext(const rtl::Reference<OpenGLContext> &xContext)
diff --git a/vcl/opengl/texture.cxx b/vcl/opengl/texture.cxx
index 2d4cb40..bf4aa1d 100644
--- a/vcl/opengl/texture.cxx
+++ b/vcl/opengl/texture.cxx
@@ -35,6 +35,7 @@ ImplOpenGLTexture::ImplOpenGLTexture( int nWidth, int nHeight, bool bAllocate )
     mnWidth( nWidth ),
     mnHeight( nHeight ),
     mnFilter( GL_NEAREST ),
+    mnOptStencil( 0 ),
     mnFreeSlots(-1)
 {
     glGenTextures( 1, &mnTexture );
@@ -67,6 +68,7 @@ ImplOpenGLTexture::ImplOpenGLTexture( int nX, int nY, int nWidth, int nHeight )
     mnWidth( nWidth ),
     mnHeight( nHeight ),
     mnFilter( GL_NEAREST ),
+    mnOptStencil( 0 ),
     mnFreeSlots(-1)
 {
     // FIXME We need the window height here
@@ -99,6 +101,7 @@ ImplOpenGLTexture::ImplOpenGLTexture( int nWidth, int nHeight, int nFormat, int
     mnWidth( nWidth ),
     mnHeight( nHeight ),
     mnFilter( GL_NEAREST ),
+    mnOptStencil( 0 ),
     mnFreeSlots(-1)
 {
     if( !mnTexture )
@@ -126,6 +129,21 @@ ImplOpenGLTexture::ImplOpenGLTexture( int nWidth, int nHeight, int nFormat, int
     VCL_GL_INFO( "OpenGLTexture " << mnTexture << " " << nWidth << "x" << nHeight << " from data" );
 }
 
+GLuint ImplOpenGLTexture::AddStencil()
+{
+    assert( mnOptStencil == 0 );
+
+    glGenRenderbuffers( 1, &mnOptStencil );
+    glBindRenderbuffer( GL_RENDERBUFFER, mnOptStencil );
+    CHECK_GL_ERROR();
+    VCL_GL_INFO( "Allocate stencil " << mnWidth << " x " << mnHeight );
+    glRenderbufferStorage( GL_RENDERBUFFER, GL_STENCIL_INDEX,
+                           mnWidth, mnHeight );
+    CHECK_GL_ERROR();
+
+    return mnOptStencil;
+}
+
 ImplOpenGLTexture::~ImplOpenGLTexture()
 {
     VCL_GL_INFO( "~OpenGLTexture " << mnTexture );
@@ -136,9 +154,11 @@ ImplOpenGLTexture::~ImplOpenGLTexture()
         // Check we have been correctly un-bound from all framebuffers.
         ImplSVData* pSVData = ImplGetSVData();
         rtl::Reference<OpenGLContext> pContext = pSVData->maGDIData.mpLastContext;
-        if (pContext.is())
+        if( pContext.is() )
             pContext->UnbindTextureFromFramebuffers( mnTexture );
 
+        if( mnOptStencil != 0 )
+            glDeleteRenderbuffers( 1, &mnOptStencil );
         glDeleteTextures( 1, &mnTexture );
     }
 }
@@ -279,6 +299,24 @@ int OpenGLTexture::GetHeight() const
     return maRect.GetHeight();
 }
 
+bool OpenGLTexture::HasStencil() const
+{
+    return mpImpl && mpImpl->mnOptStencil != 0;
+}
+
+GLuint OpenGLTexture::StencilId() const
+{
+    return mpImpl ? mpImpl->mnOptStencil : 0;
+}
+
+GLuint OpenGLTexture::AddStencil()
+{
+    if (mpImpl)
+        return mpImpl->AddStencil();
+    else
+        return 0;
+}
+
 void OpenGLTexture::GetCoord( GLfloat* pCoord, const SalTwoRect& rPosAry, bool bInverted ) const
 {
     VCL_GL_INFO( "Getting coord " << Id() << " [" << maRect.Left() << "," << maRect.Top() << "] " << GetWidth() << "x" << GetHeight() );
@@ -349,6 +387,10 @@ void OpenGLTexture::Bind()
         glBindTexture( GL_TEXTURE_2D, mpImpl->mnTexture );
         CHECK_GL_ERROR();
     }
+    else
+        VCL_GL_INFO( "OpenGLTexture::Binding invalid texture" );
+
+    CHECK_GL_ERROR();
 }
 
 void OpenGLTexture::Unbind()
diff --git a/vcl/opengl/win/gdiimpl.cxx b/vcl/opengl/win/gdiimpl.cxx
index f57c82d..666cdbf 100644
--- a/vcl/opengl/win/gdiimpl.cxx
+++ b/vcl/opengl/win/gdiimpl.cxx
@@ -29,21 +29,10 @@ void WinOpenGLSalGraphicsImpl::copyBits( const SalTwoRect& rPosAry, SalGraphics*
 rtl::Reference<OpenGLContext> WinOpenGLSalGraphicsImpl::CreateWinContext()
 {
     rtl::Reference<OpenGLContext> pContext = OpenGLContext::Create();
-    pContext->requestSingleBufferedRendering();
     pContext->init( mrParent.mhLocalDC, mrParent.mhWnd );
     return pContext;
 }
 
-bool WinOpenGLSalGraphicsImpl::UseContext( const rtl::Reference<OpenGLContext> &pContext )
-{
-    if( !pContext.is() || !pContext->isInitialized() || IsForeignContext( pContext ) )
-        return false;
-    if( IsOffscreen() )
-        return true;
-    return pContext->getOpenGLWindow().hWnd == mrParent.mhWnd &&
-           pContext->getOpenGLWindow().hDC == mrParent.mhLocalDC;
-}
-
 void WinOpenGLSalGraphicsImpl::Init()
 {
     if ( !IsOffscreen() && mpContext.is() && mpContext->isInitialized() &&
diff --git a/vcl/opengl/x11/gdiimpl.cxx b/vcl/opengl/x11/gdiimpl.cxx
index 2418bc6..595ca45c 100644
--- a/vcl/opengl/x11/gdiimpl.cxx
+++ b/vcl/opengl/x11/gdiimpl.cxx
@@ -58,18 +58,6 @@ rtl::Reference<OpenGLContext> X11OpenGLSalGraphicsImpl::CreateWinContext()
     return pContext;
 }
 
-bool X11OpenGLSalGraphicsImpl::UseContext( const rtl::Reference<OpenGLContext> &pContext )
-{
-    X11WindowProvider *pProvider = dynamic_cast<X11WindowProvider*>(mrParent.m_pFrame);
-
-    if( !pContext->isInitialized() || IsForeignContext( pContext ) )
-        return false;
-    if( !pProvider )
-        return pContext->getOpenGLWindow().win != None;
-    else
-        return pContext->getOpenGLWindow().win == pProvider->GetX11Window();
-}
-
 void X11OpenGLSalGraphicsImpl::copyBits( const SalTwoRect& rPosAry, SalGraphics* pSrcGraphics )
 {
     OpenGLSalGraphicsImpl *pImpl = pSrcGraphics ? static_cast< OpenGLSalGraphicsImpl* >(pSrcGraphics->GetImpl()) : static_cast< OpenGLSalGraphicsImpl *>(mrParent.GetImpl());
diff --git a/vcl/source/opengl/OpenGLContext.cxx b/vcl/source/opengl/OpenGLContext.cxx
index 26148a6..98be555 100644
--- a/vcl/source/opengl/OpenGLContext.cxx
+++ b/vcl/source/opengl/OpenGLContext.cxx
@@ -18,6 +18,8 @@
 #include <vcl/bmpacc.hxx>
 #include <vcl/graph.hxx>
 
+#include <osl/thread.hxx>
+
 #if defined(MACOSX)
 #include <premac.h>
 #include <AppKit/NSOpenGLView.h>
@@ -1487,6 +1489,14 @@ void OpenGLContext::swapBuffers()
 #elif defined( UNX )
     glXSwapBuffers(m_aGLWin.dpy, m_aGLWin.win);
 #endif
+
+    static bool bSleep = getenv("SAL_GL_SLEEP_ON_SWAP");
+    if (bSleep)
+    {
+        // half a second.
+        TimeValue aSleep( 0, 500*1000*1000 );
+        osl::Thread::wait( aSleep );
+    }
 }
 
 void OpenGLContext::sync()
commit b8c73f2af8ee0e26ac97901545b16e1204fca034
Author: Michael Meeks <michael.meeks at collabora.com>
Date:   Mon Nov 16 18:18:36 2015 +0000

    Get Double-buffered context creation working on linux.
    
    Change-Id: I3db1d6792fcd51577f047b82029124ec825ea319

diff --git a/vcl/source/opengl/OpenGLContext.cxx b/vcl/source/opengl/OpenGLContext.cxx
index 8c5db0f..26148a6 100644
--- a/vcl/source/opengl/OpenGLContext.cxx
+++ b/vcl/source/opengl/OpenGLContext.cxx
@@ -706,9 +706,7 @@ bool GLWindow::HasGLXExtension( const char* name ) const
 bool OpenGLContext::ImplInit()
 {
     if (!m_aGLWin.dpy)
-    {
         return false;
-    }
 
     OpenGLZone aZone;
 
@@ -722,11 +720,10 @@ bool OpenGLContext::ImplInit()
     if (!g_vShareList.empty())
         pSharedCtx = g_vShareList.front();
 
-#ifdef DBG_UTIL
     if (glXCreateContextAttribsARB && !mbRequestLegacyContext)
     {
         int best_fbc = -1;
-        GLXFBConfig* pFBC = getFBConfig(m_aGLWin.dpy, m_aGLWin.win, best_fbc, mbUseDoubleBufferedRendering, true);
+        GLXFBConfig* pFBC = getFBConfig(m_aGLWin.dpy, m_aGLWin.win, best_fbc, mbUseDoubleBufferedRendering, false);
         if (!pFBC)
             return false;
 
@@ -734,24 +731,28 @@ bool OpenGLContext::ImplInit()
         {
             int pContextAttribs[] =
             {
+#if 0 // defined(DBG_UTIL)
                 GLX_CONTEXT_MAJOR_VERSION_ARB, 3,
                 GLX_CONTEXT_MINOR_VERSION_ARB, 2,
+#endif
                 None
+
             };
             m_aGLWin.ctx = glXCreateContextAttribsARB(m_aGLWin.dpy, pFBC[best_fbc], pSharedCtx, /* direct, not via X */ GL_TRUE, pContextAttribs);
             SAL_INFO_IF(m_aGLWin.ctx, "vcl.opengl", "created a 3.2 core context");
         }
         else
             SAL_WARN("vcl.opengl", "unable to find correct FBC");
-
     }
-#endif
 
     if (!m_aGLWin.ctx)
     {
         if (!m_aGLWin.vi)
            return false;
 
+        SAL_WARN("vcl.opengl", "attempting to create a non-double-buffered "
+                               "visual matching the context");
+
         m_aGLWin.ctx = glXCreateContext(m_aGLWin.dpy,
                 m_aGLWin.vi,
                 pSharedCtx,
commit 29f28e3f409cc2c265ee068fae855cbce74cf0cf
Author: Michael Meeks <michael.meeks at collabora.com>
Date:   Mon Nov 30 16:13:42 2015 +0000

    vcl: gtk frames should DeInitialize properly, to handle GL cleanup.
    
    Change-Id: Ie6a5464c28b89f08639939690052023e685a3d33

diff --git a/vcl/unx/gtk/gtksalframe.cxx b/vcl/unx/gtk/gtksalframe.cxx
index 085eb0e..1772990 100644
--- a/vcl/unx/gtk/gtksalframe.cxx
+++ b/vcl/unx/gtk/gtksalframe.cxx
@@ -777,8 +777,10 @@ void GtkSalFrame::InvalidateGraphics()
 {
     if( m_pGraphics )
     {
-        m_pGraphics->SetDrawable( None, m_nXScreen );
+        m_pGraphics->DeInit();
         m_pGraphics->SetWindow(nullptr);
+        delete m_pGraphics;
+        m_pGraphics = nullptr;
         m_bGraphics = false;
     }
 }
@@ -846,9 +848,6 @@ GtkSalFrame::~GtkSalFrame()
         g_object_unref( G_OBJECT( m_pForeignParent ) );
     if( m_pForeignTopLevel )
         g_object_unref( G_OBJECT( m_pForeignTopLevel) );
-
-    delete m_pGraphics;
-    m_pGraphics = nullptr;
 }
 
 void GtkSalFrame::moveWindow( long nX, long nY )
commit b721fdcb6eb1866fbdd29ffa8603167caecea16e
Author: Michael Meeks <michael.meeks at collabora.com>
Date:   Thu Nov 26 21:47:35 2015 +0000

    More smoketest notes.
    
    Change-Id: I52bd1555e572c75feb0fc96368b6e61802d9d65c

diff --git a/smoketest/README b/smoketest/README
index b1d250d..30dceb6 100644
--- a/smoketest/README
+++ b/smoketest/README
@@ -12,4 +12,7 @@ data/Basic/Standard.
 macro and waits for a dispatchFinished from the macro's execution. To
 debug this best load workdir/Zip/smoketestdoc.sxw - and hit 'start
 smoketest' - this will launch a number of components and build a
-suitable report in the form of a table.
\ No newline at end of file
+suitable report in the form of a table.
+
+	The StarBasic smoketests also log their output, this ends up
+in instdir/user/temp/smoketest.log.
commit 10de96bf0fb820b38607b0c25a0d3219ad343819
Author: Caolán McNamara <caolanm at redhat.com>
Date:   Thu Dec 10 09:35:46 2015 +0000

    guard against missing spacing property
    
    Change-Id: If5c50cddfee88cc92852737c1459ebe94b7256bb

diff --git a/lotuswordpro/source/filter/lwppara.cxx b/lotuswordpro/source/filter/lwppara.cxx
index 6226e0d..17454b6 100644
--- a/lotuswordpro/source/filter/lwppara.cxx
+++ b/lotuswordpro/source/filter/lwppara.cxx
@@ -412,18 +412,20 @@ void LwpPara::RegisterStyle()
             case PP_LOCAL_SPACING:
             {
                 noSpacing = false;
-                if (!rParaStyle.GetSpacing())
-                    OverrideSpacing(nullptr,static_cast<LwpParaSpacingProperty*>(pProps)->GetSpacing(),pOverStyle);
-                else
+                LwpSpacingOverride *pSpacing = static_cast<LwpParaSpacingProperty*>(pProps)->GetSpacing();
+                if (pSpacing)
                 {
-                    std::unique_ptr<LwpSpacingOverride> const
-                        pSpacing(rParaStyle.GetSpacing()->clone());
-                    OverrideSpacing(pSpacing.get(),
-                            static_cast<LwpParaSpacingProperty*>(pProps)->GetSpacing(),
-                            pOverStyle);
+                    if (!rParaStyle.GetSpacing())
+                        OverrideSpacing(nullptr, pSpacing, pOverStyle);
+                    else
+                    {
+                        std::unique_ptr<LwpSpacingOverride> const
+                            pNewSpacing(rParaStyle.GetSpacing()->clone());
+                        OverrideSpacing(pNewSpacing.get(), pSpacing, pOverStyle);
+                    }
                 }
-            }
                 break;
+            }
             case PP_LOCAL_BORDER:
             {
                 OverrideParaBorder(pProps, pOverStyle);
commit 08fe513b89ea5102a3a233ee0bac472dc8e6b219
Author: Caolán McNamara <caolanm at redhat.com>
Date:   Thu Dec 10 09:24:14 2015 +0000

    protect against missing Table Layout
    
    Change-Id: Ie7f4cd2b411eb678642ea859d261b1b672752d94

diff --git a/lotuswordpro/source/filter/lwpcelllayout.cxx b/lotuswordpro/source/filter/lwpcelllayout.cxx
index f630a01..abe2c02 100644
--- a/lotuswordpro/source/filter/lwpcelllayout.cxx
+++ b/lotuswordpro/source/filter/lwpcelllayout.cxx
@@ -121,8 +121,9 @@ LwpTable * LwpCellLayout::GetTable()
  */
 void LwpCellLayout::SetCellMap()
 {
-    // this function is called from LwpTableLayout, so it can't be NULL
-    GetTableLayout()->SetWordProCellMap(crowid, ccolid, this);
+    LwpTableLayout * pTableLayout = GetTableLayout();
+    if (pTableLayout)
+        pTableLayout->SetWordProCellMap(crowid, ccolid, this);
 }
 /**
  * @short  Get actual width of this cell layout
commit 130eaf02de89c8996ff6e817a005993dcbd586e6
Author: Caolán McNamara <caolanm at redhat.com>
Date:   Thu Dec 10 09:16:59 2015 +0000

    guard against missing paragraph container
    
    Change-Id: I6ac074c7fe2821983b4a056e28fc5379f7a93974

diff --git a/lotuswordpro/source/filter/lwppara.hxx b/lotuswordpro/source/filter/lwppara.hxx
index 6e77876..a6d7563 100644
--- a/lotuswordpro/source/filter/lwppara.hxx
+++ b/lotuswordpro/source/filter/lwppara.hxx
@@ -323,6 +323,8 @@ inline OUString LwpPara::GetBulletStyleName() const
 }
 inline void LwpPara::AddXFContent(XFContent* pCont)
 {
+    if (!m_pXFContainer)
+        throw std::runtime_error("paragraph lacks container");
     m_pXFContainer->Add(pCont);
 }
 inline void LwpPara::SetXFContainer(XFContentContainer* pCont)
commit 1ff0a3880c48227656d2b4a823cd66a6d5c74af0
Author: David Tardon <dtardon at redhat.com>
Date:   Thu Dec 10 10:04:50 2015 +0100

    add missing #include <stdexcept>
    
    Change-Id: I9cf72b27219489a5508786881ecd95e5820c71ac

diff --git a/lotuswordpro/source/filter/lwpobj.hxx b/lotuswordpro/source/filter/lwpobj.hxx
index 0dc2d97..884ab42 100644
--- a/lotuswordpro/source/filter/lwpobj.hxx
+++ b/lotuswordpro/source/filter/lwpobj.hxx
@@ -63,6 +63,8 @@
 
 #include <sal/config.h>
 
+#include <stdexcept>
+
 #include <salhelper/simplereferenceobject.hxx>
 
 #include "lwpheader.hxx"
commit 9e8cd06234bc217490121745cfe3491c92560f8d
Author: Miklos Vajna <vmiklos at collabora.co.uk>
Date:   Thu Dec 10 09:30:00 2015 +0100

    sw: indentation fixes
    
    Change-Id: Id5c95b30eb25d8e88cb596fca283b14f1c74ef69

diff --git a/sw/inc/calbck.hxx b/sw/inc/calbck.hxx
index 8032bc9..c80cebc 100644
--- a/sw/inc/calbck.hxx
+++ b/sw/inc/calbck.hxx
@@ -87,7 +87,7 @@ namespace sw
             virtual void SwClientNotify( const SwModify&, const SfxHint& rHint) =0;
         public:
             bool IsLast() const { return !m_pLeft && !m_pRight; }
-   };
+    };
 }
 // SwClient
 class SW_DLLPUBLIC SwClient : ::sw::WriterListener
diff --git a/sw/inc/dcontact.hxx b/sw/inc/dcontact.hxx
index 73d4242..e50f999 100644
--- a/sw/inc/dcontact.hxx
+++ b/sw/inc/dcontact.hxx
@@ -232,13 +232,13 @@ class SwDrawVirtObj : public SdrVirtObj
          inserted into the drawing layer. */
         SwDrawContact&  mrDrawContact;
 
-   protected:
+    protected:
         /** AW: Need own sdr::contact::ViewContact since AnchorPos from parent is
          not used but something own (top left of new SnapRect minus top left
          of original SnapRect) */
         virtual sdr::contact::ViewContact* CreateObjectSpecificViewContact() override;
 
-   public:
+    public:
 
         SwDrawVirtObj( SdrObject&       _rNewObj,
                        SwDrawContact&   _rDrawContact );
diff --git a/sw/qa/extras/rtfimport/rtfimport.cxx b/sw/qa/extras/rtfimport/rtfimport.cxx
index 17cae46..dc47a95 100644
--- a/sw/qa/extras/rtfimport/rtfimport.cxx
+++ b/sw/qa/extras/rtfimport/rtfimport.cxx
@@ -2380,7 +2380,7 @@ DECLARE_RTFIMPORT_TEST(testTdf54584, "tdf54584.rtf")
     uno::Reference<container::XEnumeration> xFields(xFieldsAccess->createEnumeration());
     // \PAGE was ignored, so no fields were in document -> exception was thrown
     CPPUNIT_ASSERT_NO_THROW_MESSAGE("No fields in document found: field \"\\PAGE\" was not properly read",
-        xFields->nextElement());
+                                    xFields->nextElement());
 }
 
 CPPUNIT_PLUGIN_IMPLEMENT();
commit ce0ad10405bd590498d5f0c093d9afca96d3abca
Author: Dennis Francis <dennisfrancis.in at gmail.com>
Date:   Thu Dec 10 13:19:58 2015 +0530

    Fix a memleak in GtkSalFrame::SetIcon
    
    Change-Id: I70ca3c635033870ca05959561dc0f5b8a2d68939
    Reviewed-on: https://gerrit.libreoffice.org/20561
    Reviewed-by: David Tardon <dtardon at redhat.com>
    Tested-by: David Tardon <dtardon at redhat.com>

diff --git a/vcl/unx/gtk3/gtk3gtkframe.cxx b/vcl/unx/gtk3/gtk3gtkframe.cxx
index 31b608f..609bd0a 100644
--- a/vcl/unx/gtk3/gtk3gtkframe.cxx
+++ b/vcl/unx/gtk3/gtk3gtkframe.cxx
@@ -1320,6 +1320,7 @@ void GtkSalFrame::SetIcon( sal_uInt16 nIcon )
         appicon = g_strdup ("libreoffice-main");
 
     gtk_window_set_icon_name (GTK_WINDOW (m_pWindow), appicon);
+    g_free (appicon);
 }
 
 void GtkSalFrame::SetMenu( SalMenu* pSalMenu )
commit be738d33d1b9574b4afdc438af2950cea0fb301b
Author: Takeshi Abe <tabe at fixedpoint.jp>
Date:   Mon Nov 30 19:09:23 2015 +0900

    starmath: Prefix members of SmDrawingVisitor
    
    Change-Id: Ia7efb3db2d1e76aad8873cf5822107b4666249de
    Reviewed-on: https://gerrit.libreoffice.org/20281
    Tested-by: Jenkins <ci at libreoffice.org>
    Reviewed-by: David Tardon <dtardon at redhat.com>

diff --git a/starmath/inc/visitors.hxx b/starmath/inc/visitors.hxx
index 8ae394e..f51b961 100644
--- a/starmath/inc/visitors.hxx
+++ b/starmath/inc/visitors.hxx
@@ -170,8 +170,9 @@ public:
      * @remarks This constructor will do the drawing, no need to anything more.
      */
     SmDrawingVisitor( OutputDevice &rDevice, Point position, SmNode* pTree )
-        : rDev( rDevice ) {
-        this->Position = position;
+        : mrDev( rDevice )
+        , maPosition( position )
+    {
         pTree->Accept( this );
     }
     virtual ~SmDrawingVisitor() {}
@@ -215,13 +216,13 @@ private:
     /** Draw an SmSpecialNode or a subclass of this  */
     void DrawSpecialNode( SmSpecialNode* pNode );
     /** OutputDevice to draw on */
-    OutputDevice& rDev;
-    /** Position to draw on the rDev
+    OutputDevice& mrDev;
+    /** Position to draw on the mrDev
      * @remarks This variable is used to pass parameters in DrawChildren( ), this means
                 that after a call to DrawChildren( ) the contents of this method is undefined
                 so if needed cache it locally on the stack.
      */
-    Point Position;
+    Point maPosition;
 };
 
 // SmSetSelectionVisitor
diff --git a/starmath/source/visitors.cxx b/starmath/source/visitors.cxx
index 7fcd98f..2d45b23 100644
--- a/starmath/source/visitors.cxx
+++ b/starmath/source/visitors.cxx
@@ -413,9 +413,9 @@ void SmDrawingVisitor::Visit( SmRootSymbolNode* pNode )
     // draw root-sign itself
     DrawSpecialNode( pNode );
 
-    SmTmpDevice aTmpDev( rDev, true );
+    SmTmpDevice aTmpDev( mrDev, true );
     aTmpDev.SetFillColor( pNode->GetFont( ).GetColor( ) );
-    rDev.SetLineColor( );
+    mrDev.SetLineColor( );
     aTmpDev.SetFont( pNode->GetFont( ) );
 
     // since the width is always unscaled it corresponds ot the _original_
@@ -425,17 +425,17 @@ void SmDrawingVisitor::Visit( SmRootSymbolNode* pNode )
     long nBarHeight = pNode->GetWidth( ) * 7L / 100L;
     long nBarWidth = pNode->GetBodyWidth( ) + pNode->GetBorderWidth( );
     Point aBarOffset( pNode->GetWidth( ), +pNode->GetBorderWidth( ) );
-    Point aBarPos( Position + aBarOffset );
+    Point aBarPos( maPosition + aBarOffset );
 
     Rectangle  aBar( aBarPos, Size( nBarWidth, nBarHeight ) );
     //! avoid GROWING AND SHRINKING of drawn rectangle when constantly
     //! increasing zoomfactor.
     //  This is done by shifting its output-position to a point that
     //  corresponds exactly to a pixel on the output device.
-    Point  aDrawPos( rDev.PixelToLogic( rDev.LogicToPixel( aBar.TopLeft( ) ) ) );
+    Point  aDrawPos( mrDev.PixelToLogic( mrDev.LogicToPixel( aBar.TopLeft( ) ) ) );
     aBar.SetPos( aDrawPos );
 
-    rDev.DrawRect( aBar );
+    mrDev.DrawRect( aBar );
 }
 
 void SmDrawingVisitor::Visit( SmDynIntegralSymbolNode* pNode )
@@ -466,13 +466,13 @@ void SmDrawingVisitor::Visit( SmPolyLineNode* pNode )
 
     Point aOffset ( Point( ) - pNode->GetPolygon( ).GetBoundRect( ).TopLeft( )
                    + Point( nBorderwidth, nBorderwidth ) ),
-          aPos ( Position + aOffset );
+          aPos ( maPosition + aOffset );
     pNode->GetPolygon( ).Move( aPos.X( ), aPos.Y( ) );    //Works because Polygon wraps a pointer
 
-    SmTmpDevice aTmpDev ( rDev, false );
+    SmTmpDevice aTmpDev ( mrDev, false );
     aTmpDev.SetLineColor( pNode->GetFont( ).GetColor( ) );
 
-    rDev.DrawPolyLine( pNode->GetPolygon( ), aInfo );
+    mrDev.DrawPolyLine( pNode->GetPolygon( ), aInfo );
 }
 
 void SmDrawingVisitor::Visit( SmRectangleNode* pNode )
@@ -480,15 +480,15 @@ void SmDrawingVisitor::Visit( SmRectangleNode* pNode )
     if ( pNode->IsPhantom( ) )
         return;
 
-    SmTmpDevice aTmpDev ( rDev, false );
+    SmTmpDevice aTmpDev ( mrDev, false );
     aTmpDev.SetFillColor( pNode->GetFont( ).GetColor( ) );
-    rDev.SetLineColor( );
+    mrDev.SetLineColor( );
     aTmpDev.SetFont( pNode->GetFont( ) );
 
     sal_uLong  nTmpBorderWidth = pNode->GetFont( ).GetBorderWidth( );
 
     // get rectangle and remove borderspace
-    Rectangle  aTmp ( pNode->AsRectangle( ) + Position - pNode->GetTopLeft( ) );
+    Rectangle  aTmp ( pNode->AsRectangle( ) + maPosition - pNode->GetTopLeft( ) );
     aTmp.Left( )   += nTmpBorderWidth;
     aTmp.Right( )  -= nTmpBorderWidth;
     aTmp.Top( )    += nTmpBorderWidth;
@@ -501,10 +501,10 @@ void SmDrawingVisitor::Visit( SmRectangleNode* pNode )
     //! increasing zoomfactor.
     //  This is done by shifting its output-position to a point that
     //  corresponds exactly to a pixel on the output device.
-    Point  aPos ( rDev.PixelToLogic( rDev.LogicToPixel( aTmp.TopLeft( ) ) ) );
+    Point  aPos ( mrDev.PixelToLogic( mrDev.LogicToPixel( aTmp.TopLeft( ) ) ) );
     aTmp.SetPos( aPos );
 
-    rDev.DrawRect( aTmp );
+    mrDev.DrawRect( aTmp );
 }
 
 void SmDrawingVisitor::DrawTextNode( SmTextNode* pNode )
@@ -512,15 +512,15 @@ void SmDrawingVisitor::DrawTextNode( SmTextNode* pNode )
     if ( pNode->IsPhantom() || pNode->GetText().isEmpty() || pNode->GetText()[0] == '\0' )
         return;
 
-    SmTmpDevice aTmpDev ( rDev, false );
+    SmTmpDevice aTmpDev ( mrDev, false );
     aTmpDev.SetFont( pNode->GetFont( ) );
 
-    Point  aPos ( Position );
+    Point  aPos ( maPosition );
     aPos.Y( ) += pNode->GetBaselineOffset( );
     // auf Pixelkoordinaten runden
-    aPos = rDev.PixelToLogic( rDev.LogicToPixel( aPos ) );
+    aPos = mrDev.PixelToLogic( mrDev.LogicToPixel( aPos ) );
 
-    rDev.DrawStretchText( aPos, pNode->GetWidth( ), pNode->GetText( ) );
+    mrDev.DrawStretchText( aPos, pNode->GetWidth( ), pNode->GetText( ) );
 }
 
 void SmDrawingVisitor::DrawSpecialNode( SmSpecialNode* pNode )
@@ -537,13 +537,13 @@ void SmDrawingVisitor::DrawChildren( SmNode* pNode )
     if ( pNode->IsPhantom( ) )
         return;
 
-    Point rPosition = Position;
+    Point rPosition = maPosition;
 
     SmNodeIterator it( pNode );
     while( it.Next( ) )
     {
         Point  aOffset ( it->GetTopLeft( ) - pNode->GetTopLeft( ) );
-        Position = rPosition + aOffset;
+        maPosition = rPosition + aOffset;
         it->Accept( this );
     }
 }
commit c67c7c2007b7c9194304d341c6abe22a0096790c
Author: Takeshi Abe <tabe at fixedpoint.jp>
Date:   Wed Dec 9 12:47:34 2015 +0900

    Drop unused typedef
    
    Change-Id: I2bc18d48ebf4401d9af576fb1b98b69ff44ab334
    Reviewed-on: https://gerrit.libreoffice.org/20485
    Tested-by: Jenkins <ci at libreoffice.org>
    Reviewed-by: David Tardon <dtardon at redhat.com>

diff --git a/starmath/source/ElementsDockingWindow.cxx b/starmath/source/ElementsDockingWindow.cxx
index d3dd525..229eeedb 100644
--- a/starmath/source/ElementsDockingWindow.cxx
+++ b/starmath/source/ElementsDockingWindow.cxx
@@ -29,8 +29,6 @@
 #include <sfx2/sfxmodelfactory.hxx>
 #include <vcl/settings.hxx>
 
-typedef tools::SvRef<SmDocShell> SmDocShellRef;
-
 SmElement::SmElement(SmNodePointer pNode, const OUString& aText, const OUString& aHelpText) :
     mpNode(pNode),
     maText(aText),
commit cc5899ff62dd4e9c76aa456fe845c5812bb8d93a
Author: Oliver Specht <oliver.specht at cib.de>
Date:   Wed Dec 9 07:48:01 2015 +0100

    tdf#94816: fixed some problems in the mail merge wizard
    
    Some disposeAndClear have been added as calling dialogs in the wizard
    like select address list, new address list, match fields crashed in
    dbg build in shutdown because the dialogs were still alive.
    The wizard is now deleted on Cancel which didn't work anymore.
    The timeout of the preview control of page 5 has been changed
    as the preview didn't even appear on Windows in a debug build
    The timeout handler was called after the wizard has been closed and
    lead to a crash.
    
    Change-Id: I9cd01f39347744bda31a312f695d27eefa077721
    Reviewed-on: https://gerrit.libreoffice.org/20489
    Tested-by: Jenkins <ci at libreoffice.org>
    Reviewed-by: Oliver Specht <oliver.specht at cib.de>
    Tested-by: Oliver Specht <oliver.specht at cib.de>

diff --git a/sw/source/ui/dbui/createaddresslistdialog.cxx b/sw/source/ui/dbui/createaddresslistdialog.cxx
index d85bac5..d1ef267 100644
--- a/sw/source/ui/dbui/createaddresslistdialog.cxx
+++ b/sw/source/ui/dbui/createaddresslistdialog.cxx
@@ -126,8 +126,8 @@ void SwAddressControl_Impl::dispose()
     for(auto aEditIter = m_aEdits.begin(); aEditIter != m_aEdits.end(); ++aEditIter)
         aEditIter->disposeAndClear();
     m_aEdits.clear();
-    m_pScrollBar.clear();
-    m_pWindow.clear();
+    m_pScrollBar.disposeAndClear();
+    m_pWindow.disposeAndClear();
     Control::dispose();
 }
 
diff --git a/sw/source/ui/dbui/mmaddressblockpage.cxx b/sw/source/ui/dbui/mmaddressblockpage.cxx
index 84a7564..02014b3 100644
--- a/sw/source/ui/dbui/mmaddressblockpage.cxx
+++ b/sw/source/ui/dbui/mmaddressblockpage.cxx
@@ -163,7 +163,7 @@ IMPL_LINK_NOARG_TYPED(SwMailMergeAddressBlockPage, AddressListHdl_Impl, Button*,
 {
     try
     {
-        VclPtrInstance< SwAddressListDialog > xAddrDialog(this);
+        ScopedVclPtrInstance< SwAddressListDialog > xAddrDialog(this);
         if(RET_OK == xAddrDialog->Execute())
         {
             SwMailMergeConfigItem& rConfigItem = m_pWizard->GetConfigItem();
@@ -188,7 +188,7 @@ IMPL_LINK_NOARG_TYPED(SwMailMergeAddressBlockPage, AddressListHdl_Impl, Button*,
 
 IMPL_LINK_TYPED(SwMailMergeAddressBlockPage, SettingsHdl_Impl, Button*, pButton, void)
 {
-    VclPtr<SwSelectAddressBlockDialog> pDlg(
+    ScopedVclPtr<SwSelectAddressBlockDialog> pDlg(
                 VclPtr<SwSelectAddressBlockDialog>::Create(pButton, m_pWizard->GetConfigItem()));
     SwMailMergeConfigItem& rConfig = m_pWizard->GetConfigItem();
     pDlg->SetAddressBlocks(rConfig.GetAddressBlocks(), m_pSettingsWIN->GetSelectedAddress());
@@ -207,7 +207,7 @@ IMPL_LINK_TYPED(SwMailMergeAddressBlockPage, SettingsHdl_Impl, Button*, pButton,
         rConfig.SetCountrySettings(pDlg->IsIncludeCountry(), pDlg->GetCountry());
         InsertDataHdl_Impl(nullptr);
     }
-    pDlg.reset();
+    pDlg.disposeAndClear();
     GetWizard()->UpdateRoadmap();
     GetWizard()->enableButtons(WizardButtonFlags::NEXT, GetWizard()->isStateEnabled(MM_GREETINGSPAGE));
 }
diff --git a/sw/source/ui/dbui/mmgreetingspage.cxx b/sw/source/ui/dbui/mmgreetingspage.cxx
index 40c4307..105bb6e 100644
--- a/sw/source/ui/dbui/mmgreetingspage.cxx
+++ b/sw/source/ui/dbui/mmgreetingspage.cxx
@@ -103,7 +103,7 @@ IMPL_LINK_NOARG_TYPED(SwGreetingsHandler, IndividualHdl_Impl, Button*, void)
 
 IMPL_LINK_TYPED(SwGreetingsHandler, GreetingHdl_Impl, Button*, pButton, void)
 {
-    VclPtr<SwCustomizeAddressBlockDialog> pDlg(
+    ScopedVclPtr<SwCustomizeAddressBlockDialog> pDlg(
             VclPtr<SwCustomizeAddressBlockDialog>::Create(pButton, m_pWizard->GetConfigItem(),
                         pButton == m_pMalePB ?
                         SwCustomizeAddressBlockDialog::GREETING_MALE :
@@ -129,7 +129,7 @@ void    SwGreetingsHandler::UpdatePreview()
 IMPL_LINK_TYPED(SwMailMergeGreetingsPage, AssignHdl_Impl, Button*, pButton, void)
 {
     const OUString sPreview(m_pFemaleLB->GetSelectEntry() + "\n" + m_pMaleLB->GetSelectEntry());
-    VclPtr<SwAssignFieldsDialog> pDlg(
+    ScopedVclPtr<SwAssignFieldsDialog> pDlg(
             VclPtr<SwAssignFieldsDialog>::Create(pButton, m_pWizard->GetConfigItem(), sPreview, false));
     if(RET_OK == pDlg->Execute())
     {
diff --git a/sw/source/uibase/app/apphdl.cxx b/sw/source/uibase/app/apphdl.cxx
index 39ed273..bd18537 100644
--- a/sw/source/uibase/app/apphdl.cxx
+++ b/sw/source/uibase/app/apphdl.cxx
@@ -594,7 +594,7 @@ IMPL_LINK_NOARG_TYPED(SwMailMergeWizardExecutor, CancelHdl, void*, void)
     m_pMMConfig->Commit();
     delete m_pMMConfig;
     m_pMMConfig = nullptr;
-    // m_pWizard already deleted by closing the target view
+    delete m_pWizard;
     m_pWizard = nullptr;
     release();
 }
diff --git a/sw/source/uibase/dbui/mmconfigitem.cxx b/sw/source/uibase/dbui/mmconfigitem.cxx
index f78a85b..b576da3 100644
--- a/sw/source/uibase/dbui/mmconfigitem.cxx
+++ b/sw/source/uibase/dbui/mmconfigitem.cxx
@@ -734,7 +734,8 @@ SwMailMergeConfigItem::SwMailMergeConfigItem() :
 {}
 
 SwMailMergeConfigItem::~SwMailMergeConfigItem()
-{}
+{
+}
 
 void  SwMailMergeConfigItem::Commit()
 {
diff --git a/sw/source/uibase/utlui/unotools.cxx b/sw/source/uibase/utlui/unotools.cxx
index 1a2c22e..5ed25c4 100644
--- a/sw/source/uibase/utlui/unotools.cxx
+++ b/sw/source/uibase/utlui/unotools.cxx
@@ -83,7 +83,7 @@ SwOneExampleFrame::SwOneExampleFrame( vcl::Window& rWin,
 
     // the controller is asynchronously set
     aLoadedIdle.SetIdleHdl(LINK(this, SwOneExampleFrame, TimeoutHdl));
-    aLoadedIdle.SetPriority(SchedulerPriority::LOWER);
+    aLoadedIdle.SetPriority(SchedulerPriority::HIGH);
 
     CreateControl();
 
@@ -159,6 +159,8 @@ void SwOneExampleFrame::CreateControl()
 
 void    SwOneExampleFrame::DisposeControl()
 {
+    aLoadedIdle.Stop();
+    aTopWindow.clear();
     _xCursor = nullptr;
     if(_xControl.is())
         _xControl->dispose();
commit c4c059beb39079c204dc35088edd587ce58eadc3
Author: Stephan Bergmann <sbergman at redhat.com>
Date:   Thu Dec 10 08:18:15 2015 +0100

    DBG_TRACE_BASIC/PROFILING had been rotting for quite some time now
    
    ...e.g., it still used the long-gone tools String class
    
    Change-Id: I9d1930c72fbae3208a0f3da14c6991f30d89a9bc

diff --git a/basic/Library_sb.mk b/basic/Library_sb.mk
index b364190..0501c5d 100644
--- a/basic/Library_sb.mk
+++ b/basic/Library_sb.mk
@@ -134,11 +134,6 @@ $(eval $(call gb_Library_add_exception_objects,sb,\
 	basic/source/sbx/sbxvar \
 ))
 
-# Uncomment the following line if DBG_TRACE_PROFILING is active in source/inc/sbtrace.hxx
-# $(eval $(call gb_Library_use_libraries,sb,\
-	canvastools \
-))
-
 ifeq ($(OS),WNT)
 $(eval $(call gb_Library_use_system_win32_libs,sb,\
 	oleaut32 \
diff --git a/basic/source/classes/sbxmod.cxx b/basic/source/classes/sbxmod.cxx
index 3809d10..0730273 100644
--- a/basic/source/classes/sbxmod.cxx
+++ b/basic/source/classes/sbxmod.cxx
@@ -1227,10 +1227,6 @@ void SbModule::Run( SbMethod* pMeth )
                     ::basic::vba::lockControllersOfAllDocuments( xModel, false );
                     ::basic::vba::enableContainerWindowsOfAllDocuments( xModel, true );
                 }
-
-#ifdef DBG_TRACE_BASIC
-                dbg_DeInitTrace();
-#endif
             }
         }
         else
diff --git a/basic/source/comp/sbcomp.cxx b/basic/source/comp/sbcomp.cxx
index fad8e06..602099d 100644
--- a/basic/source/comp/sbcomp.cxx
+++ b/basic/source/comp/sbcomp.cxx
@@ -27,907 +27,6 @@
 #include <rtl/character.hxx>
 #include <memory>
 
-// To activate tracing enable in sbtrace.hxx
-#ifdef DBG_TRACE_BASIC
-
-// Trace ini file (set NULL to ignore)
-// can be overridden with the environment variable OOO_BASICTRACEINI
-static char     GpTraceIniFile[] = "~/BasicTrace.ini";
-//static char*  GpTraceIniFile = NULL;
-
-// Trace Settings, used if no ini file / not found in ini file
-static char     GpTraceFileNameDefault[] = "~/BasicTrace.txt";
-static char*    GpTraceFileName = GpTraceFileNameDefault;
-
-// GbTraceOn:
-// true = tracing is active, false = tracing is disabled, default = true
-// Set to false initially if you want to activate tracing on demand with
-// TraceCommand( "TraceOn" ), see below
-static bool GbTraceOn = true;
-
-// GbIncludePCodes:
-// true = PCodes are written to trace, default = false, correspondents
-// with TraceCommand( "PCodeOn" / "PCodeOff" ), see below
-static bool GbIncludePCodes = false;
-
-// GbInitOnlyAtOfficeStart:
-// true = Tracing is only intialized onces after Office start when
-// Basic runs the first time. Further calls to Basic, e.g. via events
-// use the same output file. The trace ini file is not read again.
-static bool GbInitOnlyAtOfficeStart = false;
-
-static int  GnIndentPerCallLevel = 4;
-static int  GnIndentForPCode = 2;
-
-/*
-    With trace enabled the runtime function TraceCommand
-    can be used to influence the trace functionality
-    from within the running Basic macro.
-
-    Format: TraceCommand( command as String [, param as Variant] )
-
-    Supported commands (command is NOT case sensitive):
-    TraceCommand "TraceOn"          sets GbTraceOn = true
-    TraceCommand "TraceOff"         sets GbTraceOn = false
-
-    TraceCommand "PCodeOn"          sets GbIncludePCodes = true
-    TraceCommand "PCodeOff"         sets GbIncludePCodes = false
-
-    TraceCommand "Print", aVal      writes aVal into the trace file as
-                                    long as it can be converted to string
-*/
-
-#ifdef DBG_TRACE_PROFILING
-
-#include <algorithm>
-#include <stack>
-#include <canvas/elapsedtime.hxx>
-
-//*** Profiling ***
-// GbTimerOn:
-// true = including time stamps
-static bool GbTimerOn = true;
-
-// GbTimeStampForEachStep:
-// true = prints time stamp after each command / pcode (very slow)
-static bool GbTimeStampForEachStep = false;
-
-// GbBlockAllAfterFirstFunctionUsage:
-// true = everything (commands, pcodes, functions) is only printed
-// for the first usage (improves performance when tracing / pro-
-// filing large macros)
-static bool GbBlockAllAfterFirstFunctionUsage = false;
-
-// GbBlockStepsAfterFirstFunctionUsage:
-// true = commands / pcodes are only printed for the first time
-// a function is executed. Afterwards only the entering/leaving
-// messages are logged (improves performance when tracing / pro-
-// filing large macros)
-static bool GbBlockStepsAfterFirstFunctionUsage = false;
-
-#endif
-
-
-static void lcl_skipWhites( char*& rpc )
-{
-    while( *rpc == ' ' || *rpc == '\t' )
-        ++rpc;
-}
-
-inline void lcl_findNextLine( char*& rpc, char* pe )
-{
-    // Find line end
-    while( rpc < pe && *rpc != 13 && *rpc != 10 )
-        ++rpc;
-
-    // Read all
-    while( rpc < pe && (*rpc == 13 || *rpc == 10) )
-        ++rpc;
-}
-
-static void lcl_ReadIniFile( const char* pIniFileName )
-{
-    const int BUF_SIZE = 1000;
-    static sal_Char TraceFileNameBuffer[BUF_SIZE];
-    sal_Char Buffer[BUF_SIZE];
-    sal_Char VarNameBuffer[BUF_SIZE];
-    sal_Char ValBuffer[BUF_SIZE];
-
-    FILE* pFile = fopen( pIniFileName ,"rb" );
-    if( pFile == NULL )
-        return;
-
-    size_t nRead = fread( Buffer, 1, BUF_SIZE, pFile );
-
-    // Scan
-    char* pc = Buffer;
-    char* pe = Buffer + nRead;
-    while( pc < pe )
-    {
-        lcl_skipWhites( pc ); if( pc == pe ) break;
-
-        // Read variable
-        char* pVarStart = pc;
-        while( pc < pe && rtl::isAsciiAlpha( *pc ) )
-            ++pc;
-        int nVarLen = pc - pVarStart;
-        if( nVarLen == 0 )
-        {
-            lcl_findNextLine( pc, pe );
-            continue;
-        }
-        strncpy( VarNameBuffer, pVarStart, nVarLen );
-        VarNameBuffer[nVarLen] = '\0';
-
-        // Check =
-        lcl_skipWhites( pc ); if( pc == pe ) break;
-        if( *pc != '=' )
-            continue;
-        ++pc;
-        lcl_skipWhites( pc ); if( pc == pe ) break;
-
-        // Read value
-        char* pValStart = pc;
-        while( pc < pe && *pc != 13 && *pc != 10 )
-            ++pc;
-        int nValLen = pc - pValStart;
-        if( nValLen == 0 )
-        {
-            lcl_findNextLine( pc, pe );
-            continue;
-        }
-        strncpy( ValBuffer, pValStart, nValLen );
-        ValBuffer[nValLen] = '\0';
-
-        // Match variables
-        if( strcmp( VarNameBuffer, "GpTraceFileName") == 0 )
-        {
-            strcpy( TraceFileNameBuffer, ValBuffer );
-            GpTraceFileName = TraceFileNameBuffer;
-        }
-        else
-        if( strcmp( VarNameBuffer, "GbTraceOn") == 0 )
-            GbTraceOn = (strcmp( ValBuffer, "true" ) == 0);
-        else
-        if( strcmp( VarNameBuffer, "GbIncludePCodes") == 0 )
-            GbIncludePCodes = (strcmp( ValBuffer, "true" ) == 0);
-        else
-        if( strcmp( VarNameBuffer, "GbInitOnlyAtOfficeStart") == 0 )
-            GbInitOnlyAtOfficeStart = (strcmp( ValBuffer, "true" ) == 0);
-        else
-        if( strcmp( VarNameBuffer, "GnIndentPerCallLevel") == 0 )
-            GnIndentPerCallLevel = strtol( ValBuffer, NULL, 10 );
-        else
-        if( strcmp( VarNameBuffer, "GnIndentForPCode") == 0 )
-            GnIndentForPCode = strtol( ValBuffer, NULL, 10 );
-#ifdef DBG_TRACE_PROFILING
-        else
-        if( strcmp( VarNameBuffer, "GbTimerOn") == 0 )
-            GbTimerOn = (strcmp( ValBuffer, "true" ) == 0);
-        else
-        if( strcmp( VarNameBuffer, "GbTimeStampForEachStep") == 0 )
-            GbTimeStampForEachStep = (strcmp( ValBuffer, "true" ) == 0);
-        else
-        if( strcmp( VarNameBuffer, "GbBlockAllAfterFirstFunctionUsage") == 0 )
-            GbBlockAllAfterFirstFunctionUsage = (strcmp( ValBuffer, "true" ) == 0);
-        else
-        if( strcmp( VarNameBuffer, "GbBlockStepsAfterFirstFunctionUsage") == 0 )
-            GbBlockStepsAfterFirstFunctionUsage = (strcmp( ValBuffer, "true" ) == 0);
-#endif
-    }
-    fclose( pFile );
-}
-
-struct TraceTextData
-{
-    OString m_aTraceStr_STMNT;
-    OString m_aTraceStr_PCode;
-};
-typedef std::hash_map< sal_Int32, TraceTextData > PCToTextDataMap;
-typedef std::hash_map< OUString, PCToTextDataMap*, OUStringHash, ::std::equal_to< OUString > > ModuleTraceMap;
-
-ModuleTraceMap      GaModuleTraceMap;
-ModuleTraceMap&     rModuleTraceMap = GaModuleTraceMap;
-
-static FILE* GpGlobalFile = NULL;
-
-static void lcl_lineOut( const char* pStr, const char* pPreStr = NULL, const char* pPostStr = NULL )
-{
-    if( GpGlobalFile != NULL )
-    {
-        fprintf( GpGlobalFile, "%s%s%s\n", pPreStr ? pPreStr : "", pStr, pPostStr ? pPostStr : "" );
-        fflush( GpGlobalFile );
-    }
-}
-
-const char* lcl_getSpaces( int nSpaceCount )
-{
-    static const sal_Char Spaces[] = "                                                                                                    "
-        "                                                                                                    "
-        "                                                                                                    ";
-    static const int nAvailableSpaceCount = strlen( Spaces );
-    static const sal_Char* pSpacesEnd = Spaces + nAvailableSpaceCount;
-
-    if( nSpaceCount > nAvailableSpaceCount )
-        nSpaceCount = nAvailableSpaceCount;
-
-    return pSpacesEnd - nSpaceCount;
-}
-
-static OString lcl_toOStringSkipLeadingWhites( const OUString& aStr )
-{
-    OString aOStr = OUStringToOString( OUString( aStr ), RTL_TEXTENCODING_ASCII_US );
-    const sal_Char* pStr = aOStr.getStr();
-
-    // Skip whitespace
-    sal_Char c = *pStr;
-    while( c == ' ' || c == '\t' )
-    {
-        pStr++;
-        c = *pStr;
-    }
-
-    OString aORetStr( pStr, strlen(pStr) );
-    return aORetStr;
-}
-
-OUString lcl_dumpMethodParameters( SbMethod* pMethod )
-{
-    OUString aStr;
-    if( pMethod == NULL )
-    {
-        return aStr;
-    }
-    SbxError eOld = SbxBase::GetError();
-
-    SbxArray* pParams = pMethod->GetParameters();
-    SbxInfo* pInfo = pMethod->GetInfo();
-    if ( pParams )
-    {
-        aStr += '(';
-        // 0 is sub itself
-        for ( sal_uInt16 nParam = 1; nParam < pParams->Count(); nParam++ )
-        {
-            SbxVariable* pVar = pParams->Get( nParam );
-            DBG_ASSERT( pVar, "Parameter?!" );
-            if ( !pVar->GetName().isEmpty() )
-            {
-                aStr += pVar->GetName();
-            }
-            else if ( pInfo )
-            {
-                const SbxParamInfo* pParam = pInfo->GetParam( nParam );
-                if ( pParam )
-                {
-                    aStr += pParam->aName;
-                }
-            }
-            aStr += '=';
-            SbxDataType eType = pVar->GetType();
-            if( eType & SbxARRAY )
-            {
-                aStr += "...";
-            }
-            else if( eType != SbxOBJECT )
-            {
-                aStr += pVar->GetString();
-            }
-            if ( nParam < ( pParams->Count() - 1 ) )
-            {
-                aStr += ", ";
-            }
-        }
-        aStr += ')';
-    }
-
-    SbxBase::ResetError();
-    if( eOld != ERRCODE_SBX_OK )
-    {
-        SbxBase::SetError( eOld );
-    }
-    return aStr;
-}
-
-
-// Public functions
-static bool GbSavTraceOn = false;
-
-#ifdef DBG_TRACE_PROFILING
-static canvas::tools::ElapsedTime* GpTimer = NULL;
-static double GdStartTime = 0.0;
-static double GdLastTime = 0.0;
-static bool GbBlockSteps = false;
-static bool GbBlockAll = false;
-
-struct FunctionItem
-{
-    OUString    m_aCompleteFunctionName;
-    double      m_dTotalTime;
-    double      m_dNetTime;
-    int         m_nCallCount;
-    bool        m_bBlockAll;
-    bool        m_bBlockSteps;
-
-    FunctionItem()
-        : m_dTotalTime( 0.0 )
-        , m_dNetTime( 0.0 )
-        , m_nCallCount( 0 )
-        , m_bBlockAll( false )
-        , m_bBlockSteps( false )
-    {}
-};
-typedef std::hash_map< OUString, FunctionItem*, OUStringHash, ::std::equal_to< OUString > > FunctionItemMap;
-
-static std::stack< double >             GaCallEnterTimeStack;
-static std::stack< FunctionItem* >      GaFunctionItemStack;
-static FunctionItemMap                  GaFunctionItemMap;
-
-bool compareFunctionNetTime( FunctionItem* p1, FunctionItem* p2 )
-{
-    return (p1->m_dNetTime > p2->m_dNetTime);
-}
-
-void lcl_printTimeOutput()
-{
-    // Overall time output
-    lcl_lineOut( "" );
-    lcl_lineOut( "***** Time Output *****" );
-    char TimeBuffer[500];
-    double dTotalTime = GpTimer->getElapsedTime() - GdStartTime;
-    sprintf( TimeBuffer, "Total execution time = %f ms", dTotalTime*1000.0 );
-    lcl_lineOut( TimeBuffer );
-    lcl_lineOut( "" );
-
-    if( GbTimerOn )
-    {
-        lcl_lineOut( "Functions:" );
-
-        std::vector<FunctionItem*> avFunctionItems;
-
-        FunctionItemMap::iterator it;
-        for( it = GaFunctionItemMap.begin() ; it != GaFunctionItemMap.end() ; ++it )
-        {
-            FunctionItem* pFunctionItem = it->second;
-            if( pFunctionItem != NULL )
-            {
-                avFunctionItems.push_back( pFunctionItem );
-            }
-        }
-
-        std::sort( avFunctionItems.begin(), avFunctionItems.end(), compareFunctionNetTime );
-
-        std::vector<FunctionItem*>::iterator itv;
-        for( itv = avFunctionItems.begin() ; itv != avFunctionItems.end() ; ++itv )
-        {
-            FunctionItem* pFunctionItem = *itv;
-            if( pFunctionItem != NULL )
-            {
-                OUString aCompleteFunctionName = pFunctionItem->m_aCompleteFunctionName;
-                OString aName = OUStringToOString( aCompleteFunctionName, RTL_TEXTENCODING_ASCII_US );
-                int nNameLen = aCompleteFunctionName.getLength();
-
-                double dFctTotalTime = pFunctionItem->m_dTotalTime;
-                double dFctNetTime = pFunctionItem->m_dNetTime;
-                double dFctTotalTimePercent = 100.0 * dFctTotalTime / dTotalTime;
-                double dFctNetTimePercent = 100.0 * dFctNetTime / dTotalTime;
-                int nSpaceCount = 30 - nNameLen;
-                if( nSpaceCount < 0 )
-                {
-                    nSpaceCount = 2;
-                }
-                sprintf( TimeBuffer, "%s:%sCalled %d times\t%f ms (%f%%) / net %f (%f%%) ms",
-                         aName.getStr(), lcl_getSpaces( nSpaceCount ), pFunctionItem->m_nCallCount,
-                         dFctTotalTime*1000.0, dFctTotalTimePercent, dFctNetTime*1000.0, dFctNetTimePercent );
-                lcl_lineOut( TimeBuffer );
-            }
-        }
-    }
-}
-#endif
-
-
-static bool GbInitTraceAlreadyCalled = false;
-
-void dbg_InitTrace()
-{
-    if( GbInitOnlyAtOfficeStart && GbInitTraceAlreadyCalled )
-    {
-#ifdef DBG_TRACE_PROFILING
-        if( GbTimerOn )
-        {
-            GpTimer->continueTimer();
-        }
-#endif
-        GpGlobalFile = fopen( GpTraceFileName, "a+" );
-        return;
-    }
-    GbInitTraceAlreadyCalled = true;
-
-    if( const sal_Char* pcIniFileName = ::getenv( "OOO_BASICTRACEINI" ) )
-    {
-        lcl_ReadIniFile( pcIniFileName );
-    }
-    else if( GpTraceIniFile != NULL )
-    {
-        lcl_ReadIniFile( GpTraceIniFile );
-    }
-    GpGlobalFile = fopen( GpTraceFileName, "w" );
-    GbSavTraceOn = GbTraceOn;
-    if( !GbTraceOn )
-    {
-        lcl_lineOut( "### Program started with trace off ###" );
-    }
-#ifdef DBG_TRACE_PROFILING
-    GpTimer = new canvas::tools::ElapsedTime();
-    GdStartTime = GpTimer->getElapsedTime();
-    GdLastTime = GdStartTime;
-    GbBlockSteps = false;
-    GbBlockAll = false;
-#endif
-}
-
-void dbg_DeInitTrace()
-{
-    GbTraceOn = GbSavTraceOn;
-
-#ifdef DBG_TRACE_PROFILING
-    while( !GaCallEnterTimeStack.empty() )
-    {
-        GaCallEnterTimeStack.pop();
-    }
-    while( !GaFunctionItemStack.empty() )
-    {
-        GaFunctionItemStack.pop();
-    }
-    lcl_printTimeOutput();
-
-    for( FunctionItemMap::iterator it = GaFunctionItemMap.begin() ; it != GaFunctionItemMap.end() ; ++it )
-    {
-        delete it->second;
-    }
-    GaFunctionItemMap.clear();
-
-    if( GpGlobalFile )
-    {
-        fclose( GpGlobalFile );
-        GpGlobalFile = NULL;
-    }
-
-    if( GbInitOnlyAtOfficeStart )
-    {
-        if( GbTimerOn )
-        {
-            GpTimer->pauseTimer();
-        }
-    }
-    else
-    {
-        delete GpTimer;
-    }
-#endif
-}
-
-static sal_Int32 GnLastCallLvl = 0;
-
-void dbg_tracePrint( const OUString& aStr, sal_Int32 nCallLvl, bool bCallLvlRelativeToCurrent )
-{
-    if( bCallLvlRelativeToCurrent )
-    {
-        nCallLvl += GnLastCallLvl;
-    }
-    int nIndent = nCallLvl * GnIndentPerCallLevel;
-    lcl_lineOut( OUStringToOString( OUString( aStr ), RTL_TEXTENCODING_ASCII_US ).getStr(), lcl_getSpaces( nIndent ) );
-}
-
-void dbg_traceStep( SbModule* pModule, sal_uInt32 nPC, sal_Int32 nCallLvl )
-{
-    if( !GbTraceOn )
-    {
-        return;
-    }
-#ifdef DBG_TRACE_PROFILING
-    if( GbBlockSteps || GbBlockAll )
-    {
-        return;
-    }
-    double dCurTime = 0.0;
-    bool bPrintTimeStamp = false;
-    if( GbTimerOn )
-    {
-        GpTimer->pauseTimer();
-        dCurTime = GpTimer->getElapsedTime();
-        bPrintTimeStamp = GbTimeStampForEachStep;
-    }
-#else
-    bool bPrintTimeStamp = false;
-#endif
-
-    GnLastCallLvl = nCallLvl;
-
-    SbModule* pTraceMod = pModule;
-    if( 0 != dynamic_cast<const SbClassModuleObject*>( pTraceMod) )
-    {
-        SbClassModuleObject* pClassModuleObj = (SbClassModuleObject*)(SbxBase*)pTraceMod;
-        pTraceMod = pClassModuleObj->getClassModule();
-    }
-
-    OUString aModuleName = pTraceMod->GetName();
-    ModuleTraceMap::iterator it = rModuleTraceMap.find( aModuleName );
-    if( it == rModuleTraceMap.end() )
-    {
-        OString aModuleNameStr = OUStringToOString( OUString( aModuleName ), RTL_TEXTENCODING_ASCII_US );
-        char Buffer[200];
-        sprintf( Buffer, "TRACE ERROR: Unknown module \"%s\"", aModuleNameStr.getStr() );
-        lcl_lineOut( Buffer );
-        return;
-    }
-
-    PCToTextDataMap* pInnerMap = it->second;
-    if( pInnerMap == NULL )
-    {
-        lcl_lineOut( "TRACE INTERNAL ERROR: No inner map" );
-        return;
-    }
-
-    PCToTextDataMap::iterator itInner = pInnerMap->find( nPC );
-    if( itInner == pInnerMap->end() )
-    {
-        OString aModuleNameStr = OUStringToOString( OUString( aModuleName ), RTL_TEXTENCODING_ASCII_US );
-        char Buffer[200];
-        sprintf( Buffer, "TRACE ERROR: No info for PC = %d in module \"%s\"", (int)nPC, aModuleNameStr.getStr() );
-        lcl_lineOut( Buffer );
-        return;
-    }
-
-    int nIndent = nCallLvl * GnIndentPerCallLevel;
-
-    const TraceTextData& rTraceTextData = itInner->second;
-    const OString& rStr_STMNT = rTraceTextData.m_aTraceStr_STMNT;
-    bool bSTMT = false;
-    if( !rStr_STMNT.isEmpty() )
-    {
-        bSTMT = true;
-    }
-    char TimeBuffer[200];
-    memset (TimeBuffer, 0, size(TimeBuffer));
-#ifdef DBG_TRACE_PROFILING
-    if( bPrintTimeStamp )
-    {
-        double dDiffTime = dCurTime - GdLastTime;
-        GdLastTime = dCurTime;
-        sprintf( TimeBuffer, "\t\t// Time = %f ms / += %f ms", dCurTime*1000.0, dDiffTime*1000.0 );
-    }
-#endif
-
-    if( bSTMT )
-    {
-        lcl_lineOut( rStr_STMNT.getStr(), lcl_getSpaces( nIndent ),
-                     (bPrintTimeStamp && !GbIncludePCodes) ? TimeBuffer : NULL );
-    }
-
-    if( !GbIncludePCodes )
-    {
-#ifdef DBG_TRACE_PROFILING
-        if( GbTimerOn )
-        {
-            GpTimer->continueTimer();
-        }
-#endif
-        return;
-    }
-
-    nIndent += GnIndentForPCode;
-    const OString& rStr_PCode = rTraceTextData.m_aTraceStr_PCode;
-    if( !rStr_PCode.isEmpty() )
-    {
-        lcl_lineOut( rStr_PCode.getStr(), lcl_getSpaces( nIndent ),
-                     bPrintTimeStamp ? TimeBuffer : NULL );
-    }
-
-#ifdef DBG_TRACE_PROFILING
-    if( GbTimerOn )
-    {
-        GpTimer->continueTimer();
-    }
-#endif
-}
-
-
-void dbg_traceNotifyCall( SbModule* pModule, SbMethod* pMethod, sal_Int32 nCallLvl, bool bLeave )
-{
-
-    if( !GbTraceOn )
-    {
-        return;
-    }
-#ifdef DBG_TRACE_PROFILING
-    double dCurTime = 0.0;
-    double dExecutionTime = 0.0;
-    if( GbTimerOn )
-    {
-        dCurTime = GpTimer->getElapsedTime();
-        GpTimer->pauseTimer();
-    }
-#endif
-
-    GnLastCallLvl = nCallLvl;
-
-    SbModule* pTraceMod = pModule;
-    SbClassModuleObject* pClassModuleObj = NULL;
-    if( 0 != dynamic_cast<const SbClassModuleObject*>( pTraceMod) )
-    {
-        pClassModuleObj = (SbClassModuleObject*)(SbxBase*)pTraceMod;
-        pTraceMod = pClassModuleObj->getClassModule();
-    }
-
-    OUString aCompleteFunctionName = pTraceMod->GetName();
-    if( pMethod != NULL )
-    {
-        aCompleteFunctionName +=  "::";
-        OUString aMethodName = pMethod->GetName();
-        aCompleteFunctionName += aMethodName;
-    }
-    else
-    {
-        aCompleteFunctionName += "/RunInit";
-    }
-
-    bool bOwnBlockSteps = false;
-#ifdef DBG_TRACE_PROFILING
-    bool bOwnBlockAll = false;
-    FunctionItem* pFunctionItem = NULL;
-    if( GbTimerOn )
-    {
-        FunctionItemMap::iterator itFunctionItem = GaFunctionItemMap.find( aCompleteFunctionName );
-        if( itFunctionItem != GaFunctionItemMap.end() )
-        {
-            pFunctionItem = itFunctionItem->second;
-        }
-        if( pFunctionItem == NULL )
-        {
-            DBG_ASSERT( !bLeave, "No FunctionItem in leave!" );
-
-            pFunctionItem = new FunctionItem();
-            pFunctionItem->m_aCompleteFunctionName = aCompleteFunctionName;
-            GaFunctionItemMap[ aCompleteFunctionName ] = pFunctionItem;
-        }
-        else if( GbBlockAllAfterFirstFunctionUsage && !bLeave )
-        {
-            pFunctionItem->m_bBlockAll = true;
-        }
-        else if( GbBlockStepsAfterFirstFunctionUsage && !bLeave )
-        {
-            pFunctionItem->m_bBlockSteps = true;
-        }
-
-        if( bLeave )
-        {
-            bOwnBlockAll = GbBlockAll;
-            bOwnBlockSteps = GbBlockSteps;
-            GbBlockAll = false;
-            GbBlockSteps = false;
-
-            dExecutionTime = dCurTime - GaCallEnterTimeStack.top();
-            GaCallEnterTimeStack.pop();
-
-            pFunctionItem->m_dTotalTime += dExecutionTime;
-            pFunctionItem->m_dNetTime += dExecutionTime;
-            pFunctionItem->m_nCallCount++;
-
-            GaFunctionItemStack.pop();
-            if( !GaFunctionItemStack.empty() )
-            {
-                FunctionItem* pParentItem = GaFunctionItemStack.top();
-                if( pParentItem != NULL )
-                {
-                    pParentItem->m_dNetTime -= dExecutionTime;
-
-                    GbBlockSteps = pParentItem->m_bBlockSteps;
-                    GbBlockAll = pParentItem->m_bBlockAll;
-                }
-            }
-        }
-        else
-        {
-            GbBlockSteps = bOwnBlockSteps = pFunctionItem->m_bBlockSteps;
-            GbBlockAll = bOwnBlockAll = pFunctionItem->m_bBlockAll;
-
-            GaCallEnterTimeStack.push( dCurTime );
-            GaFunctionItemStack.push( pFunctionItem );
-        }
-    }
-
-    if( bOwnBlockAll )
-    {
-        if( GbTimerOn )
-        {
-            GpTimer->continueTimer();
-        }
-        return;
-    }
-#endif
-
-    if( nCallLvl > 0 )
-    {
-        nCallLvl--;
-    }
-    int nIndent = nCallLvl * GnIndentPerCallLevel;
-    if( !bLeave && !bOwnBlockSteps )
-    {
-        static const char* pSeparator = "' ================================================================================";
-        lcl_lineOut( "" );
-        lcl_lineOut( pSeparator, lcl_getSpaces( nIndent ) );
-    }
-
-    OUString aStr;
-    if( bLeave )
-    {
-        if( !bOwnBlockSteps )
-        {
-            lcl_lineOut( "}", lcl_getSpaces( nIndent ) );
-            aStr = "' Leaving ";
-        }
-    }
-    else
-    {
-        aStr = "Entering " ;
-    }
-    if( !bLeave || !bOwnBlockSteps )
-    {
-        aStr += aCompleteFunctionName;
-    }
-    if( !bOwnBlockSteps && pClassModuleObj != NULL )
-    {
-        aStr += "[this=";
-        aStr += pClassModuleObj->GetName();
-        aStr += "]" ;
-    }
-    if( !bLeave )
-    {
-        aStr += lcl_dumpMethodParameters( pMethod );
-    }
-    const char* pPostStr = NULL;
-#ifdef DBG_TRACE_PROFILING
-    char TimeBuffer[200];
-    if( GbTimerOn && bLeave )
-    {
-        sprintf( TimeBuffer, "    // Execution Time = %f ms", dExecutionTime*1000.0 );
-        pPostStr = TimeBuffer;
-    }
-#endif
-    lcl_lineOut( (!bLeave || !bOwnBlockSteps) ? OUStringToOString( OUString( aStr ), RTL_TEXTENCODING_ASCII_US ).getStr() : "}",
-                 lcl_getSpaces( nIndent ), pPostStr );
-    if( !bLeave )
-    {
-        lcl_lineOut( "{", lcl_getSpaces( nIndent ) );
-    }
-    if( bLeave && !bOwnBlockSteps )
-    {
-        lcl_lineOut( "" );
-    }
-#ifdef DBG_TRACE_PROFILING
-    if( GbTimerOn )
-    {
-        GpTimer->continueTimer();
-    }
-#endif
-}
-
-void dbg_traceNotifyError( SbError nTraceErr, const OUString& aTraceErrMsg,
-                           bool bTraceErrHandled, sal_Int32 nCallLvl )
-{
-    if( !GbTraceOn )
-    {
-        return;
-    }
-#ifdef DBG_TRACE_PROFILING
-    if( GbBlockSteps || GbBlockAll )
-    {
-        return;
-    }
-#endif
-    GnLastCallLvl = nCallLvl;
-
-    OString aOTraceErrMsg = OUStringToOString( OUString( aTraceErrMsg ), RTL_TEXTENCODING_ASCII_US );
-
-    char Buffer[200];
-    const char* pHandledStr = bTraceErrHandled ? " / HANDLED" : "";
-    sprintf( Buffer, "*** ERROR%s, Id = %d, Msg = \"%s\" ***", pHandledStr, (int)nTraceErr, aOTraceErrMsg.getStr() );
-    int nIndent = nCallLvl * GnIndentPerCallLevel;
-    lcl_lineOut( Buffer, lcl_getSpaces( nIndent ) );
-}
-
-void dbg_RegisterTraceTextForPC( SbModule* pModule, sal_uInt32 nPC,
-                                 const OUString& aTraceStr_STMNT, const OUString& aTraceStr_PCode )
-{
-    OUString aModuleName = pModule->GetName();
-    ModuleTraceMap::iterator it = rModuleTraceMap.find( aModuleName );
-    PCToTextDataMap* pInnerMap;
-    if( it == rModuleTraceMap.end() )
-    {
-        pInnerMap = new PCToTextDataMap();
-        rModuleTraceMap[ aModuleName ] = pInnerMap;
-    }
-    else
-    {
-        pInnerMap = it->second;
-    }
-
-    TraceTextData aData;
-
-    OString aOTraceStr_STMNT = lcl_toOStringSkipLeadingWhites( aTraceStr_STMNT );
-    aData.m_aTraceStr_STMNT = aOTraceStr_STMNT;
-
-    OString aOTraceStr_PCode = lcl_toOStringSkipLeadingWhites( aTraceStr_PCode );
-    aData.m_aTraceStr_PCode = aOTraceStr_PCode;
-
-    (*pInnerMap)[nPC] = aData;
-}
-
-void RTL_Impl_TraceCommand( StarBASIC* pBasic, SbxArray& rPar, sal_Bool bWrite )
-{
-    (void)pBasic;
-    (void)bWrite;
-
-    if ( rPar.Count() < 2 )
-    {
-        StarBASIC::Error( ERRCODE_BASIC_BAD_ARGUMENT );
-        return;
-    }
-
-    OUString aCommand = rPar.Get(1)->GetString();
-
-    if( aCommand.equalsIngoreAsciiCase( "TraceOn" ) )
-    {
-        GbTraceOn = true;
-    }
-    else if( aCommand.equalsIngoreAsciiCase( "TraceOff" ) )
-    {
-        GbTraceOn = false;
-    }
-    else if( aCommand.equalsIngoreAsciiCase( "PCodeOn" ) )
-    {
-        GbIncludePCodes = true;
-    }
-    else if( aCommand.equalsIngoreAsciiCase( "PCodeOff" ) )
-    {
-        GbIncludePCodes = false;
-    }
-    else if( aCommand.equalsIngoreAsciiCase( "Print" ) )
-    {
-        if ( rPar.Count() < 3 )
-        {
-            StarBASIC::Error( ERRCODE_BASIC_BAD_ARGUMENT );
-            return;
-        }
-
-        SbxError eOld = SbxBase::GetError();
-        if( eOld != ERRCODE_SBX_OK )
-            SbxBase::ResetError();
-
-        OUString aValStr = rPar.Get(2)->GetString();
-        SbxError eErr = SbxBase::GetError();
-        if( eErr != ERRCODE_SBX_OK )
-        {
-            aValStr = "<ERROR converting value to String>";
-            SbxBase::ResetError();
-        }
-
-        char Buffer[500];
-
-        sprintf( Buffer, "### TRACE_PRINT: %s ###", OUStringToOString( OUString( aValStr ), RTL_TEXTENCODING_ASCII_US ).getStr() );
-        int nIndent = GnLastCallLvl * GnIndentPerCallLevel;
-        lcl_lineOut( Buffer, lcl_getSpaces( nIndent ) );
-
-        if( eOld != ERRCODE_SBX_OK )
-        {
-            SbxBase::SetError( eOld );
-        }
-    }
-}
-
-#endif
-
 // This routine is defined here, so that the
 // compiler can be loaded as a discrete segment.
 
diff --git a/basic/source/inc/rtlproto.hxx b/basic/source/inc/rtlproto.hxx
index c4b1083..7324e11 100644
--- a/basic/source/inc/rtlproto.hxx
+++ b/basic/source/inc/rtlproto.hxx
@@ -21,7 +21,6 @@
 #define INCLUDED_BASIC_SOURCE_INC_RTLPROTO_HXX
 
 #include <basic/sbstar.hxx>
-#include "sbtrace.hxx"
 
 #define RTLFUNC( name ) void SbRtl_##name( StarBASIC* pBasic, SbxArray& rPar, bool bWrite )
 #define RTLNAME( name ) &SbRtl_##name
@@ -357,10 +356,6 @@ extern RTLFUNC(CDec);
 
 extern RTLFUNC(Partition); // Fong
 
-#ifdef DBG_TRACE_BASIC
-extern RTLFUNC(TraceCommand);
-#endif
-
 extern double Now_Impl();
 extern void Wait_Impl( bool bDurationBased, SbxArray& rPar );
 
diff --git a/basic/source/inc/sbtrace.hxx b/basic/source/inc/sbtrace.hxx
deleted file mode 100644
index a12b302..0000000
--- a/basic/source/inc/sbtrace.hxx
+++ /dev/null
@@ -1,51 +0,0 @@
-/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
-/*
- * This file is part of the LibreOffice project.
- *
- * This Source Code Form is subject to the terms of the Mozilla Public
- * License, v. 2.0. If a copy of the MPL was not distributed with this
- * file, You can obtain one at http://mozilla.org/MPL/2.0/.
- *
- * This file incorporates work covered by the following license notice:
- *
- *   Licensed to the Apache Software Foundation (ASF) under one or more
- *   contributor license agreements. See the NOTICE file distributed
- *   with this work for additional information regarding copyright
- *   ownership. The ASF licenses this file to you under the Apache
- *   License, Version 2.0 (the "License"); you may not use this file
- *   except in compliance with the License. You may obtain a copy of
- *   the License at http://www.apache.org/licenses/LICENSE-2.0 .
- */
-
-#ifndef INCLUDED_BASIC_SOURCE_INC_SBTRACE_HXX
-#define INCLUDED_BASIC_SOURCE_INC_SBTRACE_HXX
-
-//#define DBG_TRACE_BASIC
-
-// ###############################################################################
-// ###
-// ###    ATTENTION:
-// ###
-// ###  - DBG_TRACE_PROFILING can only be activated together with DBG_TRACE_BASIC
-// ###
-// ###  - If you activate DBG_TRACE_PROFILING you also need to uncomment line
-// ###    # SHL1STDLIBS+=$(CANVASTOOLSLIB) in basic/util/makefile.mk (search
-// ###    for DBG_TRACE_PROFILING there)
-// ###
-// ###############################################################################
-//#define DBG_TRACE_PROFILING
-
-#ifdef DBG_TRACE_BASIC
-void dbg_InitTrace();
-void dbg_DeInitTrace();
-void dbg_traceStep( SbModule* pModule, UINT32 nPC, INT32 nCallLvl );
-void dbg_traceNotifyCall( SbModule* pModule, SbMethod* pMethod, INT32 nCallLvl, bool bLeave = false );
-void dbg_traceNotifyError( SbError nTraceErr, const String& aTraceErrMsg, bool bTraceErrHandled, INT32 nCallLvl );
-void dbg_RegisterTraceTextForPC( SbModule* pModule, UINT32 nPC,
-    const String& aTraceStr_STMNT, const String& aTraceStr_PCode );
-void RTL_Impl_TraceCommand( StarBASIC* pBasic, SbxArray& rPar, BOOL bWrite );
-#endif
-
-#endif
-
-/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
diff --git a/basic/source/runtime/methods1.cxx b/basic/source/runtime/methods1.cxx
index d42947f..48ef752 100644
--- a/basic/source/runtime/methods1.cxx
+++ b/basic/source/runtime/methods1.cxx
@@ -1694,13 +1694,6 @@ RTLFUNC(GetDefaultContext)
     RTL_Impl_GetDefaultContext( pBasic, rPar, bWrite );
 }
 
-#ifdef DBG_TRACE_BASIC
-RTLFUNC(TraceCommand)
-{
-    RTL_Impl_TraceCommand( pBasic, rPar, bWrite );
-}
-#endif
-
 RTLFUNC(Join)
 {
     (void)pBasic;
diff --git a/basic/source/runtime/stdobj.cxx b/basic/source/runtime/stdobj.cxx
index 20ee415..b6d7d5d 100644
--- a/basic/source/runtime/stdobj.cxx
+++ b/basic/source/runtime/stdobj.cxx
@@ -615,10 +615,6 @@ static Methods aMethods[] = {
 { "TimeValue",      SbxDATE,      1 | _FUNCTION, RTLNAME(TimeValue),0       },
   { "String",       SbxSTRING, 0,nullptr,0 },
 { "TOGGLE",         SbxINTEGER,       _CPROP,    RTLNAME(TOGGLE),0          },
-#ifdef DBG_TRACE_BASIC
-{ "TraceCommand",   SbxNULL,      1 | _FUNCTION, RTLNAME(TraceCommand),0 },
-  { "Command",      SbxSTRING,  0,NULL,0 },
-#endif
 { "Trim",           SbxSTRING,    1 | _FUNCTION, RTLNAME(Trim),0            },
   { "String",       SbxSTRING, 0,nullptr,0 },
 { "True",           SbxBOOL,          _CPROP,    RTLNAME(True),0            },
commit fb8a3fac5d448451794804a7470be45fa14da453
Author: Stephan Bergmann <sbergman at redhat.com>
Date:   Thu Dec 10 08:06:06 2015 +0100

    loplugin:nullptr: More NULL -> nullptr automatic rewrite
    
    Change-Id: Ie83819e2bcdc5fa160b39296b005ca9a5ff74b1d

diff --git a/accessibility/inc/accessibility/helper/listboxhelper.hxx b/accessibility/inc/accessibility/helper/listboxhelper.hxx
index 71bc7df..eafbbbb 100644
--- a/accessibility/inc/accessibility/helper/listboxhelper.hxx
+++ b/accessibility/inc/accessibility/helper/listboxhelper.hxx
@@ -53,7 +53,7 @@ public:
 
     virtual Rectangle       GetDropDownPosSizePixel() const override
     {
-        Rectangle aTemp = m_aComboListBox.GetWindowExtentsRelative(NULL);
+        Rectangle aTemp = m_aComboListBox.GetWindowExtentsRelative(nullptr);
         Rectangle aRet = m_aComboListBox.GetDropDownPosSizePixel();
         aRet.Move(aTemp.TopLeft().X(),aTemp.TopLeft().Y());
         return aRet;
diff --git a/avmedia/source/gstreamer/gstframegrabber.cxx b/avmedia/source/gstreamer/gstframegrabber.cxx
index cd2eadf..9608e7e 100644
--- a/avmedia/source/gstreamer/gstframegrabber.cxx
+++ b/avmedia/source/gstreamer/gstframegrabber.cxx
@@ -127,12 +127,12 @@ uno::Reference< graphic::XGraphic > SAL_CALL FrameGrabber::grabFrame( double fMe
 
     // synchronously fetch the frame
 #ifdef AVMEDIA_GST_0_10
-    g_signal_emit_by_name( pSink, "pull-preroll", &pBuf, NULL );
+    g_signal_emit_by_name( pSink, "pull-preroll", &pBuf, nullptr );
     if( pBuf )
         pCaps = GST_BUFFER_CAPS( pBuf );
 #else
     GstSample *pSample = nullptr;
-    g_signal_emit_by_name( pSink, "pull-preroll", &pSample, NULL );
+    g_signal_emit_by_name( pSink, "pull-preroll", &pSample, nullptr );
 
     if( pSample )
     {
diff --git a/avmedia/source/gstreamer/gstplayer.cxx b/avmedia/source/gstreamer/gstplayer.cxx
index 6dd0f5c..4e22086 100644
--- a/avmedia/source/gstreamer/gstplayer.cxx
+++ b/avmedia/source/gstreamer/gstplayer.cxx
@@ -458,7 +458,7 @@ GstBusSyncReply Player::processSyncMessage( GstMessage *message )
              GST_MESSAGE_TYPE_NAME( message ), (int)mnWindowID );
         if( mpXOverlay )
             g_object_unref( G_OBJECT ( mpXOverlay ) );
-        g_object_set( GST_MESSAGE_SRC( message ), "force-aspect-ratio", FALSE, NULL );
+        g_object_set( GST_MESSAGE_SRC( message ), "force-aspect-ratio", FALSE, nullptr );
         mpXOverlay = GST_VIDEO_OVERLAY( GST_MESSAGE_SRC( message ) );
         g_object_ref( G_OBJECT ( mpXOverlay ) );
         if ( mnWindowID != 0 )
@@ -489,7 +489,7 @@ GstBusSyncReply Player::processSyncMessage( GstMessage *message )
                 if( mnWidth == 0 ) {
                     GList *pStreamInfo = nullptr;
 
-                    g_object_get( G_OBJECT( mpPlaybin ), "stream-info", &pStreamInfo, NULL );
+                    g_object_get( G_OBJECT( mpPlaybin ), "stream-info", &pStreamInfo, nullptr );
 
                     for ( ; pStreamInfo != nullptr; pStreamInfo = pStreamInfo->next) {
                         GObject *pInfo = G_OBJECT( pStreamInfo->data );
@@ -498,7 +498,7 @@ GstBusSyncReply Player::processSyncMessage( GstMessage *message )
                             continue;
 
                         int nType;
-                        g_object_get( pInfo, "type", &nType, NULL );
+                        g_object_get( pInfo, "type", &nType, nullptr );
                         GEnumValue *pValue = g_enum_get_value( G_PARAM_SPEC_ENUM( g_object_class_find_property( G_OBJECT_GET_CLASS( pInfo ), "type" ) )->enum_class,
                                                                nType );
 
@@ -506,7 +506,7 @@ GstBusSyncReply Player::processSyncMessage( GstMessage *message )
                             GstStructure *pStructure;
                             GstPad *pPad;
 
-                            g_object_get( pInfo, "object", &pPad, NULL );
+                            g_object_get( pInfo, "object", &pPad, nullptr );
                             pStructure = gst_caps_get_structure( GST_PAD_CAPS( pPad ), 0 );
                             if( pStructure ) {
                                 gst_structure_get_int( pStructure, "width", &mnWidth );
@@ -542,7 +542,7 @@ GstBusSyncReply Player::processSyncMessage( GstMessage *message )
                 if( gst_structure_get( gst_caps_get_structure( caps, 0 ),
                                        "width", G_TYPE_INT, &w,
                                        "height", G_TYPE_INT, &h,
-                                       NULL ) ) {
+                                       nullptr ) ) {
                     mnWidth = w;
                     mnHeight = h;
 
@@ -585,14 +585,14 @@ void Player::preparePlaybin( const OUString& rURL, GstElement *pSink )
         mpPlaybin = gst_element_factory_make( "playbin", nullptr );
         if( pSink != nullptr ) // used for getting preferred size etc.
         {
-            g_object_set( G_OBJECT( mpPlaybin ), "video-sink", pSink, NULL );
+            g_object_set( G_OBJECT( mpPlaybin ), "video-sink", pSink, nullptr );
             mbFakeVideo = true;
         }
         else
             mbFakeVideo = false;
 
         OString ascURL = OUStringToOString( rURL, RTL_TEXTENCODING_UTF8 );
-        g_object_set( G_OBJECT( mpPlaybin ), "uri", ascURL.getStr() , NULL );
+        g_object_set( G_OBJECT( mpPlaybin ), "uri", ascURL.getStr() , nullptr );
 
         pBus = gst_element_get_bus( mpPlaybin );
         if (mbWatchID)
@@ -782,7 +782,7 @@ void SAL_CALL Player::setMute( sal_Bool bSet )
             nVolume = 0.0;
         }
 
-        g_object_set( G_OBJECT( mpPlaybin ), "volume", nVolume, NULL );
+        g_object_set( G_OBJECT( mpPlaybin ), "volume", nVolume, nullptr );
 
         mbMuted = bSet;
     }
@@ -812,7 +812,7 @@ void SAL_CALL Player::setVolumeDB( sal_Int16 nVolumeDB )
     // change volume
      if( !mbMuted && mpPlaybin )
      {
-         g_object_set( G_OBJECT( mpPlaybin ), "volume", (gdouble) mnUnmutedVolume, NULL );
+         g_object_set( G_OBJECT( mpPlaybin ), "volume", (gdouble) mnUnmutedVolume, nullptr );
      }
 }
 
@@ -828,7 +828,7 @@ sal_Int16 SAL_CALL Player::getVolumeDB()
     if( mpPlaybin ) {
         double nGstVolume = 0.0;
 
-        g_object_get( G_OBJECT( mpPlaybin ), "volume", &nGstVolume, NULL );
+        g_object_get( G_OBJECT( mpPlaybin ), "volume", &nGstVolume, nullptr );
 
         nVolumeDB = (sal_Int16) ( 20.0*log10 ( nGstVolume ) );
     }
diff --git a/avmedia/source/vlc/wrapper/SymbolLoader.hxx b/avmedia/source/vlc/wrapper/SymbolLoader.hxx
index 3cf33b6..8e3faf4 100644
--- a/avmedia/source/vlc/wrapper/SymbolLoader.hxx
+++ b/avmedia/source/vlc/wrapper/SymbolLoader.hxx
@@ -79,7 +79,7 @@ namespace
             if ( !aMethod )
             {
                 SAL_WARN("avmedia", "Cannot load method " << pMap[ i ].symName);
-                *pMap[ i ].refValue = NULL;
+                *pMap[ i ].refValue = nullptr;
                 return false;
             }
             else
diff --git a/basctl/source/basicide/basicmod.hxx b/basctl/source/basicide/basicmod.hxx
index f30c30b..f462927 100644
--- a/basctl/source/basicide/basicmod.hxx
+++ b/basctl/source/basicide/basicmod.hxx
@@ -31,7 +31,7 @@ class Module : public SfxModule
     static Module* mpModule;
 public:
     Module ( ResMgr *pMgr, SfxObjectFactory *pObjFact) :
-        SfxModule( pMgr, false, pObjFact, NULL )
+        SfxModule( pMgr, false, pObjFact, nullptr )
     { }
 public:
     static Module*& Get () { return mpModule; }
diff --git a/basebmp/source/bitmapdevice.cxx b/basebmp/source/bitmapdevice.cxx
index 37ebf91..9469d56 100644
--- a/basebmp/source/bitmapdevice.cxx
+++ b/basebmp/source/bitmapdevice.cxx
@@ -383,7 +383,7 @@ namespace
         {
             // TODO(P1): dynamic_cast usually called twice for
             // compatible formats
-            return getCompatibleBitmap(bmp).get() != NULL;
+            return getCompatibleBitmap(bmp).get() != nullptr;
         }
 
         std::shared_ptr<mask_bitmap_type> getCompatibleClipMask( const BitmapDeviceSharedPtr& bmp ) const
@@ -403,7 +403,7 @@ namespace
         {
             // TODO(P1): dynamic_cast usually called twice for
             // compatible formats
-            return std::dynamic_pointer_cast<mask_bitmap_type>( bmp ).get() != NULL;
+            return std::dynamic_pointer_cast<mask_bitmap_type>( bmp ).get() != nullptr;
         }
 
         static std::shared_ptr<alphamask_bitmap_type> getCompatibleAlphaMask( const BitmapDeviceSharedPtr& bmp )
diff --git a/compilerplugins/clang/store/nullptr.cxx b/compilerplugins/clang/store/nullptr.cxx
index 5b38bbf..8bed1ce 100644
--- a/compilerplugins/clang/store/nullptr.cxx
+++ b/compilerplugins/clang/store/nullptr.cxx
@@ -8,6 +8,7 @@
  */
 
 #include <cassert>
+#include <set>
 
 #include "compat.hxx"
 #include "plugin.hxx"
@@ -41,6 +42,8 @@ public:
 
     bool VisitImplicitCastExpr(CastExpr const * expr);
 
+    bool VisitGNUNullExpr(GNUNullExpr const * expr);
+
 private:
     bool isInLokIncludeFile(SourceLocation spellingLocation) const;
 
@@ -48,10 +51,16 @@ private:
 
     bool isMacroBodyExpansion(SourceLocation location) const;
 
+    void handleNull(
+        Expr const * expr, char const * castKind,
+        Expr::NullPointerConstantKind nullPointerKind);
+
     void rewriteOrWarn(
-        Expr const & expr, char const * castKind,
-        Expr::NullPointerConstantKind nullPointerkind,
+        Expr const * expr, char const * castKind,
+        Expr::NullPointerConstantKind nullPointerKind,
         char const * replacement);
+
+    std::set<Expr const *> gnuNulls_;
 };
 
 bool Nullptr::VisitImplicitCastExpr(CastExpr const * expr) {
@@ -78,7 +87,7 @@ bool Nullptr::VisitImplicitCastExpr(CastExpr const * expr) {
         case Expr::NPCK_ZeroLiteral:
             report(
                 DiagnosticsEngine::Warning,
-                "suspicious ValueDependendIsNull %0", expr->getLocStart())
+                "suspicious ValueDependentIsNull %0", expr->getLocStart())
                 << kindName(k) << expr->getSourceRange();
             break;
         default:
@@ -88,67 +97,20 @@ bool Nullptr::VisitImplicitCastExpr(CastExpr const * expr) {
     case Expr::NPCK_CXX11_nullptr:
         break;
     default:
-        {
-            Expr const * e = expr->getSubExpr();
-            SourceLocation loc;
-            for (;;) {
-                e = e->IgnoreImpCasts();
-                loc = e->getLocStart();
-                while (compiler.getSourceManager().isMacroArgExpansion(loc)) {
-                    loc = compiler.getSourceManager()
-                        .getImmediateMacroCallerLoc(
-                            loc);
-                }
-                if (isMacroBodyExpansion(loc)) {
-                    if (Lexer::getImmediateMacroName(
-                            loc, compiler.getSourceManager(),
-                            compiler.getLangOpts())
-                        == "NULL")
-                    {
-                        if (!compiler.getLangOpts().CPlusPlus) {
-                            return true;
-                        }
-                        loc = compiler.getSourceManager()
-                            .getImmediateExpansionRange(loc).first;
-                        if (isInUnoIncludeFile(
-                                compiler.getSourceManager().getSpellingLoc(loc))
-                            || isInLokIncludeFile(
-                                compiler.getSourceManager().getSpellingLoc(loc))
-                            || isFromCIncludeFile(
-                                compiler.getSourceManager().getSpellingLoc(
-                                    loc)))

... etc. - the rest is truncated


More information about the Libreoffice-commits mailing list