[Libreoffice-commits] .: Branch 'libreoffice-3-4' - filter/inc filter/source

Petr Mladek pmladek at kemper.freedesktop.org
Tue Jan 3 05:26:09 PST 2012


 filter/inc/filter/msfilter/msdffimp.hxx |   17 +++++++++++--
 filter/source/msfilter/msdffimp.cxx     |   40 +++++++++++++++++++++++++++-----
 2 files changed, 48 insertions(+), 9 deletions(-)

New commits:
commit e7421d2e4d6426ba9b120c52abb2a37f95207943
Author: Caolán McNamara <caolanm at redhat.com>
Date:   Wed Dec 21 17:35:39 2011 +0100

    avoid looping on busted escher records
    
    Signed-off-by: Petr Mladek <pmladek at suse.cz>

diff --git a/filter/inc/filter/msfilter/msdffimp.hxx b/filter/inc/filter/msfilter/msdffimp.hxx
index c1a0294..9344084 100644
--- a/filter/inc/filter/msfilter/msdffimp.hxx
+++ b/filter/inc/filter/msfilter/msdffimp.hxx
@@ -77,9 +77,20 @@ public:
     bool IsContainer() const { return nRecVer == DFF_PSFLAG_CONTAINER; }
     sal_uLong    GetRecBegFilePos() const { return nFilePos; }
     sal_uLong    GetRecEndFilePos() const { return nFilePos + DFF_COMMON_RECORD_HEADER_SIZE + nRecLen; }
-    void SeekToEndOfRecord(SvStream& rIn) const { rIn.Seek(nFilePos + DFF_COMMON_RECORD_HEADER_SIZE + nRecLen ); }
-    void SeekToContent(    SvStream& rIn) const { rIn.Seek(nFilePos + DFF_COMMON_RECORD_HEADER_SIZE ); }
-    void SeekToBegOfRecord(SvStream& rIn) const { rIn.Seek( nFilePos ); }
+    bool SeekToEndOfRecord(SvStream& rIn) const
+    {
+        sal_Size nPos = nFilePos + DFF_COMMON_RECORD_HEADER_SIZE + nRecLen;
+        return nPos == rIn.Seek(nPos);
+    }
+    bool SeekToContent(SvStream& rIn) const
+    {
+        sal_Size nPos = nFilePos + DFF_COMMON_RECORD_HEADER_SIZE;
+        return nPos == rIn.Seek(nPos);
+    }
+    bool SeekToBegOfRecord(SvStream& rIn) const
+    {
+        return nFilePos == rIn.Seek(nFilePos);
+    }
 
     MSFILTER_DLLPUBLIC friend SvStream& operator>>(SvStream& rIn, DffRecordHeader& rRec);
 
diff --git a/filter/source/msfilter/msdffimp.cxx b/filter/source/msfilter/msdffimp.cxx
index aabba56..5764c66 100644
--- a/filter/source/msfilter/msdffimp.cxx
+++ b/filter/source/msfilter/msdffimp.cxx
@@ -156,6 +156,11 @@ using namespace container	        ;
 static sal_uInt32 nMSOleObjCntr = 0;
 #define MSO_OLE_Obj "MSO_OLE_Obj"
 
+/*************************************************************************/
+bool lclGood(const SvStream &rStream)
+{
+    return rStream.GetError() == 0 && !rStream.IsEof();
+}
 
 /*************************************************************************/
 sal_Bool Impl_OlePres::Read( SvStream & rStm )
@@ -3545,7 +3550,7 @@ sal_Bool SvxMSDffManager::SeekToShape( SvStream& rSt, void* /* pClientData */, s
                 rSt >> aEscherF002Hd;
                 sal_uLong nEscherF002End = aEscherF002Hd.GetRecEndFilePos();
                 DffRecordHeader aEscherObjListHd;
-                while ( rSt.Tell() < nEscherF002End )
+                while (lclGood(rSt) && rSt.Tell() < nEscherF002End)
                 {
                     rSt >> aEscherObjListHd;
                     if ( aEscherObjListHd.nRecVer != 0xf )
@@ -3579,9 +3584,14 @@ bool SvxMSDffManager::SeekToRec( SvStream& rSt, sal_uInt16 nRecId, sal_uLong nMa
     bool bRet = sal_False;
     sal_uLong nFPosMerk = rSt.Tell(); // FilePos merken fuer ggf. spaetere Restauration
     DffRecordHeader aHd;
+    // make sure that we move somewhere with every iteration
+    sal_Size nStPos;
     do
     {
+        nStPos = rSt.Tell();
         rSt >> aHd;
+        if (!lclGood(rSt))
+            break;
         if ( aHd.nRecType == nRecId )
         {
             if ( nSkipCount )
@@ -3596,9 +3606,13 @@ bool SvxMSDffManager::SeekToRec( SvStream& rSt, sal_uInt16 nRecId, sal_uLong nMa
             }
         }
         if ( !bRet )
-            aHd.SeekToEndOfRecord( rSt );
+        {
+            bool bSeekSuccess = aHd.SeekToEndOfRecord( rSt );
+            if (!bSeekSuccess)
+                break;
+        }
     }
-    while ( rSt.GetError() == 0 && rSt.Tell() < nMaxFilePos && !bRet );
+    while ( lclGood(rSt) && rSt.Tell() < nMaxFilePos && rSt.Tell() != nStPos && !bRet );
     if ( !bRet )
         rSt.Seek( nFPosMerk );	// FilePos restaurieren
     return bRet;
@@ -6187,10 +6201,18 @@ void SvxMSDffManager::GetFidclData( long nOffsDggL )
 
             if ( mnIdClusters-- > 2 )
             {
-                if ( aDggAtomHd.nRecLen == ( mnIdClusters * sizeof( FIDCL ) + 16 ) )
+                const sal_Size nFIDCLsize = sizeof(sal_uInt32) * 2;
+                if ( aDggAtomHd.nRecLen == ( mnIdClusters * nFIDCLsize + 16 ) )
                 {
+                    sal_Size nStCtrlCurr = rStCtrl.Tell();
+                    sal_Size nStCtrlEnd = rStCtrl.Seek(STREAM_SEEK_TO_END);
+                    sal_Size nMaxEntriesPossible = ( nStCtrlEnd - nStCtrlCurr ) / nFIDCLsize;
+                    rStCtrl.Seek(nStCtrlCurr);
+                    mnIdClusters = std::min(nMaxEntriesPossible, static_cast<sal_Size>(mnIdClusters));
+
                     mpFidcls = new FIDCL[ mnIdClusters ];
-                    for ( sal_uInt32 i = 0; i < mnIdClusters; i++ )
+                    memset(mpFidcls, 0, mnIdClusters * sizeof(FIDCL));
+                    for (sal_uInt32 i = 0; i < mnIdClusters; ++i)
                     {
                         rStCtrl >> mpFidcls[ i ].dgid
                                 >> mpFidcls[ i ].cspidCur;
@@ -6989,6 +7011,8 @@ sal_Bool SvxMSDffManager::ReadCommonRecordHeader(DffRecordHeader& rRec, SvStream
 }
 
 
+sal_uInt32 nMaxLegalRecordLength = SAL_MAX_UINT32 - DFF_COMMON_RECORD_HEADER_SIZE;
+
 /* auch static */
 sal_Bool SvxMSDffManager::ReadCommonRecordHeader( SvStream& rSt,
                                               sal_uInt8&     rVer,
@@ -7000,7 +7024,11 @@ sal_Bool SvxMSDffManager::ReadCommonRecordHeader( SvStream& rSt,
     rSt >> nTmp >> rFbt >> rLength;
     rVer = sal::static_int_cast< sal_uInt8 >(nTmp & 15);
     rInst = nTmp >> 4;
-    return rSt.GetError() == 0;
+    if (!lclGood(rSt))
+        return false;
+    if (rLength > nMaxLegalRecordLength)
+        return false;
+    return true;
 }
 
 


More information about the Libreoffice-commits mailing list