[Libreoffice-commits] core.git: Branch 'feature/cib_contract3756' - include/oox offapi/com offapi/UnoApi_offapi.mk oox/source oox/util

Vasily Melenchuk (via logerrit) logerrit at kemper.freedesktop.org
Tue Oct 1 07:57:40 UTC 2019


 include/oox/crypto/AgileEngine.hxx                  |   28 ++--
 include/oox/crypto/CryptoEngine.hxx                 |   68 ----------
 include/oox/crypto/DocumentDecryption.hxx           |    5 
 include/oox/crypto/DocumentEncryption.hxx           |    4 
 include/oox/crypto/IRMEngine.hxx                    |   42 ++----
 include/oox/crypto/Standard2007Engine.hxx           |   30 ++--
 offapi/UnoApi_offapi.mk                             |    1 
 offapi/com/sun/star/packages/XPackageEncryption.idl |   84 ++++++++++++
 oox/source/crypto/AgileEngine.cxx                   |   63 ++++++---
 oox/source/crypto/DocumentDecryption.cxx            |   72 +++++-----
 oox/source/crypto/DocumentEncryption.cxx            |   53 ++++---
 oox/source/crypto/IRMEngine.cxx                     |  133 ++++++++++++--------
 oox/source/crypto/Standard2007Engine.cxx            |   61 ++++++---
 oox/util/oox.component                              |   16 ++
 14 files changed, 391 insertions(+), 269 deletions(-)

New commits:
commit 4d0e087cb05e145146b73f6691caa4c8e4c8bb7b
Author:     Vasily Melenchuk <vasily.melenchuk at cib.de>
AuthorDate: Fri Sep 27 11:56:00 2019 +0300
Commit:     Vasily Melenchuk <vasily.melenchuk at cib.de>
CommitDate: Tue Oct 1 10:56:14 2019 +0300

    msdoc crypto: move crypto engines to service
    
    New interface XPackageEncryption was created. All existing
    crypto engines are refactored to be implmentations of this interface.
    
    Change-Id: Id063aca1474f76a926a2e47eecd4c12ebe79650f

diff --git a/include/oox/crypto/AgileEngine.hxx b/include/oox/crypto/AgileEngine.hxx
index 60d19fed11db..3a8b49e21de8 100644
--- a/include/oox/crypto/AgileEngine.hxx
+++ b/include/oox/crypto/AgileEngine.hxx
@@ -15,9 +15,9 @@
 
 #include <oox/dllapi.h>
 #include <oox/crypto/CryptTools.hxx>
-#include <oox/crypto/CryptoEngine.hxx>
 #include <rtl/ustring.hxx>
 #include <sal/types.h>
+#include <com/sun/star/packages/XPackageEncryption.hpp>
 
 namespace oox {
     class BinaryXInputStream;
@@ -74,7 +74,7 @@ enum class AgileEncryptionPreset
     AES_256_SHA512,
 };
 
-class OOX_DLLPUBLIC AgileEngine : public CryptoEngine
+class OOX_DLLPUBLIC AgileEngine : public cppu::WeakImplHelper<css::packages::XPackageEncryption>
 {
 private:
     std::vector<sal_uInt8> mKey;
@@ -82,7 +82,7 @@ private:
     AgileEncryptionPreset meEncryptionPreset;
     css::uno::Reference< css::uno::XComponentContext > mxContext;
 
-    css::uno::Reference<css::io::XInputStream> getStream(css::uno::Sequence<css::beans::NamedValue> & rStreams, const OUString sStreamName);
+    css::uno::Reference<css::io::XInputStream> getStream(const css::uno::Sequence<css::beans::NamedValue> & rStreams, const OUString sStreamName);
 
     void calculateHashFinal(const OUString& rPassword, std::vector<sal_uInt8>& aHashFinal);
 
@@ -131,24 +131,24 @@ public:
 
     // Decryption
 
-    bool generateEncryptionKey(OUString const & rPassword) override;
-    bool readEncryptionInfo(css::uno::Sequence<css::beans::NamedValue> aStreams) override;
-    bool decrypt(BinaryXInputStream& aInputStream,
-                 BinaryXOutputStream& aOutputStream) override;
+    sal_Bool generateEncryptionKey(const OUString & rPassword) override;
+    sal_Bool readEncryptionInfo(const css::uno::Sequence<css::beans::NamedValue>& aStreams) override;
+    sal_Bool decrypt(const css::uno::Reference<css::io::XInputStream>& rxInputStream,
+                 css::uno::Reference<css::io::XOutputStream>& rxOutputStream) override;
 
-    bool checkDataIntegrity() override;
+
+    sal_Bool checkDataIntegrity() override;
 
     // Encryption
 
-    void writeEncryptionInfo(oox::ole::OleStorage& rOleStorage) override;
+    css::uno::Sequence<css::beans::NamedValue> writeEncryptionInfo() override;
 
-    void encrypt(css::uno::Reference<css::io::XInputStream>&  rxInputStream,
-                 css::uno::Reference<css::io::XOutputStream>& rxOutputStream,
-                 sal_uInt32 nSize) override;
+    void encrypt(const css::uno::Reference<css::io::XInputStream>& rxInputStream,
+                 css::uno::Reference<css::io::XOutputStream>& rxOutputStream) override;
 
-    bool setupEncryption(css::uno::Sequence<css::beans::NamedValue>& rMediaEncData) override;
+    sal_Bool setupEncryption(const css::uno::Sequence<css::beans::NamedValue>& rMediaEncData) override;
 
-    virtual void createEncryptionData(comphelper::SequenceAsHashMap & aEncryptionData, const OUString rPassword) override;
+    css::uno::Sequence<css::beans::NamedValue> createEncryptionData(const OUString& rPassword) override;
 };
 
 } // namespace core
diff --git a/include/oox/crypto/CryptoEngine.hxx b/include/oox/crypto/CryptoEngine.hxx
deleted file mode 100644
index f985f2d7fb45..000000000000
--- a/include/oox/crypto/CryptoEngine.hxx
+++ /dev/null
@@ -1,68 +0,0 @@
-/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
-/*
- * This file is part of the LibreOffice project.
- *
- * This Source Code Form is subject to the terms of the Mozilla Public
- * License, v. 2.0. If a copy of the MPL was not distributed with this
- * file, You can obtain one at http://mozilla.org/MPL/2.0/.
- *
- */
-
-#ifndef INCLUDED_OOX_CRYPTO_CRYPTOENGINE_HXX
-#define INCLUDED_OOX_CRYPTO_CRYPTOENGINE_HXX
-
-#include <vector>
-
-#include <rtl/ustring.hxx>
-#include <sal/types.h>
-
-#include <com/sun/star/io/XInputStream.hpp>
-#include <com/sun/star/io/XOutputStream.hpp>
-#include <com/sun/star/uno/Sequence.hxx>
-
-namespace oox {
-    class BinaryXInputStream;
-    class BinaryXOutputStream;
-}
-
-namespace oox {
-namespace core {
-
-class CryptoEngine
-{
-public:
-    CryptoEngine()
-    {}
-
-    virtual ~CryptoEngine()
-    {}
-
-    // Decryption
-    virtual bool readEncryptionInfo(css::uno::Sequence<css::beans::NamedValue> aStreams) = 0;
-
-    virtual bool generateEncryptionKey(const OUString& rPassword) = 0;
-
-    virtual bool decrypt(
-                    BinaryXInputStream& aInputStream,
-                    BinaryXOutputStream& aOutputStream) = 0;
-
-    // Encryption
-    virtual void writeEncryptionInfo(oox::ole::OleStorage& rOleStorage) = 0;
-
-    virtual void createEncryptionData(comphelper::SequenceAsHashMap & aEncryptionData, const OUString rPassword) = 0;
-
-    virtual bool setupEncryption(css::uno::Sequence<css::beans::NamedValue>& rMediaEncData) = 0;
-
-    virtual void encrypt(css::uno::Reference<css::io::XInputStream> & rxInputStream,
-                         css::uno::Reference<css::io::XOutputStream> & rxOutputStream,
-                         sal_uInt32 nSize) = 0;
-
-    virtual bool checkDataIntegrity() = 0;
-};
-
-} // namespace core
-} // namespace oox
-
-#endif
-
-/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
diff --git a/include/oox/crypto/DocumentDecryption.hxx b/include/oox/crypto/DocumentDecryption.hxx
index 248f33f61734..fdea2c25f9f7 100644
--- a/include/oox/crypto/DocumentDecryption.hxx
+++ b/include/oox/crypto/DocumentDecryption.hxx
@@ -17,7 +17,6 @@
 
 #include <com/sun/star/uno/Reference.hxx>
 #include <com/sun/star/uno/Sequence.hxx>
-#include <oox/crypto/CryptoEngine.hxx>
 #include <rtl/ustring.hxx>
 
 namespace com { namespace sun { namespace star {
@@ -25,6 +24,7 @@ namespace com { namespace sun { namespace star {
     namespace io { class XInputStream; }
     namespace io { class XStream; }
     namespace uno { class XComponentContext; }
+    namespace packages { class XPackageEncryption; }
 } } }
 
 namespace oox { namespace ole { class OleStorage; } }
@@ -37,8 +37,7 @@ class OOX_DLLPUBLIC DocumentDecryption
 private:
     oox::ole::OleStorage&                      mrOleStorage;
     css::uno::Sequence<css::beans::NamedValue> maStreamsSequence;
-    std::unique_ptr<CryptoEngine>              mEngine;
-    OUString                                   msEngineName;
+    css::uno::Reference< css::packages::XPackageEncryption > mxPackageEncryption;
     css::uno::Reference< css::uno::XComponentContext > mxContext;
 
     void readStrongEncryptionInfo();
diff --git a/include/oox/crypto/DocumentEncryption.hxx b/include/oox/crypto/DocumentEncryption.hxx
index 9e9c013456ca..d33450a3b791 100644
--- a/include/oox/crypto/DocumentEncryption.hxx
+++ b/include/oox/crypto/DocumentEncryption.hxx
@@ -15,11 +15,11 @@
 
 #include <com/sun/star/uno/Reference.hxx>
 #include <com/sun/star/uno/Sequence.hxx>
-#include <oox/crypto/CryptoEngine.hxx>
 #include <rtl/ustring.hxx>
 
 namespace com { namespace sun { namespace star {
     namespace io { class XStream; }
+    namespace packages { class XPackageEncryption; }
 } } }
 
 namespace oox { namespace ole { class OleStorage; } }
@@ -32,7 +32,7 @@ class OOX_DLLPUBLIC DocumentEncryption
 private:
     css::uno::Reference< css::io::XStream > mxDocumentStream;
     oox::ole::OleStorage& mrOleStorage;
-    std::unique_ptr<CryptoEngine>   mEngine;
+    css::uno::Reference< css::packages::XPackageEncryption > mxPackageEncryption;
     css::uno::Sequence< css::beans::NamedValue >& mMediaEncData;
     css::uno::Reference< css::uno::XComponentContext > mxContext;
 
diff --git a/include/oox/crypto/IRMEngine.hxx b/include/oox/crypto/IRMEngine.hxx
index 9bf610904a9d..c8ae7b125d86 100644
--- a/include/oox/crypto/IRMEngine.hxx
+++ b/include/oox/crypto/IRMEngine.hxx
@@ -12,19 +12,12 @@
 #define INCLUDED_OOX_CRYPTO_IRMENGINE_HXX
 
 #include <oox/dllapi.h>
-#include <oox/crypto/CryptoEngine.hxx>
-#include <filter/msfilter/mscodec.hxx>
+#include <com/sun/star/packages/XPackageEncryption.hpp>
 #include <rtl/ustring.hxx>
 #include <sal/types.h>
 
 namespace oox
 {
-class BinaryXInputStream;
-class BinaryXOutputStream;
-}
-
-namespace oox
-{
 namespace core
 {
 struct OOX_DLLPUBLIC IRMEncryptionInfo
@@ -33,37 +26,40 @@ struct OOX_DLLPUBLIC IRMEncryptionInfo
     bool bCanRead;
 };
 
-class OOX_DLLPUBLIC IRMEngine : public CryptoEngine
+class OOX_DLLPUBLIC IRMEngine : public cppu::WeakImplHelper<css::packages::XPackageEncryption>
 {
     IRMEncryptionInfo mInfo;
     css::uno::Reference<css::uno::XComponentContext> mxContext;
 
     css::uno::Reference<css::io::XInputStream>
-    getStream(css::uno::Sequence<css::beans::NamedValue>& rStreams, const OUString sStreamName);
+    getStream(const css::uno::Sequence<css::beans::NamedValue>& rStreams,
+              const OUString sStreamName);
 
 public:
     IRMEngine(const css::uno::Reference<css::uno::XComponentContext>& rxContext);
 
-    bool readEncryptionInfo(css::uno::Sequence<css::beans::NamedValue> aStreams) override;
+    // Decryption
 
-    virtual bool generateEncryptionKey(OUString const& rPassword) override;
+    sal_Bool generateEncryptionKey(const OUString& rPassword) override;
+    sal_Bool
+    readEncryptionInfo(const css::uno::Sequence<css::beans::NamedValue>& aStreams) override;
+    sal_Bool decrypt(const css::uno::Reference<css::io::XInputStream>& rxInputStream,
+                     css::uno::Reference<css::io::XOutputStream>& rxOutputStream) override;
 
-    virtual bool decrypt(BinaryXInputStream& aInputStream,
-                         BinaryXOutputStream& aOutputStream) override;
+    sal_Bool checkDataIntegrity() override;
 
-    bool checkDataIntegrity() override;
+    // Encryption
 
-    void encrypt(css::uno::Reference<css::io::XInputStream>& rxInputStream,
-                 css::uno::Reference<css::io::XOutputStream>& rxOutputStream,
-                 sal_uInt32 nSize) override;
+    css::uno::Sequence<css::beans::NamedValue> writeEncryptionInfo() override;
 
-    virtual void writeEncryptionInfo(oox::ole::OleStorage& rOleStorage) override;
+    void encrypt(const css::uno::Reference<css::io::XInputStream>& rxInputStream,
+                 css::uno::Reference<css::io::XOutputStream>& rxOutputStream) override;
 
-    virtual void createEncryptionData(comphelper::SequenceAsHashMap& aEncryptionData,
-                                      const OUString rPassword) override;
+    sal_Bool
+    setupEncryption(const css::uno::Sequence<css::beans::NamedValue>& rMediaEncData) override;
 
-    virtual bool
-    setupEncryption(css::uno::Sequence<css::beans::NamedValue>& rMediaEncData) override;
+    css::uno::Sequence<css::beans::NamedValue>
+    createEncryptionData(const OUString& rPassword) override;
 };
 
 } // namespace core
diff --git a/include/oox/crypto/Standard2007Engine.hxx b/include/oox/crypto/Standard2007Engine.hxx
index e0ed99b79e33..d853f4e1a1af 100644
--- a/include/oox/crypto/Standard2007Engine.hxx
+++ b/include/oox/crypto/Standard2007Engine.hxx
@@ -12,7 +12,7 @@
 #define INCLUDED_OOX_CRYPTO_STANDARD2007ENGINE_HXX
 
 #include <oox/dllapi.h>
-#include <oox/crypto/CryptoEngine.hxx>
+#include <com/sun/star/packages/XPackageEncryption.hpp>
 #include <filter/msfilter/mscodec.hxx>
 #include <rtl/ustring.hxx>
 #include <sal/types.h>
@@ -25,7 +25,7 @@ namespace oox {
 namespace oox {
 namespace core {
 
-class OOX_DLLPUBLIC Standard2007Engine : public CryptoEngine
+class OOX_DLLPUBLIC Standard2007Engine : public cppu::WeakImplHelper<css::packages::XPackageEncryption>
 {
     msfilter::StandardEncryptionInfo mInfo;
     std::vector<sal_uInt8> mKey;
@@ -34,31 +34,31 @@ class OOX_DLLPUBLIC Standard2007Engine : public CryptoEngine
     bool generateVerifier();
     bool calculateEncryptionKey(const OUString& rPassword);
 
-    css::uno::Reference<css::io::XInputStream> getStream(css::uno::Sequence<css::beans::NamedValue> & rStreams, const OUString sStreamName);
+    css::uno::Reference<css::io::XInputStream> getStream(const css::uno::Sequence<css::beans::NamedValue> & rStreams, const OUString sStreamName);
 
 public:
     Standard2007Engine(const css::uno::Reference<css::uno::XComponentContext>& rxContext);
 
-    bool readEncryptionInfo(css::uno::Sequence<css::beans::NamedValue> aStreams) override;
+    // Decryption
 
-    virtual bool generateEncryptionKey(OUString const & rPassword) override;
+    sal_Bool generateEncryptionKey(const OUString & rPassword) override;
+    sal_Bool readEncryptionInfo(const css::uno::Sequence<css::beans::NamedValue>& aStreams) override;
+    sal_Bool decrypt(const css::uno::Reference<css::io::XInputStream>& rxInputStream,
+                 css::uno::Reference<css::io::XOutputStream>& rxOutputStream) override;
 
-    virtual bool decrypt(
-                    BinaryXInputStream& aInputStream,
-                    BinaryXOutputStream& aOutputStream) override;
 
-    bool checkDataIntegrity() override;
+    sal_Bool checkDataIntegrity() override;
 
-    void encrypt(css::uno::Reference<css::io::XInputStream>&  rxInputStream,
-                 css::uno::Reference<css::io::XOutputStream>& rxOutputStream,
-                 sal_uInt32 nSize) override;
+    // Encryption
 
-    virtual void writeEncryptionInfo(oox::ole::OleStorage& rOleStorage) override;
+    css::uno::Sequence<css::beans::NamedValue> writeEncryptionInfo() override;
 
-    virtual void createEncryptionData(comphelper::SequenceAsHashMap & aEncryptionData, const OUString rPassword) override;
+    void encrypt(const css::uno::Reference<css::io::XInputStream>& rxInputStream,
+                 css::uno::Reference<css::io::XOutputStream>& rxOutputStream) override;
 
-    virtual bool setupEncryption(css::uno::Sequence<css::beans::NamedValue>& rMediaEncData) override;
+    sal_Bool setupEncryption(const css::uno::Sequence<css::beans::NamedValue>& rMediaEncData) override;
 
+    css::uno::Sequence<css::beans::NamedValue> createEncryptionData(const OUString& rPassword) override;
 };
 
 } // namespace core
diff --git a/offapi/UnoApi_offapi.mk b/offapi/UnoApi_offapi.mk
index 59d7e16772c8..be0d7791d777 100644
--- a/offapi/UnoApi_offapi.mk
+++ b/offapi/UnoApi_offapi.mk
@@ -2928,6 +2928,7 @@ $(eval $(call gb_UnoApi_add_idlfiles,offapi,com/sun/star/packages,\
 	NoRawFormatException \
 	WrongPasswordException \
 	XDataSinkEncrSupport \
+	XPackageEncryption \
 ))
 $(eval $(call gb_UnoApi_add_idlfiles,offapi,com/sun/star/packages/manifest,\
 	XManifestReader \
diff --git a/offapi/com/sun/star/packages/XPackageEncryption.idl b/offapi/com/sun/star/packages/XPackageEncryption.idl
new file mode 100644
index 000000000000..298a089af6c7
--- /dev/null
+++ b/offapi/com/sun/star/packages/XPackageEncryption.idl
@@ -0,0 +1,84 @@
+/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
+/*
+ * This file is part of the LibreOffice project.
+ *
+ * This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
+ *
+ * This file incorporates work covered by the following license notice:
+ *
+ *   Licensed to the Apache Software Foundation (ASF) under one or more
+ *   contributor license agreements. See the NOTICE file distributed
+ *   with this work for additional information regarding copyright
+ *   ownership. The ASF licenses this file to you under the Apache
+ *   License, Version 2.0 (the "License"); you may not use this file
+ *   except in compliance with the License. You may obtain a copy of
+ *   the License at http://www.apache.org/licenses/LICENSE-2.0 .
+ */
+#ifndef __com_sun_star_packages_XPackageEncryption_idl__
+#define __com_sun_star_packages_XPackageEncryption_idl__
+
+#include <com/sun/star/uno/XInterface.idl>
+
+#include <com/sun/star/io/XInputStream.idl>
+#include <com/sun/star/io/XOutputStream.idl>
+
+
+module com {  module sun {  module star {  module packages {
+
+
+/**
+    TODO
+ */
+interface XPackageEncryption: com::sun::star::uno::XInterface
+{
+    /**
+        TODO
+     */
+    boolean readEncryptionInfo([in] sequence < com::sun::star::beans::NamedValue > rOleStreams);
+
+    /**
+        TODO
+     */
+    boolean generateEncryptionKey([in] string rPassword);
+
+    /**
+        TODO
+     */
+    boolean decrypt([in] com::sun::star::io::XInputStream rxInputStream,
+                    [out] com::sun::star::io::XOutputStream rxOutputStream);
+
+    /**
+        TODO
+     */
+    sequence<com::sun::star::beans::NamedValue> writeEncryptionInfo();
+
+    /**
+        TODO
+     */
+    sequence<com::sun::star::beans::NamedValue> createEncryptionData([in] string rPassword);
+
+    /**
+        TODO
+     */
+    boolean setupEncryption([in] sequence<com::sun::star::beans::NamedValue> rMediaEncData);
+
+    /**
+        TODO
+     */
+    void encrypt([in] com::sun::star::io::XInputStream rxInputStream,
+                 [out] com::sun::star::io::XOutputStream rxOutputStream);
+
+    /**
+        TODO
+     */
+    boolean checkDataIntegrity();
+};
+
+
+}; }; }; };
+
+#endif
+
+/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
diff --git a/oox/source/crypto/AgileEngine.cxx b/oox/source/crypto/AgileEngine.cxx
index c3bd6e16378d..35104903d918 100644
--- a/oox/source/crypto/AgileEngine.cxx
+++ b/oox/source/crypto/AgileEngine.cxx
@@ -30,6 +30,7 @@
 #include <com/sun/star/io/XSeekable.hpp>
 #include <com/sun/star/io/XStream.hpp>
 #include <com/sun/star/io/SequenceInputStream.hpp>
+#include <com/sun/star/io/XSequenceOutputStream.hpp>
 #include <com/sun/star/uno/XComponentContext.hpp>
 #include <com/sun/star/xml/sax/XFastParser.hpp>
 #include <com/sun/star/xml/sax/XFastTokenHandler.hpp>
@@ -47,6 +48,14 @@ using namespace css::xml;
 namespace oox {
 namespace core {
 
+extern "C" SAL_DLLPUBLIC_EXPORT uno::XInterface*
+    com_sun_star_comp_oox_crypto_Agile_get_implementation(
+        XComponentContext* pCtx, Sequence<Any> const& /*arguments*/)
+{
+    return cppu::acquire(new AgileEngine(pCtx/*, arguments*/));
+}
+
+
 namespace {
 
 OUString stripNamespacePrefix(OUString const & rsInputName)
@@ -350,7 +359,7 @@ void AgileEngine::decryptEncryptionKey(OUString const & rPassword)
 }
 
 // TODO: Rename
-bool AgileEngine::generateEncryptionKey(OUString const & rPassword)
+sal_Bool AgileEngine::generateEncryptionKey(OUString const & rPassword)
 {
     bool bResult = decryptAndCheckVerifierHash(rPassword);
 
@@ -414,7 +423,7 @@ bool AgileEngine::decryptHmacValue()
     return true;
 }
 
-bool AgileEngine::checkDataIntegrity()
+sal_Bool AgileEngine::checkDataIntegrity()
 {
     bool bResult = (mInfo.hmacHash.size() == mInfo.hmacCalculatedHash.size() &&
                std::equal(mInfo.hmacHash.begin(), mInfo.hmacHash.end(), mInfo.hmacCalculatedHash.begin()));
@@ -422,11 +431,14 @@ bool AgileEngine::checkDataIntegrity()
     return bResult;
 }
 
-bool AgileEngine::decrypt(BinaryXInputStream& aInputStream,
-                          BinaryXOutputStream& aOutputStream)
+sal_Bool AgileEngine::decrypt(const css::uno::Reference<css::io::XInputStream>&  rxInputStream,
+    css::uno::Reference<css::io::XOutputStream>& rxOutputStream)
 {
     CryptoHash aCryptoHash(mInfo.hmacKey, cryptoHashTypeFromString(mInfo.hashAlgorithm));
 
+    BinaryXInputStream aInputStream(rxInputStream, true);
+    BinaryXOutputStream aOutputStream(rxOutputStream, true);
+
     sal_uInt32 totalSize = aInputStream.readuInt32(); // Document unencrypted size - 4 bytes
     // account for size in HMAC
     std::vector<sal_uInt8> aSizeBytes(sizeof(sal_uInt32));
@@ -484,10 +496,12 @@ bool AgileEngine::decrypt(BinaryXInputStream& aInputStream,
 
     mInfo.hmacCalculatedHash = aCryptoHash.finalize();
 
+    rxOutputStream->flush();
+
     return true;
 }
 
-uno::Reference<io::XInputStream> AgileEngine::getStream(Sequence<NamedValue> & rStreams, const OUString sStreamName)
+uno::Reference<io::XInputStream> AgileEngine::getStream(const Sequence<NamedValue> & rStreams, const OUString sStreamName)
 {
     for (const auto & aStream : rStreams)
     {
@@ -502,7 +516,7 @@ uno::Reference<io::XInputStream> AgileEngine::getStream(Sequence<NamedValue> & r
     return nullptr;
 }
 
-bool AgileEngine::readEncryptionInfo(Sequence<NamedValue> aStreams)
+sal_Bool AgileEngine::readEncryptionInfo(const Sequence<NamedValue>& aStreams)
 {
     uno::Reference<io::XInputStream> xEncryptionInfo = getStream(aStreams, "EncryptionInfo");
 
@@ -682,7 +696,7 @@ bool AgileEngine::encryptEncryptionKey(OUString const & rPassword)
     return true;
 }
 
-bool AgileEngine::setupEncryption(css::uno::Sequence<css::beans::NamedValue>& rMediaEncData)
+sal_Bool AgileEngine::setupEncryption(const css::uno::Sequence<css::beans::NamedValue>& rMediaEncData)
 {
     if (meEncryptionPreset == AgileEncryptionPreset::AES_128_SHA1)
         setupEncryptionParameters({ 100000, 16, 128, 20, 16, OUString("AES"), OUString("ChainingModeCBC"), OUString("SHA1") });
@@ -692,7 +706,7 @@ bool AgileEngine::setupEncryption(css::uno::Sequence<css::beans::NamedValue>& rM
     OUString sPassword;
     for (int i = 0; i < rMediaEncData.getLength(); i++)
     {
-        if (rMediaEncData[i].Name == "Password")
+        if (rMediaEncData[i].Name == "OOXPassword")
         {
             OUString sCryptoType;
             rMediaEncData[i].Value >>= sPassword;
@@ -702,9 +716,13 @@ bool AgileEngine::setupEncryption(css::uno::Sequence<css::beans::NamedValue>& rM
     return setupEncryptionKey(sPassword);
 }
 
-void AgileEngine::createEncryptionData(comphelper::SequenceAsHashMap & aEncryptionData, const OUString rPassword)
+uno::Sequence<beans::NamedValue> AgileEngine::createEncryptionData(const OUString & rPassword)
 {
+    comphelper::SequenceAsHashMap aEncryptionData;
     aEncryptionData["OOXPassword"] <<= rPassword;
+    aEncryptionData["CryptoType"] <<= OUString("AgileEngine");
+
+    return aEncryptionData.getAsConstNamedValueList();
 }
 
 void AgileEngine::setupEncryptionParameters(AgileEncryptionParameters const & rAgileEncryptionParameters)
@@ -738,10 +756,12 @@ bool AgileEngine::setupEncryptionKey(OUString const & rPassword)
     return true;
 }
 
-void AgileEngine::writeEncryptionInfo(oox::ole::OleStorage& rOleStorage)
+css::uno::Sequence<css::beans::NamedValue> AgileEngine::writeEncryptionInfo()
 {
-    Reference<XOutputStream> xEncryptionInfo(rOleStorage.openOutputStream("EncryptionInfo"), UNO_SET_THROW);
-    BinaryXOutputStream rStream(xEncryptionInfo, false);
+    Reference<XOutputStream> aEncryptionInfoStream(
+        mxContext->getServiceManager()->createInstanceWithContext("com.sun.star.io.SequenceOutputStream", mxContext),
+        UNO_QUERY);
+    BinaryXOutputStream rStream(aEncryptionInfoStream, false);
 
     rStream.WriteUInt32(msfilter::VERSION_INFO_AGILE);
     rStream.WriteUInt32(msfilter::AGILE_ENCRYPTION_RESERVED);
@@ -798,21 +818,28 @@ void AgileEngine::writeEncryptionInfo(oox::ole::OleStorage& rOleStorage)
     rStream.writeMemory(aMemStream.GetData(), aMemStream.GetSize());
 
     rStream.close();
-    xEncryptionInfo->flush();
-    xEncryptionInfo->closeOutput();
+    aEncryptionInfoStream->flush();
+
+    // Store all streams into sequence and return back
+    comphelper::SequenceAsHashMap aStreams;
+
+    Reference<XSequenceOutputStream> aEncryptionInfoSequenceStream(aEncryptionInfoStream, UNO_QUERY);
+    aStreams["EncryptionInfo"] <<= aEncryptionInfoSequenceStream->getWrittenBytes();
+    return aStreams.getAsConstNamedValueList();
 }
 
-void AgileEngine::encrypt(css::uno::Reference<css::io::XInputStream> &  rxInputStream,
-                          css::uno::Reference<css::io::XOutputStream> & rxOutputStream,
-                          sal_uInt32 nSize)
+void AgileEngine::encrypt(const css::uno::Reference<css::io::XInputStream> &  rxInputStream,
+                          css::uno::Reference<css::io::XOutputStream> & rxOutputStream)
 {
     CryptoHash aCryptoHash(mInfo.hmacKey, cryptoHashTypeFromString(mInfo.hashAlgorithm));
 
     BinaryXOutputStream aBinaryOutputStream(rxOutputStream, false);
     BinaryXInputStream aBinaryInputStream(rxInputStream, false);
+    Reference<XSeekable> xSeekable(rxInputStream, UNO_QUERY);
+    sal_uInt32 nLength = xSeekable->getLength();
 
     std::vector<sal_uInt8> aSizeBytes(sizeof(sal_uInt32));
-    ByteOrderConverter::writeLittleEndian(aSizeBytes.data(), nSize);
+    ByteOrderConverter::writeLittleEndian(aSizeBytes.data(), nLength);
     aBinaryOutputStream.writeMemory(aSizeBytes.data(), aSizeBytes.size()); // size
     aCryptoHash.update(aSizeBytes, aSizeBytes.size());
 
diff --git a/oox/source/crypto/DocumentDecryption.cxx b/oox/source/crypto/DocumentDecryption.cxx
index 7d9427a5bb41..ea3ed1123532 100644
--- a/oox/source/crypto/DocumentDecryption.cxx
+++ b/oox/source/crypto/DocumentDecryption.cxx
@@ -14,14 +14,12 @@
 #include <cppuhelper/implbase.hxx>
 
 #include <com/sun/star/beans/NamedValue.hpp>
+#include <com/sun/star/io/XSeekable.hpp>
 #include <com/sun/star/io/XStream.hpp>
 #include <com/sun/star/uno/XComponentContext.hpp>
-#include <oox/crypto/AgileEngine.hxx>
-#include <oox/crypto/Standard2007Engine.hxx>
-#include <oox/crypto/IRMEngine.hxx>
-#include <oox/helper/binaryinputstream.hxx>
-#include <oox/helper/binaryoutputstream.hxx>
+#include <com/sun/star/packages/XPackageEncryption.hpp>
 #include <oox/ole/olestorage.hxx>
+#include <filter/msfilter/mscodec.hxx>
 
 namespace {
 
@@ -81,8 +79,8 @@ DocumentDecryption::DocumentDecryption(const css::uno::Reference< css::uno::XCom
 
 bool DocumentDecryption::generateEncryptionKey(const OUString& rPassword)
 {
-    if (mEngine)
-        return mEngine->generateEncryptionKey(rPassword);
+    if (mxPackageEncryption.is())
+        return mxPackageEncryption->generateEncryptionKey(rPassword);
     return false;
 }
 
@@ -93,16 +91,20 @@ void DocumentDecryption::readStrongEncryptionInfo()
     BinaryXInputStream aBinaryInputStream(xEncryptionInfo, true);
     sal_uInt32 aVersion = aBinaryInputStream.readuInt32();
 
+    uno::Sequence< uno::Any > aArguments;
+
     switch (aVersion)
     {
     case msfilter::VERSION_INFO_2007_FORMAT:
     case msfilter::VERSION_INFO_2007_FORMAT_SP2:
-        msEngineName = "Standard"; // Set encryption info format
-        mEngine.reset(new Standard2007Engine(mxContext));
+        mxPackageEncryption.set(
+            mxContext->getServiceManager()->createInstanceWithArgumentsAndContext(
+                "com.sun.star.comp.oox.crypto.Standard2007Engine", aArguments, mxContext), css::uno::UNO_QUERY);
         break;
     case msfilter::VERSION_INFO_AGILE:
-        msEngineName = "Agile"; // Set encryption info format
-        mEngine.reset(new AgileEngine(mxContext));
+        mxPackageEncryption.set(
+            mxContext->getServiceManager()->createInstanceWithArgumentsAndContext(
+                "com.sun.star.comp.oox.crypto.AgileEngine", aArguments, mxContext), css::uno::UNO_QUERY);
         break;
     default:
         break;
@@ -146,23 +148,15 @@ bool DocumentDecryption::readEncryptionInfo()
             aDataSpaceStream.skip((4 - (aDataSpaceNameLength & 3)) & 3);  // Skip padding
         }
 
-        if (sDataSpaceName == "DRMEncryptedDataSpace")
-        {
-            msEngineName = "IRM"; // Set encryption info format
-            mEngine.reset(new IRMEngine(mxContext));
-        }
-        else if (sDataSpaceName == "\011DRMDataSpace") // 0x09DRMDataSpace
-        {
-            // TODO: IRM binary file
-        }
-        else if (sDataSpaceName == "StrongEncryptionDataSpace")
+        uno::Sequence< uno::Any > aArguments;
+        mxPackageEncryption.set(
+            mxContext->getServiceManager()->createInstanceWithArgumentsAndContext(
+                "com.sun.star.comp.oox.crypto." + sDataSpaceName, aArguments, mxContext), css::uno::UNO_QUERY);
+
+        if (!mxPackageEncryption.is() && sDataSpaceName == "StrongEncryptionDataSpace")
         {
             readStrongEncryptionInfo();
         }
-        else
-        {
-            SAL_WARN("oox", "Unknown dataspace - document will be not decrypted!");
-        }
     }
     else
     {
@@ -172,20 +166,21 @@ bool DocumentDecryption::readEncryptionInfo()
         readStrongEncryptionInfo();
     }
 
-    if (!mEngine)
+    if (!mxPackageEncryption.is())
+    {
+        // we do not know how to decrypt this document
         return false;
+    }
 
-    return mEngine->readEncryptionInfo(maStreamsSequence);
+    return mxPackageEncryption->readEncryptionInfo(maStreamsSequence);
 }
 
 uno::Sequence<beans::NamedValue> DocumentDecryption::createEncryptionData(const OUString& rPassword)
 {
-    comphelper::SequenceAsHashMap aEncryptionData;
+    if (!mxPackageEncryption.is())
+        return uno::Sequence<beans::NamedValue>();
 
-    aEncryptionData["CryptoType"] <<= msEngineName;
-    mEngine->createEncryptionData(aEncryptionData, rPassword);
-
-    return aEncryptionData.getAsConstNamedValueList();
+    return mxPackageEncryption->createEncryptionData(rPassword);
 }
 
 bool DocumentDecryption::decrypt(const uno::Reference<io::XStream>& xDocumentStream)
@@ -195,21 +190,22 @@ bool DocumentDecryption::decrypt(const uno::Reference<io::XStream>& xDocumentStr
     if (!mrOleStorage.isStorage())
         return false;
 
+    if (!mxPackageEncryption.is())
+        return false;
+
     // open the required input streams in the encrypted package
     uno::Reference<io::XInputStream> xEncryptedPackage = mrOleStorage.openInputStream("EncryptedPackage");
 
     // create temporary file for unencrypted package
     uno::Reference<io::XOutputStream> xDecryptedPackage = xDocumentStream->getOutputStream();
-    BinaryXOutputStream aDecryptedPackage(xDecryptedPackage, true);
-    BinaryXInputStream aEncryptedPackage(xEncryptedPackage, true);
 
-    bResult = mEngine->decrypt(aEncryptedPackage, aDecryptedPackage);
+    bResult = mxPackageEncryption->decrypt(xEncryptedPackage, xDecryptedPackage);
 
-    xDecryptedPackage->flush();
-    aDecryptedPackage.seekToStart();
+    css::uno::Reference<io::XSeekable> xSeekable(xDecryptedPackage, css::uno::UNO_QUERY);
+    xSeekable->seek(0);
 
     if (bResult)
-        return mEngine->checkDataIntegrity();
+        return mxPackageEncryption->checkDataIntegrity();
 
     return bResult;
 }
diff --git a/oox/source/crypto/DocumentEncryption.cxx b/oox/source/crypto/DocumentEncryption.cxx
index 8aac457c67d2..2dba0f035df5 100644
--- a/oox/source/crypto/DocumentEncryption.cxx
+++ b/oox/source/crypto/DocumentEncryption.cxx
@@ -9,16 +9,13 @@
  */
 
 #include <oox/crypto/DocumentEncryption.hxx>
-#include <oox/crypto/Standard2007Engine.hxx>
-#include <oox/crypto/IRMEngine.hxx>
 
 #include <com/sun/star/io/XInputStream.hpp>
 #include <com/sun/star/io/XOutputStream.hpp>
 #include <com/sun/star/io/XStream.hpp>
 #include <com/sun/star/io/XSeekable.hpp>
+#include <com/sun/star/packages/XPackageEncryption.hpp>
 
-#include <oox/helper/binaryinputstream.hxx>
-#include <oox/helper/binaryoutputstream.hxx>
 #include <oox/ole/olestorage.hxx>
 
 namespace oox {
@@ -26,11 +23,12 @@ namespace core {
 
 using namespace css::io;
 using namespace css::uno;
+using namespace css::beans;
 
-DocumentEncryption::DocumentEncryption(const css::uno::Reference< css::uno::XComponentContext >& rxContext,
+DocumentEncryption::DocumentEncryption(const Reference< XComponentContext >& rxContext,
                                        Reference<XStream> const & xDocumentStream,
                                        oox::ole::OleStorage& rOleStorage,
-                                       Sequence<css::beans::NamedValue>& rMediaEncData)
+                                       Sequence<NamedValue>& rMediaEncData)
     : mxContext(rxContext)
     , mxDocumentStream(xDocumentStream)
     , mrOleStorage(rOleStorage)
@@ -43,25 +41,28 @@ DocumentEncryption::DocumentEncryption(const css::uno::Reference< css::uno::XCom
         {
             OUString sCryptoType;
             rMediaEncData[i].Value >>= sCryptoType;
-            if (sCryptoType == "IRM")
-            {
-                mEngine.reset(new IRMEngine(mxContext));
-            }
-            else if (sCryptoType == "Standard" || sCryptoType == "Agile")
-            {
-                mEngine.reset(new Standard2007Engine(mxContext));
-            }
-            else
+
+            if (sCryptoType == "Standard")
+                sCryptoType = "Standard2007Engine";
+
+            Sequence<Any> aArguments;
+            mxPackageEncryption.set(
+                mxContext->getServiceManager()->createInstanceWithArgumentsAndContext(
+                    "com.sun.star.comp.oox.crypto." + sCryptoType, aArguments, mxContext), css::uno::UNO_QUERY);
+
+            if (!mxPackageEncryption.is())
             {
                 SAL_WARN("oox", "Requested encryption method \"" << sCryptoType << "\" is not supported");
             }
+
+            break;
         }
     }
 }
 
 bool DocumentEncryption::encrypt()
 {
-    if (!mEngine)
+    if (!mxPackageEncryption.is())
         return false;
 
     Reference<XInputStream> xInputStream (mxDocumentStream->getInputStream(), UNO_SET_THROW);
@@ -70,20 +71,32 @@ bool DocumentEncryption::encrypt()
     if (!xSeekable.is())
         return false;
 
-    sal_uInt32 aLength = xSeekable->getLength(); // check length of the stream
     xSeekable->seek(0); // seek to begin of the document stream
 
     if (!mrOleStorage.isStorage())
         return false;
 
-    mEngine->setupEncryption(mMediaEncData);
+    mxPackageEncryption->setupEncryption(mMediaEncData);
 
     Reference<XOutputStream> xOutputStream(mrOleStorage.openOutputStream("EncryptedPackage"), UNO_SET_THROW);
-    mEngine->encrypt(xInputStream, xOutputStream, aLength);
+    mxPackageEncryption->encrypt(xInputStream, xOutputStream);
     xOutputStream->flush();
     xOutputStream->closeOutput();
 
-    mEngine->writeEncryptionInfo(mrOleStorage);
+    Sequence<NamedValue> aStreams = mxPackageEncryption->writeEncryptionInfo();
+
+    for (const NamedValue & aStream : aStreams)
+    {
+        Reference<XOutputStream> xOutputStream(mrOleStorage.openOutputStream(aStream.Name), UNO_SET_THROW);
+        BinaryXOutputStream aBinaryOutputStream(xOutputStream, true);
+
+        css::uno::Sequence<sal_Int8> aStreamSequence;
+        aStream.Value >>= aStreamSequence;
+
+        aBinaryOutputStream.writeData(aStreamSequence);
+
+        aBinaryOutputStream.close();
+    }
 
     return true;
 }
diff --git a/oox/source/crypto/IRMEngine.cxx b/oox/source/crypto/IRMEngine.cxx
index 1301a3b51279..95135722ee08 100644
--- a/oox/source/crypto/IRMEngine.cxx
+++ b/oox/source/crypto/IRMEngine.cxx
@@ -30,6 +30,7 @@
 #include <com/sun/star/io/XSeekable.hpp>
 #include <com/sun/star/io/XStream.hpp>
 #include <com/sun/star/io/SequenceInputStream.hpp>
+#include <com/sun/star/io/XSequenceOutputStream.hpp>
 #include <com/sun/star/uno/XComponentContext.hpp>
 #include <com/sun/star/xml/sax/XFastParser.hpp>
 #include <com/sun/star/xml/sax/XFastTokenHandler.hpp>
@@ -50,15 +51,26 @@ namespace oox
 {
 namespace core
 {
+extern "C" SAL_DLLPUBLIC_EXPORT uno::XInterface*
+com_sun_star_comp_oox_crypto_DRMEncryptedDataSpace_get_implementation(
+    XComponentContext* pCtx, Sequence<Any> const& /*arguments*/)
+{
+    return cppu::acquire(new IRMEngine(pCtx /*, arguments*/));
+}
+
 IRMEngine::IRMEngine(const Reference<XComponentContext>& rxContext)
     : mxContext(rxContext)
 {
 }
 
-bool IRMEngine::checkDataIntegrity() { return true; }
+sal_Bool IRMEngine::checkDataIntegrity() { return true; }
 
-bool IRMEngine::decrypt(BinaryXInputStream& aInputStream, BinaryXOutputStream& aOutputStream)
+sal_Bool IRMEngine::decrypt(const Reference<XInputStream>& rxInputStream,
+                            Reference<XOutputStream>& rxOutputStream)
 {
+    BinaryXInputStream aInputStream(rxInputStream, true);
+    BinaryXOutputStream aOutputStream(rxOutputStream, true);
+
     aInputStream.readInt64(); // Skip stream size
 
     HRESULT hr = IpcInitialize();
@@ -66,6 +78,7 @@ bool IRMEngine::decrypt(BinaryXInputStream& aInputStream, BinaryXOutputStream& a
     {
         // ERROR_ALREADY_INITIALIZED not an error
         // TODO: some reaction?
+        return false;
     }
 
     // Get decryption key
@@ -77,6 +90,7 @@ bool IRMEngine::decrypt(BinaryXInputStream& aInputStream, BinaryXOutputStream& a
     if (FAILED(hr))
     {
         // TODO: some reaction?
+        return false;
     }
 
     // Read rights
@@ -85,6 +99,7 @@ bool IRMEngine::decrypt(BinaryXInputStream& aInputStream, BinaryXOutputStream& a
     if (FAILED(hr))
     {
         // TODO: some reaction?
+        return false;
     }
     mInfo.bCanRead = value;
 
@@ -94,6 +109,7 @@ bool IRMEngine::decrypt(BinaryXInputStream& aInputStream, BinaryXOutputStream& a
     if (FAILED(hr))
     {
         // TODO: some reaction?
+        return false;
     }
 
     char* pEncryptedBuffer = new char[*blockSize];
@@ -112,6 +128,7 @@ bool IRMEngine::decrypt(BinaryXInputStream& aInputStream, BinaryXOutputStream& a
         if (FAILED(hr))
         {
             // TODO: some reaction?
+            return false;
         }
 
         aOutputStream.writeArray(pDecryptedBuffer, bytes);
@@ -122,22 +139,26 @@ bool IRMEngine::decrypt(BinaryXInputStream& aInputStream, BinaryXOutputStream& a
     delete[] pEncryptedBuffer;
     delete[] pDecryptedBuffer;
 
+    rxOutputStream->flush();
+
     return true;
 }
 
-void IRMEngine::createEncryptionData(comphelper::SequenceAsHashMap& aEncryptionData,
-                                     const OUString rPassword)
+uno::Sequence<beans::NamedValue> IRMEngine::createEncryptionData(const OUString& /*rPassword*/)
 {
-    aEncryptionData["OOXPassword"] <<= rPassword;
-
     css::uno::Sequence<sal_uInt8> seq;
     seq.realloc(mInfo.license.getLength());
     memcpy(seq.getArray(), mInfo.license.getStr(), mInfo.license.getLength());
 
-    aEncryptionData["license"] <<= seq;
+    comphelper::SequenceAsHashMap aEncryptionData;
+    aEncryptionData["LicenseKey"] <<= seq;
+    aEncryptionData["CryptoType"] <<= OUString("DRMEncryptedDataSpace");
+    aEncryptionData["OOXPassword"] <<= OUString("1");
+
+    return aEncryptionData.getAsConstNamedValueList();
 }
 
-uno::Reference<io::XInputStream> IRMEngine::getStream(Sequence<NamedValue>& rStreams,
+uno::Reference<io::XInputStream> IRMEngine::getStream(const Sequence<NamedValue>& rStreams,
                                                       const OUString sStreamName)
 {
     for (const auto& aStream : rStreams)
@@ -155,7 +176,7 @@ uno::Reference<io::XInputStream> IRMEngine::getStream(Sequence<NamedValue>& rStr
     return nullptr;
 }
 
-bool IRMEngine::readEncryptionInfo(uno::Sequence<beans::NamedValue> aStreams)
+sal_Bool IRMEngine::readEncryptionInfo(const uno::Sequence<beans::NamedValue>& aStreams)
 {
     // Read TransformInfo storage for IRM ECMA documents (MS-OFFCRYPTO 2.2.4)
     uno::Reference<io::XInputStream> xTransformInfoStream
@@ -198,11 +219,11 @@ bool IRMEngine::readEncryptionInfo(uno::Sequence<beans::NamedValue> aStreams)
     return true;
 }
 
-bool IRMEngine::setupEncryption(css::uno::Sequence<css::beans::NamedValue>& rMediaEncData)
+sal_Bool IRMEngine::setupEncryption(const Sequence<NamedValue>& rMediaEncData)
 {
     for (int i = 0; i < rMediaEncData.getLength(); i++)
     {
-        if (rMediaEncData[i].Name == "license")
+        if (rMediaEncData[i].Name == "LicenseKey")
         {
             css::uno::Sequence<sal_uInt8> seq;
             rMediaEncData[i].Value >>= seq;
@@ -213,11 +234,13 @@ bool IRMEngine::setupEncryption(css::uno::Sequence<css::beans::NamedValue>& rMed
     return true;
 }
 
-void IRMEngine::writeEncryptionInfo(oox::ole::OleStorage& rOleStorage)
+Sequence<NamedValue> IRMEngine::writeEncryptionInfo()
 {
     // Write 0x6DataSpaces/DataSpaceMap
     Reference<XOutputStream> xDataSpaceMap(
-        rOleStorage.openOutputStream("\006DataSpaces/DataSpaceMap"), UNO_SET_THROW);
+        mxContext->getServiceManager()->createInstanceWithContext(
+            "com.sun.star.io.SequenceOutputStream", mxContext),
+        UNO_QUERY);
     BinaryXOutputStream aDataSpaceMapStream(xDataSpaceMap, false);
 
     aDataSpaceMapStream.WriteInt32(8); // Header length
@@ -227,42 +250,37 @@ void IRMEngine::writeEncryptionInfo(oox::ole::OleStorage& rOleStorage)
     OUString sDataSpaceName("DRMEncryptedDataSpace");
     OUString sReferenceComponent("EncryptedPackage");
 
-    aDataSpaceMapStream.WriteInt32(0x58); // Length
+    aDataSpaceMapStream.WriteInt32(0x60); // Length
     aDataSpaceMapStream.WriteInt32(1); // References count
     aDataSpaceMapStream.WriteInt32(0); // References component type
 
     aDataSpaceMapStream.WriteInt32(sReferenceComponent.getLength() * 2);
     aDataSpaceMapStream.writeUnicodeArray(sReferenceComponent);
-    while (aDataSpaceMapStream.tell() % 4) // Padding
+    for (int i = 0; i < sReferenceComponent.getLength() * 2 % 4; i++) // Padding
     {
         aDataSpaceMapStream.writeValue<sal_Char>(0);
     }
 
     aDataSpaceMapStream.WriteInt32(sDataSpaceName.getLength() * 2);
     aDataSpaceMapStream.writeUnicodeArray(sDataSpaceName);
-    while (aDataSpaceMapStream.tell() % 4) // Padding
+    for (int i = 0; i < sDataSpaceName.getLength() * 2 % 4; i++) // Padding
     {
         aDataSpaceMapStream.writeValue<sal_Char>(0);
     }
 
-    // Write length
-    sal_uInt32 nLength = aDataSpaceMapStream.tell() - 8;
-    aDataSpaceMapStream.seek(8);
-    aDataSpaceMapStream.WriteInt32(nLength);
-
     aDataSpaceMapStream.close();
     xDataSpaceMap->flush();
-    xDataSpaceMap->closeOutput();
 
     // Write 0x6DataSpaces/Version
-    Reference<XOutputStream> xVersion(rOleStorage.openOutputStream("\006DataSpaces/Version"),
-                                      UNO_SET_THROW);
+    Reference<XOutputStream> xVersion(mxContext->getServiceManager()->createInstanceWithContext(
+                                          "com.sun.star.io.SequenceOutputStream", mxContext),
+                                      UNO_QUERY);
     BinaryXOutputStream aVersionStream(xVersion, false);
 
     OUString sFeatureIdentifier("Microsoft.Container.DataSpaces");
     aVersionStream.WriteInt32(sFeatureIdentifier.getLength() * 2);
     aVersionStream.writeUnicodeArray(sFeatureIdentifier);
-    while (aVersionStream.tell() % 4) // Padding
+    for (int i = 0; i < sFeatureIdentifier.getLength() * 2 % 4; i++) // Padding
     {
         aVersionStream.writeValue<sal_Char>(0);
     }
@@ -273,59 +291,55 @@ void IRMEngine::writeEncryptionInfo(oox::ole::OleStorage& rOleStorage)
 
     aVersionStream.close();
     xVersion->flush();
-    xVersion->closeOutput();
 
     // Write 0x6DataSpaces/DataSpaceInfo/[dataspacename]
-    OUString sStreamName = "\006DataSpaces/DataSpaceInfo/" + sDataSpaceName;
-    Reference<XOutputStream> xDataSpaceInfo(rOleStorage.openOutputStream(sStreamName),
-                                            UNO_SET_THROW);
+    Reference<XOutputStream> xDataSpaceInfo(
+        mxContext->getServiceManager()->createInstanceWithContext(
+            "com.sun.star.io.SequenceOutputStream", mxContext),
+        UNO_QUERY);
     BinaryXOutputStream aDataSpaceInfoStream(xDataSpaceInfo, false);
 
-    aDataSpaceInfoStream.WriteInt32(8); // Header length
+    aDataSpaceInfoStream.WriteInt32(0x08); // Header length
     aDataSpaceInfoStream.WriteInt32(1); // Entries count
 
     OUString sTransformName("DRMEncryptedTransform");
     aDataSpaceInfoStream.WriteInt32(sTransformName.getLength() * 2);
     aDataSpaceInfoStream.writeUnicodeArray(sTransformName);
-    while (aDataSpaceInfoStream.tell() % 4) // Padding
+    for (int i = 0; i < sTransformName.getLength() * 2 % 4; i++) // Padding
     {
         aDataSpaceInfoStream.writeValue<sal_Char>(0);
     }
 
     aDataSpaceInfoStream.close();
     xDataSpaceInfo->flush();
-    xDataSpaceInfo->closeOutput();
 
     // Write 0x6DataSpaces/TransformInfo/[transformname]
-    sStreamName = "\006DataSpaces/TransformInfo/" + sTransformName + "/\006Primary";
-    Reference<XOutputStream> xTransformInfo(rOleStorage.openOutputStream(sStreamName),
-                                            UNO_SET_THROW);
+    Reference<XOutputStream> xTransformInfo(
+        mxContext->getServiceManager()->createInstanceWithContext(
+            "com.sun.star.io.SequenceOutputStream", mxContext),
+        UNO_QUERY);
     BinaryXOutputStream aTransformInfoStream(xTransformInfo, false);
+    OUString sTransformId("{C73DFACD-061F-43B0-8B64-0C620D2A8B50}");
 
     // MS-OFFCRYPTO 2.1.8: TransformInfoHeader
-    aTransformInfoStream.WriteInt32(0); // TransformLength, will be written later
+    sal_uInt32 nLength
+        = sTransformId.getLength() * 2 + ((4 - (sTransformId.getLength() & 3)) & 3) + 10;
+    aTransformInfoStream.WriteInt32(nLength); // TransformLength, will be written later
     aTransformInfoStream.WriteInt32(1); // TransformType
 
     // TransformId
-    OUString sTransformId("{C73DFACD-061F-43B0-8B64-0C620D2A8B50}");
     aTransformInfoStream.WriteInt32(sTransformId.getLength() * 2);
     aTransformInfoStream.writeUnicodeArray(sTransformId);
-    while (aTransformInfoStream.tell() % 4) // Padding
+    for (int i = 0; i < sTransformId.getLength() * 2 % 4; i++) // Padding
     {
         aTransformInfoStream.writeValue<sal_Char>(0);
     }
 
-    // Calculate length and write it into beginning
-    nLength = aTransformInfoStream.tell();
-    aTransformInfoStream.seek(0);
-    aTransformInfoStream.WriteInt32(nLength);
-    aTransformInfoStream.seek(nLength);
-
     // TransformName
     OUString sTransformInfoName("Microsoft.Metadata.DRMTransform");
     aTransformInfoStream.WriteInt32(sTransformInfoName.getLength() * 2);
     aTransformInfoStream.writeUnicodeArray(sTransformInfoName);
-    while (aTransformInfoStream.tell() % 4) // Padding
+    for (int i = 0; i < sTransformInfoName.getLength() * 2 % 4; i++) // Padding
     {
         aTransformInfoStream.writeValue<sal_Char>(0);
     }
@@ -336,19 +350,36 @@ void IRMEngine::writeEncryptionInfo(oox::ole::OleStorage& rOleStorage)
 
     aTransformInfoStream.WriteInt32(4); // Extensibility Header
 
-    aTransformInfoStream.WriteInt32(mInfo.license.getLength() - 3); // LicenseLength
+    aTransformInfoStream.WriteInt32(mInfo.license.getLength() - 3); // LicenseLength - BOM
     aTransformInfoStream.writeArray<sal_Char>(mInfo.license.getStr() + 3,
                                               mInfo.license.getLength() - 3);
     aTransformInfoStream.writeValue<sal_Char>(0);
 
     aTransformInfoStream.close();
     xTransformInfo->flush();
-    xTransformInfo->closeOutput();
+
+    // Store all streams into sequence and return back
+    comphelper::SequenceAsHashMap aStreams;
+
+    Reference<XSequenceOutputStream> xDataSpaceMapSequence(xDataSpaceMap, UNO_QUERY);
+    aStreams["\006DataSpaces/DataSpaceMap"] <<= xDataSpaceMapSequence->getWrittenBytes();
+
+    Reference<XSequenceOutputStream> xVersionSequence(xVersion, UNO_QUERY);
+    aStreams["\006DataSpaces/Version"] <<= xVersionSequence->getWrittenBytes();
+
+    OUString sStreamName = "\006DataSpaces/DataSpaceInfo/" + sDataSpaceName;
+    Reference<XSequenceOutputStream> xDataSpaceInfoSequence(xDataSpaceInfo, UNO_QUERY);
+    aStreams[sStreamName] <<= xDataSpaceInfoSequence->getWrittenBytes();
+
+    sStreamName = "\006DataSpaces/TransformInfo/" + sTransformName + "/\006Primary";
+    Reference<XSequenceOutputStream> xTransformInfoSequence(xTransformInfo, UNO_QUERY);
+    aStreams[sStreamName] <<= xTransformInfoSequence->getWrittenBytes();
+
+    return aStreams.getAsConstNamedValueList();
 }
 
-void IRMEngine::encrypt(css::uno::Reference<css::io::XInputStream>& rxInputStream,
-                        css::uno::Reference<css::io::XOutputStream>& rxOutputStream,
-                        sal_uInt32 /*nSize*/)
+void IRMEngine::encrypt(const Reference<XInputStream>& rxInputStream,
+                        Reference<XOutputStream>& rxOutputStream)
 {
     HRESULT hr = IpcInitialize();
 
@@ -408,7 +439,7 @@ void IRMEngine::encrypt(css::uno::Reference<css::io::XInputStream>& rxInputStrea
     delete[] pDecryptedBuffer;
 }
 
-bool IRMEngine::generateEncryptionKey(const OUString& /*password*/) { return true; }
+sal_Bool IRMEngine::generateEncryptionKey(const OUString& /*password*/) { return true; }
 
 } // namespace core
 } // namespace oox
diff --git a/oox/source/crypto/Standard2007Engine.cxx b/oox/source/crypto/Standard2007Engine.cxx
index b48f6e517758..50f23e2cf491 100644
--- a/oox/source/crypto/Standard2007Engine.cxx
+++ b/oox/source/crypto/Standard2007Engine.cxx
@@ -11,7 +11,9 @@
 #include <oox/crypto/Standard2007Engine.hxx>
 
 #include <com/sun/star/io/XStream.hpp>
+#include <com/sun/star/io/XSeekable.hpp>
 #include <com/sun/star/io/SequenceInputStream.hpp>
+#include <com/sun/star/io/XSequenceOutputStream.hpp>
 #include <oox/crypto/CryptTools.hxx>
 #include <oox/helper/binaryinputstream.hxx>
 #include <oox/helper/binaryoutputstream.hxx>
@@ -27,6 +29,13 @@ using namespace css::uno;
 namespace oox {
 namespace core {
 
+extern "C" SAL_DLLPUBLIC_EXPORT XInterface*
+    com_sun_star_comp_oox_crypto_Standard2007_get_implementation(
+        XComponentContext* pCtx, Sequence<Any> const& /*arguments*/)
+{
+    return cppu::acquire(new Standard2007Engine(pCtx/*, arguments*/));
+}
+
 /* =========================================================================== */
 /*  Kudos to Caolan McNamara who provided the core decryption implementations. */
 /* =========================================================================== */
@@ -129,7 +138,7 @@ bool Standard2007Engine::calculateEncryptionKey(const OUString& rPassword)
     return true;
 }
 
-bool Standard2007Engine::generateEncryptionKey(const OUString& password)
+sal_Bool Standard2007Engine::generateEncryptionKey(const OUString& password)
 {
     mKey.clear();
     /*
@@ -171,9 +180,12 @@ bool Standard2007Engine::generateEncryptionKey(const OUString& password)
     return std::equal(hash.begin(), hash.end(), verifierHash.begin());
 }
 
-bool Standard2007Engine::decrypt(BinaryXInputStream& aInputStream,
-                                 BinaryXOutputStream& aOutputStream)
+sal_Bool Standard2007Engine::decrypt(const css::uno::Reference<css::io::XInputStream>& rxInputStream,
+    css::uno::Reference<css::io::XOutputStream>& rxOutputStream)
 {
+    BinaryXInputStream aInputStream(rxInputStream, true);
+    BinaryXOutputStream aOutputStream(rxOutputStream, true);
+
     sal_uInt32 totalSize = aInputStream.readuInt32(); // Document unencrypted size - 4 bytes
     aInputStream.skip(4); // Reserved 4 Bytes
 
@@ -192,20 +204,27 @@ bool Standard2007Engine::decrypt(BinaryXInputStream& aInputStream,
         aOutputStream.writeMemory(outputBuffer.data(), writeLength);
         remaining -= outputLength;
     }
+
+    rxOutputStream->flush();
+
     return true;
 }
 
-bool Standard2007Engine::checkDataIntegrity()
+sal_Bool Standard2007Engine::checkDataIntegrity()
 {
     return true;
 }
 
-void Standard2007Engine::createEncryptionData(comphelper::SequenceAsHashMap & aEncryptionData, const OUString rPassword)
+css::uno::Sequence<css::beans::NamedValue> Standard2007Engine::createEncryptionData(const OUString& rPassword)
 {
+    comphelper::SequenceAsHashMap aEncryptionData;
     aEncryptionData["OOXPassword"] <<= rPassword;
+    aEncryptionData["CryptoType"] <<= OUString("Standard2007Engine");
+
+    return aEncryptionData.getAsConstNamedValueList();
 }
 
-bool Standard2007Engine::setupEncryption(css::uno::Sequence<css::beans::NamedValue>& rMediaEncData)
+sal_Bool Standard2007Engine::setupEncryption(const css::uno::Sequence<css::beans::NamedValue>& rMediaEncData)
 {
     mInfo.header.flags        = msfilter::ENCRYPTINFO_AES | msfilter::ENCRYPTINFO_CRYPTOAPI;
     mInfo.header.algId        = msfilter::ENCRYPT_ALGO_AES128;
@@ -238,10 +257,12 @@ bool Standard2007Engine::setupEncryption(css::uno::Sequence<css::beans::NamedVal
     return true;
 }
 
-void Standard2007Engine::writeEncryptionInfo(oox::ole::OleStorage& rOleStorage)
+css::uno::Sequence<css::beans::NamedValue> Standard2007Engine::writeEncryptionInfo()
 {
-    Reference<XOutputStream> xEncryptionInfo(rOleStorage.openOutputStream("EncryptionInfo"), UNO_SET_THROW);
-    BinaryXOutputStream rStream(xEncryptionInfo, false);
+    Reference<XOutputStream> aEncryptionInfoStream(
+        mxContext->getServiceManager()->createInstanceWithContext("com.sun.star.io.SequenceOutputStream", mxContext),
+        UNO_QUERY);
+    BinaryXOutputStream rStream(aEncryptionInfoStream, false);
 
     rStream.WriteUInt32(msfilter::VERSION_INFO_2007_FORMAT);
 
@@ -260,21 +281,27 @@ void Standard2007Engine::writeEncryptionInfo(oox::ole::OleStorage& rOleStorage)
     rStream.writeMemory(&mInfo.verifier, sizeof(msfilter::EncryptionVerifierAES));
 
     rStream.close();
-    xEncryptionInfo->flush();
-    xEncryptionInfo->closeOutput();
+    aEncryptionInfoStream->flush();
+
+    // Store all streams into sequence and return back
+    comphelper::SequenceAsHashMap aStreams;
+
+    Reference<XSequenceOutputStream> aEncryptionInfoSequenceStream(aEncryptionInfoStream, UNO_QUERY);
+    aStreams["EncryptionInfo"] <<= aEncryptionInfoSequenceStream->getWrittenBytes();
+    return aStreams.getAsConstNamedValueList();
 }
 
-void Standard2007Engine::encrypt(css::uno::Reference<css::io::XInputStream> &  rxInputStream,
-                                 css::uno::Reference<css::io::XOutputStream> & rxOutputStream,
-                                 sal_uInt32 nSize)
+void Standard2007Engine::encrypt(const css::uno::Reference<css::io::XInputStream> &  rxInputStream,
+                                 css::uno::Reference<css::io::XOutputStream> & rxOutputStream)
 {
     if (mKey.empty())
         return;
 
     BinaryXOutputStream aBinaryOutputStream(rxOutputStream, false);
     BinaryXInputStream aBinaryInputStream(rxInputStream, false);
+    Reference<XSeekable> xSeekable(rxInputStream, UNO_QUERY);
 
-    aBinaryOutputStream.WriteUInt32(nSize); // size
+    aBinaryOutputStream.WriteUInt32(xSeekable->getLength()); // size
     aBinaryOutputStream.WriteUInt32(0U);    // reserved
 
     std::vector<sal_uInt8> inputBuffer(1024);
@@ -296,7 +323,7 @@ void Standard2007Engine::encrypt(css::uno::Reference<css::io::XInputStream> &  r
     }
 }
 
-css::uno::Reference<css::io::XInputStream> Standard2007Engine::getStream(css::uno::Sequence<css::beans::NamedValue> & rStreams, const OUString sStreamName)
+css::uno::Reference<css::io::XInputStream> Standard2007Engine::getStream(const css::uno::Sequence<css::beans::NamedValue> & rStreams, const OUString sStreamName)
 {
     for (const auto & aStream : rStreams)
     {
@@ -311,7 +338,7 @@ css::uno::Reference<css::io::XInputStream> Standard2007Engine::getStream(css::un
     return nullptr;
 }
 
-bool Standard2007Engine::readEncryptionInfo(css::uno::Sequence<css::beans::NamedValue> aStreams)
+sal_Bool Standard2007Engine::readEncryptionInfo(const css::uno::Sequence<css::beans::NamedValue>& aStreams)
 {
     Reference<css::io::XInputStream> rxInputStream = getStream(aStreams, "EncryptionInfo");
     BinaryXInputStream aBinaryStream(rxInputStream, false);
diff --git a/oox/util/oox.component b/oox/util/oox.component
index 32a8100b8fb8..0643a417bfa3 100644
--- a/oox/util/oox.component
+++ b/oox/util/oox.component
@@ -40,4 +40,20 @@
     constructor="com_sun_star_comp_oox_ShapeContextHandler_get_implementation">
     <service name="com.sun.star.xml.sax.FastShapeContextHandler"/>
   </implementation>
+  <implementation name="com.sun.star.comp.oox.crypto.DRMEncryptedDataSpace"
+    constructor="com_sun_star_comp_oox_crypto_DRMEncryptedDataSpace_get_implementation">
+    <service name="com.sun.star.packages.XPackageEncryption"/>
+  </implementation>
+  <implementation name="com.sun.star.comp.oox.crypto.DRMDataSpace"
+    constructor="com_sun_star_comp_oox_crypto_DRMDataSpace_get_implementation">
+    <service name="com.sun.star.packages.XPackageEncryption"/>
+  </implementation>
+  <implementation name="com.sun.star.comp.oox.crypto.Standard2007Engine"
+    constructor="com_sun_star_comp_oox_crypto_Standard2007_get_implementation">
+    <service name="com.sun.star.packages.XPackageEncryption"/>
+  </implementation>
+  <implementation name="com.sun.star.comp.oox.crypto.AgileEngine"
+    constructor="com_sun_star_comp_oox_crypto_Agile_get_implementation">
+    <service name="com.sun.star.packages.XPackageEncryption"/>
+  </implementation>
 </component>


More information about the Libreoffice-commits mailing list