[Libreoffice-commits] core.git: Branch 'libreoffice-5-4' - include/vcl vcl/qa vcl/source

Caolán McNamara caolanm at redhat.com
Wed Apr 4 14:50:05 UTC 2018


 include/vcl/gdimtf.hxx                                   |    9 ++-
 include/vcl/metaact.hxx                                  |    6 +-
 vcl/qa/cppunit/graphicfilter/data/svm/fail/ofz7165-1.svm |binary
 vcl/source/gdi/gdimtf.cxx                                |   40 +++++++++++++--
 vcl/source/gdi/metaact.cxx                               |    4 -
 5 files changed, 48 insertions(+), 11 deletions(-)

New commits:
commit fc6e9a715c74b2ff74ff9370fe5f5a29e20be8cd
Author: Caolán McNamara <caolanm at redhat.com>
Date:   Wed Mar 28 08:53:20 2018 +0100

    ofz#7165 set a recursion limit for svm in svm
    
    Change-Id: Id9089986012588690b6d5e33cd71d094ef2357dd
    Reviewed-on: https://gerrit.libreoffice.org/51984
    Tested-by: Jenkins <ci at libreoffice.org>
    Reviewed-by: Michael Stahl <Michael.Stahl at cib.de>

diff --git a/include/vcl/gdimtf.hxx b/include/vcl/gdimtf.hxx
index 383c7b3de445..ac8fa53e915c 100644
--- a/include/vcl/gdimtf.hxx
+++ b/include/vcl/gdimtf.hxx
@@ -38,7 +38,7 @@ namespace tools {
     class PolyPolygon;
 }
 class Gradient;
-
+struct ImplMetaReadData;
 
 #define GDI_METAFILE_END                ((size_t)0xFFFFFFFF)
 #define GDI_METAFILE_LABEL_NOTFOUND     ((size_t)0xFFFFFFFF)
@@ -53,6 +53,9 @@ enum class MtfConversion
 typedef Color (*ColorExchangeFnc)( const Color& rColor, const void* pColParam );
 typedef BitmapEx (*BmpExchangeFnc)( const BitmapEx& rBmpEx, const void* pBmpParam );
 
+VCL_DLLPUBLIC SvStream& ReadGDIMetaFile(SvStream& rIStm, GDIMetaFile& rGDIMetaFile, ImplMetaReadData* pReadData = nullptr);
+VCL_DLLPUBLIC SvStream& WriteGDIMetaFile( SvStream& rOStm, const GDIMetaFile& rGDIMetaFile );
+
 class VCL_DLLPUBLIC GDIMetaFile final
 {
 private:
@@ -187,8 +190,8 @@ public:
 
     // Stream-operators write (still) the old format
     // and read both the old and the new format
-    friend VCL_DLLPUBLIC SvStream& ReadGDIMetaFile( SvStream& rIStm, GDIMetaFile& rGDIMetaFile );
-    friend VCL_DLLPUBLIC SvStream& WriteGDIMetaFile( SvStream& rOStm, const GDIMetaFile& rGDIMetaFile );
+    friend VCL_DLLPUBLIC SvStream& ReadGDIMetaFile(SvStream& rIStm, GDIMetaFile& rGDIMetaFile, ImplMetaReadData* pReadData);
+    friend VCL_DLLPUBLIC SvStream& WriteGDIMetaFile(SvStream& rOStm, const GDIMetaFile& rGDIMetaFile);
 
     /// Creates an antialiased thumbnail
     bool            CreateThumbnail(BitmapEx& rBitmapEx,
diff --git a/include/vcl/metaact.hxx b/include/vcl/metaact.hxx
index 8fe4f1d43845..0d472dd098f7 100644
--- a/include/vcl/metaact.hxx
+++ b/include/vcl/metaact.hxx
@@ -44,9 +44,11 @@ enum class DrawTextFlags;
 struct ImplMetaReadData
 {
     rtl_TextEncoding meActualCharSet;
+    int mnParseDepth;
 
-    ImplMetaReadData() :
-        meActualCharSet( RTL_TEXTENCODING_ASCII_US )
+    ImplMetaReadData()
+        : meActualCharSet(RTL_TEXTENCODING_ASCII_US)
+        , mnParseDepth(0)
     {}
 };
 
diff --git a/vcl/qa/cppunit/graphicfilter/data/svm/fail/ofz7165-1.svm b/vcl/qa/cppunit/graphicfilter/data/svm/fail/ofz7165-1.svm
new file mode 100644
index 000000000000..ad722ea13a6c
Binary files /dev/null and b/vcl/qa/cppunit/graphicfilter/data/svm/fail/ofz7165-1.svm differ
diff --git a/vcl/source/gdi/gdimtf.cxx b/vcl/source/gdi/gdimtf.cxx
index d339f7f5ff46..7fb6875de148 100644
--- a/vcl/source/gdi/gdimtf.cxx
+++ b/vcl/source/gdi/gdimtf.cxx
@@ -2664,7 +2664,31 @@ sal_uLong GDIMetaFile::GetSizeBytes() const
     return nSizeBytes;
 }
 
-SvStream& ReadGDIMetaFile( SvStream& rIStm, GDIMetaFile& rGDIMetaFile )
+namespace
+{
+    class DepthGuard
+    {
+    private:
+        ImplMetaReadData& m_rData;
+        rtl_TextEncoding m_eOrigCharSet;
+    public:
+        DepthGuard(ImplMetaReadData& rData, SvStream& rIStm)
+            : m_rData(rData)
+            , m_eOrigCharSet(m_rData.meActualCharSet)
+        {
+            ++m_rData.mnParseDepth;
+            m_rData.meActualCharSet = rIStm.GetStreamCharSet();
+        }
+        bool TooDeep() const { return m_rData.mnParseDepth > 1024; }
+        ~DepthGuard()
+        {
+            --m_rData.mnParseDepth;
+            m_rData.meActualCharSet = m_eOrigCharSet;
+        }
+    };
+}
+
+SvStream& ReadGDIMetaFile(SvStream& rIStm, GDIMetaFile& rGDIMetaFile, ImplMetaReadData* pData)
 {
     if (rIStm.GetError())
     {
@@ -2698,12 +2722,20 @@ SvStream& ReadGDIMetaFile( SvStream& rIStm, GDIMetaFile& rGDIMetaFile )
 
             pCompat.reset(); // destructor writes stuff into the header
 
-            ImplMetaReadData aReadData;
-            aReadData.meActualCharSet = rIStm.GetStreamCharSet();
+            std::unique_ptr<ImplMetaReadData> xReadData;
+            if (!pData)
+            {
+                xReadData.reset(new ImplMetaReadData);
+                pData = xReadData.get();
+            }
+            DepthGuard aDepthGuard(*pData, rIStm);
+
+            if (aDepthGuard.TooDeep())
+                throw std::runtime_error("too much recursion");
 
             for( sal_uInt32 nAction = 0UL; ( nAction < nCount ) && !rIStm.IsEof(); nAction++ )
             {
-                MetaAction* pAction = MetaAction::ReadMetaAction( rIStm, &aReadData );
+                MetaAction* pAction = MetaAction::ReadMetaAction(rIStm, pData);
                 if( pAction )
                 {
                     if (pAction->GetType() == MetaActionType::COMMENT)
diff --git a/vcl/source/gdi/metaact.cxx b/vcl/source/gdi/metaact.cxx
index 1376476634c2..d4b0c1b65f32 100644
--- a/vcl/source/gdi/metaact.cxx
+++ b/vcl/source/gdi/metaact.cxx
@@ -3046,10 +3046,10 @@ void MetaFloatTransparentAction::Write( SvStream& rOStm, ImplMetaWriteData* pDat
     WriteGradient( rOStm, maGradient );
 }
 
-void MetaFloatTransparentAction::Read( SvStream& rIStm, ImplMetaReadData* )
+void MetaFloatTransparentAction::Read(SvStream& rIStm, ImplMetaReadData* pData)
 {
     VersionCompat aCompat(rIStm, StreamMode::READ);
-    ReadGDIMetaFile( rIStm, maMtf );
+    ReadGDIMetaFile(rIStm, maMtf, pData);
     ReadPair( rIStm, maPoint );
     ReadPair( rIStm, maSize );
     ReadGradient( rIStm, maGradient );


More information about the Libreoffice-commits mailing list