[libxslt] document('') fails to return stylesheets parsed from memory



commit 5e184e7154e8aa466e988f17c8b97b65196f94bf
Author: Jason Viers <bean beanalby net>
Date:   Thu Aug 16 17:41:00 2012 +0800

    document('') fails to return stylesheets parsed from memory
    
    If an XSL stylesheet is from memory (e.g. xmlParseMemory), then xpath
    expressions referencing "document('')" will never return a match.
    
    When getting down into it, I understand the logic "document() is resolved
    relative to the XSL's location, reading from memory has no location, therefore
    buzz off", but the XSL spec seems to address this:
    
    http://www.w3.org/TR/xslt#document
    "Note that a zero-length URI reference is a reference to the document relative
    to which the URI reference is being resolved; thus document("") refers to the
    root node of the stylesheet; the tree representation of the stylesheet is
    exactly the same as if the XML document containing the stylesheet was the
    initial source document."
    
    The fact that the behavior differs in this case between fromFile & fromMemory
    definitely caught me off guard, and IMHO fixing that scenario is worth the
    one-off-ness of the fix.

 libxslt/functions.c |   14 ++++++++++----
 1 files changed, 10 insertions(+), 4 deletions(-)
---
diff --git a/libxslt/functions.c b/libxslt/functions.c
index 01852b8..5a8eb79 100644
--- a/libxslt/functions.c
+++ b/libxslt/functions.c
@@ -302,6 +302,8 @@ xsltDocumentFunction(xmlXPathParserContextPtr ctxt, int nargs)
     if (obj->stringval == NULL) {
         valuePush(ctxt, xmlXPathNewNodeSet(NULL));
     } else {
+        xsltTransformContextPtr tctxt;
+        tctxt = xsltXPathGetTransformContext(ctxt);
         if ((obj2 != NULL) && (obj2->nodesetval != NULL) &&
             (obj2->nodesetval->nodeNr > 0) &&
             IS_XSLT_REAL_NODE(obj2->nodesetval->nodeTab[0])) {
@@ -314,9 +316,6 @@ xsltDocumentFunction(xmlXPathParserContextPtr ctxt, int nargs)
             }
             base = xmlNodeGetBase(target->doc, target);
         } else {
-            xsltTransformContextPtr tctxt;
-
-            tctxt = xsltXPathGetTransformContext(ctxt);
             if ((tctxt != NULL) && (tctxt->inst != NULL)) {
                 base = xmlNodeGetBase(tctxt->inst->doc, tctxt->inst);
             } else if ((tctxt != NULL) && (tctxt->style != NULL) &&
@@ -329,7 +328,14 @@ xsltDocumentFunction(xmlXPathParserContextPtr ctxt, int nargs)
         if (base != NULL)
             xmlFree(base);
         if (URI == NULL) {
-            valuePush(ctxt, xmlXPathNewNodeSet(NULL));
+            if ((tctxt != NULL) && (tctxt->style != NULL) &&
+                (tctxt->style->doc != NULL) &&
+                (xmlStrEqual(URI, tctxt->style->doc->URL))) {
+                /* This selects the stylesheet's doc itself. */
+                valuePush(ctxt, xmlXPathNewNodeSet((xmlNodePtr) tctxt->style->doc));
+            } else {
+                valuePush(ctxt, xmlXPathNewNodeSet(NULL));
+            }
         } else {
 	    xsltDocumentFunctionLoadDocument( ctxt, URI );
 	    xmlFree(URI);



[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]