[Libreoffice-commits] core.git: Branch 'feature/perfwork' - 2 commits - comphelper/source include/comphelper sax/source

Matúš Kukan matus.kukan at collabora.com
Fri Sep 26 15:44:17 PDT 2014


 comphelper/source/streaming/seqstream.cxx |   23 +++--
 include/comphelper/seqstream.hxx          |    2 
 sax/source/tools/fastserializer.cxx       |  129 ++++++++++++++++--------------
 sax/source/tools/fastserializer.hxx       |   20 +---
 sax/source/tools/fshelper.cxx             |    6 -
 5 files changed, 97 insertions(+), 83 deletions(-)

New commits:
commit 784d4bea86d8cbb3a855e557c465ce50a049cefc
Author: Matúš Kukan <matus.kukan at collabora.com>
Date:   Fri Sep 26 17:17:50 2014 +0200

    FastSerializer: Avoid sequences where possible
    
    Change-Id: I359ca9d3b766b71904e4199ebfbdbd5b203775cc

diff --git a/comphelper/source/streaming/seqstream.cxx b/comphelper/source/streaming/seqstream.cxx
index aec4519..91fdc7d7 100644
--- a/comphelper/source/streaming/seqstream.cxx
+++ b/comphelper/source/streaming/seqstream.cxx
@@ -156,14 +156,19 @@ OSequenceOutputStream::OSequenceOutputStream(Sequence< sal_Int8 >& _rSeq, double
         // this heuristic is as good as any other ... supply better parameters if you don't like it :)
 }
 
-
 void SAL_CALL OSequenceOutputStream::writeBytes( const Sequence< sal_Int8 >& _rData ) throw(NotConnectedException, BufferSizeExceededException, IOException, RuntimeException, std::exception)
 {
+    writeBytes(_rData.getConstArray(), _rData.getLength());
+}
+
+void SAL_CALL OSequenceOutputStream::writeBytes( const sal_Int8* pStr, sal_Int32 nLen )
+    throw(NotConnectedException, BufferSizeExceededException, IOException, RuntimeException, std::exception)
+{
     if (!m_bConnected)
         throw NotConnectedException();
 
     // ensure the sequence has enough space left
-    if (m_nSize + _rData.getLength() > m_rSequence.getLength())
+    if (m_nSize + nLen > m_rSequence.getLength())
     {
         sal_Int32 nCurrentLength = m_rSequence.getLength();
         sal_Int32 nNewLength = static_cast< sal_Int32 >(
@@ -177,18 +182,18 @@ void SAL_CALL OSequenceOutputStream::writeBytes( const Sequence< sal_Int8 >& _rD
             // such a large step is not allowed
             nNewLength = nCurrentLength + m_nMaximumResize;
 
-        if (nNewLength < m_nSize + _rData.getLength())
+        if (nNewLength < m_nSize + nLen)
         {   // it's not enough .... the data would not fit
 
             // let's take the double amount of the length of the data to be written, as the next write
             // request could be as large as this one
-            sal_Int32 nNewGrowth = _rData.getLength() * 2;
+            sal_Int32 nNewGrowth = nLen * 2;
             if ((m_nMaximumResize > 0) && (nNewGrowth > m_nMaximumResize))
             {   // we came to the limit, again ...
                 nNewGrowth = m_nMaximumResize;
-                if (nNewGrowth + nCurrentLength < m_nSize + _rData.getLength())
+                if (nNewGrowth + nCurrentLength < m_nSize + nLen)
                     // but it would not fit if we respect the limit
-                    nNewGrowth = m_nSize + _rData.getLength() - nCurrentLength;
+                    nNewGrowth = m_nSize + nLen - nCurrentLength;
             }
             nNewLength = nCurrentLength + nNewGrowth;
         }
@@ -199,11 +204,11 @@ void SAL_CALL OSequenceOutputStream::writeBytes( const Sequence< sal_Int8 >& _rD
         m_rSequence.realloc(nNewLength);
     }
 
-    OSL_ENSURE(m_rSequence.getLength() >= m_nSize + _rData.getLength(),
+    OSL_ENSURE(m_rSequence.getLength() >= m_nSize + nLen,
         "ooops ... the realloc algorithm seems to be wrong :( !");
 
-    memcpy(m_rSequence.getArray() + m_nSize, _rData.getConstArray(), _rData.getLength());
-    m_nSize += _rData.getLength();
+    memcpy(m_rSequence.getArray() + m_nSize, pStr, nLen);
+    m_nSize += nLen;
 }
 
 
diff --git a/include/comphelper/seqstream.hxx b/include/comphelper/seqstream.hxx
index 75b1934..1288a9b 100644
--- a/include/comphelper/seqstream.hxx
+++ b/include/comphelper/seqstream.hxx
@@ -119,6 +119,8 @@ public:
 
     /// same as XOutputStream::writeBytes (as expected :)
     virtual void SAL_CALL writeBytes( const ::com::sun::star::uno::Sequence< sal_Int8 >& aData ) throw(::com::sun::star::io::NotConnectedException, ::com::sun::star::io::BufferSizeExceededException, ::com::sun::star::io::IOException, ::com::sun::star::uno::RuntimeException, std::exception) SAL_OVERRIDE;
+    void SAL_CALL writeBytes( const sal_Int8* pStr, sal_Int32 nLen )
+        throw(::com::sun::star::io::NotConnectedException, ::com::sun::star::io::BufferSizeExceededException, ::com::sun::star::io::IOException, ::com::sun::star::uno::RuntimeException, std::exception);
     /** Resizes the sequence used for writing to the really used size.
      *  Next time, writeBytes will write to the beginning of the sequence.
     */
diff --git a/sax/source/tools/fastserializer.cxx b/sax/source/tools/fastserializer.cxx
index 300c0d3..455df0b 100644
--- a/sax/source/tools/fastserializer.cxx
+++ b/sax/source/tools/fastserializer.cxx
@@ -37,7 +37,6 @@ using ::comphelper::SequenceAsVector;
 using ::com::sun::star::uno::Reference;
 using ::com::sun::star::uno::RuntimeException;
 using ::com::sun::star::uno::Sequence;
-using ::com::sun::star::uno::toUnoSequence;
 using ::com::sun::star::xml::FastAttribute;
 using ::com::sun::star::xml::Attribute;
 using ::com::sun::star::xml::sax::SAXException;
@@ -50,6 +49,18 @@ using ::com::sun::star::io::BufferSizeExceededException;
 #define HAS_NAMESPACE(x) ((x & 0xffff0000) != 0)
 #define NAMESPACE(x) (x >> 16)
 #define TOKEN(x) (x & 0xffff)
+// number of characters without terminating 0
+#define N_CHARS(string) (SAL_N_ELEMENTS(string) - 1)
+
+static const char sClosingBracket[] = ">";
+static const char sSlashAndClosingBracket[] = "/>";
+static const char sColon[] = ":";
+static const char sOpeningBracket[] = "<";
+static const char sOpeningBracketAndSlash[] = "</";
+static const char sQuote[] = "\"";
+static const char sEqualSignAndQuote[] = "=\"";
+static const char sSpace[] = " ";
+static const char sXmlHeader[] = "<?xml version=\"1.0\" encoding=\"UTF-8\" standalone=\"yes\"?>\n";
 
 namespace sax_fastparser {
     FastSaxSerializer::FastSaxSerializer( )
@@ -58,22 +69,13 @@ namespace sax_fastparser {
         , mxOutputStream()
         , mxFastTokenHandler()
         , maMarkStack()
-        , maClosingBracket((const sal_Int8 *)">", 1)
-        , maSlashAndClosingBracket((const sal_Int8 *)"/>", 2)
-        , maColon((const sal_Int8 *)":", 1)
-        , maOpeningBracket((const sal_Int8 *)"<", 1)
-        , maOpeningBracketAndSlash((const sal_Int8 *)"</", 2)
-        , maQuote((const sal_Int8 *)"\"", 1)
-        , maEqualSignAndQuote((const sal_Int8 *)"=\"", 2)
-        , maSpace((const sal_Int8 *)" ", 1)
     {
     }
     FastSaxSerializer::~FastSaxSerializer() {}
 
     void SAL_CALL FastSaxSerializer::startDocument(  ) throw (SAXException, RuntimeException)
     {
-        rtl::ByteSequence aXmlHeader((const sal_Int8*) "<?xml version=\"1.0\" encoding=\"UTF-8\" standalone=\"yes\"?>\n", 56);
-        writeBytes(toUnoSequence(aXmlHeader));
+        writeBytes(sXmlHeader, N_CHARS(sXmlHeader));
     }
 
     void FastSaxSerializer::write( const OUString& sOutput, bool bEscape )
@@ -118,7 +120,7 @@ namespace sax_fastparser {
     {
         if( HAS_NAMESPACE( nElement ) ) {
             writeBytes(mxFastTokenHandler->getUTF8Identifier(NAMESPACE(nElement)));
-            writeBytes(toUnoSequence(maColon));
+            writeBytes(sColon, N_CHARS(sColon));
             writeBytes(mxFastTokenHandler->getUTF8Identifier(TOKEN(nElement)));
         } else
             writeBytes(mxFastTokenHandler->getUTF8Identifier(nElement));
@@ -133,7 +135,7 @@ namespace sax_fastparser {
             Sequence<sal_Int8> const name(
                 mxFastTokenHandler->getUTF8Identifier(TOKEN(nElement)));
             return OString(reinterpret_cast<sal_Char const*>(ns.getConstArray()), ns.getLength())
-                 + OString(reinterpret_cast<sal_Char const*>(maColon.getConstArray()), maColon.getLength())
+                 + OString(sColon, N_CHARS(sColon))
                  + OString(reinterpret_cast<sal_Char const*>(name.getConstArray()), name.getLength());
         } else {
             Sequence<sal_Int8> const name(
@@ -153,12 +155,12 @@ namespace sax_fastparser {
         m_DebugStartedElements.push(Element);
 #endif
 
-        writeBytes(toUnoSequence(maOpeningBracket));
+        writeBytes(sOpeningBracket, N_CHARS(sOpeningBracket));
 
         writeId(Element);
         writeFastAttributeList(Attribs);
 
-        writeBytes(toUnoSequence(maClosingBracket));
+        writeBytes(sClosingBracket, N_CHARS(sClosingBracket));
     }
 
     void SAL_CALL FastSaxSerializer::endFastElement( ::sal_Int32 Element )
@@ -171,11 +173,11 @@ namespace sax_fastparser {
         m_DebugStartedElements.pop();
 #endif
 
-        writeBytes(toUnoSequence(maOpeningBracketAndSlash));
+        writeBytes(sOpeningBracketAndSlash, N_CHARS(sOpeningBracketAndSlash));
 
         writeId(Element);
 
-        writeBytes(toUnoSequence(maClosingBracket));
+        writeBytes(sClosingBracket, N_CHARS(sClosingBracket));
     }
 
     void SAL_CALL FastSaxSerializer::singleFastElement( ::sal_Int32 Element, const Reference< XFastAttributeList >& Attribs )
@@ -184,12 +186,12 @@ namespace sax_fastparser {
         if ( !maMarkStack.empty() )
             maMarkStack.top()->setCurrentElement( Element );
 
-        writeBytes(toUnoSequence(maOpeningBracket));
+        writeBytes(sOpeningBracket, N_CHARS(sOpeningBracket));
 
         writeId(Element);
         writeFastAttributeList(Attribs);
 
-        writeBytes(toUnoSequence(maSlashAndClosingBracket));
+        writeBytes(sSlashAndClosingBracket, N_CHARS(sSlashAndClosingBracket));
     }
 
     void SAL_CALL FastSaxSerializer::setOutputStream( const ::com::sun::star::uno::Reference< ::com::sun::star::io::XOutputStream >& xOutputStream )
@@ -213,7 +215,7 @@ namespace sax_fastparser {
         sal_Int32 nAttrLength = aAttrSeq.getLength();
         for (sal_Int32 i = 0; i < nAttrLength; i++)
         {
-            writeBytes(toUnoSequence(maSpace));
+            writeBytes(sSpace, N_CHARS(sSpace));
 
             OUString const& rAttrName(pAttr[i].Name);
 #ifdef DBG_UTIL
@@ -222,9 +224,9 @@ namespace sax_fastparser {
             DebugAttributes.insert(rAttrName);
 #endif
             write(rAttrName);
-            writeBytes(toUnoSequence(maEqualSignAndQuote));
+            writeBytes(sEqualSignAndQuote, N_CHARS(sEqualSignAndQuote));
             write(pAttr[i].Value, true);
-            writeBytes(toUnoSequence(maQuote));
+            writeBytes(sQuote, N_CHARS(sQuote));
         }
 
         Sequence< FastAttribute > aFastAttrSeq = Attribs->getFastAttributes();
@@ -232,7 +234,7 @@ namespace sax_fastparser {
         sal_Int32 nFastAttrLength = aFastAttrSeq.getLength();
         for (sal_Int32 j = 0; j < nFastAttrLength; j++)
         {
-            writeBytes(toUnoSequence(maSpace));
+            writeBytes(sSpace, N_CHARS(sSpace));
 
             sal_Int32 nToken = pFastAttr[j].Token;
             writeId(nToken);
@@ -245,11 +247,11 @@ namespace sax_fastparser {
             DebugAttributes.insert(name);
 #endif
 
-            writeBytes(toUnoSequence(maEqualSignAndQuote));
+            writeBytes(sEqualSignAndQuote, N_CHARS(sEqualSignAndQuote));
 
             write(pFastAttr[j].Value, true);
 
-            writeBytes(toUnoSequence(maQuote));
+            writeBytes(sQuote, N_CHARS(sQuote));
         }
     }
 
@@ -292,24 +294,31 @@ namespace sax_fastparser {
         }
     }
 
-    void FastSaxSerializer::writeBytes( const char* pStr, size_t nLen )
+    void FastSaxSerializer::writeBytes( const Sequence< sal_Int8 >& rData )
         throw ( NotConnectedException, BufferSizeExceededException, IOException, RuntimeException )
     {
-        writeBytes( Sequence< sal_Int8 >(
-            reinterpret_cast<const sal_Int8*>(pStr), nLen) );
+        writeBytes( reinterpret_cast<const char*>(rData.getConstArray()), rData.getLength() );
     }
 
-    void FastSaxSerializer::writeBytes( const Sequence< ::sal_Int8 >& aData ) throw ( NotConnectedException, BufferSizeExceededException, IOException, RuntimeException )
+    void FastSaxSerializer::writeBytes( const char* pStr, size_t nLen )
+        throw ( NotConnectedException, BufferSizeExceededException, IOException, RuntimeException )
     {
         if ( maMarkStack.empty() )
-            writeOutput( aData );
+            writeOutput( reinterpret_cast<const sal_Int8*>(pStr), nLen );
         else
-            maMarkStack.top()->append( aData );
+            maMarkStack.top()->append( Sequence< sal_Int8 >(
+                reinterpret_cast<const sal_Int8*>(pStr), nLen) );
     }
 
     void FastSaxSerializer::writeOutput( const Sequence< ::sal_Int8 >& aData ) throw ( NotConnectedException, BufferSizeExceededException, IOException, RuntimeException )
     {
-        maOutputStream.writeBytes( aData );
+        writeOutput( aData.getConstArray(), aData.getLength() );
+    }
+
+    void FastSaxSerializer::writeOutput( const sal_Int8* pStr, size_t nLen )
+        throw ( NotConnectedException, BufferSizeExceededException, IOException, RuntimeException )
+    {
+        maOutputStream.writeBytes( pStr, nLen );
         // Write when the sequence gets big enough
         if (maOutputStream.getSize() > 0x10000)
         {
diff --git a/sax/source/tools/fastserializer.hxx b/sax/source/tools/fastserializer.hxx
index bf27abc..b84c1cc 100644
--- a/sax/source/tools/fastserializer.hxx
+++ b/sax/source/tools/fastserializer.hxx
@@ -213,19 +213,12 @@ private:
 #endif
 
     void writeFastAttributeList( const ::com::sun::star::uno::Reference< ::com::sun::star::xml::sax::XFastAttributeList >& Attribs );
+    /// Write to maOutputData and if it's big enough flush that to mxOutputStream
+    void writeOutput( const sal_Int8* pStr, size_t nLen )
+        throw (css::io::NotConnectedException, css::io::BufferSizeExceededException, css::io::IOException, css::uno::RuntimeException);
     void writeOutput( const css::uno::Sequence< ::sal_Int8 >& aData )
         throw (css::io::NotConnectedException, css::io::BufferSizeExceededException, css::io::IOException, css::uno::RuntimeException);
 
-protected:
-    rtl::ByteSequence maClosingBracket;
-    rtl::ByteSequence maSlashAndClosingBracket;
-    rtl::ByteSequence maColon;
-    rtl::ByteSequence maOpeningBracket;
-    rtl::ByteSequence maOpeningBracketAndSlash;
-    rtl::ByteSequence maQuote;
-    rtl::ByteSequence maEqualSignAndQuote;
-    rtl::ByteSequence maSpace;
-
     /** Forward the call to the output stream, or write to the stack.
 
         The latter in the case that we are inside a mark().
commit 15f69ed1845cc520cecd61ce70a62c599aede145
Author: Matúš Kukan <matus.kukan at collabora.com>
Date:   Fri Sep 26 15:08:17 2014 +0200

    FastSerializer: Remove escapeXml() creating OUString(Buffer)
    
    Instead directly write the content.
    
    Change-Id: I7b6db925348b879a013acbd2a76a80d590f721c0

diff --git a/sax/source/tools/fastserializer.cxx b/sax/source/tools/fastserializer.cxx
index 56b27af..300c0d3 100644
--- a/sax/source/tools/fastserializer.cxx
+++ b/sax/source/tools/fastserializer.cxx
@@ -76,39 +76,36 @@ namespace sax_fastparser {
         writeBytes(toUnoSequence(aXmlHeader));
     }
 
-    OUString FastSaxSerializer::escapeXml( const OUString& s )
+    void FastSaxSerializer::write( const OUString& sOutput, bool bEscape )
     {
-        OUStringBuffer sBuf( s.getLength() );
-        const sal_Unicode* pStr = s.getStr();
-        sal_Int32 nLen = s.getLength();
-        for( sal_Int32 i = 0; i < nLen; ++i)
+        write( OUStringToOString(sOutput, RTL_TEXTENCODING_UTF8), bEscape );
+    }
+
+    void FastSaxSerializer::write( const OString& sOutput, bool bEscape )
+    {
+        if (!bEscape)
         {
-            sal_Unicode c = pStr[ i ];
+            writeBytes( sOutput.getStr(), sOutput.getLength() );
+            return;
+        }
+
+        const char* pStr = sOutput.getStr();
+        sal_Int32 nLen = sOutput.getLength();
+        for (sal_Int32 i = 0; i < nLen; ++i)
+        {
+            char c = pStr[ i ];
             switch( c )
             {
-                case '<':   sBuf.appendAscii( "<" );     break;
-                case '>':   sBuf.appendAscii( ">" );     break;
-                case '&':   sBuf.appendAscii( "&" );    break;
-                case '\'':  sBuf.appendAscii( "'" );   break;
-                case '"':   sBuf.appendAscii( """ );   break;
-                case '\n':  sBuf.appendAscii( "
" );    break;
-                case '\r':  sBuf.appendAscii( "
" );    break;
-                default:    sBuf.append( c );               break;
+                case '<':   writeBytes( "<", 4 );     break;
+                case '>':   writeBytes( ">", 4 );     break;
+                case '&':   writeBytes( "&", 5 );    break;
+                case '\'':  writeBytes( "'", 6 );   break;
+                case '"':   writeBytes( """, 6 );   break;
+                case '\n':  writeBytes( "
", 5 );    break;
+                case '\r':  writeBytes( "
", 5 );    break;
+                default:    writeBytes( &c, 1 );          break;
             }
         }
-        return sBuf.makeStringAndClear();
-    }
-
-    void FastSaxSerializer::write( const OUString& sOutput )
-    {
-        write( OUStringToOString(sOutput, RTL_TEXTENCODING_UTF8) );
-    }
-
-    void FastSaxSerializer::write( const OString& sOutput )
-    {
-        writeBytes( Sequence< sal_Int8 >(
-                    reinterpret_cast< const sal_Int8*>( sOutput.getStr() ),
-                    sOutput.getLength() ) );
     }
 
     void SAL_CALL FastSaxSerializer::endDocument(  ) throw (SAXException, RuntimeException)
@@ -226,7 +223,7 @@ namespace sax_fastparser {
 #endif
             write(rAttrName);
             writeBytes(toUnoSequence(maEqualSignAndQuote));
-            write(escapeXml(pAttr[i].Value));
+            write(pAttr[i].Value, true);
             writeBytes(toUnoSequence(maQuote));
         }
 
@@ -250,7 +247,7 @@ namespace sax_fastparser {
 
             writeBytes(toUnoSequence(maEqualSignAndQuote));
 
-            write(escapeXml(pFastAttr[j].Value));
+            write(pFastAttr[j].Value, true);
 
             writeBytes(toUnoSequence(maQuote));
         }
@@ -295,6 +292,13 @@ namespace sax_fastparser {
         }
     }
 
+    void FastSaxSerializer::writeBytes( const char* pStr, size_t nLen )
+        throw ( NotConnectedException, BufferSizeExceededException, IOException, RuntimeException )
+    {
+        writeBytes( Sequence< sal_Int8 >(
+            reinterpret_cast<const sal_Int8*>(pStr), nLen) );
+    }
+
     void FastSaxSerializer::writeBytes( const Sequence< ::sal_Int8 >& aData ) throw ( NotConnectedException, BufferSizeExceededException, IOException, RuntimeException )
     {
         if ( maMarkStack.empty() )
diff --git a/sax/source/tools/fastserializer.hxx b/sax/source/tools/fastserializer.hxx
index d754b98..bf27abc 100644
--- a/sax/source/tools/fastserializer.hxx
+++ b/sax/source/tools/fastserializer.hxx
@@ -110,10 +110,8 @@ public:
     void SAL_CALL writeId( ::sal_Int32 Element );
     OString SAL_CALL getId( ::sal_Int32 Element );
 
-    void write( const OUString& s );
-    void write( const OString& s );
-
-    static OUString escapeXml( const OUString& s );
+    void write( const OUString& s, bool bEscape = false );
+    void write( const OString& s, bool bEscape = false );
 
 public:
     /** From now on, don't write directly to the stream, but to top of a stack.
@@ -233,6 +231,7 @@ protected:
         The latter in the case that we are inside a mark().
      */
     void writeBytes( const ::com::sun::star::uno::Sequence< ::sal_Int8 >& aData ) throw (::com::sun::star::io::NotConnectedException, ::com::sun::star::io::BufferSizeExceededException, ::com::sun::star::io::IOException, ::com::sun::star::uno::RuntimeException);
+    void writeBytes( const char* pStr, size_t nLen ) throw (::com::sun::star::io::NotConnectedException, ::com::sun::star::io::BufferSizeExceededException, ::com::sun::star::io::IOException, ::com::sun::star::uno::RuntimeException);
 };
 
 } // namespace sax_fastparser
diff --git a/sax/source/tools/fshelper.cxx b/sax/source/tools/fshelper.cxx
index cb2c7f7..0e5df28 100644
--- a/sax/source/tools/fshelper.cxx
+++ b/sax/source/tools/fshelper.cxx
@@ -139,12 +139,14 @@ FastSerializerHelper* FastSerializerHelper::write(double value)
 
 FastSerializerHelper* FastSerializerHelper::writeEscaped(const char* value)
 {
-    return writeEscaped(OUString::createFromAscii(value));
+    mpSerializer->write(OString(value), true);
+    return this;
 }
 
 FastSerializerHelper* FastSerializerHelper::writeEscaped(const OUString& value)
 {
-    return write(FastSaxSerializer::escapeXml(value));
+    mpSerializer->write(value, true);
+    return this;
 }
 
 FastSerializerHelper* FastSerializerHelper::writeId(sal_Int32 tokenId)


More information about the Libreoffice-commits mailing list