From 22fc899b2da378bff95096d020154429228e3873 Mon Sep 17 00:00:00 2001 From: Daniel Veillard Date: Thu, 1 Feb 2001 20:01:42 +0000 Subject: [PATCH] Work on implementing import support: - libxslt/Makefile.am libxslt/imports.[ch]: new module to implement import cascade lookups and traversal - libxslt/attributes.c libxslt/namespaces.c libxslt/pattern.[ch] libxslt/transform.c libxslt/xslt.c libxslt/xsltInternals.h: started coding the import cascade lookup in the places needed, probably incomplete. Daniel --- ChangeLog | 9 ++ libxslt/Makefile.am | 2 + libxslt/attributes.c | 23 +++- libxslt/imports.c | 273 ++++++++++++++++++++++++++++++++++++++++++++++++ libxslt/imports.h | 35 +++++++ libxslt/namespaces.c | 22 ++-- libxslt/pattern.c | 185 +++++++++++++++----------------- libxslt/pattern.h | 5 +- libxslt/transform.c | 34 ++---- libxslt/xslt.c | 119 +-------------------- libxslt/xsltInternals.h | 3 + 11 files changed, 446 insertions(+), 264 deletions(-) create mode 100644 libxslt/imports.c create mode 100644 libxslt/imports.h diff --git a/ChangeLog b/ChangeLog index 2053037..1ffa204 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,12 @@ +Thu Feb 1 20:58:54 CET 2001 Daniel Veillard + + * libxslt/Makefile.am libxslt/imports.[ch]: new module to + implement import cascade lookups and traversal + * libxslt/attributes.c libxslt/namespaces.c libxslt/pattern.[ch] + libxslt/transform.c libxslt/xslt.c libxslt/xsltInternals.h: + started coding the import cascade lookup in the places needed, + probably incomplete. + Thu Feb 1 18:04:39 CET 2001 Daniel Veillard * libxslt/xsltInternals.h libxslt/xslt.h: started implementing diff --git a/libxslt/Makefile.am b/libxslt/Makefile.am index a29ec9e..6501507 100644 --- a/libxslt/Makefile.am +++ b/libxslt/Makefile.am @@ -13,6 +13,7 @@ xsltinc_HEADERS = \ variables.h \ functions.h \ namespaces.h \ + imports.h \ attributes.h \ transform.h \ xsltInternals.h @@ -25,6 +26,7 @@ libxslt_la_SOURCES = \ variables.c \ functions.c \ namespaces.c \ + imports.c \ attributes.c \ transform.c diff --git a/libxslt/attributes.c b/libxslt/attributes.c index ac54dcb..f119f42 100644 --- a/libxslt/attributes.c +++ b/libxslt/attributes.c @@ -43,6 +43,15 @@ #include "attributes.h" #include "namespaces.h" #include "templates.h" +#include "imports.h" + +/* + * TODO: merge attribute sets from different import precedence. + * all this should be precomputed just before the transformation + * starts or at first hit with a cache in the context. + * The simple way for now would be to not allow redefinition of + * attributes once generated in the output tree, possibly costlier. + */ /* * Useful macros @@ -382,6 +391,7 @@ xsltApplyAttributeSet(xsltTransformContextPtr ctxt, xmlNodePtr node, xmlChar *prefix = NULL; xmlChar *attribute, *end; xsltAttrElemPtr values; + xsltStylesheetPtr style; if (attributes == NULL) { return; @@ -407,11 +417,14 @@ xsltApplyAttributeSet(xsltTransformContextPtr ctxt, xmlNodePtr node, prefix = NULL; } - /* TODO: apply cascade */ - values = xmlHashLookup2(ctxt->style->attributeSets, ncname, prefix); - while (values != NULL) { - xsltAttribute(ctxt, node, values->attr); - values = values->next; + style = ctxt->style; + while (style != NULL) { + values = xmlHashLookup2(style->attributeSets, ncname, prefix); + while (values != NULL) { + xsltAttribute(ctxt, node, values->attr); + values = values->next; + } + style = xsltNextImport(style); } if (attribute != NULL) xmlFree(attribute); diff --git a/libxslt/imports.c b/libxslt/imports.c new file mode 100644 index 0000000..44316a0 --- /dev/null +++ b/libxslt/imports.c @@ -0,0 +1,273 @@ +/* + * imports.c: Implementation of the XSLT imports + * + * Reference: + * http://www.w3.org/TR/1999/REC-xslt-19991116 + * + * See Copyright for the status of this software. + * + * Daniel.Veillard@imag.fr + */ + +#include "xsltconfig.h" + +#include + +#ifdef HAVE_SYS_TYPES_H +#include +#endif +#ifdef HAVE_MATH_H +#include +#endif +#ifdef HAVE_FLOAT_H +#include +#endif +#ifdef HAVE_IEEEFP_H +#include +#endif +#ifdef HAVE_NAN_H +#include +#endif +#ifdef HAVE_CTYPE_H +#include +#endif + +#include +#include +#include +#include +#include +#include "xslt.h" +#include "xsltInternals.h" +#include "xsltutils.h" +#include "imports.h" + + + +/************************************************************************ + * * + * Module interfaces * + * * + ************************************************************************/ + +/** + * xsltParseStylesheetImport: + * @style: the XSLT stylesheet + * @template: the "strip-space" element + * + * parse an XSLT stylesheet strip-space element and record + * elements needing stripping + */ + +void +xsltParseStylesheetImport(xsltStylesheetPtr style, xmlNodePtr cur) { + xmlDocPtr import = NULL; + xmlChar *base = NULL; + xmlChar *uriRef = NULL; + xmlChar *URI = NULL; + xsltStylesheetPtr res; + + if ((cur == NULL) || (style == NULL)) + return; + + uriRef = xmlGetNsProp(cur, (const xmlChar *)"href", XSLT_NAMESPACE); + if (uriRef == NULL) { + xsltGenericError(xsltGenericErrorContext, + "xsl:import : missing href attribute\n"); + goto error; + } + + base = xmlNodeGetBase(style->doc, cur); + URI = xmlBuildURI(uriRef, base); + if (URI == NULL) { + xsltGenericError(xsltGenericErrorContext, + "xsl:import : invalid URI reference %s\n", uriRef); + goto error; + } + import = xmlParseFile((const char *)URI); + if (import == NULL) { + xsltGenericError(xsltGenericErrorContext, + "xsl:import : unable to load %s\n", URI); + goto error; + } + + res = xsltParseStylesheetDoc(import); + if (res != NULL) { + res->parent = style; + res->next = style->imports; + style->imports = res; + } + +error: + if (import != NULL) + xmlFreeDoc(import); + if (uriRef != NULL) + xmlFree(uriRef); + if (base != NULL) + xmlFree(base); + if (URI != NULL) + xmlFree(URI); +} + +/** + * xsltParseStylesheetInclude: + * @style: the XSLT stylesheet + * @template: the "strip-space" element + * + * parse an XSLT stylesheet strip-space element and record + * elements needing stripping + */ + +void +xsltParseStylesheetInclude(xsltStylesheetPtr style, xmlNodePtr cur) { + xmlDocPtr include = NULL, oldDoc; + xmlChar *base = NULL; + xmlChar *uriRef = NULL; + xmlChar *URI = NULL; + + if ((cur == NULL) || (style == NULL)) + return; + + uriRef = xmlGetNsProp(cur, (const xmlChar *)"href", XSLT_NAMESPACE); + if (uriRef == NULL) { + xsltGenericError(xsltGenericErrorContext, + "xsl:include : missing href attribute\n"); + goto error; + } + + base = xmlNodeGetBase(style->doc, cur); + URI = xmlBuildURI(uriRef, base); + if (URI == NULL) { + xsltGenericError(xsltGenericErrorContext, + "xsl:include : invalid URI reference %s\n", uriRef); + goto error; + } + include = xmlParseFile((const char *)URI); + if (include == NULL) { + xsltGenericError(xsltGenericErrorContext, + "xsl:include : unable to load %s\n", URI); + goto error; + } + + oldDoc = style->doc; + style->doc = include; + xsltParseStylesheetProcess(style, include); + style->doc = oldDoc; + +error: + if (include != NULL) + xmlFreeDoc(include); + if (uriRef != NULL) + xmlFree(uriRef); + if (base != NULL) + xmlFree(base); + if (URI != NULL) + xmlFree(URI); +} + +/** + * xsltNextImport: + * @cur: the current XSLT stylesheet + * + * Find the next stylesheet in import precedence. + * + * Returns the next stylesheet or NULL if it was the last one + */ + +xsltStylesheetPtr +xsltNextImport(xsltStylesheetPtr cur) { + if (cur == NULL) + return(NULL); + if (cur->imports != NULL) + return(cur->imports); + if (cur->next != NULL) + return(cur->next) ; + do { + cur = cur->parent; + if (cur == NULL) return(NULL); + if (cur->next != NULL) return(cur->next); + } while (cur != NULL); + return(cur); +} + +/** + * xsltFindElemSpaceHandling: + * ctxt: an XSLT transformation context + * node: an XML node + * + * Find strip-space or preserve-space informations for an element + * respect the import precedence or the wildcards + * + * Returns 1 if space should be stripped, 0 if not, and 2 if everything + * should be CDTATA wrapped. + */ + +int +xsltFindElemSpaceHandling(xsltTransformContextPtr ctxt, xmlNodePtr node) { + xsltStylesheetPtr style; + const xmlChar *val; + + if ((ctxt == NULL) || (node == NULL)) + return(0); + style = ctxt->style; + while (style != NULL) { + /* TODO: add namespaces support */ + val = (const xmlChar *) + xmlHashLookup(style->stripSpaces, node->name); + if (val != NULL) { + if (xmlStrEqual(val, (xmlChar *) "strip")) + return(1); + if (xmlStrEqual(val, (xmlChar *) "preserve")) + return(0); + } + val = (const xmlChar *) + xmlHashLookup(ctxt->style->stripSpaces, + (const xmlChar *)"*"); + if ((val != NULL) && + (xmlStrEqual(val, (xmlChar *) "strip"))) + return(1); + if (xmlStrEqual(val, (xmlChar *) "preserve")) + return(0); + + style = xsltNextImport(style); + } + return(0); +} + +/** + * xsltFindTemplate: + * ctxt: an XSLT transformation context + * @name: the template name + * @nameURI: the template name URI + * + * Finds the named template, apply import precedence rule. + * + * Returns the xsltTemplatePtr or NULL if not found + */ +xsltTemplatePtr +xsltFindTemplate(xsltTransformContextPtr ctxt, const xmlChar *name, + const xmlChar *nameURI) { + xsltTemplatePtr cur; + xsltStylesheetPtr style; + + if ((ctxt == NULL) || (name == NULL)) + return(NULL); + style = ctxt->style; + while (style != NULL) { + cur = style->templates; + while (cur != NULL) { + if (xmlStrEqual(name, cur->name)) { + if (((nameURI == NULL) && (cur->nameURI == NULL)) || + ((nameURI != NULL) && (cur->nameURI != NULL) && + (xmlStrEqual(nameURI, cur->nameURI)))) { + return(cur); + } + } + cur = cur->next; + } + + style = xsltNextImport(style); + } + return(NULL); +} + diff --git a/libxslt/imports.h b/libxslt/imports.h new file mode 100644 index 0000000..9aa280a --- /dev/null +++ b/libxslt/imports.h @@ -0,0 +1,35 @@ +/* + * imports.h: interface for the XSLT import support + * + * See Copyright for the status of this software. + * + * Daniel.Veillard@imag.fr + */ + +#ifndef __XML_XSLT_IMPORTS_H__ +#define __XML_XSLT_IMPORTS_H__ + +#include +#include "xsltInternals.h" + +#ifdef __cplusplus +extern "C" { +#endif + +void xsltParseStylesheetImport(xsltStylesheetPtr style, + xmlNodePtr cur); +void xsltParseStylesheetInclude(xsltStylesheetPtr style, + xmlNodePtr cur); +xsltStylesheetPtr xsltNextImport (xsltStylesheetPtr style); +int xsltFindElemSpaceHandling(xsltTransformContextPtr ctxt, + xmlNodePtr node); +xsltTemplatePtr xsltFindTemplate (xsltTransformContextPtr ctxt, + const xmlChar *name, + const xmlChar *nameURI); + +#ifdef __cplusplus +} +#endif + +#endif /* __XML_XSLT_IMPORTS_H__ */ + diff --git a/libxslt/namespaces.c b/libxslt/namespaces.c index 384836d..1e69978 100644 --- a/libxslt/namespaces.c +++ b/libxslt/namespaces.c @@ -41,6 +41,7 @@ #include "xsltInternals.h" #include "xsltutils.h" #include "namespaces.h" +#include "imports.h" @@ -134,18 +135,25 @@ error: xmlNsPtr xsltGetNamespace(xsltTransformContextPtr ctxt, xmlNodePtr cur, xmlNsPtr ns, xmlNodePtr out) { + xsltStylesheetPtr style; xmlNsPtr ret; - const xmlChar *URI; + const xmlChar *URI = NULL; /* the replacement URI */ if ((ctxt == NULL) || (cur == NULL) || (out == NULL) || (ns == NULL)) return(NULL); - /* TODO apply cascading */ - if (ctxt->style->nsAliases != NULL) { - URI = (const xmlChar *) xmlHashLookup(ctxt->style->nsAliases, ns->href); - if (URI == NULL) - URI = ns->href; - } else + style = ctxt->style; + while (style != NULL) { + if (style->nsAliases != NULL) + URI = (const xmlChar *) + xmlHashLookup(ctxt->style->nsAliases, ns->href); + if (URI != NULL) + break; + + style = xsltNextImport(style); + } + + if (URI == NULL) URI = ns->href; if ((out->parent != NULL) && diff --git a/libxslt/pattern.c b/libxslt/pattern.c index 8d5556a..62f870a 100644 --- a/libxslt/pattern.c +++ b/libxslt/pattern.c @@ -22,6 +22,7 @@ #include "xslt.h" #include "xsltInternals.h" #include "xsltutils.h" +#include "imports.h" /* #define DEBUG_PARSING */ @@ -1229,7 +1230,7 @@ next_pattern: /** * xsltGetTemplate: - * @style: an XSLT stylesheet + * @ctxt: a XSLT process context * @node: an XML Node * * Finds the template applying to this node @@ -1237,30 +1238,90 @@ next_pattern: * Returns the xsltTemplatePtr or NULL if not found */ xsltTemplatePtr -xsltGetTemplate(xsltStylesheetPtr style, xmlNodePtr node) { +xsltGetTemplate(xsltTransformContextPtr ctxt, xmlNodePtr node) { + xsltStylesheetPtr style; xsltTemplatePtr ret = NULL; const xmlChar *name = NULL; xsltCompMatchPtr list = NULL; - if ((style == NULL) || (node == NULL)) + if ((ctxt == NULL) || (node == NULL)) return(NULL); - /* TODO : handle IDs/keys here ! */ - if (style->templatesHash != NULL) { + style = ctxt->style; + while (style != NULL) { + /* TODO : handle IDs/keys here ! */ + if (style->templatesHash != NULL) { + /* + * Use the top name as selector + */ + switch (node->type) { + case XML_ELEMENT_NODE: + case XML_ATTRIBUTE_NODE: + case XML_PI_NODE: + name = node->name; + break; + case XML_DOCUMENT_NODE: + case XML_HTML_DOCUMENT_NODE: + case XML_TEXT_NODE: + case XML_CDATA_SECTION_NODE: + case XML_COMMENT_NODE: + case XML_ENTITY_REF_NODE: + case XML_ENTITY_NODE: + case XML_DOCUMENT_TYPE_NODE: + case XML_DOCUMENT_FRAG_NODE: + case XML_NOTATION_NODE: + case XML_DTD_NODE: + case XML_ELEMENT_DECL: + case XML_ATTRIBUTE_DECL: + case XML_ENTITY_DECL: + case XML_NAMESPACE_DECL: + case XML_XINCLUDE_START: + case XML_XINCLUDE_END: + break; + default: + return(NULL); + + } + } + if (name != NULL) { + /* + * find the list of appliable expressions based on the name + */ + list = (xsltCompMatchPtr) xmlHashLookup(style->templatesHash, name); + } + while (list != NULL) { + if (xsltTestCompMatch(list, node)) { + ret = list->template; + break; + } + list = list->next; + } + list = NULL; + /* - * Use the top name as selector + * find alternate generic matches */ switch (node->type) { case XML_ELEMENT_NODE: + list = style->elemMatch; + break; case XML_ATTRIBUTE_NODE: + list = style->attrMatch; + break; case XML_PI_NODE: - name = node->name; + list = style->piMatch; break; case XML_DOCUMENT_NODE: case XML_HTML_DOCUMENT_NODE: + list = style->rootMatch; + break; case XML_TEXT_NODE: case XML_CDATA_SECTION_NODE: + list = style->textMatch; + break; case XML_COMMENT_NODE: + list = style->commentMatch; + break; case XML_ENTITY_REF_NODE: case XML_ENTITY_NODE: case XML_DOCUMENT_TYPE_NODE: @@ -1275,74 +1336,25 @@ xsltGetTemplate(xsltStylesheetPtr style, xmlNodePtr node) { case XML_XINCLUDE_END: break; default: - return(NULL); + break; } - } - if (name != NULL) { - /* - * find the list of appliable expressions based on the name - */ - list = (xsltCompMatchPtr) xmlHashLookup(style->templatesHash, name); - } - while (list != NULL) { - if (xsltTestCompMatch(list, node)) { - ret = list->template; - break; + while ((list != NULL) && + ((ret == NULL) || (list->priority > ret->priority))) { + if (xsltTestCompMatch(list, node)) { + ret = list->template; + break; + } } - list = list->next; - } - list = NULL; + if (ret != NULL) + return(ret); - /* - * find alternate generic matches - */ - switch (node->type) { - case XML_ELEMENT_NODE: - list = style->elemMatch; - break; - case XML_ATTRIBUTE_NODE: - list = style->attrMatch; - break; - case XML_PI_NODE: - list = style->piMatch; - break; - case XML_DOCUMENT_NODE: - case XML_HTML_DOCUMENT_NODE: - list = style->rootMatch; - break; - case XML_TEXT_NODE: - case XML_CDATA_SECTION_NODE: - list = style->textMatch; - break; - case XML_COMMENT_NODE: - list = style->commentMatch; - break; - case XML_ENTITY_REF_NODE: - case XML_ENTITY_NODE: - case XML_DOCUMENT_TYPE_NODE: - case XML_DOCUMENT_FRAG_NODE: - case XML_NOTATION_NODE: - case XML_DTD_NODE: - case XML_ELEMENT_DECL: - case XML_ATTRIBUTE_DECL: - case XML_ENTITY_DECL: - case XML_NAMESPACE_DECL: - case XML_XINCLUDE_START: - case XML_XINCLUDE_END: - break; - default: - break; - - } - while ((list != NULL) && - ((ret == NULL) || (list->priority > ret->priority))) { - if (xsltTestCompMatch(list, node)) { - ret = list->template; - break; - } + /* + * Cycle on next stylesheet import. + */ + style = xsltNextImport(style); } - return(ret); + return(NULL); } @@ -1373,36 +1385,3 @@ xsltFreeTemplateHashes(xsltStylesheetPtr style) { xsltFreeCompMatchList(style->commentMatch); } -/** - * xsltFindTemplate: - * @style: an XSLT stylesheet - * @name: the template name - * @nameURI: the template name URI - * - * Finds the named template. - * - * Returns the xsltTemplatePtr or NULL if not found - */ -xsltTemplatePtr -xsltFindTemplate(xsltStylesheetPtr style, const xmlChar *name, - const xmlChar *nameURI) { - xsltTemplatePtr cur; - - if ((style == NULL) || (name == NULL)) - return(NULL); - - /* TODO: apply stylesheet import order */ - cur = style->templates; - while (cur != NULL) { - if (xmlStrEqual(name, cur->name)) { - if (((nameURI == NULL) && (cur->nameURI == NULL)) || - ((nameURI != NULL) && (cur->nameURI != NULL) && - (xmlStrEqual(nameURI, cur->nameURI)))) { - return(cur); - } - } - cur = cur->next; - } - return(NULL); -} - diff --git a/libxslt/pattern.h b/libxslt/pattern.h index 96d32ae..30f9daf 100644 --- a/libxslt/pattern.h +++ b/libxslt/pattern.h @@ -17,12 +17,9 @@ extern "C" { int xsltAddTemplate (xsltStylesheetPtr style, xsltTemplatePtr cur); -xsltTemplatePtr xsltGetTemplate (xsltStylesheetPtr style, +xsltTemplatePtr xsltGetTemplate (xsltTransformContextPtr ctxt, xmlNodePtr node); void xsltFreeTemplateHashes (xsltStylesheetPtr style); -xsltTemplatePtr xsltFindTemplate (xsltStylesheetPtr style, - const xmlChar *name, - const xmlChar *nameURI); #ifdef __cplusplus } #endif diff --git a/libxslt/transform.c b/libxslt/transform.c index 578f7a6..5695ea2 100644 --- a/libxslt/transform.c +++ b/libxslt/transform.c @@ -33,6 +33,7 @@ #include "namespaces.h" #include "attributes.h" #include "templates.h" +#include "imports.h" #define DEBUG_PROCESS @@ -795,30 +796,9 @@ xsltDefaultProcessOneNode(xsltTransformContextPtr ctxt, xmlNodePtr node) { if ((IS_BLANK_NODE(cur)) && (cur->parent != NULL) && (ctxt->style->stripSpaces != NULL)) { - const xmlChar *val; - - if (strip_spaces == -1) { - /* TODO: add namespaces support */ - val = (const xmlChar *) - xmlHashLookup(ctxt->style->stripSpaces, - cur->parent->name); - if (val != NULL) { - if (xmlStrEqual(val, (xmlChar *) "strip")) - strip_spaces = 1; - if (xmlStrEqual(val, (xmlChar *) "preserve")) - strip_spaces = 0; - } - if (strip_spaces == -1) { - val = (const xmlChar *) - xmlHashLookup(ctxt->style->stripSpaces, - (const xmlChar *)"*"); - if ((val != NULL) && - (xmlStrEqual(val, (xmlChar *) "strip"))) - strip_spaces = 1; - else - strip_spaces = 0; - } - } + if (strip_spaces == -1) + strip_spaces = + xsltFindElemSpaceHandling(ctxt, cur->parent); if (strip_spaces == 1) { delete = cur; break; @@ -928,9 +908,9 @@ xsltCallTemplate(xsltTransformContextPtr ctxt, xmlNodePtr node, } } if (ns != NULL) - template = xsltFindTemplate(ctxt->style, ncname, ns->href); + template = xsltFindTemplate(ctxt, ncname, ns->href); else - template = xsltFindTemplate(ctxt->style, ncname, NULL); + template = xsltFindTemplate(ctxt, ncname, NULL); if (template == NULL) { xsltGenericError(xsltGenericDebugContext, "xslt:call-template: template %s not found\n", cur->name); @@ -1614,7 +1594,7 @@ xsltProcessOneNode(xsltTransformContextPtr ctxt, xmlNodePtr node) { xsltTemplatePtr template; xmlNodePtr oldNode; - template = xsltGetTemplate(ctxt->style, node); + template = xsltGetTemplate(ctxt, node); /* * If no template is found, apply the default rule. */ diff --git a/libxslt/xslt.c b/libxslt/xslt.c index d641412..eeb13dc 100644 --- a/libxslt/xslt.c +++ b/libxslt/xslt.c @@ -28,6 +28,7 @@ #include "namespaces.h" #include "attributes.h" #include "xsltutils.h" +#include "imports.h" #define DEBUG_PARSING @@ -41,9 +42,6 @@ #define IS_BLANK_NODE(n) \ (((n)->type == XML_TEXT_NODE) && (xsltIsBlank((n)->content))) -xsltStylesheetPtr xsltParseStylesheetProcess(xsltStylesheetPtr ret, - xmlDocPtr doc); -xsltStylesheetPtr xsltParseStylesheetDoc(xmlDocPtr doc); /************************************************************************ * * @@ -604,121 +602,6 @@ xsltParseStylesheetPreserveSpace(xsltStylesheetPtr style, xmlNodePtr cur) { } /** - * xsltParseStylesheetImport: - * @style: the XSLT stylesheet - * @template: the "strip-space" element - * - * parse an XSLT stylesheet strip-space element and record - * elements needing stripping - */ - -void -xsltParseStylesheetImport(xsltStylesheetPtr style, xmlNodePtr cur) { - xmlDocPtr import = NULL; - xmlChar *base = NULL; - xmlChar *uriRef = NULL; - xmlChar *URI = NULL; - xsltStylesheetPtr res; - - if ((cur == NULL) || (style == NULL)) - return; - - uriRef = xmlGetNsProp(cur, (const xmlChar *)"href", XSLT_NAMESPACE); - if (uriRef == NULL) { - xsltGenericError(xsltGenericErrorContext, - "xsl:import : missing href attribute\n"); - goto error; - } - - base = xmlNodeGetBase(style->doc, cur); - URI = xmlBuildURI(uriRef, base); - if (URI == NULL) { - xsltGenericError(xsltGenericErrorContext, - "xsl:import : invalid URI reference %s\n", uriRef); - goto error; - } - import = xmlParseFile((const char *)URI); - if (import == NULL) { - xsltGenericError(xsltGenericErrorContext, - "xsl:import : unable to load %s\n", URI); - goto error; - } - - res = xsltParseStylesheetDoc(import); - if (res != NULL) { - res->parent = style; - res->next = style->imports; - style->imports = res; - } - -error: - if (import != NULL) - xmlFreeDoc(import); - if (uriRef != NULL) - xmlFree(uriRef); - if (base != NULL) - xmlFree(base); - if (URI != NULL) - xmlFree(URI); -} - -/** - * xsltParseStylesheetInclude: - * @style: the XSLT stylesheet - * @template: the "strip-space" element - * - * parse an XSLT stylesheet strip-space element and record - * elements needing stripping - */ - -void -xsltParseStylesheetInclude(xsltStylesheetPtr style, xmlNodePtr cur) { - xmlDocPtr include = NULL, oldDoc; - xmlChar *base = NULL; - xmlChar *uriRef = NULL; - xmlChar *URI = NULL; - - if ((cur == NULL) || (style == NULL)) - return; - - uriRef = xmlGetNsProp(cur, (const xmlChar *)"href", XSLT_NAMESPACE); - if (uriRef == NULL) { - xsltGenericError(xsltGenericErrorContext, - "xsl:include : missing href attribute\n"); - goto error; - } - - base = xmlNodeGetBase(style->doc, cur); - URI = xmlBuildURI(uriRef, base); - if (URI == NULL) { - xsltGenericError(xsltGenericErrorContext, - "xsl:include : invalid URI reference %s\n", uriRef); - goto error; - } - include = xmlParseFile((const char *)URI); - if (include == NULL) { - xsltGenericError(xsltGenericErrorContext, - "xsl:include : unable to load %s\n", URI); - goto error; - } - - oldDoc = style->doc; - style->doc = include; - xsltParseStylesheetProcess(style, include); - style->doc = oldDoc; - -error: - if (include != NULL) - xmlFreeDoc(include); - if (uriRef != NULL) - xmlFree(uriRef); - if (base != NULL) - xmlFree(base); - if (URI != NULL) - xmlFree(URI); -} - -/** * xsltParseStylesheetStripSpace: * @style: the XSLT stylesheet * @template: the "strip-space" element diff --git a/libxslt/xsltInternals.h b/libxslt/xsltInternals.h index 542774d..c185ea3 100644 --- a/libxslt/xsltInternals.h +++ b/libxslt/xsltInternals.h @@ -201,6 +201,9 @@ void xsltFreeStylesheet (xsltStylesheetPtr sheet); int xsltIsBlank (xmlChar *str); void xsltFreeStackElemList (xsltStackElemPtr elem); +xsltStylesheetPtr xsltParseStylesheetProcess(xsltStylesheetPtr ret, + xmlDocPtr doc); +xsltStylesheetPtr xsltParseStylesheetDoc (xmlDocPtr doc); #ifdef __cplusplus } #endif -- 2.7.4