* *
********
+Leak:
+ - find and fix memleak in xmlspec
+ => this is new ...
+
Doc:
- manpage and doc for xsltproc
- example in 2.7 would force to validate
Import:
- -> make sure we use the cascade wherever it's needed
Extra functions:
-> document() should not be a problem since Result Tree Fragments are
implemented
=> started, incomplete
- -> missing key support
ID and Key support:
-> Id should be simple, key will probably requires some hash tables.
-Templates:
- -> check the built-in template rule for attributes
- -> make sure @xxx matches are applied
-
Pattern tester:
-> try to optimize for ID scan and tests.
- -> support for mode
Pattern scanner:
-> add error checks on all returns
-> add lang and case-order
-> add foreign sorting functions (interfaces ?).
-Validity:
- -> should we add validation by default ? Make this an option
- -> redirrect validity errors
-
-Contextual error reporting:
- -> provide a couple of functions providing context analysis, not urgent
-
********
* *
* DONE *
* *
********
+Templates:
+ -> check the built-in template rule for attributes
+ -> make sure @xxx matches are applied
+
+Contextual error reporting:
+ -> provide a couple of functions providing context analysis, not urgent
+
+Validity:
+ -> should we add validation by default ? Make this an option
+ -> redirrect validity errors
+ => done added a special parsing mode
+
Import:
-> parse them
-> provide functions to circulate in the import tree of stylesheets
+ -> make sure we use the cascade wherever it's needed
Extra functions:
-> make a separate module.
Pattern scanner:
-> compute priority
-> handle unions
+ -> support for mode
=> done
Pattern tester:
* Daniel.Veillard@imag.fr
*/
+/*
+ * TODO: handle pathological cases like *[*[@a="b"]]
+ * TODO: detect [number] at compilation, optimize accordingly
+ */
+
#include "xsltconfig.h"
#include <string.h>
xmlChar *value;
xmlChar *value2;
xmlChar *value3;
+ /*
+ * Optimisations for count
+ */
+ xmlNodePtr previous;
+ int index;
+ int len;
};
struct _xsltCompMatch {
(node->type == XML_ELEMENT_NODE) &&
(node->parent != NULL)) {
- /* TODO: cache those informations !!! */
- xmlNodePtr siblings = node->parent->children;
+ if ((select->previous != NULL) &&
+ (select->previous->parent == node->parent)) {
+ /*
+ * just walk back to adjust the index
+ */
+ int i = 0;
+ xmlNodePtr sibling = node;
- while (siblings != NULL) {
- if (siblings->type == XML_ELEMENT_NODE) {
- if (siblings == node) {
- len++;
- pos = len;
- } else if (xmlStrEqual(node->name,
- siblings->name)) {
- len++;
+ while (sibling != NULL) {
+ if (sibling == select->previous)
+ break;
+ if (xmlStrEqual(node->name, sibling->name)) {
+ if ((select->value2 == NULL) ||
+ ((sibling->ns != NULL) &&
+ (xmlStrEqual(select->value2,
+ sibling->ns->href))))
+ i++;
+ }
+ sibling = sibling->prev;
+ }
+ if (sibling == NULL) {
+ /* hum going backward in document order ... */
+ i = 0;
+ sibling = node;
+ while (sibling != NULL) {
+ if (sibling == select->previous)
+ break;
+ if ((select->value2 == NULL) ||
+ ((sibling->ns != NULL) &&
+ (xmlStrEqual(select->value2,
+ sibling->ns->href))))
+ i--;
+ sibling = sibling->next;
}
}
- siblings = siblings->next;
+ if (sibling != NULL) {
+ pos = select->index + i;
+ len = select->len;
+ select->previous = node;
+ select->index = pos;
+ } else
+ pos = 0;
+ } else {
+ /*
+ * recompute the index
+ */
+ xmlNodePtr siblings = node->parent->children;
+
+ while (siblings != NULL) {
+ if (siblings->type == XML_ELEMENT_NODE) {
+ if (siblings == node) {
+ len++;
+ pos = len;
+ } else if (xmlStrEqual(node->name,
+ siblings->name)) {
+ if ((select->value2 == NULL) ||
+ ((siblings->ns != NULL) &&
+ (xmlStrEqual(select->value2,
+ siblings->ns->href))))
+ len++;
+ }
+ }
+ siblings = siblings->next;
+ }
}
if (pos != 0) {
ctxt->xpathCtxt->contextSize = len;
ctxt->xpathCtxt->proximityPosition = pos;
+ select->previous = node;
+ select->index = pos;
+ select->len = len;
}
} else if ((select != NULL) && (select->op == XSLT_OP_ALL)) {
- xmlNodePtr siblings = node->parent->children;
+ if ((select->previous != NULL) &&
+ (select->previous->parent == node->parent)) {
+ /*
+ * just walk back to adjust the index
+ */
+ int i = 0;
+ xmlNodePtr sibling = node;
+
+ while (sibling != NULL) {
+ if (sibling == select->previous)
+ break;
+ if (sibling->type == XML_ELEMENT_NODE)
+ i++;
+ sibling = sibling->prev;
+ }
+ if (sibling == NULL) {
+ /* hum going backward in document order ... */
+ i = 0;
+ sibling = node;
+ while (sibling != NULL) {
+ if (sibling == select->previous)
+ break;
+ if (sibling->type == XML_ELEMENT_NODE)
+ i--;
+ sibling = sibling->next;
+ }
+ }
+ if (sibling != NULL) {
+ pos = select->index + i;
+ len = select->len;
+ select->previous = node;
+ select->index = pos;
+ } else
+ pos = 0;
+ } else {
+ /*
+ * recompute the index
+ */
+ xmlNodePtr siblings = node->parent->children;
- while (siblings != NULL) {
- if (siblings->type == XML_ELEMENT_NODE) {
- len++;
- if (siblings == node) {
- pos = len;
+ while (siblings != NULL) {
+ if (siblings->type == XML_ELEMENT_NODE) {
+ len++;
+ if (siblings == node) {
+ pos = len;
+ }
}
+ siblings = siblings->next;
}
- siblings = siblings->next;
}
if (pos != 0) {
ctxt->xpathCtxt->contextSize = len;
ctxt->xpathCtxt->proximityPosition = pos;
+ select->previous = node;
+ select->index = pos;
+ select->len = len;
}
}
oldNode = ctxt->node;
int varsNr; /* Nb of variable list in the stack */
int varsMax; /* Size of the variable list stack */
xsltStackElemPtr *varsTab; /* the variable list stack */
+ int varsComputed; /* switched during param template
+ evaluation */
+
+ /*
+ * Extensions
+ */
+ xmlHashTablePtr extFunctions; /* the extension functions */
+ xmlHashTablePtr extElements; /* the extension elements */
const xmlChar *mode; /* the current mode */
const xmlChar *modeURI; /* the current mode URI */
xsltTransformState state; /* the current state */
};
+typedef void (*xsltTransformFunction) (xsltTransformContextPtr ctxt,
+ xmlNodePtr node, xmlNodePtr inst);
+
#define CHECK_STOPPED if (ctxt->state == XSLT_STATE_STOPPED) return;
#define CHECK_STOPPEDE if (ctxt->state == XSLT_STATE_STOPPED) goto error;
#define CHECK_STOPPED0 if (ctxt->state == XSLT_STATE_STOPPED) return(0);