tdf#104878 speed up GfxLink compare

which shaves 5% off the rendering time

Change-Id: Iab2a92088c5d1e8840a53ff57ab1a95ba5ec8e0a
Reviewed-on: https://gerrit.libreoffice.org/c/core/+/91947
Tested-by: Jenkins
Reviewed-by: Noel Grandin <noel.grandin@collabora.co.uk>
diff --git a/include/vcl/gfxlink.hxx b/include/vcl/gfxlink.hxx
index 0376149..0e11623 100644
--- a/include/vcl/gfxlink.hxx
+++ b/include/vcl/gfxlink.hxx
@@ -62,9 +62,8 @@
private:
    GfxLinkType     meType;
    sal_uInt32      mnUserId;

    mutable std::shared_ptr<sal_uInt8> mpSwapInData;

    mutable size_t  maHash;
    sal_uInt32      mnSwapInDataSize;
    MapMode         maPrefMapMode;
    Size            maPrefSize;
@@ -82,6 +81,8 @@

    GfxLinkType         GetType() const { return meType;}

    size_t              GetHash() const;

    void                SetUserId( sal_uInt32 nUserId ) { mnUserId = nUserId; }
    sal_uInt32          GetUserId() const { return mnUserId; }

diff --git a/vcl/source/gdi/gfxlink.cxx b/vcl/source/gdi/gfxlink.cxx
index 785d86d..9a3f656 100644
--- a/vcl/source/gdi/gfxlink.cxx
+++ b/vcl/source/gdi/gfxlink.cxx
@@ -24,6 +24,7 @@
#include <vcl/gfxlink.hxx>
#include <vcl/graphicfilter.hxx>
#include <memory>
#include <boost/functional/hash.hpp>

GfxLink::GfxLink()
    : meType(GfxLinkType::NONE)
@@ -34,6 +35,8 @@
{
}



GfxLink::GfxLink(std::unique_ptr<sal_uInt8[]> pBuf, sal_uInt32 nSize, GfxLinkType nType)
    : meType(nType)
    , mnUserId(0)
@@ -46,26 +49,41 @@
                "GfxLink::GfxLink(): empty/NULL buffer given");
}

bool GfxLink::operator==( const GfxLink& rGfxLink ) const
size_t GfxLink::GetHash() const
{
    bool bIsEqual = false;

    if ( ( mnSwapInDataSize == rGfxLink.mnSwapInDataSize ) && ( meType == rGfxLink.meType ) )
    if (!maHash)
    {
        const sal_uInt8* pSource = GetData();
        const sal_uInt8* pDest = rGfxLink.GetData();
        sal_uInt32 nSourceSize = GetDataSize();
        sal_uInt32 nDestSize = rGfxLink.GetDataSize();
        if ( pSource && pDest && ( nSourceSize == nDestSize ) )
        {
            bIsEqual = memcmp( pSource, pDest, nSourceSize ) == 0;
        }
        else if ( ( pSource == nullptr ) && ( pDest == nullptr ) )
            bIsEqual = true;
        std::size_t seed = 0;
        boost::hash_combine(seed, mnSwapInDataSize);
        boost::hash_combine(seed, meType);
        const sal_uInt8* pData = GetData();
        if (pData)
            seed += boost::hash_range(pData, pData + GetDataSize());
        maHash = seed;

    }
    return bIsEqual;
    return maHash;
}

bool GfxLink::operator==( const GfxLink& rGfxLink ) const
{
    if (GetHash() != rGfxLink.GetHash())
        return false;

    if ( mnSwapInDataSize != rGfxLink.mnSwapInDataSize ||
         meType != rGfxLink.meType )
        return false;

    const sal_uInt8* pSource = GetData();
    const sal_uInt8* pDest = rGfxLink.GetData();
    if ( pSource == pDest )
        return true;
    sal_uInt32 nSourceSize = GetDataSize();
    sal_uInt32 nDestSize = rGfxLink.GetDataSize();
    if ( pSource && pDest && ( nSourceSize == nDestSize ) )
        return (memcmp( pSource, pDest, nSourceSize ) == 0);
    return false;
}

bool GfxLink::IsNative() const
{