15821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/*
25821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * extensions.c: Implemetation of the extensions support
35821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
45821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Reference:
55821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *   http://www.w3.org/TR/1999/REC-xslt-19991116
65821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
75821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * See Copyright for the status of this software.
85821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
95821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * daniel@veillard.com
105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#define IN_LIBXSLT
135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "libxslt.h"
145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include <string.h>
165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include <limits.h>
175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include <libxml/xmlmemory.h>
195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include <libxml/tree.h>
205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include <libxml/hash.h>
215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include <libxml/xmlerror.h>
225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include <libxml/parserInternals.h>
235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include <libxml/xpathInternals.h>
245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#ifdef WITH_MODULES
255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include <libxml/xmlmodule.h>
265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include <libxml/list.h>
285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include <libxml/xmlIO.h>
295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "xslt.h"
305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "xsltInternals.h"
315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "xsltutils.h"
325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "imports.h"
335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "extensions.h"
345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#ifdef _WIN32
365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include <stdlib.h>             /* for _MAX_PATH */
375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#ifndef PATH_MAX
385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#define PATH_MAX _MAX_PATH
395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#ifdef WITH_XSLT_DEBUG
435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#define WITH_XSLT_DEBUG_EXTENSIONS
445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/************************************************************************
475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * 									*
485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * 			Private Types and Globals			*
495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * 									*
505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ************************************************************************/
515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)typedef struct _xsltExtDef xsltExtDef;
535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)typedef xsltExtDef *xsltExtDefPtr;
545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)struct _xsltExtDef {
555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    struct _xsltExtDef *next;
565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlChar *prefix;
575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlChar *URI;
585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    void *data;
595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)};
605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)typedef struct _xsltExtModule xsltExtModule;
625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)typedef xsltExtModule *xsltExtModulePtr;
635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)struct _xsltExtModule {
645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltExtInitFunction initFunc;
655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltExtShutdownFunction shutdownFunc;
665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltStyleExtInitFunction styleInitFunc;
675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltStyleExtShutdownFunction styleShutdownFunc;
685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)};
695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)typedef struct _xsltExtData xsltExtData;
715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)typedef xsltExtData *xsltExtDataPtr;
725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)struct _xsltExtData {
735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltExtModulePtr extModule;
745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    void *extData;
755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)};
765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)typedef struct _xsltExtElement xsltExtElement;
785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)typedef xsltExtElement *xsltExtElementPtr;
795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)struct _xsltExtElement {
805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltPreComputeFunction precomp;
815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltTransformFunction transform;
825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)};
835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)static xmlHashTablePtr xsltExtensionsHash = NULL;
855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)static xmlHashTablePtr xsltFunctionsHash = NULL;
865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)static xmlHashTablePtr xsltElementsHash = NULL;
875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)static xmlHashTablePtr xsltTopLevelsHash = NULL;
885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)static xmlHashTablePtr xsltModuleHash = NULL;
895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)static xmlMutexPtr xsltExtMutex = NULL;
905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/************************************************************************
925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * 									*
935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * 			Type functions 					*
945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * 									*
955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ************************************************************************/
965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltNewExtDef:
995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @prefix:  the extension prefix
1005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @URI:  the namespace URI
1015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
1025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Create a new XSLT ExtDef
1035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
1045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Returns the newly allocated xsltExtDefPtr or NULL in case of error
1055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
1065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)static xsltExtDefPtr
1075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltNewExtDef(const xmlChar * prefix, const xmlChar * URI)
1085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
1095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltExtDefPtr cur;
1105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    cur = (xsltExtDefPtr) xmlMalloc(sizeof(xsltExtDef));
1125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (cur == NULL) {
1135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xsltTransformError(NULL, NULL, NULL,
1145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                           "xsltNewExtDef : malloc failed\n");
1155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (NULL);
1165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
1175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    memset(cur, 0, sizeof(xsltExtDef));
1185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (prefix != NULL)
1195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        cur->prefix = xmlStrdup(prefix);
1205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (URI != NULL)
1215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        cur->URI = xmlStrdup(URI);
1225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return (cur);
1235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
1245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
1265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltFreeExtDef:
1275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @extensiond:  an XSLT extension definition
1285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
1295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Free up the memory allocated by @extensiond
1305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
1315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)static void
1325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltFreeExtDef(xsltExtDefPtr extensiond)
1335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
1345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (extensiond == NULL)
1355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return;
1365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (extensiond->prefix != NULL)
1375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xmlFree(extensiond->prefix);
1385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (extensiond->URI != NULL)
1395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xmlFree(extensiond->URI);
1405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlFree(extensiond);
1415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
1425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
1445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltFreeExtDefList:
1455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @extensiond:  an XSLT extension definition list
1465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
1475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Free up the memory allocated by all the elements of @extensiond
1485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
1495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)static void
1505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltFreeExtDefList(xsltExtDefPtr extensiond)
1515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
1525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltExtDefPtr cur;
1535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    while (extensiond != NULL) {
1555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        cur = extensiond;
1565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        extensiond = extensiond->next;
1575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xsltFreeExtDef(cur);
1585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
1595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
1605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
1625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltNewExtModule:
1635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @initFunc:  the module initialization function
1645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @shutdownFunc:  the module shutdown function
1655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @styleInitFunc:  the stylesheet module data allocator function
1665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @styleShutdownFunc:  the stylesheet module data free function
1675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
1685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Create a new XSLT extension module
1695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
1705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Returns the newly allocated xsltExtModulePtr or NULL in case of error
1715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
1725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)static xsltExtModulePtr
1735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltNewExtModule(xsltExtInitFunction initFunc,
1745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                 xsltExtShutdownFunction shutdownFunc,
1755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                 xsltStyleExtInitFunction styleInitFunc,
1765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                 xsltStyleExtShutdownFunction styleShutdownFunc)
1775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
1785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltExtModulePtr cur;
1795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    cur = (xsltExtModulePtr) xmlMalloc(sizeof(xsltExtModule));
1815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (cur == NULL) {
1825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xsltTransformError(NULL, NULL, NULL,
1835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                           "xsltNewExtModule : malloc failed\n");
1845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (NULL);
1855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
1865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    cur->initFunc = initFunc;
1875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    cur->shutdownFunc = shutdownFunc;
1885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    cur->styleInitFunc = styleInitFunc;
1895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    cur->styleShutdownFunc = styleShutdownFunc;
1905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return (cur);
1915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
1925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
1945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltFreeExtModule:
1955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @ext:  an XSLT extension module
1965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
1975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Free up the memory allocated by @ext
1985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
1995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)static void
2005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltFreeExtModule(xsltExtModulePtr ext)
2015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
2025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (ext == NULL)
2035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return;
2045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlFree(ext);
2055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
2065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
2085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltNewExtData:
2095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @extModule:  the module
2105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @extData:  the associated data
2115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
2125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Create a new XSLT extension module data wrapper
2135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
2145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Returns the newly allocated xsltExtDataPtr or NULL in case of error
2155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
2165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)static xsltExtDataPtr
2175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltNewExtData(xsltExtModulePtr extModule, void *extData)
2185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
2195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltExtDataPtr cur;
2205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (extModule == NULL)
2225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (NULL);
2235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    cur = (xsltExtDataPtr) xmlMalloc(sizeof(xsltExtData));
2245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (cur == NULL) {
2255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xsltTransformError(NULL, NULL, NULL,
2265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                           "xsltNewExtData : malloc failed\n");
2275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (NULL);
2285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
2295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    cur->extModule = extModule;
2305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    cur->extData = extData;
2315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return (cur);
2325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
2335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
2355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltFreeExtData:
2365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @ext:  an XSLT extension module data wrapper
2375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
2385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Free up the memory allocated by @ext
2395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
2405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)static void
2415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltFreeExtData(xsltExtDataPtr ext)
2425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
2435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (ext == NULL)
2445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return;
2455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlFree(ext);
2465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
2475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
2495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltNewExtElement:
2505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @precomp:  the pre-computation function
2515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @transform:  the transformation function
2525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
2535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Create a new XSLT extension element
2545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
2555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Returns the newly allocated xsltExtElementPtr or NULL in case of
2565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * error
2575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
2585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)static xsltExtElementPtr
2595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltNewExtElement(xsltPreComputeFunction precomp,
2605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                  xsltTransformFunction transform)
2615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
2625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltExtElementPtr cur;
2635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (transform == NULL)
2655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (NULL);
2665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    cur = (xsltExtElementPtr) xmlMalloc(sizeof(xsltExtElement));
2685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (cur == NULL) {
2695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xsltTransformError(NULL, NULL, NULL,
2705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                           "xsltNewExtElement : malloc failed\n");
2715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (NULL);
2725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
2735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    cur->precomp = precomp;
2745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    cur->transform = transform;
2755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return (cur);
2765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
2775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
2795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltFreeExtElement:
2805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @ext: an XSLT extension element
2815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
2825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Frees up the memory allocated by @ext
2835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
2845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)static void
2855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltFreeExtElement(xsltExtElementPtr ext)
2865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
2875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (ext == NULL)
2885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return;
2895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlFree(ext);
2905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
2915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#ifdef WITH_MODULES
2945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)typedef void (*exsltRegisterFunction) (void);
2955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#ifndef PATH_MAX
2975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#define PATH_MAX 4096
2985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
2995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
3015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltExtModuleRegisterDynamic:
3025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @URI:  the function or element namespace URI
3035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
3045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Dynamically loads an extension plugin when available.
3055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
3065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * The plugin name is derived from the URI by removing the
3075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * initial protocol designation, e.g. "http://", then converting
3085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * the characters ".", "-", "/", and "\" into "_", the removing
3095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * any trailing "/", then concatenating LIBXML_MODULE_EXTENSION.
3105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
3115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Plugins are loaded from the directory specified by the
3125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * environment variable LIBXSLT_PLUGINS_PATH, or if NULL,
3135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * by LIBXSLT_DEFAULT_PLUGINS_PATH() which is determined at
3145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * compile time.
3155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
3165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Returns 0 if successful, -1 in case of error.
3175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
3185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)static int
3205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltExtModuleRegisterDynamic(const xmlChar * URI)
3215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
3225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlModulePtr m;
3245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    exsltRegisterFunction regfunc;
3255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlChar *ext_name;
3265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    char module_filename[PATH_MAX];
3275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    const xmlChar *ext_directory = NULL;
3285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    const xmlChar *protocol = NULL;
3295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlChar *i, *regfunc_name;
3305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    void *vregfunc;
3315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    int rc;
3325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    /* check for bad inputs */
3345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (URI == NULL)
3355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (-1);
3365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (NULL == xsltModuleHash) {
3385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xsltModuleHash = xmlHashCreate(5);
3395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        if (xsltModuleHash == NULL)
3405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            return (-1);
3415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
3425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlMutexLock(xsltExtMutex);
3445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    /* have we attempted to register this module already? */
3465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (xmlHashLookup(xsltModuleHash, URI) != NULL) {
3475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xmlMutexUnlock(xsltExtMutex);
3485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (-1);
3495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
3505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlMutexUnlock(xsltExtMutex);
3515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    /* transform extension namespace into a module name */
3535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    protocol = xmlStrstr(URI, BAD_CAST "://");
3545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (protocol == NULL) {
3555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        ext_name = xmlStrdup(URI);
3565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    } else {
3575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        ext_name = xmlStrdup(protocol + 3);
3585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
3595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (ext_name == NULL) {
3605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (-1);
3615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
3625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    i = ext_name;
3645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    while ('\0' != *i) {
3655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        if (('/' == *i) || ('\\' == *i) || ('.' == *i) || ('-' == *i))
3665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            *i = '_';
3675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        i++;
3685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
3695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (*(i - 1) == '_')
3715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        *i = '\0';
3725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    /* determine module directory */
3745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    ext_directory = (xmlChar *) getenv("LIBXSLT_PLUGINS_PATH");
3755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (NULL == ext_directory) {
3775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        ext_directory = BAD_CAST LIBXSLT_DEFAULT_PLUGINS_PATH();
3785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	if (NULL == ext_directory)
3795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	  return (-1);
3805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
3815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#ifdef WITH_XSLT_DEBUG_EXTENSIONS
3825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    else
3835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      xsltGenericDebug(xsltGenericDebugContext,
3845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)		       "LIBXSLT_PLUGINS_PATH is %s\n", ext_directory);
3855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
3865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    /* build the module filename, and confirm the module exists */
3885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlStrPrintf((xmlChar *) module_filename, sizeof(module_filename),
3895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                 BAD_CAST "%s/%s%s",
3905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                 ext_directory, ext_name, LIBXML_MODULE_EXTENSION);
3915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#ifdef WITH_XSLT_DEBUG_EXTENSIONS
3935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltGenericDebug(xsltGenericDebugContext,
3945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                     "Attempting to load plugin: %s for URI: %s\n",
3955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                     module_filename, URI);
3965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
3975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (1 != xmlCheckFilename(module_filename)) {
3995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#ifdef WITH_XSLT_DEBUG_EXTENSIONS
4015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	xsltGenericDebug(xsltGenericDebugContext,
4025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                     "xmlCheckFilename failed for plugin: %s\n", module_filename);
4035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
4045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xmlFree(ext_name);
4065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (-1);
4075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
4085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    /* attempt to open the module */
4105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    m = xmlModuleOpen(module_filename, 0);
4115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (NULL == m) {
4125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#ifdef WITH_XSLT_DEBUG_EXTENSIONS
4145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	xsltGenericDebug(xsltGenericDebugContext,
4155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                     "xmlModuleOpen failed for plugin: %s\n", module_filename);
4165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
4175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xmlFree(ext_name);
4195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (-1);
4205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
4215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    /* construct initialization func name */
4235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    regfunc_name = xmlStrdup(ext_name);
4245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    regfunc_name = xmlStrcat(regfunc_name, BAD_CAST "_init");
4255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    vregfunc = NULL;
4275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    rc = xmlModuleSymbol(m, (const char *) regfunc_name, &vregfunc);
4285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    regfunc = vregfunc;
4295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (0 == rc) {
4305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        /*
4315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	 * Call the module's init function.  Note that this function
4325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	 * calls xsltRegisterExtModuleFull which will add the module
4335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	 * to xsltExtensionsHash (together with it's entry points).
4345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	 */
4355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        (*regfunc) ();
4365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        /* register this module in our hash */
4385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xmlMutexLock(xsltExtMutex);
4395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xmlHashAddEntry(xsltModuleHash, URI, (void *) m);
4405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xmlMutexUnlock(xsltExtMutex);
4415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    } else {
4425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#ifdef WITH_XSLT_DEBUG_EXTENSIONS
4445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	xsltGenericDebug(xsltGenericDebugContext,
4455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                     "xmlModuleSymbol failed for plugin: %s, regfunc: %s\n",
4465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                     module_filename, regfunc_name);
4475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
4485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        /* if regfunc not found unload the module immediately */
4505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xmlModuleClose(m);
4515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
4525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlFree(ext_name);
4545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlFree(regfunc_name);
4555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return (NULL == regfunc) ? -1 : 0;
4565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
4575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#else
4585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)static int
4595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltExtModuleRegisterDynamic(const xmlChar * URI ATTRIBUTE_UNUSED)
4605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
4615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return -1;
4625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
4635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
4645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/************************************************************************
4665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * 									*
4675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * 		The stylesheet extension prefixes handling		*
4685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * 									*
4695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ************************************************************************/
4705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
4735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltFreeExts:
4745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @style: an XSLT stylesheet
4755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
4765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Free up the memory used by XSLT extensions in a stylesheet
4775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
4785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void
4795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltFreeExts(xsltStylesheetPtr style)
4805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
4815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (style->nsDefs != NULL)
4825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xsltFreeExtDefList((xsltExtDefPtr) style->nsDefs);
4835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
4845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
4865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltRegisterExtPrefix:
4875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @style: an XSLT stylesheet
4885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @prefix: the prefix used (optional)
4895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @URI: the URI associated to the extension
4905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
4915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Registers an extension namespace
4925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * This is called from xslt.c during compile-time.
4935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * The given prefix is not needed.
4945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Called by:
4955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *   xsltParseExtElemPrefixes() (new function)
4965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *   xsltRegisterExtPrefix() (old function)
4975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
4985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Returns 0 in case of success, 1 if the @URI was already
4995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *         registered as an extension namespace and
5005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *         -1 in case of failure
5015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
5025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)int
5035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltRegisterExtPrefix(xsltStylesheetPtr style,
5045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                      const xmlChar * prefix, const xmlChar * URI)
5055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
5065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltExtDefPtr def, ret;
5075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if ((style == NULL) || (URI == NULL))
5095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (-1);
5105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#ifdef WITH_XSLT_DEBUG_EXTENSIONS
5125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltGenericDebug(xsltGenericDebugContext,
5135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	"Registering extension namespace '%s'.\n", URI);
5145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
5155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    def = (xsltExtDefPtr) style->nsDefs;
5165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#ifdef XSLT_REFACTORED
5175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    /*
5185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    * The extension is associated with a namespace name.
5195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    */
5205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    while (def != NULL) {
5215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        if (xmlStrEqual(URI, def->URI))
5225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            return (1);
5235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        def = def->next;
5245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
5255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#else
5265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    while (def != NULL) {
5275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        if (xmlStrEqual(prefix, def->prefix))
5285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            return (-1);
5295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        def = def->next;
5305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
5315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
5325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    ret = xsltNewExtDef(prefix, URI);
5335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (ret == NULL)
5345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (-1);
5355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    ret->next = (xsltExtDefPtr) style->nsDefs;
5365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    style->nsDefs = ret;
5375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    /*
5395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)     * check whether there is an extension module with a stylesheet
5405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)     * initialization function.
5415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)     */
5425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#ifdef XSLT_REFACTORED
5435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    /*
5445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    * Don't initialize modules based on specified namespaces via
5455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    * the attribute "[xsl:]extension-element-prefixes".
5465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    */
5475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#else
5485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (xsltExtensionsHash != NULL) {
5495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xsltExtModulePtr module;
5505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xmlMutexLock(xsltExtMutex);
5525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        module = xmlHashLookup(xsltExtensionsHash, URI);
5535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xmlMutexUnlock(xsltExtMutex);
5545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        if (NULL == module) {
5555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            if (!xsltExtModuleRegisterDynamic(URI)) {
5565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                xmlMutexLock(xsltExtMutex);
5575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                module = xmlHashLookup(xsltExtensionsHash, URI);
5585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                xmlMutexUnlock(xsltExtMutex);
5595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            }
5605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        }
5615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        if (module != NULL) {
5625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            xsltStyleGetExtData(style, URI);
5635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        }
5645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
5655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
5665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return (0);
5675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
5685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/************************************************************************
5705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * 									*
5715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * 		The extensions modules interfaces			*
5725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * 									*
5735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ************************************************************************/
5745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
5765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltRegisterExtFunction:
5775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @ctxt: an XSLT transformation context
5785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @name: the name of the element
5795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @URI: the URI associated to the element
5805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @function: the actual implementation which should be called
5815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
5825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Registers an extension function
5835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
5845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Returns 0 in case of success, -1 in case of failure
5855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
5865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)int
5875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltRegisterExtFunction(xsltTransformContextPtr ctxt, const xmlChar * name,
5885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                        const xmlChar * URI, xmlXPathFunction function)
5895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
5905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    int ret;
5915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if ((ctxt == NULL) || (name == NULL) ||
5935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        (URI == NULL) || (function == NULL))
5945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (-1);
5955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (ctxt->xpathCtxt != NULL) {
5965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xmlXPathRegisterFuncNS(ctxt->xpathCtxt, name, URI, function);
5975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
5985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (ctxt->extFunctions == NULL)
5995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        ctxt->extFunctions = xmlHashCreate(10);
6005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (ctxt->extFunctions == NULL)
6015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (-1);
6025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    ret = xmlHashAddEntry2(ctxt->extFunctions, name, URI,
6045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                           XML_CAST_FPTR(function));
6055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return(ret);
6075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
6085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
6105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltRegisterExtElement:
6115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @ctxt: an XSLT transformation context
6125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @name: the name of the element
6135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @URI: the URI associated to the element
6145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @function: the actual implementation which should be called
6155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
6165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Registers an extension element
6175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
6185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Returns 0 in case of success, -1 in case of failure
6195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
6205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)int
6215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltRegisterExtElement(xsltTransformContextPtr ctxt, const xmlChar * name,
6225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                       const xmlChar * URI, xsltTransformFunction function)
6235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
6245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if ((ctxt == NULL) || (name == NULL) ||
6255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        (URI == NULL) || (function == NULL))
6265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (-1);
6275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (ctxt->extElements == NULL)
6285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        ctxt->extElements = xmlHashCreate(10);
6295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (ctxt->extElements == NULL)
6305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (-1);
6315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return (xmlHashAddEntry2
6325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            (ctxt->extElements, name, URI, XML_CAST_FPTR(function)));
6335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
6345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
6365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltFreeCtxtExts:
6375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @ctxt: an XSLT transformation context
6385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
6395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Free the XSLT extension data
6405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
6415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void
6425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltFreeCtxtExts(xsltTransformContextPtr ctxt)
6435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
6445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (ctxt->extElements != NULL)
6455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xmlHashFree(ctxt->extElements, NULL);
6465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (ctxt->extFunctions != NULL)
6475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xmlHashFree(ctxt->extFunctions, NULL);
6485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
6495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
6515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltStyleGetStylesheetExtData:
6525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @style: an XSLT stylesheet
6535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @URI:  the URI associated to the exension module
6545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
6555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Fires the compile-time initialization callback
6565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * of an extension module and returns a container
6575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * holding the user-data (retrieved via the callback).
6585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
6595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Returns the create module-data container
6605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *         or NULL if such a module was not registered.
6615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
6625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)static xsltExtDataPtr
6635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltStyleInitializeStylesheetModule(xsltStylesheetPtr style,
6645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)				     const xmlChar * URI)
6655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
6665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltExtDataPtr dataContainer;
6675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    void *userData = NULL;
6685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltExtModulePtr module;
6695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if ((style == NULL) || (URI == NULL))
6715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	return(NULL);
6725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (xsltExtensionsHash == NULL) {
6745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#ifdef WITH_XSLT_DEBUG_EXTENSIONS
6755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	xsltGenericDebug(xsltGenericDebugContext,
6765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	    "Not registered extension module: %s\n", URI);
6775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
6785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	return(NULL);
6795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
6805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlMutexLock(xsltExtMutex);
6825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    module = xmlHashLookup(xsltExtensionsHash, URI);
6845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlMutexUnlock(xsltExtMutex);
6865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (module == NULL) {
6885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#ifdef WITH_XSLT_DEBUG_EXTENSIONS
6895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	xsltGenericDebug(xsltGenericDebugContext,
6905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	    "Not registered extension module: %s\n", URI);
6915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
6925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	return (NULL);
6935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
6945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    /*
6955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    * The specified module was registered so initialize it.
6965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    */
6975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (style->extInfos == NULL) {
6985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	style->extInfos = xmlHashCreate(10);
6995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	if (style->extInfos == NULL)
7005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	    return (NULL);
7015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
7025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    /*
7035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    * Fire the initialization callback if available.
7045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    */
7055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (module->styleInitFunc == NULL) {
7065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#ifdef WITH_XSLT_DEBUG_EXTENSIONS
7075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	xsltGenericDebug(xsltGenericDebugContext,
7085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	    "Initializing module with *no* callback: %s\n", URI);
7095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
7105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    } else {
7115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#ifdef WITH_XSLT_DEBUG_EXTENSIONS
7125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	xsltGenericDebug(xsltGenericDebugContext,
7135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	    "Initializing module with callback: %s\n", URI);
7145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
7155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	/*
7165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	* Fire the initialization callback.
7175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	*/
7185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	userData = module->styleInitFunc(style, URI);
7195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
7205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    /*
7215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    * Store the user-data in the context of the given stylesheet.
7225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    */
7235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    dataContainer = xsltNewExtData(module, userData);
7245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (dataContainer == NULL)
7255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	return (NULL);
7265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (xmlHashAddEntry(style->extInfos, URI,
7285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	(void *) dataContainer) < 0)
7295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    {
7305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	xsltTransformError(NULL, style, NULL,
7315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	    "Failed to register module '%s'.\n", URI);
7325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	style->errors++;
7335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	if (module->styleShutdownFunc)
7345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	    module->styleShutdownFunc(style, URI, userData);
7355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	xsltFreeExtData(dataContainer);
7365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	return (NULL);
7375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
7385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return(dataContainer);
7405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
7415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
7435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltStyleGetExtData:
7445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @style: an XSLT stylesheet
7455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @URI:  the URI associated to the exension module
7465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
7475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Retrieve the data associated to the extension module
7485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * in this given stylesheet.
7495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Called by:
7505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *   xsltRegisterExtPrefix(),
7515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *   ( xsltExtElementPreCompTest(), xsltExtInitTest )
7525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
7535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Returns the pointer or NULL if not present
7545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
7555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void *
7565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltStyleGetExtData(xsltStylesheetPtr style, const xmlChar * URI)
7575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
7585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltExtDataPtr dataContainer = NULL;
7595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltStylesheetPtr tmpStyle;
7605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if ((style == NULL) || (URI == NULL) ||
7625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	(xsltExtensionsHash == NULL))
7635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	return (NULL);
7645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#ifdef XSLT_REFACTORED
7675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    /*
7685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    * This is intended for global storage, so only the main
7695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    * stylesheet will hold the data.
7705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    */
7715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    tmpStyle = style;
7725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    while (tmpStyle->parent != NULL)
7735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	tmpStyle = tmpStyle->parent;
7745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (tmpStyle->extInfos != NULL) {
7755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	dataContainer =
7765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	    (xsltExtDataPtr) xmlHashLookup(tmpStyle->extInfos, URI);
7775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	if (dataContainer != NULL) {
7785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	    /*
7795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	    * The module was already initialized in the context
7805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	    * of this stylesheet; just return the user-data that
7815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	    * comes with it.
7825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	    */
7835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	    return(dataContainer->extData);
7845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	}
7855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
7865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#else
7875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    /*
7885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    * Old behaviour.
7895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    */
7905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    tmpStyle = style;
7915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    while (tmpStyle != NULL) {
7925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	if (tmpStyle->extInfos != NULL) {
7935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	    dataContainer =
7945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)		(xsltExtDataPtr) xmlHashLookup(tmpStyle->extInfos, URI);
7955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	    if (dataContainer != NULL) {
7965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)		return(dataContainer->extData);
7975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	    }
7985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	}
7995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	tmpStyle = xsltNextImport(tmpStyle);
8005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
8015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    tmpStyle = style;
8025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
8035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
8045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    dataContainer =
8055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xsltStyleInitializeStylesheetModule(tmpStyle, URI);
8065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (dataContainer != NULL)
8075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	return (dataContainer->extData);
8085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return(NULL);
8095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
8105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
8115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#ifdef XSLT_REFACTORED
8125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
8135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltStyleStylesheetLevelGetExtData:
8145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @style: an XSLT stylesheet
8155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @URI:  the URI associated to the exension module
8165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
8175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Retrieve the data associated to the extension module in this given
8185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * stylesheet.
8195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
8205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Returns the pointer or NULL if not present
8215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
8225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void *
8235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltStyleStylesheetLevelGetExtData(xsltStylesheetPtr style,
8245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)				   const xmlChar * URI)
8255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
8265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltExtDataPtr dataContainer = NULL;
8275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
8285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if ((style == NULL) || (URI == NULL) ||
8295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	(xsltExtensionsHash == NULL))
8305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	return (NULL);
8315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
8325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (style->extInfos != NULL) {
8335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	dataContainer = (xsltExtDataPtr) xmlHashLookup(style->extInfos, URI);
8345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	/*
8355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	* The module was already initialized in the context
8365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	* of this stylesheet; just return the user-data that
8375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	* comes with it.
8385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	*/
8395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	if (dataContainer)
8405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	    return(dataContainer->extData);
8415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
8425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
8435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    dataContainer =
8445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xsltStyleInitializeStylesheetModule(style, URI);
8455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (dataContainer != NULL)
8465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	return (dataContainer->extData);
8475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return(NULL);
8485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
8495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
8505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
8515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
8525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltGetExtData:
8535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @ctxt: an XSLT transformation context
8545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @URI:  the URI associated to the exension module
8555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
8565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Retrieve the data associated to the extension module in this given
8575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * transformation.
8585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
8595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Returns the pointer or NULL if not present
8605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
8615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void *
8625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltGetExtData(xsltTransformContextPtr ctxt, const xmlChar * URI)
8635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
8645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltExtDataPtr data;
8655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
8665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if ((ctxt == NULL) || (URI == NULL))
8675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (NULL);
8685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (ctxt->extInfos == NULL) {
8695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        ctxt->extInfos = xmlHashCreate(10);
8705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        if (ctxt->extInfos == NULL)
8715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            return (NULL);
8725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        data = NULL;
8735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    } else {
8745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        data = (xsltExtDataPtr) xmlHashLookup(ctxt->extInfos, URI);
8755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
8765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (data == NULL) {
8775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        void *extData;
8785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xsltExtModulePtr module;
8795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
8805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xmlMutexLock(xsltExtMutex);
8815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
8825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        module = xmlHashLookup(xsltExtensionsHash, URI);
8835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
8845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xmlMutexUnlock(xsltExtMutex);
8855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
8865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        if (module == NULL) {
8875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#ifdef WITH_XSLT_DEBUG_EXTENSIONS
8885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            xsltGenericDebug(xsltGenericDebugContext,
8895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                             "Not registered extension module: %s\n", URI);
8905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
8915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            return (NULL);
8925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        } else {
8935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            if (module->initFunc == NULL)
8945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                return (NULL);
8955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
8965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#ifdef WITH_XSLT_DEBUG_EXTENSIONS
8975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            xsltGenericDebug(xsltGenericDebugContext,
8985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                             "Initializing module: %s\n", URI);
8995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
9005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
9015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            extData = module->initFunc(ctxt, URI);
9025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            if (extData == NULL)
9035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                return (NULL);
9045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
9055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            data = xsltNewExtData(module, extData);
9065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            if (data == NULL)
9075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                return (NULL);
9085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            if (xmlHashAddEntry(ctxt->extInfos, URI, (void *) data) < 0) {
9095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                xsltTransformError(ctxt, NULL, NULL,
9105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                   "Failed to register module data: %s\n",
9115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                   URI);
9125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                if (module->shutdownFunc)
9135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                    module->shutdownFunc(ctxt, URI, extData);
9145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                xsltFreeExtData(data);
9155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                return (NULL);
9165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            }
9175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        }
9185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
9195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return (data->extData);
9205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
9215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
9225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)typedef struct _xsltInitExtCtxt xsltInitExtCtxt;
9235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)struct _xsltInitExtCtxt {
9245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltTransformContextPtr ctxt;
9255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    int ret;
9265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)};
9275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
9285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
9295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltInitCtxtExt:
9305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @styleData:  the registered stylesheet data for the module
9315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @ctxt:  the XSLT transformation context + the return value
9325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @URI:  the extension URI
9335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
9345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Initializes an extension module
9355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
9365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)static void
9375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltInitCtxtExt(xsltExtDataPtr styleData, xsltInitExtCtxt * ctxt,
9385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                const xmlChar * URI)
9395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
9405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltExtModulePtr module;
9415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltExtDataPtr ctxtData;
9425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    void *extData;
9435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
9445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if ((styleData == NULL) || (ctxt == NULL) || (URI == NULL) ||
9455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        (ctxt->ret == -1)) {
9465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#ifdef WITH_XSLT_DEBUG_EXTENSIONS
9475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xsltGenericDebug(xsltGenericDebugContext,
9485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                         "xsltInitCtxtExt: NULL param or error\n");
9495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
9505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return;
9515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
9525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    module = styleData->extModule;
9535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if ((module == NULL) || (module->initFunc == NULL)) {
9545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#ifdef WITH_XSLT_DEBUG_EXTENSIONS
9555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xsltGenericDebug(xsltGenericDebugContext,
9565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                         "xsltInitCtxtExt: no module or no initFunc\n");
9575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
9585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return;
9595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
9605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
9615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    ctxtData = (xsltExtDataPtr) xmlHashLookup(ctxt->ctxt->extInfos, URI);
9625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (ctxtData != NULL) {
9635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#ifdef WITH_XSLT_DEBUG_EXTENSIONS
9645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xsltGenericDebug(xsltGenericDebugContext,
9655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                         "xsltInitCtxtExt: already initialized\n");
9665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
9675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return;
9685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
9695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
9705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    extData = module->initFunc(ctxt->ctxt, URI);
9715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (extData == NULL) {
9725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#ifdef WITH_XSLT_DEBUG_EXTENSIONS
9735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xsltGenericDebug(xsltGenericDebugContext,
9745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                         "xsltInitCtxtExt: no extData\n");
9755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
9765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
9775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    ctxtData = xsltNewExtData(module, extData);
9785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (ctxtData == NULL) {
9795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        ctxt->ret = -1;
9805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return;
9815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
9825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
9835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (ctxt->ctxt->extInfos == NULL)
9845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        ctxt->ctxt->extInfos = xmlHashCreate(10);
9855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (ctxt->ctxt->extInfos == NULL) {
9865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        ctxt->ret = -1;
9875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return;
9885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
9895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
9905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (xmlHashAddEntry(ctxt->ctxt->extInfos, URI, ctxtData) < 0) {
9915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xsltGenericError(xsltGenericErrorContext,
9925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                         "Failed to register module data: %s\n", URI);
9935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        if (module->shutdownFunc)
9945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            module->shutdownFunc(ctxt->ctxt, URI, extData);
9955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xsltFreeExtData(ctxtData);
9965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        ctxt->ret = -1;
9975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return;
9985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
9995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#ifdef WITH_XSLT_DEBUG_EXTENSIONS
10005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltGenericDebug(xsltGenericDebugContext, "Registered module %s\n",
10015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                     URI);
10025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
10035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    ctxt->ret++;
10045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
10055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
10065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
10075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltInitCtxtExts:
10085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @ctxt: an XSLT transformation context
10095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
10105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Initialize the set of modules with registered stylesheet data
10115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
10125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Returns the number of modules initialized or -1 in case of error
10135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
10145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)int
10155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltInitCtxtExts(xsltTransformContextPtr ctxt)
10165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
10175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltStylesheetPtr style;
10185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltInitExtCtxt ctx;
10195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
10205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (ctxt == NULL)
10215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (-1);
10225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
10235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    style = ctxt->style;
10245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (style == NULL)
10255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (-1);
10265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
10275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    ctx.ctxt = ctxt;
10285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    ctx.ret = 0;
10295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
10305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    while (style != NULL) {
10315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        if (style->extInfos != NULL) {
10325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            xmlHashScan(style->extInfos,
10335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                        (xmlHashScanner) xsltInitCtxtExt, &ctx);
10345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            if (ctx.ret == -1)
10355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                return (-1);
10365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        }
10375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        style = xsltNextImport(style);
10385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
10395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#ifdef WITH_XSLT_DEBUG_EXTENSIONS
10405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltGenericDebug(xsltGenericDebugContext, "Registered %d modules\n",
10415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                     ctx.ret);
10425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
10435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return (ctx.ret);
10445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
10455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
10465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
10475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltShutdownCtxtExt:
10485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @data:  the registered data for the module
10495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @ctxt:  the XSLT transformation context
10505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @URI:  the extension URI
10515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
10525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Shutdown an extension module loaded
10535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
10545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)static void
10555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltShutdownCtxtExt(xsltExtDataPtr data, xsltTransformContextPtr ctxt,
10565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                    const xmlChar * URI)
10575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
10585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltExtModulePtr module;
10595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
10605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if ((data == NULL) || (ctxt == NULL) || (URI == NULL))
10615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return;
10625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    module = data->extModule;
10635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if ((module == NULL) || (module->shutdownFunc == NULL))
10645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return;
10655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
10665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#ifdef WITH_XSLT_DEBUG_EXTENSIONS
10675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltGenericDebug(xsltGenericDebugContext,
10685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                     "Shutting down module : %s\n", URI);
10695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
10705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    module->shutdownFunc(ctxt, URI, data->extData);
10715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
10725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
10735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
10745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltShutdownCtxtExts:
10755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @ctxt: an XSLT transformation context
10765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
10775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Shutdown the set of modules loaded
10785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
10795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void
10805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltShutdownCtxtExts(xsltTransformContextPtr ctxt)
10815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
10825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (ctxt == NULL)
10835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return;
10845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (ctxt->extInfos == NULL)
10855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return;
10865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlHashScan(ctxt->extInfos, (xmlHashScanner) xsltShutdownCtxtExt,
10875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                ctxt);
10885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlHashFree(ctxt->extInfos, (xmlHashDeallocator) xsltFreeExtData);
10895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    ctxt->extInfos = NULL;
10905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
10915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
10925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
10935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltShutdownExt:
10945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @data:  the registered data for the module
10955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @ctxt:  the XSLT stylesheet
10965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @URI:  the extension URI
10975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
10985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Shutdown an extension module loaded
10995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
11005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)static void
11015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltShutdownExt(xsltExtDataPtr data, xsltStylesheetPtr style,
11025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                const xmlChar * URI)
11035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
11045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltExtModulePtr module;
11055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
11065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if ((data == NULL) || (style == NULL) || (URI == NULL))
11075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return;
11085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    module = data->extModule;
11095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if ((module == NULL) || (module->styleShutdownFunc == NULL))
11105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return;
11115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
11125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#ifdef WITH_XSLT_DEBUG_EXTENSIONS
11135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltGenericDebug(xsltGenericDebugContext,
11145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                     "Shutting down module : %s\n", URI);
11155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
11165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    module->styleShutdownFunc(style, URI, data->extData);
11175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    /*
11185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    * Don't remove the entry from the hash table here, since
11195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    * this will produce segfaults - this fixes bug #340624.
11205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    *
11215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    * xmlHashRemoveEntry(style->extInfos, URI,
11225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    *   (xmlHashDeallocator) xsltFreeExtData);
11235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    */
11245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
11255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
11265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
11275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltShutdownExts:
11285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @style: an XSLT stylesheet
11295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
11305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Shutdown the set of modules loaded
11315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
11325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void
11335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltShutdownExts(xsltStylesheetPtr style)
11345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
11355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (style == NULL)
11365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return;
11375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (style->extInfos == NULL)
11385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return;
11395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlHashScan(style->extInfos, (xmlHashScanner) xsltShutdownExt, style);
11405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlHashFree(style->extInfos, (xmlHashDeallocator) xsltFreeExtData);
11415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    style->extInfos = NULL;
11425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
11435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
11445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
11455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltCheckExtPrefix:
11465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @style: the stylesheet
11475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @URI: the namespace prefix (possibly NULL)
11485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
11495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Check if the given prefix is one of the declared extensions.
11505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * This is intended to be called only at compile-time.
11515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Called by:
11525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *  xsltGetInheritedNsList() (xslt.c)
11535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *  xsltParseTemplateContent (xslt.c)
11545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
11555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Returns 1 if this is an extension, 0 otherwise
11565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
11575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)int
11585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltCheckExtPrefix(xsltStylesheetPtr style, const xmlChar * URI)
11595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
11605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#ifdef XSLT_REFACTORED
11615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if ((style == NULL) || (style->compCtxt == NULL) ||
11625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	(XSLT_CCTXT(style)->inode == NULL) ||
11635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	(XSLT_CCTXT(style)->inode->extElemNs == NULL))
11645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (0);
11655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    /*
11665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    * Lookup the extension namespaces registered
11675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    * at the current node in the stylesheet's tree.
11685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    */
11695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (XSLT_CCTXT(style)->inode->extElemNs != NULL) {
11705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	int i;
11715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	xsltPointerListPtr list = XSLT_CCTXT(style)->inode->extElemNs;
11725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
11735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	for (i = 0; i < list->number; i++) {
11745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	    if (xmlStrEqual((const xmlChar *) list->items[i],
11755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)		URI))
11765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	    {
11775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)		return(1);
11785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	    }
11795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	}
11805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
11815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#else
11825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltExtDefPtr cur;
11835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
11845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if ((style == NULL) || (style->nsDefs == NULL))
11855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (0);
11865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (URI == NULL)
11875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        URI = BAD_CAST "#default";
11885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    cur = (xsltExtDefPtr) style->nsDefs;
11895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    while (cur != NULL) {
11905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	/*
11915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	* NOTE: This was change to work on namespace names rather
11925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	* than namespace prefixes. This fixes bug #339583.
11935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	* TODO: Consider renaming the field "prefix" of xsltExtDef
11945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	*  to "href".
11955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	*/
11965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        if (xmlStrEqual(URI, cur->prefix))
11975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            return (1);
11985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        cur = cur->next;
11995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
12005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
12015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return (0);
12025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
12035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
12045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
12055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltCheckExtURI:
12065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @style: the stylesheet
12075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @URI: the namespace URI (possibly NULL)
12085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
12095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Check if the given prefix is one of the declared extensions.
12105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * This is intended to be called only at compile-time.
12115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Called by:
12125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *  xsltPrecomputeStylesheet() (xslt.c)
12135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *  xsltParseTemplateContent (xslt.c)
12145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
12155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Returns 1 if this is an extension, 0 otherwise
12165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
12175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)int
12185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltCheckExtURI(xsltStylesheetPtr style, const xmlChar * URI)
12195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
12205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltExtDefPtr cur;
12215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
12225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if ((style == NULL) || (style->nsDefs == NULL))
12235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (0);
12245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (URI == NULL)
12255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (0);
12265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    cur = (xsltExtDefPtr) style->nsDefs;
12275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    while (cur != NULL) {
12285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        if (xmlStrEqual(URI, cur->URI))
12295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            return (1);
12305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        cur = cur->next;
12315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
12325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return (0);
12335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
12345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
12355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
12365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltRegisterExtModuleFull:
12375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @URI:  URI associated to this module
12385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @initFunc:  the module initialization function
12395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @shutdownFunc:  the module shutdown function
12405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @styleInitFunc:  the module initialization function
12415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @styleShutdownFunc:  the module shutdown function
12425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
12435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Register an XSLT extension module to the library.
12445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
12455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Returns 0 if sucessful, -1 in case of error
12465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
12475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)int
12485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltRegisterExtModuleFull(const xmlChar * URI,
12495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                          xsltExtInitFunction initFunc,
12505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                          xsltExtShutdownFunction shutdownFunc,
12515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                          xsltStyleExtInitFunction styleInitFunc,
12525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                          xsltStyleExtShutdownFunction styleShutdownFunc)
12535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
12545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    int ret;
12555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltExtModulePtr module;
12565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
12575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if ((URI == NULL) || (initFunc == NULL))
12585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (-1);
12595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (xsltExtensionsHash == NULL)
12605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xsltExtensionsHash = xmlHashCreate(10);
12615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
12625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (xsltExtensionsHash == NULL)
12635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (-1);
12645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
12655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlMutexLock(xsltExtMutex);
12665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
12675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    module = xmlHashLookup(xsltExtensionsHash, URI);
12685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (module != NULL) {
12695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        if ((module->initFunc == initFunc) &&
12705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            (module->shutdownFunc == shutdownFunc))
12715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            ret = 0;
12725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        else
12735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            ret = -1;
12745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        goto done;
12755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
12765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    module = xsltNewExtModule(initFunc, shutdownFunc,
12775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                              styleInitFunc, styleShutdownFunc);
12785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (module == NULL) {
12795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        ret = -1;
12805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        goto done;
12815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
12825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    ret = xmlHashAddEntry(xsltExtensionsHash, URI, (void *) module);
12835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
12845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)done:
12855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlMutexUnlock(xsltExtMutex);
12865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return (ret);
12875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
12885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
12895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
12905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltRegisterExtModule:
12915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @URI:  URI associated to this module
12925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @initFunc:  the module initialization function
12935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @shutdownFunc:  the module shutdown function
12945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
12955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Register an XSLT extension module to the library.
12965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
12975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Returns 0 if sucessful, -1 in case of error
12985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
12995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)int
13005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltRegisterExtModule(const xmlChar * URI,
13015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                      xsltExtInitFunction initFunc,
13025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                      xsltExtShutdownFunction shutdownFunc)
13035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
13045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return xsltRegisterExtModuleFull(URI, initFunc, shutdownFunc,
13055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                     NULL, NULL);
13065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
13075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
13085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
13095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltUnregisterExtModule:
13105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @URI:  URI associated to this module
13115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
13125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Unregister an XSLT extension module from the library.
13135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
13145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Returns 0 if sucessful, -1 in case of error
13155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
13165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)int
13175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltUnregisterExtModule(const xmlChar * URI)
13185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
13195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    int ret;
13205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
13215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (URI == NULL)
13225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (-1);
13235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (xsltExtensionsHash == NULL)
13245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (-1);
13255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
13265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlMutexLock(xsltExtMutex);
13275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
13285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    ret = xmlHashRemoveEntry(xsltExtensionsHash, URI,
13295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                             (xmlHashDeallocator) xsltFreeExtModule);
13305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
13315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlMutexUnlock(xsltExtMutex);
13325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
13335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return (ret);
13345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
13355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
13365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
13375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltUnregisterAllExtModules:
13385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
13395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Unregister all the XSLT extension module from the library.
13405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
13415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)static void
13425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltUnregisterAllExtModules(void)
13435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
13445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (xsltExtensionsHash == NULL)
13455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return;
13465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
13475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlMutexLock(xsltExtMutex);
13485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
13495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlHashFree(xsltExtensionsHash,
13505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                (xmlHashDeallocator) xsltFreeExtModule);
13515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltExtensionsHash = NULL;
13525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
13535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlMutexUnlock(xsltExtMutex);
13545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
13555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
13565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
13575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltXPathGetTransformContext:
13585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @ctxt:  an XPath transformation context
13595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
13605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Provides the XSLT transformation context from the XPath transformation
13615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * context. This is useful when an XPath function in the extension module
13625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * is called by the XPath interpreter and that the XSLT context is needed
13635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * for example to retrieve the associated data pertaining to this XSLT
13645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * transformation.
13655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
13665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Returns the XSLT transformation context or NULL in case of error.
13675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
13685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltTransformContextPtr
13695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltXPathGetTransformContext(xmlXPathParserContextPtr ctxt)
13705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
13715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if ((ctxt == NULL) || (ctxt->context == NULL))
13725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (NULL);
13735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return (ctxt->context->extra);
13745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
13755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
13765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
13775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltRegisterExtModuleFunction:
13785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @name:  the function name
13795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @URI:  the function namespace URI
13805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @function:  the function callback
13815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
13825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Registers an extension module function.
13835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
13845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Returns 0 if successful, -1 in case of error.
13855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
13865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)int
13875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltRegisterExtModuleFunction(const xmlChar * name, const xmlChar * URI,
13885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                              xmlXPathFunction function)
13895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
13905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if ((name == NULL) || (URI == NULL) || (function == NULL))
13915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (-1);
13925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
13935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (xsltFunctionsHash == NULL)
13945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xsltFunctionsHash = xmlHashCreate(10);
13955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (xsltFunctionsHash == NULL)
13965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (-1);
13975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
13985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlMutexLock(xsltExtMutex);
13995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
14005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlHashUpdateEntry2(xsltFunctionsHash, name, URI,
14015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                        XML_CAST_FPTR(function), NULL);
14025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
14035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlMutexUnlock(xsltExtMutex);
14045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
14055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return (0);
14065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
14075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
14085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
14095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltExtModuleFunctionLookup:
14105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @name:  the function name
14115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @URI:  the function namespace URI
14125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
14135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Looks up an extension module function
14145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
14155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Returns the function if found, NULL otherwise.
14165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
14175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xmlXPathFunction
14185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltExtModuleFunctionLookup(const xmlChar * name, const xmlChar * URI)
14195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
14205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlXPathFunction ret;
14215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
14225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if ((xsltFunctionsHash == NULL) || (name == NULL) || (URI == NULL))
14235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (NULL);
14245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
14255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlMutexLock(xsltExtMutex);
14265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
14275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    XML_CAST_FPTR(ret) = xmlHashLookup2(xsltFunctionsHash, name, URI);
14285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
14295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlMutexUnlock(xsltExtMutex);
14305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
14315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    /* if lookup fails, attempt a dynamic load on supported platforms */
14325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (NULL == ret) {
14335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        if (!xsltExtModuleRegisterDynamic(URI)) {
14345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            xmlMutexLock(xsltExtMutex);
14355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
14365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            XML_CAST_FPTR(ret) =
14375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                xmlHashLookup2(xsltFunctionsHash, name, URI);
14385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
14395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            xmlMutexUnlock(xsltExtMutex);
14405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        }
14415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
14425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
14435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return ret;
14445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
14455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
14465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
14475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltUnregisterExtModuleFunction:
14485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @name:  the function name
14495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @URI:  the function namespace URI
14505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
14515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Unregisters an extension module function
14525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
14535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Returns 0 if successful, -1 in case of error.
14545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
14555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)int
14565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltUnregisterExtModuleFunction(const xmlChar * name, const xmlChar * URI)
14575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
14585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    int ret;
14595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
14605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if ((xsltFunctionsHash == NULL) || (name == NULL) || (URI == NULL))
14615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (-1);
14625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
14635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlMutexLock(xsltExtMutex);
14645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
14655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    ret = xmlHashRemoveEntry2(xsltFunctionsHash, name, URI, NULL);
14665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
14675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlMutexUnlock(xsltExtMutex);
14685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
14695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return(ret);
14705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
14715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
14725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
14735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltUnregisterAllExtModuleFunction:
14745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
14755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Unregisters all extension module function
14765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
14775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)static void
14785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltUnregisterAllExtModuleFunction(void)
14795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
14805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlMutexLock(xsltExtMutex);
14815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
14825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlHashFree(xsltFunctionsHash, NULL);
14835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltFunctionsHash = NULL;
14845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
14855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlMutexUnlock(xsltExtMutex);
14865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
14875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
14885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
14895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
14905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltNewElemPreComp:
14915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @style:  the XSLT stylesheet
14925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @inst:  the element node
14935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @function: the transform function
14945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
14955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Creates and initializes an #xsltElemPreComp
14965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
14975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Returns the new and initialized #xsltElemPreComp
14985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
14995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltElemPreCompPtr
15005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltNewElemPreComp(xsltStylesheetPtr style, xmlNodePtr inst,
15015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                   xsltTransformFunction function)
15025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
15035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltElemPreCompPtr cur;
15045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
15055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    cur = (xsltElemPreCompPtr) xmlMalloc(sizeof(xsltElemPreComp));
15065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (cur == NULL) {
15075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xsltTransformError(NULL, style, NULL,
15085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                           "xsltNewExtElement : malloc failed\n");
15095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (NULL);
15105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
15115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    memset(cur, 0, sizeof(xsltElemPreComp));
15125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
15135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltInitElemPreComp(cur, style, inst, function,
15145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                        (xsltElemPreCompDeallocator) xmlFree);
15155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
15165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return (cur);
15175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
15185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
15195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
15205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltInitElemPreComp:
15215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @comp:  an #xsltElemPreComp (or generally a derived structure)
15225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @style:  the XSLT stylesheet
15235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @inst:  the element node
15245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @function:  the transform function
15255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @freeFunc:  the @comp deallocator
15265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
15275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Initializes an existing #xsltElemPreComp structure. This is usefull
15285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * when extending an #xsltElemPreComp to store precomputed data.
15295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * This function MUST be called on any extension element precomputed
15305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * data struct.
15315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
15325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void
15335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltInitElemPreComp(xsltElemPreCompPtr comp, xsltStylesheetPtr style,
15345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                    xmlNodePtr inst, xsltTransformFunction function,
15355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                    xsltElemPreCompDeallocator freeFunc)
15365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
15375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    comp->type = XSLT_FUNC_EXTENSION;
15385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    comp->func = function;
15395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    comp->inst = inst;
15405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    comp->free = freeFunc;
15415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
15425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    comp->next = style->preComps;
15435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    style->preComps = comp;
15445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
15455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
15465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
15475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltPreComputeExtModuleElement:
15485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @style:  the stylesheet
15495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @inst:  the element node
15505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
15515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Precomputes an extension module element
15525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
15535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Returns the precomputed data
15545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
15555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltElemPreCompPtr
15565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltPreComputeExtModuleElement(xsltStylesheetPtr style, xmlNodePtr inst)
15575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
15585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltExtElementPtr ext;
15595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltElemPreCompPtr comp = NULL;
15605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
15615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if ((style == NULL) || (inst == NULL) ||
15625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        (inst->type != XML_ELEMENT_NODE) || (inst->ns == NULL))
15635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (NULL);
15645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
15655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlMutexLock(xsltExtMutex);
15665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
15675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    ext = (xsltExtElementPtr)
15685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xmlHashLookup2(xsltElementsHash, inst->name, inst->ns->href);
15695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
15705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlMutexUnlock(xsltExtMutex);
15715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
15725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    /*
15735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    * EXT TODO: Now what?
15745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    */
15755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (ext == NULL)
15765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (NULL);
15775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
15785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (ext->precomp != NULL) {
15795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	/*
15805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	* REVISIT TODO: Check if the text below is correct.
15815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	* This will return a xsltElemPreComp structure or NULL.
15825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	* 1) If the the author of the extension needs a
15835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	*  custom structure to hold the specific values of
15845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	*  this extension, he will derive a structure based on
15855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	*  xsltElemPreComp; thus we obviously *cannot* refactor
15865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	*  the xsltElemPreComp structure, since all already derived
15875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	*  user-defined strucures will break.
15885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	*  Example: For the extension xsl:document,
15895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	*   in xsltDocumentComp() (preproc.c), the structure
15905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	*   xsltStyleItemDocument is allocated, filled with
15915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	*   specific values and returned.
15925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	* 2) If the author needs no values to be stored in
15935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	*  this structure, then he'll return NULL;
15945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	*/
15955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        comp = ext->precomp(style, inst, ext->transform);
15965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
15975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (comp == NULL) {
15985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	/*
15995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	* Default creation of a xsltElemPreComp structure, if
16005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	* the author of this extension did not create a custom
16015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	* structure.
16025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	*/
16035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        comp = xsltNewElemPreComp(style, inst, ext->transform);
16045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
16055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
16065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return (comp);
16075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
16085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
16095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
16105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltRegisterExtModuleElement:
16115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @name:  the element name
16125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @URI:  the element namespace URI
16135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @precomp:  the pre-computation callback
16145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @transform:  the transformation callback
16155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
16165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Registers an extension module element.
16175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
16185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Returns 0 if successful, -1 in case of error.
16195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
16205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)int
16215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltRegisterExtModuleElement(const xmlChar * name, const xmlChar * URI,
16225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                             xsltPreComputeFunction precomp,
16235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                             xsltTransformFunction transform)
16245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
16255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    int ret;
16265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
16275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltExtElementPtr ext;
16285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
16295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if ((name == NULL) || (URI == NULL) || (transform == NULL))
16305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (-1);
16315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
16325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (xsltElementsHash == NULL)
16335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xsltElementsHash = xmlHashCreate(10);
16345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (xsltElementsHash == NULL)
16355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (-1);
16365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
16375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlMutexLock(xsltExtMutex);
16385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
16395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    ext = xsltNewExtElement(precomp, transform);
16405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (ext == NULL) {
16415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        ret = -1;
16425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        goto done;
16435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
16445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
16455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlHashUpdateEntry2(xsltElementsHash, name, URI, (void *) ext,
16465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                        (xmlHashDeallocator) xsltFreeExtElement);
16475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
16485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)done:
16495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlMutexUnlock(xsltExtMutex);
16505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
16515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return (0);
16525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
16535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
16545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
16555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltExtElementLookup:
16565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @ctxt:  an XSLT process context
16575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @name:  the element name
16585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @URI:  the element namespace URI
16595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
16605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Looks up an extension element. @ctxt can be NULL to search only in
16615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * module elements.
16625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
16635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Returns the element callback or NULL if not found
16645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
16655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltTransformFunction
16665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltExtElementLookup(xsltTransformContextPtr ctxt,
16675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                     const xmlChar * name, const xmlChar * URI)
16685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
16695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltTransformFunction ret;
16705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
16715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if ((name == NULL) || (URI == NULL))
16725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (NULL);
16735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
16745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if ((ctxt != NULL) && (ctxt->extElements != NULL)) {
16755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        XML_CAST_FPTR(ret) = xmlHashLookup2(ctxt->extElements, name, URI);
16765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        if (ret != NULL) {
16775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            return(ret);
16785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        }
16795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
16805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
16815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    ret = xsltExtModuleElementLookup(name, URI);
16825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
16835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return (ret);
16845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
16855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
16865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
16875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltExtModuleElementLookup:
16885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @name:  the element name
16895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @URI:  the element namespace URI
16905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
16915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Looks up an extension module element
16925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
16935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Returns the callback function if found, NULL otherwise.
16945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
16955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltTransformFunction
16965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltExtModuleElementLookup(const xmlChar * name, const xmlChar * URI)
16975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
16985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltExtElementPtr ext;
16995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
17005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if ((xsltElementsHash == NULL) || (name == NULL) || (URI == NULL))
17015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (NULL);
17025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
17035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlMutexLock(xsltExtMutex);
17045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
17055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    ext = (xsltExtElementPtr) xmlHashLookup2(xsltElementsHash, name, URI);
17065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
17075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlMutexUnlock(xsltExtMutex);
17085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
17095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    /*
17105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)     * if function lookup fails, attempt a dynamic load on
17115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)     * supported platforms
17125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)     */
17135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (NULL == ext) {
17145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        if (!xsltExtModuleRegisterDynamic(URI)) {
17155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            xmlMutexLock(xsltExtMutex);
17165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
17175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            ext = (xsltExtElementPtr)
17185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	          xmlHashLookup2(xsltElementsHash, name, URI);
17195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
17205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            xmlMutexUnlock(xsltExtMutex);
17215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        }
17225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
17235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
17245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (ext == NULL)
17255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (NULL);
17265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return (ext->transform);
17275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
17285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
17295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
17305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltExtModuleElementPreComputeLookup:
17315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @name:  the element name
17325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @URI:  the element namespace URI
17335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
17345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Looks up an extension module element pre-computation function
17355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
17365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Returns the callback function if found, NULL otherwise.
17375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
17385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltPreComputeFunction
17395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltExtModuleElementPreComputeLookup(const xmlChar * name,
17405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                     const xmlChar * URI)
17415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
17425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltExtElementPtr ext;
17435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
17445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if ((xsltElementsHash == NULL) || (name == NULL) || (URI == NULL))
17455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (NULL);
17465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
17475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlMutexLock(xsltExtMutex);
17485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
17495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    ext = (xsltExtElementPtr) xmlHashLookup2(xsltElementsHash, name, URI);
17505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
17515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlMutexUnlock(xsltExtMutex);
17525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
17535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (ext == NULL) {
17545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        if (!xsltExtModuleRegisterDynamic(URI)) {
17555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            xmlMutexLock(xsltExtMutex);
17565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
17575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            ext = (xsltExtElementPtr)
17585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)	          xmlHashLookup2(xsltElementsHash, name, URI);
17595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
17605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            xmlMutexUnlock(xsltExtMutex);
17615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        }
17625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
17635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
17645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (ext == NULL)
17655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (NULL);
17665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return (ext->precomp);
17675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
17685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
17695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
17705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltUnregisterExtModuleElement:
17715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @name:  the element name
17725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @URI:  the element namespace URI
17735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
17745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Unregisters an extension module element
17755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
17765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Returns 0 if successful, -1 in case of error.
17775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
17785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)int
17795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltUnregisterExtModuleElement(const xmlChar * name, const xmlChar * URI)
17805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
17815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    int ret;
17825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
17835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if ((xsltElementsHash == NULL) || (name == NULL) || (URI == NULL))
17845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (-1);
17855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
17865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlMutexLock(xsltExtMutex);
17875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
17885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    ret = xmlHashRemoveEntry2(xsltElementsHash, name, URI,
17895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                              (xmlHashDeallocator) xsltFreeExtElement);
17905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
17915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlMutexUnlock(xsltExtMutex);
17925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
17935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return(ret);
17945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
17955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
17965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
17975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltUnregisterAllExtModuleElement:
17985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
17995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Unregisters all extension module element
18005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
18015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)static void
18025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltUnregisterAllExtModuleElement(void)
18035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
18045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlMutexLock(xsltExtMutex);
18055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
18065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlHashFree(xsltElementsHash, (xmlHashDeallocator) xsltFreeExtElement);
18075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltElementsHash = NULL;
18085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
18095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlMutexUnlock(xsltExtMutex);
18105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
18115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
18125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
18135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltRegisterExtModuleTopLevel:
18145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @name:  the top-level element name
18155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @URI:  the top-level element namespace URI
18165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @function:  the top-level element callback
18175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
18185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Registers an extension module top-level element.
18195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
18205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Returns 0 if successful, -1 in case of error.
18215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
18225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)int
18235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltRegisterExtModuleTopLevel(const xmlChar * name, const xmlChar * URI,
18245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                              xsltTopLevelFunction function)
18255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
18265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if ((name == NULL) || (URI == NULL) || (function == NULL))
18275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (-1);
18285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
18295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (xsltTopLevelsHash == NULL)
18305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xsltTopLevelsHash = xmlHashCreate(10);
18315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (xsltTopLevelsHash == NULL)
18325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (-1);
18335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
18345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlMutexLock(xsltExtMutex);
18355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
18365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlHashUpdateEntry2(xsltTopLevelsHash, name, URI,
18375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                        XML_CAST_FPTR(function), NULL);
18385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
18395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlMutexUnlock(xsltExtMutex);
18405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
18415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return (0);
18425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
18435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
18445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
18455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltExtModuleTopLevelLookup:
18465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @name:  the top-level element name
18475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @URI:  the top-level element namespace URI
18485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
18495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Looks up an extension module top-level element
18505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
18515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Returns the callback function if found, NULL otherwise.
18525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
18535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltTopLevelFunction
18545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltExtModuleTopLevelLookup(const xmlChar * name, const xmlChar * URI)
18555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
18565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltTopLevelFunction ret;
18575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
18585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if ((xsltTopLevelsHash == NULL) || (name == NULL) || (URI == NULL))
18595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (NULL);
18605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
18615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlMutexLock(xsltExtMutex);
18625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
18635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    XML_CAST_FPTR(ret) = xmlHashLookup2(xsltTopLevelsHash, name, URI);
18645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
18655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlMutexUnlock(xsltExtMutex);
18665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
18675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    /* if lookup fails, attempt a dynamic load on supported platforms */
18685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (NULL == ret) {
18695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        if (!xsltExtModuleRegisterDynamic(URI)) {
18705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            xmlMutexLock(xsltExtMutex);
18715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
18725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            XML_CAST_FPTR(ret) = xmlHashLookup2(xsltTopLevelsHash, name, URI);
18735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
18745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            xmlMutexUnlock(xsltExtMutex);
18755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        }
18765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
18775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
18785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return (ret);
18795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
18805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
18815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
18825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltUnregisterExtModuleTopLevel:
18835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @name:  the top-level element name
18845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @URI:  the top-level element namespace URI
18855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
18865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Unregisters an extension module top-level element
18875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
18885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Returns 0 if successful, -1 in case of error.
18895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
18905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)int
18915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltUnregisterExtModuleTopLevel(const xmlChar * name, const xmlChar * URI)
18925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
18935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    int ret;
18945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
18955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if ((xsltTopLevelsHash == NULL) || (name == NULL) || (URI == NULL))
18965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (-1);
18975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
18985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlMutexLock(xsltExtMutex);
18995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
19005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    ret = xmlHashRemoveEntry2(xsltTopLevelsHash, name, URI, NULL);
19015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
19025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlMutexUnlock(xsltExtMutex);
19035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
19045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return(ret);
19055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
19065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
19075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
19085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltUnregisterAllExtModuleTopLevel:
19095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
19105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Unregisters all extension module function
19115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
19125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)static void
19135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltUnregisterAllExtModuleTopLevel(void)
19145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
19155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlMutexLock(xsltExtMutex);
19165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
19175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlHashFree(xsltTopLevelsHash, NULL);
19185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltTopLevelsHash = NULL;
19195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
19205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlMutexUnlock(xsltExtMutex);
19215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
19225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
19235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
19245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltGetExtInfo:
19255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @style:  pointer to a stylesheet
19265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @URI:    the namespace URI desired
19275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
19285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * looks up URI in extInfos of the stylesheet
19295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
19305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * returns a pointer to the hash table if found, else NULL
19315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
19325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xmlHashTablePtr
19335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltGetExtInfo(xsltStylesheetPtr style, const xmlChar * URI)
19345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
19355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltExtDataPtr data;
19365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
19375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    /*
19385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    * TODO: Why do we have a return type of xmlHashTablePtr?
19395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    *   Is the user-allocated data for extension modules expected
19405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    *   to be a xmlHashTablePtr only? Or is this intended for
19415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    *   the EXSLT module only?
19425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    */
19435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
19445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (style != NULL && style->extInfos != NULL) {
19455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        data = xmlHashLookup(style->extInfos, URI);
19465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        if (data != NULL && data->extData != NULL)
19475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            return data->extData;
19485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
19495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return NULL;
19505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
19515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
19525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/************************************************************************
19535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * 									*
19545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * 		Test module http://xmlsoft.org/XSLT/			*
19555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * 									*
19565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ************************************************************************/
19575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
19585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/************************************************************************
19595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * 									*
19605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * 		Test of the extension module API			*
19615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * 									*
19625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ************************************************************************/
19635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
19645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)static xmlChar *testData = NULL;
19655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)static xmlChar *testStyleData = NULL;
19665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
19675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
19685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltExtFunctionTest:
19695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @ctxt:  the XPath Parser context
19705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @nargs:  the number of arguments
19715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
19725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * function libxslt:test() for testing the extensions support.
19735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
19745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)static void
19755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltExtFunctionTest(xmlXPathParserContextPtr ctxt,
19765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                    int nargs ATTRIBUTE_UNUSED)
19775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
19785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltTransformContextPtr tctxt;
19795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    void *data = NULL;
19805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
19815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    tctxt = xsltXPathGetTransformContext(ctxt);
19825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
19835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (testData == NULL) {
19845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xsltGenericDebug(xsltGenericDebugContext,
19855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                         "xsltExtFunctionTest: not initialized,"
19865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                         " calling xsltGetExtData\n");
19875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        data = xsltGetExtData(tctxt, (const xmlChar *) XSLT_DEFAULT_URL);
19885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        if (data == NULL) {
19895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            xsltTransformError(tctxt, NULL, NULL,
19905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                               "xsltExtElementTest: not initialized\n");
19915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            return;
19925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        }
19935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
19945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (tctxt == NULL) {
19955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xsltTransformError(xsltXPathGetTransformContext(ctxt), NULL, NULL,
19965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                           "xsltExtFunctionTest: failed to get the transformation context\n");
19975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return;
19985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
19995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (data == NULL)
20005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        data = xsltGetExtData(tctxt, (const xmlChar *) XSLT_DEFAULT_URL);
20015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (data == NULL) {
20025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xsltTransformError(xsltXPathGetTransformContext(ctxt), NULL, NULL,
20035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                           "xsltExtFunctionTest: failed to get module data\n");
20045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return;
20055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
20065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (data != testData) {
20075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xsltTransformError(xsltXPathGetTransformContext(ctxt), NULL, NULL,
20085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                           "xsltExtFunctionTest: got wrong module data\n");
20095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return;
20105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
20115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#ifdef WITH_XSLT_DEBUG_FUNCTION
20125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltGenericDebug(xsltGenericDebugContext,
20135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                     "libxslt:test() called with %d args\n", nargs);
20145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
20155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
20165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
20175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
20185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltExtElementPreCompTest:
20195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @style:  the stylesheet
20205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @inst:  the instruction in the stylesheet
20215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
20225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Process a libxslt:test node
20235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
20245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)static xsltElemPreCompPtr
20255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltExtElementPreCompTest(xsltStylesheetPtr style, xmlNodePtr inst,
20265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                          xsltTransformFunction function)
20275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
20285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltElemPreCompPtr ret;
20295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
20305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (style == NULL) {
20315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xsltTransformError(NULL, NULL, inst,
20325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                           "xsltExtElementTest: no transformation context\n");
20335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (NULL);
20345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
20355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (testStyleData == NULL) {
20365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xsltGenericDebug(xsltGenericDebugContext,
20375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                         "xsltExtElementPreCompTest: not initialized,"
20385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                         " calling xsltStyleGetExtData\n");
20395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xsltStyleGetExtData(style, (const xmlChar *) XSLT_DEFAULT_URL);
20405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        if (testStyleData == NULL) {
20415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            xsltTransformError(NULL, style, inst,
20425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                               "xsltExtElementPreCompTest: not initialized\n");
20435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            if (style != NULL)
20445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                style->errors++;
20455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            return (NULL);
20465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        }
20475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
20485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (inst == NULL) {
20495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xsltTransformError(NULL, style, inst,
20505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                           "xsltExtElementPreCompTest: no instruction\n");
20515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        if (style != NULL)
20525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            style->errors++;
20535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (NULL);
20545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
20555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    ret = xsltNewElemPreComp(style, inst, function);
20565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return (ret);
20575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
20585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
20595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
20605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltExtElementTest:
20615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @ctxt:  an XSLT processing context
20625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @node:  The current node
20635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @inst:  the instruction in the stylesheet
20645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @comp:  precomputed informations
20655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
20665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Process a libxslt:test node
20675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
20685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)static void
20695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltExtElementTest(xsltTransformContextPtr ctxt, xmlNodePtr node,
20705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                   xmlNodePtr inst,
20715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                   xsltElemPreCompPtr comp ATTRIBUTE_UNUSED)
20725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
20735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlNodePtr commentNode;
20745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
20755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (testData == NULL) {
20765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xsltGenericDebug(xsltGenericDebugContext,
20775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                         "xsltExtElementTest: not initialized,"
20785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                         " calling xsltGetExtData\n");
20795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xsltGetExtData(ctxt, (const xmlChar *) XSLT_DEFAULT_URL);
20805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        if (testData == NULL) {
20815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            xsltTransformError(ctxt, NULL, inst,
20825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                               "xsltExtElementTest: not initialized\n");
20835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            return;
20845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        }
20855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
20865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (ctxt == NULL) {
20875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xsltTransformError(ctxt, NULL, inst,
20885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                           "xsltExtElementTest: no transformation context\n");
20895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return;
20905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
20915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (node == NULL) {
20925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xsltTransformError(ctxt, NULL, inst,
20935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                           "xsltExtElementTest: no current node\n");
20945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return;
20955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
20965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (inst == NULL) {
20975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xsltTransformError(ctxt, NULL, inst,
20985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                           "xsltExtElementTest: no instruction\n");
20995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return;
21005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
21015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (ctxt->insert == NULL) {
21025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xsltTransformError(ctxt, NULL, inst,
21035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                           "xsltExtElementTest: no insertion point\n");
21045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return;
21055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
21065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    commentNode = xmlNewComment((const xmlChar *)
21075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                "libxslt:test element test worked");
21085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlAddChild(ctxt->insert, commentNode);
21095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
21105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
21115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
21125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltExtInitTest:
21135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @ctxt:  an XSLT transformation context
21145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @URI:  the namespace URI for the extension
21155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
21165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * A function called at initialization time of an XSLT extension module
21175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
21185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Returns a pointer to the module specific data for this transformation
21195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
21205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)static void *
21215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltExtInitTest(xsltTransformContextPtr ctxt, const xmlChar * URI)
21225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
21235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (testStyleData == NULL) {
21245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xsltGenericDebug(xsltGenericErrorContext,
21255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                         "xsltExtInitTest: not initialized,"
21265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                         " calling xsltStyleGetExtData\n");
21275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        testStyleData = xsltStyleGetExtData(ctxt->style, URI);
21285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        if (testStyleData == NULL) {
21295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            xsltTransformError(ctxt, NULL, NULL,
21305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                               "xsltExtInitTest: not initialized\n");
21315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            return (NULL);
21325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        }
21335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
21345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (testData != NULL) {
21355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xsltTransformError(ctxt, NULL, NULL,
21365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                           "xsltExtInitTest: already initialized\n");
21375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (NULL);
21385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
21395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    testData = (void *) "test data";
21405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltGenericDebug(xsltGenericDebugContext,
21415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                     "Registered test module : %s\n", URI);
21425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return (testData);
21435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
21445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
21455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
21465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
21475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltExtShutdownTest:
21485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @ctxt:  an XSLT transformation context
21495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @URI:  the namespace URI for the extension
21505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @data:  the data associated to this module
21515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
21525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * A function called at shutdown time of an XSLT extension module
21535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
21545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)static void
21555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltExtShutdownTest(xsltTransformContextPtr ctxt,
21565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                    const xmlChar * URI, void *data)
21575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
21585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (testData == NULL) {
21595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xsltTransformError(ctxt, NULL, NULL,
21605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                           "xsltExtShutdownTest: not initialized\n");
21615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return;
21625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
21635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (data != testData) {
21645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xsltTransformError(ctxt, NULL, NULL,
21655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                           "xsltExtShutdownTest: wrong data\n");
21665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
21675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    testData = NULL;
21685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltGenericDebug(xsltGenericDebugContext,
21695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                     "Unregistered test module : %s\n", URI);
21705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
21715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
21725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
21735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltExtStyleInitTest:
21745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @style:  an XSLT stylesheet
21755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @URI:  the namespace URI for the extension
21765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
21775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * A function called at initialization time of an XSLT extension module
21785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
21795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Returns a pointer to the module specific data for this transformation
21805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
21815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)static void *
21825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltExtStyleInitTest(xsltStylesheetPtr style ATTRIBUTE_UNUSED,
21835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                     const xmlChar * URI)
21845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
21855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (testStyleData != NULL) {
21865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xsltTransformError(NULL, NULL, NULL,
21875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                           "xsltExtInitTest: already initialized\n");
21885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return (NULL);
21895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
21905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    testStyleData = (void *) "test data";
21915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltGenericDebug(xsltGenericDebugContext,
21925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                     "Registered test module : %s\n", URI);
21935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return (testStyleData);
21945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
21955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
21965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
21975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
21985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltExtStyleShutdownTest:
21995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @style:  an XSLT stylesheet
22005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @URI:  the namespace URI for the extension
22015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @data:  the data associated to this module
22025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
22035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * A function called at shutdown time of an XSLT extension module
22045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
22055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)static void
22065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltExtStyleShutdownTest(xsltStylesheetPtr style ATTRIBUTE_UNUSED,
22075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                         const xmlChar * URI, void *data)
22085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
22095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (testStyleData == NULL) {
22105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xsltGenericError(xsltGenericErrorContext,
22115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                         "xsltExtShutdownTest: not initialized\n");
22125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return;
22135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
22145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (data != testStyleData) {
22155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xsltTransformError(NULL, NULL, NULL,
22165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                           "xsltExtShutdownTest: wrong data\n");
22175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
22185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    testStyleData = NULL;
22195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltGenericDebug(xsltGenericDebugContext,
22205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                     "Unregistered test module : %s\n", URI);
22215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
22225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
22235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
22245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltRegisterTestModule:
22255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
22265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Registers the test module
22275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
22285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void
22295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltRegisterTestModule(void)
22305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
22315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltInitGlobals();
22325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltRegisterExtModuleFull((const xmlChar *) XSLT_DEFAULT_URL,
22335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                              xsltExtInitTest, xsltExtShutdownTest,
22345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                              xsltExtStyleInitTest,
22355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                              xsltExtStyleShutdownTest);
22365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltRegisterExtModuleFunction((const xmlChar *) "test",
22375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                  (const xmlChar *) XSLT_DEFAULT_URL,
22385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                  xsltExtFunctionTest);
22395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltRegisterExtModuleElement((const xmlChar *) "test",
22405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                 (const xmlChar *) XSLT_DEFAULT_URL,
22415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                 xsltExtElementPreCompTest,
22425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                 xsltExtElementTest);
22435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
22445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
22455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)static void
22465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltHashScannerModuleFree(void *payload ATTRIBUTE_UNUSED,
22475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                          void *data ATTRIBUTE_UNUSED,
22485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                          xmlChar * name ATTRIBUTE_UNUSED)
22495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
22505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#ifdef WITH_MODULES
22515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlModuleClose(payload);
22525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
22535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
22545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
22555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
22565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltInitGlobals:
22575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
22585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Initialize the global variables for extensions
22595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
22605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void
22615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltInitGlobals(void)
22625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
22635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (xsltExtMutex == NULL) {
22645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xsltExtMutex = xmlNewMutex();
22655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
22665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
22675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
22685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
22695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltCleanupGlobals:
22705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
22715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Unregister all global variables set up by the XSLT library
22725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
22735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void
22745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltCleanupGlobals(void)
22755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
22765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltUnregisterAllExtModules();
22775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltUnregisterAllExtModuleFunction();
22785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltUnregisterAllExtModuleElement();
22795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltUnregisterAllExtModuleTopLevel();
22805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
22815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlMutexLock(xsltExtMutex);
22825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    /* cleanup dynamic module hash */
22835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (NULL != xsltModuleHash) {
22845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xmlHashScan(xsltModuleHash, xsltHashScannerModuleFree, 0);
22855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xmlHashFree(xsltModuleHash, NULL);
22865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xsltModuleHash = NULL;
22875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
22885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlMutexUnlock(xsltExtMutex);
22895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
22905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xmlFreeMutex(xsltExtMutex);
22915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltExtMutex = NULL;
22925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    xsltUninit();
22935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
22945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
22955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)static void
22965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltDebugDumpExtensionsCallback(void *function ATTRIBUTE_UNUSED,
22975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                FILE * output, const xmlChar * name,
22985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                const xmlChar * URI,
22995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                const xmlChar * not_used ATTRIBUTE_UNUSED)
23005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
23015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (!name || !URI)
23025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return;
23035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    fprintf(output, "{%s}%s\n", URI, name);
23045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
23055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
23065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)static void
23075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltDebugDumpExtModulesCallback(void *function ATTRIBUTE_UNUSED,
23085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                FILE * output, const xmlChar * URI,
23095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                const xmlChar * not_used ATTRIBUTE_UNUSED,
23105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                const xmlChar * not_used2 ATTRIBUTE_UNUSED)
23115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
23125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (!URI)
23135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return;
23145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    fprintf(output, "%s\n", URI);
23155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
23165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
23175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/**
23185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * xsltDebugDumpExtensions:
23195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * @output:  the FILE * for the output, if NULL stdout is used
23205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *
23215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) * Dumps a list of the registered XSLT extension functions and elements
23225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) */
23235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void
23245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)xsltDebugDumpExtensions(FILE * output)
23255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles){
23265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (output == NULL)
23275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        output = stdout;
23285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    fprintf(output,
23295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            "Registered XSLT Extensions\n--------------------------\n");
23305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (!xsltFunctionsHash)
23315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        fprintf(output, "No registered extension functions\n");
23325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    else {
23335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        fprintf(output, "Registered Extension Functions:\n");
23345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xmlMutexLock(xsltExtMutex);
23355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xmlHashScanFull(xsltFunctionsHash,
23365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                        (xmlHashScannerFull)
23375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                        xsltDebugDumpExtensionsCallback, output);
23385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xmlMutexUnlock(xsltExtMutex);
23395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
23405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (!xsltElementsHash)
23415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        fprintf(output, "\nNo registered extension elements\n");
23425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    else {
23435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        fprintf(output, "\nRegistered Extension Elements:\n");
23445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xmlMutexLock(xsltExtMutex);
23455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xmlHashScanFull(xsltElementsHash,
23465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                        (xmlHashScannerFull)
23475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                        xsltDebugDumpExtensionsCallback, output);
23485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xmlMutexUnlock(xsltExtMutex);
23495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
23505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (!xsltExtensionsHash)
23515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        fprintf(output, "\nNo registered extension modules\n");
23525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    else {
23535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        fprintf(output, "\nRegistered Extension Modules:\n");
23545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xmlMutexLock(xsltExtMutex);
23555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xmlHashScanFull(xsltExtensionsHash,
23565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                        (xmlHashScannerFull)
23575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                        xsltDebugDumpExtModulesCallback, output);
23585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        xmlMutexUnlock(xsltExtMutex);
23595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
23605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
23615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
2362