[PATCH 1/4] Added support for libxslt in xsltfilter

Peter Jentsch pjotr at guineapics.de
Sun Jan 2 05:02:18 PST 2011


libxslt will be used to perform xsl transformations if either Java is
not available/configured at compile time or the 2nd, currently unused
"UserData" parameter of the xslt filter is "libxslt" (w/o the quotes)
---
 filter/source/xsltfilter/LibXSLTTransformer.cxx |  282 +++++++++++++++++++++++
 filter/source/xsltfilter/LibXSLTTransformer.hxx |  145 ++++++++++++
 filter/source/xsltfilter/XSLTFilter.cxx         |  129 +++++++----
 filter/source/xsltfilter/makefile.mk            |   16 ++-
 4 files changed, 526 insertions(+), 46 deletions(-)
 create mode 100644 filter/source/xsltfilter/LibXSLTTransformer.cxx
 create mode 100644 filter/source/xsltfilter/LibXSLTTransformer.hxx

diff --git a/filter/source/xsltfilter/LibXSLTTransformer.cxx b/filter/source/xsltfilter/LibXSLTTransformer.cxx
new file mode 100644
index 0000000..da51908
--- /dev/null
+++ b/filter/source/xsltfilter/LibXSLTTransformer.cxx
@@ -0,0 +1,282 @@
+ /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
+ // MARKER(update_precomp.py): autogen include statement, do not remove
+ #include "precompiled_filter.hxx"
+
+ #include <stdio.h>
+ #include <list>
+ #include <map>
+ #include <iostream>
+ #include <libxml/parser.h>
+ #include <libxml/tree.h>
+ #include <libxml/xmlIO.h>
+ #include <libxslt/transform.h>
+ #include <libxslt/xsltutils.h>
+ #include <libxslt/variables.h>
+
+ #include <cppuhelper/factory.hxx>
+ #include <cppuhelper/servicefactory.hxx>
+ #include <cppuhelper/implbase4.hxx>
+ #include <cppuhelper/implbase.hxx>
+ #include <osl/module.h>
+ #include <osl/file.hxx>
+ #include <osl/process.h>
+ #include <com/sun/star/lang/XComponent.hpp>
+ #include <com/sun/star/lang/XInitialization.hpp>
+ #include <com/sun/star/uno/Any.hxx>
+ #include <com/sun/star/beans/NamedValue.hpp>
+ #include <com/sun/star/io/XInputStream.hpp>
+ #include <com/sun/star/io/XOutputStream.hpp>
+ #include <com/sun/star/io/XActiveDataSource.hpp>
+ #include <com/sun/star/io/XActiveDataSink.hpp>
+ #include <com/sun/star/io/XActiveDataControl.hpp>
+ #include <com/sun/star/io/XStreamListener.hpp>
+
+ #include <LibXSLTTransformer.hxx>
+
+ using namespace ::rtl;
+ using namespace ::cppu;
+ using namespace ::osl;
+ using namespace ::com::sun::star::beans;
+ using namespace ::com::sun::star::io;
+ using namespace ::com::sun::star::uno;
+ using namespace ::com::sun::star::lang;
+ using namespace ::com::sun::star::registry;
+ using ::std::list;
+ using ::std::map;
+ using ::std::pair;
+
+ namespace XSLT {
+     const char* const LibXSLTTransformer::PARAM_SOURCE_URL = "sourceURL";
+     const char* const LibXSLTTransformer::PARAM_SOURCE_BASE_URL = "sourceBaseURL";
+     const char* const LibXSLTTransformer::PARAM_TARGET_URL = "targetURL";
+     const char* const LibXSLTTransformer::PARAM_TARGET_BASE_URL = "targetBaseURL";
+     const char* const LibXSLTTransformer::PARAM_DOCTYPE_SYSTEM = "sytemType";
+     const char* const LibXSLTTransformer::PARAM_DOCTYPE_PUBLIC = "publicType";
+     struct ParserInputBufferCallback {
+         static int on_read(void * context, char * buffer, int len) {
+             Reader * tmp = static_cast<Reader*>(context);
+             return tmp->read(buffer, len);
+         }
+         static int on_close(void * context) {
+             Reader * tmp = static_cast<Reader*>(context);
+             return tmp->closeInput();
+         }
+     };
+     struct ParserOutputBufferCallback {
+         static int on_write(void * context, const char * buffer, int len) {
+             Reader * tmp = static_cast<Reader*>(context);
+             return tmp->write(buffer, len);
+         }
+         static int on_close(void * context) {
+             Reader * tmp = static_cast<Reader*>(context);
+             return tmp->closeOutput();
+         }
+     };
+     Reader::Reader(LibXSLTTransformer* transformer):
+         m_transformer(transformer),
+         m_terminated(false),
+         m_readBuf(INPUT_BUFFER_SIZE),
+         m_writeBuf(OUTPUT_BUFFER_SIZE) {
+         LIBXML_TEST_VERSION;
+     };
+
+     int
+     Reader::read(char * buffer, int len) {
+         //        const char *ptr = (const char *) context;
+         if (buffer == NULL || len < 0) return(-1);
+         sal_Int32 n;
+         Reference<XInputStream> xis = this->m_transformer->getInputStream();
+         n = xis.get()->readBytes(m_readBuf, len);
+         if (n > 0) {
+             memcpy(buffer, m_readBuf.getArray(), n);
+         }
+         return n;
+     }
+     int Reader::write(const char * buffer, int len) {
+         if (buffer == NULL || len < 0) return -1;
+         if (len > 0) {
+             Reference<XOutputStream> xos = m_transformer->getOutputStream();
+             sal_Int32 writeLen = len;
+             sal_Int32 bufLen = ::std::min(writeLen, OUTPUT_BUFFER_SIZE);
+             const sal_uInt8* memPtr = reinterpret_cast< const sal_uInt8* >( buffer );
+             while( writeLen > 0 ) {
+                 sal_Int32 n = ::std::min(writeLen, bufLen);
+                 m_writeBuf.realloc( n );
+                 memcpy( m_writeBuf.getArray(), memPtr, static_cast< size_t >( n ) );
+                 xos.get()->writeBytes(m_writeBuf);
+                 memPtr += n;
+                 writeLen -= n;
+             }
+         }
+         return len;
+     }
+     int Reader::closeInput() {
+         return 0;
+     }
+     int Reader::closeOutput() {
+         Reference<XOutputStream>  xos = m_transformer->getOutputStream();
+         if (xos.is()) {
+             xos.get()->flush();
+             xos.get()->closeOutput();
+         }
+         m_transformer->done();
+         return 0;
+     }
+     void Reader::run() {
+         OSL_ASSERT(m_transformer != NULL);
+         OSL_ASSERT(m_transformer->getInputStream().is());
+         OSL_ASSERT(m_transformer->getOutputStream().is());
+         OSL_ASSERT(m_transformer->getStyleSheetURL());
+         ::std::map<const char*, OString>::iterator pit;
+         ::std::map<const char*, OString> pmap = m_transformer->getParameters();
+         const char* params[pmap.size()*2 + 1]; // build parameters
+         int paramIndex = 0;
+         for (pit = pmap.begin(); pit != pmap.end(); pit++) {
+             params[paramIndex++] = (*pit).first;
+             params[paramIndex++] = (*pit).second.getStr();
+         }
+         params[paramIndex] = NULL;
+         xmlDocPtr doc = xmlReadIO(&ParserInputBufferCallback::on_read,
+                                   &ParserInputBufferCallback::on_close,
+                                   static_cast<void*>(this),
+                                   NULL,
+                                   NULL,
+                                   0);
+         xsltStylesheetPtr styleSheet = xsltParseStylesheetFile((const xmlChar *) m_transformer->getStyleSheetURL().getStr());
+         xmlDocPtr result = NULL;
+         xsltTransformContextPtr tcontext = NULL;
+         if (styleSheet) {
+             tcontext = xsltNewTransformContext(styleSheet, doc);
+             xsltQuoteUserParams(tcontext, params);
+             result = xsltApplyStylesheetUser(styleSheet, doc, 0, 0, 0, tcontext);
+         }
+         if (result) {
+             xmlCharEncodingHandlerPtr encoder = xmlGetCharEncodingHandler(XML_CHAR_ENCODING_UTF8);
+             xmlOutputBufferPtr outBuf = xmlAllocOutputBuffer(encoder);
+             outBuf->context = static_cast<void *>(this);
+             outBuf->writecallback = &ParserOutputBufferCallback::on_write;
+             outBuf->closecallback = &ParserOutputBufferCallback::on_close;
+             xsltSaveResultTo(outBuf, result, styleSheet);
+         } else {
+             xmlErrorPtr lastErr = xmlGetLastError();
+             OUString msg;
+             if (lastErr) {
+                 msg = OUString::createFromAscii(lastErr->message);
+             } else {
+                 msg = OUString::createFromAscii("Unknown XSLT transformation error");
+             }
+             m_transformer->error(msg);
+         }
+         closeOutput();
+         xsltFreeStylesheet(styleSheet);
+         xsltFreeTransformContext(tcontext);
+         xmlFreeDoc(doc);
+         xmlFreeDoc(result);
+     };
+     void Reader::onTerminated() {
+         m_terminated = true;
+     };
+     Reader::~Reader() {}
+     LibXSLTTransformer::LibXSLTTransformer( const Reference< XMultiServiceFactory > &r )
+         : m_rServiceFactory(r) {
+     }
+     void LibXSLTTransformer::setInputStream(const Reference<XInputStream>& inputStream)
+         throw (RuntimeException) {
+         m_rInputStream = inputStream;
+     }
+     Reference<XInputStream> LibXSLTTransformer::getInputStream()
+         throw (RuntimeException) {
+         return m_rInputStream;
+     }
+     void LibXSLTTransformer::setOutputStream(const Reference<XOutputStream>& outputStream)
+         throw (RuntimeException) {
+         m_rOutputStream = outputStream;
+     }
+     Reference<XOutputStream> LibXSLTTransformer::getOutputStream()
+         throw (RuntimeException) {
+         return m_rOutputStream;
+     }
+     void LibXSLTTransformer::addListener(const Reference<XStreamListener>& listener)
+         throw (RuntimeException) {
+         m_listeners.insert(m_listeners.begin(), listener);
+     }
+     void LibXSLTTransformer::removeListener(const Reference<XStreamListener>& listener)
+         throw (RuntimeException) {
+         m_listeners.remove(listener);
+     }
+     void LibXSLTTransformer::start()
+         throw (RuntimeException) {
+         ListenerList::iterator it;
+         for (it=m_listeners.begin(); it != m_listeners.end(); it++) {
+             Reference<XStreamListener> xl = *it;
+             xl.get()->started();
+         }
+         Reader* r = new Reader(this);
+         r->create();
+     }
+
+     void LibXSLTTransformer::error(const OUString& msg) {
+         ListenerList l = m_listeners;
+         Any arg;
+         arg <<= Exception(msg, *this);
+         for (ListenerList::iterator it=l.begin(); it != l.end(); it++) {
+             Reference<XStreamListener> xl = *it;
+             if (xl.is()) {
+                 xl.get()->error(arg);
+             }
+         }
+     }
+     void LibXSLTTransformer::done() {
+         ListenerList l = m_listeners;
+         for (ListenerList::iterator it=l.begin(); it != l.end(); it++) {
+             Reference<XStreamListener> xl = *it;
+             if (xl.is()) {
+                 xl.get()->closed();
+             }
+         }
+     }
+     void LibXSLTTransformer::terminate()
+         throw (RuntimeException) {
+         m_parameters.clear();
+     }
+     void LibXSLTTransformer::initialize(const Sequence<Any>& params)
+         throw (RuntimeException) {
+         xmlSubstituteEntitiesDefault(0);
+         m_parameters.clear();
+         for (int i = 0; i < params.getLength(); i++) {
+             NamedValue nv;
+             params[i] >>= nv;
+             OString nameUTF8 = OUStringToOString(nv.Name, RTL_TEXTENCODING_UTF8);
+             OUString value;
+             OString valueUTF8;
+             if (nv.Value >>= value) {
+                 valueUTF8 = OUStringToOString(value, RTL_TEXTENCODING_UTF8);
+             } else {
+                 // ignore non-string parameters
+                 continue;
+             }
+             if (nameUTF8.equals("StylesheetURL")) {
+                 m_styleSheetURL = valueUTF8;
+             } else if (nameUTF8.equals("SourceURL")) {
+                 m_parameters.insert(pair<const char*, OString>(PARAM_SOURCE_URL, valueUTF8));
+             } else if (nameUTF8.equals("SourceBaseURL")) {
+                 m_parameters.insert(pair<const char*, OString>(PARAM_SOURCE_BASE_URL, valueUTF8));
+             } else if (nameUTF8.equals("TargetURL")) {
+                 m_parameters.insert(pair<const char*, OString>(PARAM_TARGET_URL, valueUTF8));
+             } else if (nameUTF8.equals("TargetBaseURL")) {
+                 m_parameters.insert(pair<const char*, OString>(PARAM_TARGET_BASE_URL, valueUTF8));
+             } else if (nameUTF8.equals("DoctypeSystem")) {
+                 m_parameters.insert(pair<const char*, OString>(PARAM_DOCTYPE_SYSTEM, valueUTF8));
+             } else if (nameUTF8.equals("DoctypePublic")) {
+                 m_parameters.insert(pair<const char*, OString>(PARAM_DOCTYPE_PUBLIC, valueUTF8));
+             }
+         }
+     }
+     const OString LibXSLTTransformer::getStyleSheetURL() {
+         return m_styleSheetURL;
+     }
+     ::std::map<const char*, OString> LibXSLTTransformer::getParameters() {
+         return m_parameters;
+     }
+ }
+ /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
diff --git a/filter/source/xsltfilter/LibXSLTTransformer.hxx b/filter/source/xsltfilter/LibXSLTTransformer.hxx
new file mode 100644
index 0000000..376075e
--- /dev/null
+++ b/filter/source/xsltfilter/LibXSLTTransformer.hxx
@@ -0,0 +1,145 @@
+ /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
+ // MARKER(update_precomp.py): autogen include statement, do not remove
+ #ifndef __LIBXSLTTRANSFORMER_HXX__
+ #define __LIBXSLTTRANSFORMER_HXX__
+ #include "precompiled_filter.hxx"
+
+ #include <stdio.h>
+
+ #include <list>
+ #include <map>
+
+ #include <libxml/parser.h>
+ #include <libxml/tree.h>
+ #include <libxml/xmlIO.h>
+ #include <libxslt/transform.h>
+
+ #include <cppuhelper/factory.hxx>
+ #include <cppuhelper/servicefactory.hxx>
+ #include <cppuhelper/implbase4.hxx>
+ #include <cppuhelper/implbase.hxx>
+
+ #include <osl/thread.hxx>
+
+ #include <com/sun/star/uno/Any.hxx>
+
+ #include <com/sun/star/io/XInputStream.hpp>
+ #include <com/sun/star/io/XOutputStream.hpp>
+ #include <com/sun/star/io/XActiveDataSource.hpp>
+ #include <com/sun/star/io/XActiveDataSink.hpp>
+ #include <com/sun/star/io/XActiveDataControl.hpp>
+ #include <com/sun/star/io/XStreamListener.hpp>
+ #include <com/sun/star/lang/XInitialization.hpp>
+ #include <com/sun/star/beans/NamedValue.hpp>
+
+ #define _INPUT_BUFFER_SIZE 1024
+ #define _OUTPUT_BUFFER_SIZE 1024
+
+ using namespace ::rtl;
+ using namespace ::cppu;
+ using namespace ::osl;
+ using namespace ::com::sun::star::beans;
+ using namespace ::com::sun::star::io;
+ using namespace ::com::sun::star::uno;
+ using namespace ::com::sun::star::lang;
+
+ using ::std::list;
+ using ::std::map;
+
+ namespace XSLT {
+
+
+     class LibXSLTTransformer : public WeakImplHelper4< XActiveDataSink, XActiveDataSource, XActiveDataControl, XInitialization>
+     {
+     private:
+         static const char* const PARAM_SOURCE_URL;
+         static const char* const PARAM_SOURCE_BASE_URL;
+         static const char* const PARAM_TARGET_URL;
+         static const char* const PARAM_TARGET_BASE_URL;
+         static const char* const PARAM_DOCTYPE_SYSTEM;
+         static const char* const PARAM_DOCTYPE_PUBLIC;
+
+         // the UNO ServiceFactory
+         Reference< XMultiServiceFactory > m_rServiceFactory;
+
+         Reference< XInputStream> m_rInputStream;
+
+         Reference < XOutputStream > m_rOutputStream;
+
+         typedef ::std::list<Reference< XStreamListener > > ListenerList;
+
+         ListenerList m_listeners;
+
+         OString m_styleSheetURL;
+
+         ::std::map<const char *, OString> m_parameters;
+
+     public:
+
+         // ctor...
+         LibXSLTTransformer( const Reference< XMultiServiceFactory > &r );
+
+
+
+
+         // XActiveDataSink
+         virtual void SAL_CALL setInputStream(const Reference<XInputStream>& inputStream)
+             throw (RuntimeException);
+         virtual Reference<XInputStream> SAL_CALL getInputStream()
+             throw (RuntimeException);
+         // XActiveDataSource
+         virtual void SAL_CALL setOutputStream(const Reference<XOutputStream>& outputStream)
+             throw (RuntimeException);
+         virtual Reference<XOutputStream> SAL_CALL getOutputStream()
+             throw (RuntimeException);
+         // XActiveDataControl
+         virtual void SAL_CALL addListener(const Reference<XStreamListener>& listener)
+             throw (RuntimeException);
+         virtual void SAL_CALL removeListener(const Reference<XStreamListener>& listener)
+             throw (RuntimeException);
+         virtual void SAL_CALL start()
+             throw (RuntimeException);
+         virtual void SAL_CALL terminate()
+             throw (RuntimeException);
+         virtual void SAL_CALL initialize(const Sequence<Any>& params)
+             throw (RuntimeException);
+
+         void SAL_CALL done();
+
+         void SAL_CALL error(const OUString& msg);
+
+         const OString SAL_CALL getStyleSheetURL();
+
+         ::std::map<const char*, OString> SAL_CALL getParameters();
+
+     };
+
+     class Reader: public osl::Thread
+     {
+     public:
+         Reader(LibXSLTTransformer* transformer);
+         int SAL_CALL read(char * buffer, int len);
+         int SAL_CALL write(const char * buffer, int len);
+         int SAL_CALL closeInput();
+         int SAL_CALL closeOutput();
+
+     protected:
+         virtual ~Reader();
+
+     private:
+         static const sal_Int32 OUTPUT_BUFFER_SIZE = _OUTPUT_BUFFER_SIZE;
+         static const sal_Int32 INPUT_BUFFER_SIZE = _INPUT_BUFFER_SIZE;
+         LibXSLTTransformer* m_transformer;
+         sal_Bool m_terminated;
+         Sequence<sal_Int8> m_readBuf;
+         Sequence<sal_Int8> m_writeBuf;
+         virtual void SAL_CALL run();
+         virtual void SAL_CALL onTerminated();
+     };
+
+ }
+
+
+ #endif // __LIBXSLTTRANSFORMER_HXX__
+
+ /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
diff --git a/filter/source/xsltfilter/XSLTFilter.cxx b/filter/source/xsltfilter/XSLTFilter.cxx
index b2c2858..2e3f5af 100644
--- a/filter/source/xsltfilter/XSLTFilter.cxx
+++ b/filter/source/xsltfilter/XSLTFilter.cxx
@@ -76,6 +76,13 @@
 
 #include <xmloff/attrlist.hxx>
 #include <fla.hxx>
+#include <LibXSLTTransformer.hxx>
+
+#ifdef SOLAR_JAVA
+#define USE_LIBXSLT_DEFAULT sal_False
+#else
+#define USE_LIBXSLT_DEFAULT sal_True
+#endif
 
 using namespace ::rtl;
 using namespace ::cppu;
@@ -221,6 +228,9 @@ void FLABridge::setDocumentLocator(const Reference<XLocator>& doclocator)
 class XSLTFilter : public WeakImplHelper4< XImportFilter, XExportFilter, XDocumentHandler, XStreamListener>
 {
 private:
+    static const OUString JAXT_HELPER_SERVICE_IMPL;
+    static const OUString LIBXSLT_HELPER_SERVICE_IMPL;
+
     // the UNO ServiceFactory
     Reference< XMultiServiceFactory > m_rServiceFactory;
 
@@ -232,12 +242,12 @@ private:
     sal_Bool m_bPrettyPrint;
 
     Reference< XActiveDataControl > m_tcontrol;
+
     oslCondition  m_cTransformed;
     sal_Bool m_bTerminated;
     sal_Bool m_bError;
 
     OUString m_aExportBaseUrl;
-    OUString m_aOldBaseUrl;
 
     OUString rel2abs(const OUString&);
     OUString expandUrl(const OUString&);
@@ -287,6 +297,9 @@ public:
         throw (SAXException,RuntimeException);
 };
 
+const OUString XSLTFilter::JAXT_HELPER_SERVICE_IMPL = OUString(RTL_CONSTASCII_USTRINGPARAM("com.sun.star.comp.JAXTHelper"));
+const OUString XSLTFilter::LIBXSLT_HELPER_SERVICE_IMPL = OUString(RTL_CONSTASCII_USTRINGPARAM("com.sun.star.comp.documentconversion.LibXSLTTransformer"));
+
 XSLTFilter::XSLTFilter( const Reference< XMultiServiceFactory > &r )
     : m_rServiceFactory(r)
     , m_bPrettyPrint(sal_True)
@@ -411,8 +424,17 @@ sal_Bool XSLTFilter::importer(
     nv.Value <<= OUString(INetURLObject(aURL).getBase());
     args[2] <<= nv;
 
-    m_tcontrol = Reference< XActiveDataControl >(m_rServiceFactory->createInstanceWithArguments(
-        OUString( RTL_CONSTASCII_USTRINGPARAM( "com.sun.star.comp.JAXTHelper" )), args), UNO_QUERY);
+    sal_Bool useLibXSLT = USE_LIBXSLT_DEFAULT;
+    if (!useLibXSLT) {
+        useLibXSLT = msUserData[1].equalsIgnoreAsciiCaseAscii("libxslt");
+    }
+    if (useLibXSLT) {
+        m_tcontrol = Reference< XActiveDataControl >(m_rServiceFactory->createInstanceWithArguments(
+        LIBXSLT_HELPER_SERVICE_IMPL, args), UNO_QUERY);
+    } else {
+        m_tcontrol = Reference< XActiveDataControl >(m_rServiceFactory->createInstanceWithArguments(
+        JAXT_HELPER_SERVICE_IMPL, args), UNO_QUERY);
+    }
 
     OSL_ASSERT(xHandler.is());
     OSL_ASSERT(xInputStream.is());
@@ -538,8 +560,17 @@ sal_Bool XSLTFilter::exporter(
     nv.Value <<= m_aExportBaseUrl;
     args[3] <<= nv;
 
-    m_tcontrol = Reference< XActiveDataControl >(m_rServiceFactory->createInstanceWithArguments(
-        OUString( RTL_CONSTASCII_USTRINGPARAM( "com.sun.star.comp.JAXTHelper" )), args), UNO_QUERY);
+    sal_Bool useLibXSLT = USE_LIBXSLT_DEFAULT;
+    if (!useLibXSLT) {
+        useLibXSLT = msUserData[1].equalsIgnoreAsciiCaseAscii("libxslt");
+    }
+    if (useLibXSLT) {
+        m_tcontrol = Reference< XActiveDataControl >(m_rServiceFactory->createInstanceWithArguments(
+        LIBXSLT_HELPER_SERVICE_IMPL, args), UNO_QUERY);
+    } else {
+        m_tcontrol = Reference< XActiveDataControl >(m_rServiceFactory->createInstanceWithArguments(
+        JAXT_HELPER_SERVICE_IMPL, args), UNO_QUERY);
+    }
 
     OSL_ASSERT(m_rDocumentHandler.is());
     OSL_ASSERT(m_rOutputStream.is());
@@ -647,28 +678,19 @@ void XSLTFilter::setDocumentLocator(const Reference<XLocator>& doclocator)
 // --------------------------------------
 // Component management
 // --------------------------------------
-#define SERVICE_NAME "com.sun.star.documentconversion.XSLTFilter"
-#define IMPLEMENTATION_NAME "com.sun.star.comp.documentconversion.XSLTFilter"
+#define FILTER_SERVICE_NAME "com.sun.star.documentconversion.XSLTFilter"
+#define FILTER_IMPL_NAME "com.sun.star.comp.documentconversion.XSLTFilter"
+#define TRANSFORMER_SERVICE_NAME "com.sun.star.documentconversion.LibXSLTTransformer"
+#define TRANSFORMER_IMPL_NAME "com.sun.star.comp.documentconversion.LibXSLTTransformer"
 
-static Reference< XInterface > SAL_CALL CreateInstance( const Reference< XMultiServiceFactory > &r)
+static Reference< XInterface > SAL_CALL CreateTransformerInstance( const Reference< XMultiServiceFactory > &r)
 {
-    return Reference< XInterface >(( OWeakObject *)new XSLTFilter(r));
+    return Reference< XInterface >(( OWeakObject *)new LibXSLTTransformer(r));
 }
 
-static Sequence< OUString > getSupportedServiceNames()
+static Reference< XInterface > SAL_CALL CreateFilterInstance( const Reference< XMultiServiceFactory > &r)
 {
-    static Sequence < OUString > *pNames = 0;
-    if( ! pNames )
-    {
-        MutexGuard guard( Mutex::getGlobalMutex() );
-        if( !pNames )
-        {
-            static Sequence< OUString > seqNames(1);
-                seqNames.getArray()[0] = OUString(RTL_CONSTASCII_USTRINGPARAM(SERVICE_NAME));
-            pNames = &seqNames;
-        }
-    }
-    return *pNames;
+    return Reference< XInterface >(( OWeakObject *)new XSLTFilter(r));
 }
 
 }
@@ -685,27 +707,26 @@ void SAL_CALL component_getImplementationEnvironment(
 
 sal_Bool SAL_CALL component_writeInfo(void * /* pServiceManager */, void * pRegistryKey )
 {
+    sal_Bool bRetVal = sal_False;
     if (pRegistryKey)
     {
         try
         {
-            Reference< XRegistryKey > xNewKey(
-                reinterpret_cast< XRegistryKey * >( pRegistryKey )->createKey(
-                    OUString( RTL_CONSTASCII_USTRINGPARAM( "/" IMPLEMENTATION_NAME "/UNO/SERVICES" )) ) );
+            Reference< XRegistryKey > pXNewKey( static_cast< XRegistryKey* >( pRegistryKey ) );
+            pXNewKey->createKey( OUString( RTL_CONSTASCII_USTRINGPARAM( "/" FILTER_IMPL_NAME "/UNO/SERVICES/" FILTER_SERVICE_NAME ) ) );
+            bRetVal = sal_True;
 
-            const Sequence< OUString > & rSNL = getSupportedServiceNames();
-            const OUString * pArray = rSNL.getConstArray();
-            for ( sal_Int32 nPos = rSNL.getLength(); nPos--; )
-                xNewKey->createKey( pArray[nPos] );
-
-            return sal_True;
+            pXNewKey=  static_cast< XRegistryKey* >( pRegistryKey );
+            pXNewKey->createKey( OUString( RTL_CONSTASCII_USTRINGPARAM( "/" TRANSFORMER_IMPL_NAME "/UNO/SERVICES/" TRANSFORMER_SERVICE_NAME ) ) );
+            bRetVal = sal_True;
         }
-        catch (InvalidRegistryException &)
+        catch( InvalidRegistryException& )
         {
-            OSL_ENSURE( sal_False, "### InvalidRegistryException!" );
+            OSL_ENSURE(sal_False, "InvalidRegistryException caught");
+            bRetVal = sal_False;
         }
     }
-    return sal_False;
+    return bRetVal;
 }
 
 void * SAL_CALL component_getFactory(
@@ -713,17 +734,37 @@ void * SAL_CALL component_getFactory(
 {
     void * pRet = 0;
 
-    if (pServiceManager && rtl_str_compare( pImplName, IMPLEMENTATION_NAME ) == 0)
-    {
-        Reference< XSingleServiceFactory > xFactory( createSingleFactory(
-            reinterpret_cast< XMultiServiceFactory * >( pServiceManager ),
-            OUString::createFromAscii( pImplName ),
-            CreateInstance, getSupportedServiceNames() ) );
+    if (pServiceManager) {
+        if (rtl_str_compare( pImplName, FILTER_IMPL_NAME ) == 0) {
+            Sequence< OUString > serviceNames( 1 );
+            serviceNames.getArray( )[0] = OUString( RTL_CONSTASCII_USTRINGPARAM( FILTER_SERVICE_NAME ) );
+
+            Reference< XSingleServiceFactory > xFactory(
+                                                        createSingleFactory(
+                                                                            reinterpret_cast< XMultiServiceFactory * >( pServiceManager ),
+                                                                            OUString::createFromAscii( pImplName ),
+                                                                            CreateFilterInstance, serviceNames ) );
+
+            if (xFactory.is())
+                {
+                    xFactory->acquire();
+                    pRet = xFactory.get();
+                }
+        } else if (rtl_str_compare( pImplName, TRANSFORMER_IMPL_NAME ) == 0) {
+            Sequence< OUString > serviceNames( 1 );
+            serviceNames.getArray( )[0] = OUString( RTL_CONSTASCII_USTRINGPARAM( TRANSFORMER_SERVICE_NAME ) );
+            Reference< XSingleServiceFactory > xFactory(
+                                                        createSingleFactory(
+                                                                            reinterpret_cast< XMultiServiceFactory * >( pServiceManager ),
+                                                                            OUString::createFromAscii( pImplName ),
+                                                                            CreateTransformerInstance, serviceNames ) );
+
+            if (xFactory.is())
+                {
+                    xFactory->acquire();
+                    pRet = xFactory.get();
+                }
 
-        if (xFactory.is())
-        {
-            xFactory->acquire();
-            pRet = xFactory.get();
         }
     }
     return pRet;
diff --git a/filter/source/xsltfilter/makefile.mk b/filter/source/xsltfilter/makefile.mk
index a5e2713..ee23cfd 100644
--- a/filter/source/xsltfilter/makefile.mk
+++ b/filter/source/xsltfilter/makefile.mk
@@ -33,9 +33,19 @@ LIBTARGET=NO
 
 # --- Settings -----------------------------------------------------
 CLASSDIR!:=$(CLASSDIR)$/$(TARGET)
+
 .INCLUDE: settings.mk
 
-SLOFILES=$(SLO)$/XSLTFilter.obj $(SLO)$/fla.obj
+.IF "$(SYSTEM_LIBXSLT)" == "YES"
+CFLAGS+= $(LIBXSLT_CFLAGS)
+.ELSE
+LIBXSLTINCDIR=external$/libxslt
+CFLAGS+= -I$(SOLARINCDIR)$/$(LIBXSLTINCDIR)
+.ENDIF
+
+
+
+SLOFILES=$(SLO)$/XSLTFilter.obj $(SLO)$/LibXSLTTransformer.obj $(SLO)$/fla.obj
 LIBNAME=xsltfilter
 SHL1TARGETDEPN=makefile.mk
 SHL1OBJS=$(SLOFILES)
@@ -50,7 +60,9 @@ SHL1STDLIBS= \
     $(CPPUHELPERLIB)    \
     $(CPPULIB)          \
     $(XMLOFFLIB) \
-    $(SALLIB)
+    $(SALLIB) \
+    $(LIBXML2LIB) \
+    $(XSLTLIB)
 
 .IF "$(SOLAR_JAVA)"!=""
 
-- 
1.7.1




More information about the LibreOffice mailing list