package: Better to use temporary files for huge memory zip streams
ZipPackageBuffer was holding the whole compressed data stream in one uno::Sequence which seems to be a lot for big documents in some cases. Change-Id: Ib10d00ac54df9674231f4bbf047fab7e9b0a7d45
This commit is contained in:
@@ -20,6 +20,7 @@
|
|||||||
#define INCLUDED_PACKAGE_INC_ZIPOUTPUTENTRY_HXX
|
#define INCLUDED_PACKAGE_INC_ZIPOUTPUTENTRY_HXX
|
||||||
|
|
||||||
#include <com/sun/star/io/XOutputStream.hpp>
|
#include <com/sun/star/io/XOutputStream.hpp>
|
||||||
|
#include <com/sun/star/io/XTempFile.hpp>
|
||||||
#include <com/sun/star/uno/Reference.hxx>
|
#include <com/sun/star/uno/Reference.hxx>
|
||||||
#include <com/sun/star/uno/XComponentContext.hpp>
|
#include <com/sun/star/uno/XComponentContext.hpp>
|
||||||
#include <com/sun/star/xml/crypto/XCipherContext.hpp>
|
#include <com/sun/star/xml/crypto/XCipherContext.hpp>
|
||||||
@@ -36,7 +37,7 @@ class ZipOutputEntry
|
|||||||
{
|
{
|
||||||
::com::sun::star::uno::Sequence< sal_Int8 > m_aDeflateBuffer;
|
::com::sun::star::uno::Sequence< sal_Int8 > m_aDeflateBuffer;
|
||||||
ZipUtils::Deflater m_aDeflater;
|
ZipUtils::Deflater m_aDeflater;
|
||||||
css::uno::Reference< ZipPackageBuffer > m_pBuffer;
|
css::uno::Reference< css::io::XTempFile > m_xTempFile;
|
||||||
css::uno::Reference< css::io::XOutputStream > m_xOutStream;
|
css::uno::Reference< css::io::XOutputStream > m_xOutStream;
|
||||||
|
|
||||||
::com::sun::star::uno::Reference< ::com::sun::star::xml::crypto::XCipherContext > m_xCipherContext;
|
::com::sun::star::uno::Reference< ::com::sun::star::xml::crypto::XCipherContext > m_xCipherContext;
|
||||||
@@ -56,7 +57,7 @@ public:
|
|||||||
|
|
||||||
~ZipOutputEntry();
|
~ZipOutputEntry();
|
||||||
|
|
||||||
css::uno::Sequence< sal_Int8 > getData();
|
css::uno::Reference< css::io::XInputStream > getData();
|
||||||
ZipEntry* getZipEntry() { return m_pCurrentEntry; }
|
ZipEntry* getZipEntry() { return m_pCurrentEntry; }
|
||||||
ZipPackageStream* getZipPackageStream() { return m_pCurrentStream; }
|
ZipPackageStream* getZipPackageStream() { return m_pCurrentStream; }
|
||||||
bool isEncrypt() { return m_bEncryptCurrentEntry; }
|
bool isEncrypt() { return m_bEncryptCurrentEntry; }
|
||||||
|
@@ -19,6 +19,7 @@
|
|||||||
|
|
||||||
#include <ZipOutputEntry.hxx>
|
#include <ZipOutputEntry.hxx>
|
||||||
|
|
||||||
|
#include <com/sun/star/io/TempFile.hpp>
|
||||||
#include <com/sun/star/packages/zip/ZipConstants.hpp>
|
#include <com/sun/star/packages/zip/ZipConstants.hpp>
|
||||||
#include <comphelper/storagehelper.hxx>
|
#include <comphelper/storagehelper.hxx>
|
||||||
|
|
||||||
@@ -57,8 +58,8 @@ ZipOutputEntry::ZipOutputEntry(
|
|||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
m_pBuffer = new ZipPackageBuffer(n_ConstBufferSize);
|
m_xTempFile = io::TempFile::create(rxContext);
|
||||||
m_xOutStream = m_pBuffer;
|
m_xOutStream = m_xTempFile->getOutputStream();
|
||||||
}
|
}
|
||||||
assert(m_pCurrentEntry->nMethod == DEFLATED && "Use ZipPackageStream::rawWrite() for STORED entries");
|
assert(m_pCurrentEntry->nMethod == DEFLATED && "Use ZipPackageStream::rawWrite() for STORED entries");
|
||||||
if (m_bEncryptCurrentEntry)
|
if (m_bEncryptCurrentEntry)
|
||||||
@@ -72,10 +73,12 @@ ZipOutputEntry::~ZipOutputEntry( void )
|
|||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
uno::Sequence< sal_Int8 > ZipOutputEntry::getData()
|
uno::Reference< io::XInputStream > ZipOutputEntry::getData()
|
||||||
{
|
{
|
||||||
m_pBuffer->realloc(m_pBuffer->getPosition());
|
m_xOutStream->closeOutput();
|
||||||
return m_pBuffer->getSequence();
|
uno::Reference< io::XSeekable > xTempSeek(m_xOutStream, UNO_QUERY_THROW);
|
||||||
|
xTempSeek->seek(0);
|
||||||
|
return m_xTempFile->getInputStream();
|
||||||
}
|
}
|
||||||
|
|
||||||
void ZipOutputEntry::closeEntry()
|
void ZipOutputEntry::closeEntry()
|
||||||
|
@@ -20,6 +20,7 @@
|
|||||||
#include <ZipOutputStream.hxx>
|
#include <ZipOutputStream.hxx>
|
||||||
|
|
||||||
#include <com/sun/star/packages/zip/ZipConstants.hpp>
|
#include <com/sun/star/packages/zip/ZipConstants.hpp>
|
||||||
|
#include <com/sun/star/io/XInputStream.hpp>
|
||||||
#include <com/sun/star/io/XOutputStream.hpp>
|
#include <com/sun/star/io/XOutputStream.hpp>
|
||||||
#include <comphelper/storagehelper.hxx>
|
#include <comphelper/storagehelper.hxx>
|
||||||
#include <osl/diagnose.h>
|
#include <osl/diagnose.h>
|
||||||
@@ -101,7 +102,20 @@ void ZipOutputStream::finish()
|
|||||||
for (size_t i = 0; i < m_aEntries.size(); i++)
|
for (size_t i = 0; i < m_aEntries.size(); i++)
|
||||||
{
|
{
|
||||||
writeLOC(m_aEntries[i]->getZipEntry(), m_aEntries[i]->isEncrypt());
|
writeLOC(m_aEntries[i]->getZipEntry(), m_aEntries[i]->isEncrypt());
|
||||||
rawWrite(m_aEntries[i]->getData());
|
|
||||||
|
sal_Int32 nRead;
|
||||||
|
uno::Sequence< sal_Int8 > aSequence(n_ConstBufferSize);
|
||||||
|
uno::Reference< io::XInputStream > xInput = m_aEntries[i]->getData();
|
||||||
|
do
|
||||||
|
{
|
||||||
|
nRead = xInput->readBytes(aSequence, n_ConstBufferSize);
|
||||||
|
if (nRead < n_ConstBufferSize)
|
||||||
|
aSequence.realloc(nRead);
|
||||||
|
|
||||||
|
rawWrite(aSequence);
|
||||||
|
}
|
||||||
|
while (nRead == n_ConstBufferSize);
|
||||||
|
|
||||||
rawCloseEntry(m_aEntries[i]->isEncrypt());
|
rawCloseEntry(m_aEntries[i]->isEncrypt());
|
||||||
|
|
||||||
m_aEntries[i]->getZipPackageStream()->successfullyWritten(m_aEntries[i]->getZipEntry());
|
m_aEntries[i]->getZipPackageStream()->successfullyWritten(m_aEntries[i]->getZipEntry());
|
||||||
|
Reference in New Issue
Block a user