ReactOS 0.4.16-dev-2208-g6350669
variables.c File Reference
#include "libxslt.h"
#include <string.h>
#include <libxml/xmlmemory.h>
#include <libxml/tree.h>
#include <libxml/valid.h>
#include <libxml/hash.h>
#include <libxml/xmlerror.h>
#include <libxml/xpath.h>
#include <libxml/xpathInternals.h>
#include <libxml/parserInternals.h>
#include <libxml/dict.h>
#include "xslt.h"
#include "xsltInternals.h"
#include "xsltutils.h"
#include "variables.h"
#include "transform.h"
#include "imports.h"
#include "preproc.h"
#include "keys.h"
Include dependency graph for variables.c:

Go to the source code of this file.

Macros

#define IN_LIBXSLT
 
#define XSLT_VAR_GLOBAL   (1<<0)
 
#define XSLT_VAR_IN_SELECT   (1<<1)
 
#define XSLT_TCTXT_VARIABLE(c)   ((xsltStackElemPtr) (c)->contextVariable)
 

Functions

xmlDocPtr xsltCreateRVT (xsltTransformContextPtr ctxt)
 
int xsltRegisterTmpRVT (xsltTransformContextPtr ctxt, xmlDocPtr RVT)
 
int xsltRegisterLocalRVT (xsltTransformContextPtr ctxt, xmlDocPtr RVT)
 
int xsltExtensionInstructionResultFinalize (xsltTransformContextPtr ctxt ATTRIBUTE_UNUSED)
 
int xsltExtensionInstructionResultRegister (xsltTransformContextPtr ctxt ATTRIBUTE_UNUSED, xmlXPathObjectPtr obj ATTRIBUTE_UNUSED)
 
int xsltFlagRVTs (xsltTransformContextPtr ctxt, xmlXPathObjectPtr obj, int val)
 
void xsltReleaseRVT (xsltTransformContextPtr ctxt, xmlDocPtr RVT)
 
int xsltRegisterPersistRVT (xsltTransformContextPtr ctxt, xmlDocPtr RVT)
 
void xsltFreeRVTs (xsltTransformContextPtr ctxt)
 
static xsltStackElemPtr xsltNewStackElem (xsltTransformContextPtr ctxt)
 
static xsltStackElemPtr xsltCopyStackElem (xsltStackElemPtr elem)
 
static void xsltFreeStackElem (xsltStackElemPtr elem)
 
static void xsltFreeStackElemEntry (void *payload, const xmlChar *name ATTRIBUTE_UNUSED)
 
void xsltFreeStackElemList (xsltStackElemPtr elem)
 
: the local part of the name

xsltStackLookup: @ctxt: an XSLT transformation context

@nameURI: the URI part of the name

Locate an element in the stack based on its name.

static xsltStackElemPtr xsltStackLookup (xsltTransformContextPtr ctxt, const xmlChar *name, const xmlChar *nameURI)
 
: the variable name

xsltXPathVariableLookup: @ctxt: a void * but the the XSLT transformation context actually

@ns_uri: the variable namespace URI

This is the entry point when a varibale is needed by the XPath interpretor.

Returns the value or NULL if not found

static int xsltCheckStackElem (xsltTransformContextPtr ctxt, const xmlChar *name, const xmlChar *nameURI)
 
static int xsltAddStackElem (xsltTransformContextPtr ctxt, xsltStackElemPtr elem)
 
int xsltAddStackElemList (xsltTransformContextPtr ctxt, xsltStackElemPtr elems)
 
static xmlXPathObjectPtr xsltEvalVariable (xsltTransformContextPtr ctxt, xsltStackElemPtr variable, xsltStylePreCompPtr castedComp)
 
static xmlXPathObjectPtr xsltEvalGlobalVariable (xsltStackElemPtr elem, xsltTransformContextPtr ctxt)
 
static void xsltEvalGlobalVariableWrapper (void *payload, void *data, const xmlChar *name ATTRIBUTE_UNUSED)
 
int xsltEvalGlobalVariables (xsltTransformContextPtr ctxt)
 
static int xsltRegisterGlobalVariable (xsltStylesheetPtr style, const xmlChar *name, const xmlChar *ns_uri, const xmlChar *sel, xmlNodePtr tree, xsltStylePreCompPtr comp, const xmlChar *value)
 
static xmlXPathObjectPtr xsltGlobalVariableLookup (xsltTransformContextPtr ctxt, const xmlChar *name, const xmlChar *ns_uri)
 
xmlXPathObjectPtr xsltVariableLookup (xsltTransformContextPtr ctxt, const xmlChar *name, const xmlChar *ns_uri)
 
xsltStackElemPtr xsltParseStylesheetCallerParam (xsltTransformContextPtr ctxt, xmlNodePtr inst)
 
void xsltParseGlobalVariable (xsltStylesheetPtr style, xmlNodePtr cur)
 
void xsltParseGlobalParam (xsltStylesheetPtr style, xmlNodePtr cur)
 
void xsltParseStylesheetVariable (xsltTransformContextPtr ctxt, xmlNodePtr inst)
 
void xsltParseStylesheetParam (xsltTransformContextPtr ctxt, xmlNodePtr cur)
 
void xsltFreeGlobalVariables (xsltTransformContextPtr ctxt)
 
xmlXPathObjectPtr xsltXPathVariableLookup (void *ctxt, const xmlChar *name, const xmlChar *ns_uri)
 
: a null terminated parameter name

xsltProcessUserParamInternal

@ctxt: the XSLT transformation context

@value: a null terminated value (may be an XPath expression) @eval: 0 to treat the value literally, else evaluate as XPath expression

If @eval is 0 then @value is treated literally and is stored in the global parameter/variable table without any change.

Uf @eval is 1 then @value is treated as an XPath expression and is evaluated. In this case, if you want to pass a string which will be interpreted literally then it must be enclosed in single or double quotes. If the string contains single quotes (double quotes) then it cannot be enclosed single quotes (double quotes). If the string which you want to be treated literally contains both single and double quotes (e.g. Meet at Joe's for "Twelfth Night" at 7 o'clock) then there is no suitable quoting character. You cannot use ' or " inside the string because the replacement of character entities with their equivalents is done at a different stage of processing. The solution is to call xsltQuoteUserParams or xsltQuoteOneUserParam.

This needs to be done on parsed stylesheets before starting to apply transformations. Normally this will be called (directly or indirectly) only from xsltEvalUserParams, xsltEvalOneUserParam, xsltQuoteUserParams, or xsltQuoteOneUserParam.

Returns 0 in case of success, -1 in case of error

static int xsltProcessUserParamInternal (xsltTransformContextPtr ctxt, const xmlChar *name, const xmlChar *value, int eval)
 
int xsltEvalUserParams (xsltTransformContextPtr ctxt, const char **params)
 
int xsltQuoteUserParams (xsltTransformContextPtr ctxt, const char **params)
 
: a null terminated string giving the name of the parameter

xsltQuoteOneUserParam: @ctxt: the XSLT transformation context

@value: a null terminated string giving the parameter value

This is normally called from xsltQuoteUserParams to process a single parameter from a list of parameters. The @value is stored in the context's global variable/parameter hash table.

Returns 0 in case of success, -1 in case of error.

int xsltEvalOneUserParam (xsltTransformContextPtr ctxt, const xmlChar *name, const xmlChar *value)
 
int xsltQuoteOneUserParam (xsltTransformContextPtr ctxt, const xmlChar *name, const xmlChar *value)
 
static xsltStackElemPtr xsltBuildVariable (xsltTransformContextPtr ctxt, xsltStylePreCompPtr castedComp, xmlNodePtr tree)
 
static int xsltRegisterVariable (xsltTransformContextPtr ctxt, xsltStylePreCompPtr castedComp, xmlNodePtr tree, int isParam)
 

Variables

static const xmlCharxsltComputingGlobalVarMarker
 

Macro Definition Documentation

◆ IN_LIBXSLT

#define IN_LIBXSLT

Definition at line 12 of file variables.c.

◆ XSLT_TCTXT_VARIABLE

#define XSLT_TCTXT_VARIABLE (   c)    ((xsltStackElemPtr) (c)->contextVariable)

Definition at line 48 of file variables.c.

◆ XSLT_VAR_GLOBAL

#define XSLT_VAR_GLOBAL   (1<<0)

Definition at line 46 of file variables.c.

◆ XSLT_VAR_IN_SELECT

#define XSLT_VAR_IN_SELECT   (1<<1)

Definition at line 47 of file variables.c.

Function Documentation

◆ xsltAddStackElem()

static int xsltAddStackElem ( xsltTransformContextPtr  ctxt,
xsltStackElemPtr  elem 
)
static

xsltAddStackElem: @ctxt: xn XSLT transformation context @elem: a stack element

Push an element (or list) onto the stack. In case of a list, each member will be pushed into a seperate slot; i.e. there's always 1 stack entry for 1 stack element.

Returns 0 in case of success, -1 in case of failure.

Definition at line 754 of file variables.c.

755{
756 if ((ctxt == NULL) || (elem == NULL))
757 return(-1);
758
759 do {
760 if (ctxt->varsNr >= ctxt->varsMax) {
761 xsltStackElemPtr *tmp;
762 int newMax = ctxt->varsMax == 0 ? 10 : 2 * ctxt->varsMax;
763
764 tmp = (xsltStackElemPtr *) xmlRealloc(ctxt->varsTab,
765 newMax * sizeof(*tmp));
766 if (tmp == NULL) {
767 xmlGenericError(xmlGenericErrorContext, "realloc failed !\n");
768 return (-1);
769 }
770 ctxt->varsTab = tmp;
771 ctxt->varsMax = newMax;
772 }
773 ctxt->varsTab[ctxt->varsNr++] = elem;
774 ctxt->vars = elem;
775
776 elem = elem->next;
777 } while (elem != NULL);
778
779 return(0);
780}
#define NULL
Definition: types.h:112
static size_t elem
Definition: string.c:71
void * xmlGenericErrorContext
Definition: globals.c:410
xmlReallocFunc xmlRealloc
Definition: globals.c:214
xmlGenericErrorFunc xmlGenericError
Definition: globals.c:396
xsltStackElemPtr vars
xsltStackElemPtr * varsTab

Referenced by xsltAddStackElemList(), and xsltRegisterVariable().

◆ xsltAddStackElemList()

int xsltAddStackElemList ( xsltTransformContextPtr  ctxt,
xsltStackElemPtr  elems 
)

xsltAddStackElemList: @ctxt: xn XSLT transformation context @elems: a stack element list

Push an element list onto the stack.

Returns 0 in case of success, -1 in case of failure.

Definition at line 792 of file variables.c.

793{
794 return(xsltAddStackElem(ctxt, elems));
795}
static int xsltAddStackElem(xsltTransformContextPtr ctxt, xsltStackElemPtr elem)
Definition: variables.c:754

◆ xsltBuildVariable()

static xsltStackElemPtr xsltBuildVariable ( xsltTransformContextPtr  ctxt,
xsltStylePreCompPtr  castedComp,
xmlNodePtr  tree 
)
static

xsltBuildVariable: @ctxt: the XSLT transformation context @comp: the precompiled form @tree: the tree if select is NULL

Computes a new variable value.

Returns the xsltStackElemPtr or NULL in case of error

Definition at line 1790 of file variables.c.

1793{
1794#ifdef XSLT_REFACTORED
1795 xsltStyleBasicItemVariablePtr comp =
1796 (xsltStyleBasicItemVariablePtr) castedComp;
1797#else
1798 xsltStylePreCompPtr comp = castedComp;
1799#endif
1801
1802#ifdef WITH_XSLT_DEBUG_VARIABLE
1804 "Building variable %s", comp->name));
1805 if (comp->select != NULL)
1807 " select %s", comp->select));
1809#endif
1810
1811 elem = xsltNewStackElem(ctxt);
1812 if (elem == NULL)
1813 return(NULL);
1814 elem->comp = (xsltStylePreCompPtr) comp;
1815 elem->name = comp->name;
1816 elem->select = comp->select;
1817 elem->nameURI = comp->ns;
1818 elem->tree = tree;
1819 elem->value = xsltEvalVariable(ctxt, elem,
1820 (xsltStylePreCompPtr) comp);
1821 elem->computed = 1;
1822 return(elem);
1823}
struct _tree tree
static xmlXPathObjectPtr xsltEvalVariable(xsltTransformContextPtr ctxt, xsltStackElemPtr variable, xsltStylePreCompPtr castedComp)
Definition: variables.c:814
static xsltStackElemPtr xsltNewStackElem(xsltTransformContextPtr ctxt)
Definition: variables.c:503
xsltStylePreComp * xsltStylePreCompPtr
xmlGenericErrorFunc xsltGenericDebug
Definition: xsltutils.c:632
void * xsltGenericDebugContext
Definition: xsltutils.c:633
@ XSLT_TRACE_VARIABLES
Definition: xsltutils.h:124
#define XSLT_TRACE(ctxt, code, call)
Definition: xsltutils.h:132

Referenced by xsltParseStylesheetCallerParam(), and xsltRegisterVariable().

◆ xsltCheckStackElem()

static int xsltCheckStackElem ( xsltTransformContextPtr  ctxt,
const xmlChar name,
const xmlChar nameURI 
)
static

Definition at line 719 of file variables.c.

720 {
722
723 if ((ctxt == NULL) || (name == NULL))
724 return(-1);
725
726 cur = xsltStackLookup(ctxt, name, nameURI);
727 if (cur == NULL)
728 return(0);
729 if (cur->comp != NULL) {
730 if (cur->comp->type == XSLT_FUNC_WITHPARAM)
731 return(3);
732 else if (cur->comp->type == XSLT_FUNC_PARAM)
733 return(2);
734 }
735
736 return(1);
737}
FxCollectionEntry * cur
Definition: name.c:39
static xsltStackElemPtr xsltStackLookup(xsltTransformContextPtr ctxt, const xmlChar *name, const xmlChar *nameURI)
Definition: variables.c:650
@ XSLT_FUNC_WITHPARAM
@ XSLT_FUNC_PARAM

Referenced by xsltRegisterVariable().

◆ xsltCopyStackElem()

static xsltStackElemPtr xsltCopyStackElem ( xsltStackElemPtr  elem)
static

xsltCopyStackElem: @elem: an XSLT stack element

Makes a copy of the stack element

Returns the copy of NULL

Definition at line 539 of file variables.c.

539 {
541
543 if (cur == NULL) {
545 "xsltCopyStackElem : malloc failed\n");
546 return(NULL);
547 }
548 memset(cur, 0, sizeof(xsltStackElem));
549 cur->context = elem->context;
550 cur->name = elem->name;
551 cur->nameURI = elem->nameURI;
552 cur->select = elem->select;
553 cur->tree = elem->tree;
554 cur->comp = elem->comp;
555 return(cur);
556}
xmlMallocFunc xmlMalloc
Definition: globals.c:193
#define memset(x, y, z)
Definition: compat.h:39
xsltStackElem * xsltStackElemPtr
void xsltTransformError(xsltTransformContextPtr ctxt, xsltStylesheetPtr style, xmlNodePtr node, const char *msg,...)
Definition: xsltutils.c:762

Referenced by xsltEvalGlobalVariables().

◆ xsltCreateRVT()

xmlDocPtr xsltCreateRVT ( xsltTransformContextPtr  ctxt)

xsltCreateRVT: @ctxt: an XSLT transformation context

Creates a Result Value Tree (the XSLT 1.0 term for this is "Result Tree Fragment")

Returns the result value tree or NULL in case of API or internal errors.

Definition at line 65 of file variables.c.

66{
67 xmlDocPtr container;
68
69 /*
70 * Question: Why is this function public?
71 * Answer: It is called by the EXSLT module.
72 */
73 if (ctxt == NULL)
74 return(NULL);
75
76 /*
77 * Reuse a RTF from the cache if available.
78 */
79 if (ctxt->cache->RVT) {
80 container = ctxt->cache->RVT;
81 ctxt->cache->RVT = (xmlDocPtr) container->next;
82 /* clear the internal pointers */
83 container->next = NULL;
84 container->prev = NULL;
85 if (ctxt->cache->nbRVT > 0)
86 ctxt->cache->nbRVT--;
87#ifdef XSLT_DEBUG_PROFILE_CACHE
88 ctxt->cache->dbgReusedRVTs++;
89#endif
90 return(container);
91 }
92
93 container = xmlNewDoc(NULL);
94 if (container == NULL)
95 return(NULL);
96 container->dict = ctxt->dict;
99 container->doc = container;
100 container->parent = NULL;
101 return(container);
102}
if(dx< 0)
Definition: linetemp.h:194
int xmlDictReference(xmlDictPtr dict)
Definition: dict.c:317
xsltTransformCachePtr cache
#define XSLT_MARK_RES_TREE_FRAG(n)
Definition: xsltInternals.h:47

Referenced by xsltEvalGlobalVariable(), and xsltEvalVariable().

◆ xsltEvalGlobalVariable()

static xmlXPathObjectPtr xsltEvalGlobalVariable ( xsltStackElemPtr  elem,
xsltTransformContextPtr  ctxt 
)
static

xsltEvalGlobalVariable: @elem: the variable or parameter @ctxt: the XSLT transformation context

Evaluates a the value of a global xsl:variable or xsl:param declaration.

Returns the XPath Object value or NULL in case of error

Definition at line 1047 of file variables.c.

1048{
1049 xmlXPathObjectPtr result = NULL;
1050 xmlNodePtr oldInst;
1051 const xmlChar* oldVarName;
1052
1053#ifdef XSLT_REFACTORED
1054 xsltStyleBasicItemVariablePtr comp;
1055#else
1057#endif
1058
1059 if ((ctxt == NULL) || (elem == NULL))
1060 return(NULL);
1061 if (elem->computed)
1062 return(elem->value);
1063
1064
1065#ifdef WITH_XSLT_DEBUG_VARIABLE
1067 "Evaluating global variable %s\n", elem->name));
1068#endif
1069
1070#ifdef WITH_DEBUGGER
1071 if ((ctxt->debugStatus != XSLT_DEBUG_NONE) &&
1072 elem->comp && elem->comp->inst)
1073 xslHandleDebugger(elem->comp->inst, NULL, NULL, ctxt);
1074#endif
1075
1076 oldInst = ctxt->inst;
1077#ifdef XSLT_REFACTORED
1078 comp = (xsltStyleBasicItemVariablePtr) elem->comp;
1079#else
1080 comp = elem->comp;
1081#endif
1082 oldVarName = elem->name;
1084 /*
1085 * OPTIMIZE TODO: We should consider instantiating global vars/params
1086 * on-demand. The vars/params don't need to be evaluated if never
1087 * called; and in the case of global params, if values for such params
1088 * are provided by the user.
1089 */
1090 if (elem->select != NULL) {
1091 xmlXPathCompExprPtr xpExpr = NULL;
1092 xmlDocPtr oldXPDoc;
1093 xmlNodePtr oldXPContextNode;
1094 int oldXPProximityPosition, oldXPContextSize, oldXPNsNr;
1095 xmlNsPtr *oldXPNamespaces;
1096 xmlXPathContextPtr xpctxt = ctxt->xpathCtxt;
1097
1098 if ((comp != NULL) && (comp->comp != NULL)) {
1099 xpExpr = comp->comp;
1100 } else {
1101 xpExpr = xmlXPathCtxtCompile(ctxt->xpathCtxt, elem->select);
1102 }
1103 if (xpExpr == NULL)
1104 goto error;
1105
1106
1107 if (comp != NULL)
1108 ctxt->inst = comp->inst;
1109 else
1110 ctxt->inst = NULL;
1111 /*
1112 * SPEC XSLT 1.0:
1113 * "At top-level, the expression or template specifying the
1114 * variable value is evaluated with the same context as that used
1115 * to process the root node of the source document: the current
1116 * node is the root node of the source document and the current
1117 * node list is a list containing just the root node of the source
1118 * document."
1119 */
1120 /*
1121 * Save context states.
1122 */
1123 oldXPDoc = xpctxt->doc;
1124 oldXPContextNode = xpctxt->node;
1125 oldXPProximityPosition = xpctxt->proximityPosition;
1126 oldXPContextSize = xpctxt->contextSize;
1127 oldXPNamespaces = xpctxt->namespaces;
1128 oldXPNsNr = xpctxt->nsNr;
1129
1130 xpctxt->node = ctxt->initialContextNode;
1131 xpctxt->doc = ctxt->initialContextDoc;
1132 xpctxt->contextSize = 1;
1133 xpctxt->proximityPosition = 1;
1134
1135 if (comp != NULL) {
1136
1137#ifdef XSLT_REFACTORED
1138 if (comp->inScopeNs != NULL) {
1139 xpctxt->namespaces = comp->inScopeNs->list;
1140 xpctxt->nsNr = comp->inScopeNs->xpathNumber;
1141 } else {
1142 xpctxt->namespaces = NULL;
1143 xpctxt->nsNr = 0;
1144 }
1145#else
1146 xpctxt->namespaces = comp->nsList;
1147 xpctxt->nsNr = comp->nsNr;
1148#endif
1149 } else {
1150 xpctxt->namespaces = NULL;
1151 xpctxt->nsNr = 0;
1152 }
1153
1154 result = xmlXPathCompiledEval(xpExpr, xpctxt);
1155
1156 /*
1157 * Restore Context states.
1158 */
1159 xpctxt->doc = oldXPDoc;
1160 xpctxt->node = oldXPContextNode;
1161 xpctxt->contextSize = oldXPContextSize;
1162 xpctxt->proximityPosition = oldXPProximityPosition;
1163 xpctxt->namespaces = oldXPNamespaces;
1164 xpctxt->nsNr = oldXPNsNr;
1165
1166 if ((comp == NULL) || (comp->comp == NULL))
1167 xmlXPathFreeCompExpr(xpExpr);
1168 if (result == NULL) {
1169 if (comp == NULL)
1171 "Evaluating global variable %s failed\n", elem->name);
1172 else
1173 xsltTransformError(ctxt, NULL, comp->inst,
1174 "Evaluating global variable %s failed\n", elem->name);
1175 ctxt->state = XSLT_STATE_STOPPED;
1176 goto error;
1177 }
1178
1179 /*
1180 * Mark all RVTs that are referenced from result as part
1181 * of this variable so they won't be freed too early.
1182 */
1184
1185#ifdef WITH_XSLT_DEBUG_VARIABLE
1186#ifdef LIBXML_DEBUG_ENABLED
1189 xmlXPathDebugDumpObject((FILE *)xsltGenericDebugContext,
1190 result, 0);
1191#endif
1192#endif
1193 } else {
1194 if (elem->tree == NULL) {
1195 result = xmlXPathNewCString("");
1196 } else {
1197 xmlDocPtr container;
1198 xmlNodePtr oldInsert;
1199 xmlDocPtr oldOutput, oldXPDoc;
1200 /*
1201 * Generate a result tree fragment.
1202 */
1203 container = xsltCreateRVT(ctxt);
1204 if (container == NULL)
1205 goto error;
1206 /*
1207 * Let the lifetime of the tree fragment be handled by
1208 * the Libxslt's garbage collector.
1209 */
1211
1212 oldOutput = ctxt->output;
1213 oldInsert = ctxt->insert;
1214
1215 oldXPDoc = ctxt->xpathCtxt->doc;
1216
1217 ctxt->output = container;
1218 ctxt->insert = (xmlNodePtr) container;
1219
1220 ctxt->xpathCtxt->doc = ctxt->initialContextDoc;
1221 /*
1222 * Process the sequence constructor.
1223 */
1224 xsltApplyOneTemplate(ctxt, ctxt->node, elem->tree, NULL, NULL);
1225
1226 ctxt->xpathCtxt->doc = oldXPDoc;
1227
1228 ctxt->insert = oldInsert;
1229 ctxt->output = oldOutput;
1230
1231 result = xmlXPathNewValueTree((xmlNodePtr) container);
1232 if (result == NULL) {
1233 result = xmlXPathNewCString("");
1234 } else {
1235 /*
1236 * This stops older libxml2 versions from freeing the nodes
1237 * in the tree.
1238 */
1239 result->boolval = 0;
1240 }
1241#ifdef WITH_XSLT_DEBUG_VARIABLE
1242#ifdef LIBXML_DEBUG_ENABLED
1245 xmlXPathDebugDumpObject((FILE *)xsltGenericDebugContext,
1246 result, 0);
1247#endif
1248#endif
1249 }
1250 }
1251
1252error:
1253 elem->name = oldVarName;
1254 ctxt->inst = oldInst;
1255 if (result != NULL) {
1256 elem->value = result;
1257 elem->computed = 1;
1258 }
1259 return(result);
1260}
void xsltApplyOneTemplate(xsltTransformContextPtr ctxt, xmlNodePtr contextNode, xmlNodePtr list, xsltTemplatePtr templ ATTRIBUTE_UNUSED, xsltStackElemPtr params)
Definition: transform.c:3313
#define stdout
#define stderr
GLuint64EXT * result
Definition: glext.h:11304
#define error(str)
Definition: mkdosfs.c:1605
xsltTransformState state
xmlNodePtr initialContextNode
xmlXPathContextPtr xpathCtxt
XSLTPUBFUN void XSLTCALL xslHandleDebugger(xmlNodePtr cur, xmlNodePtr node, xsltTemplatePtr templ, xsltTransformContextPtr ctxt)
xmlDocPtr xsltCreateRVT(xsltTransformContextPtr ctxt)
Definition: variables.c:65
int xsltRegisterPersistRVT(xsltTransformContextPtr ctxt, xmlDocPtr RVT)
Definition: variables.c:417
int xsltFlagRVTs(xsltTransformContextPtr ctxt, xmlXPathObjectPtr obj, int val)
Definition: variables.c:258
static const xmlChar * xsltComputingGlobalVarMarker
Definition: variables.c:43
#define XSLT_RVT_GLOBAL
Definition: variables.h:62
unsigned char xmlChar
Definition: xmlstring.h:28
@ XSLT_STATE_STOPPED
@ XSLT_DEBUG_NONE
Definition: xsltutils.h:304

Referenced by xsltEvalGlobalVariableWrapper(), and xsltGlobalVariableLookup().

◆ xsltEvalGlobalVariables()

int xsltEvalGlobalVariables ( xsltTransformContextPtr  ctxt)

xsltEvalGlobalVariables: @ctxt: the XSLT transformation context

Evaluates all global variables and parameters of a stylesheet. For internal use only. This is called at start of a transformation.

Returns 0 in case of success, -1 in case of error

Definition at line 1279 of file variables.c.

1279 {
1282
1283 if ((ctxt == NULL) || (ctxt->document == NULL))
1284 return(-1);
1285
1286#ifdef WITH_XSLT_DEBUG_VARIABLE
1288 "Registering global variables\n"));
1289#endif
1290 /*
1291 * Walk the list from the stylesheets and populate the hash table
1292 */
1293 style = ctxt->style;
1294 while (style != NULL) {
1295 elem = style->variables;
1296
1297#ifdef WITH_XSLT_DEBUG_VARIABLE
1298 if ((style->doc != NULL) && (style->doc->URL != NULL)) {
1300 "Registering global variables from %s\n",
1301 style->doc->URL));
1302 }
1303#endif
1304
1305 while (elem != NULL) {
1306 xsltStackElemPtr def;
1307
1308 /*
1309 * Global variables are stored in the variables pool.
1310 */
1311 def = (xsltStackElemPtr)
1313 elem->name, elem->nameURI);
1314 if (def == NULL) {
1315
1316 def = xsltCopyStackElem(elem);
1317 if (xmlHashAddEntry2(ctxt->globalVars,
1318 elem->name, elem->nameURI, def) < 0) {
1320 "hash update failed\n");
1321 xsltFreeStackElem(def);
1322 return(-1);
1323 }
1324 } else if ((elem->comp != NULL) &&
1325 (elem->comp->type == XSLT_FUNC_VARIABLE)) {
1326 /*
1327 * Redefinition of variables from a different stylesheet
1328 * should not generate a message.
1329 */
1330 if ((elem->comp->inst != NULL) &&
1331 (def->comp != NULL) && (def->comp->inst != NULL) &&
1332 (elem->comp->inst->doc == def->comp->inst->doc))
1333 {
1334 xsltTransformError(ctxt, style, elem->comp->inst,
1335 "Global variable %s already defined\n", elem->name);
1336 if (style != NULL) style->errors++;
1337 }
1338 }
1339 elem = elem->next;
1340 }
1341
1343 }
1344
1345 /*
1346 * This part does the actual evaluation
1347 */
1349
1350 return(0);
1351}
Arabic default style
Definition: afstyles.h:94
xsltStylesheetPtr xsltNextImport(xsltStylesheetPtr cur)
Definition: imports.c:297
void xmlHashScan(xmlHashTablePtr hash, xmlHashScanner scan, void *data)
Definition: hash.c:898
void * xmlHashLookup2(xmlHashTablePtr hash, const xmlChar *key, const xmlChar *key2)
Definition: hash.c:754
int xmlHashAddEntry2(xmlHashTablePtr hash, const xmlChar *key, const xmlChar *key2, void *payload)
Definition: hash.c:639
xsltStylePreCompPtr comp
xsltDocumentPtr document
xmlHashTablePtr globalVars
xsltStylesheetPtr style
static xsltStackElemPtr xsltCopyStackElem(xsltStackElemPtr elem)
Definition: variables.c:539
static void xsltEvalGlobalVariableWrapper(void *payload, void *data, const xmlChar *name ATTRIBUTE_UNUSED)
Definition: variables.c:1263
static void xsltFreeStackElem(xsltStackElemPtr elem)
Definition: variables.c:565
@ XSLT_FUNC_VARIABLE

Referenced by xsltApplyStylesheetInternal().

◆ xsltEvalGlobalVariableWrapper()

static void xsltEvalGlobalVariableWrapper ( void payload,
void data,
const xmlChar *name  ATTRIBUTE_UNUSED 
)
static

Definition at line 1263 of file variables.c.

1264 {
1267}
GLint GLenum GLsizei GLsizei GLsizei GLint GLsizei const GLvoid * data
Definition: gl.h:1950
static xmlXPathObjectPtr xsltEvalGlobalVariable(xsltStackElemPtr elem, xsltTransformContextPtr ctxt)
Definition: variables.c:1047

Referenced by xsltEvalGlobalVariables().

◆ xsltEvalOneUserParam()

int xsltEvalOneUserParam ( xsltTransformContextPtr  ctxt,
const xmlChar name,
const xmlChar value 
)

Definition at line 1751 of file variables.c.

1753 {
1755 1 /* xpath eval ? */);
1756}
Definition: pdh_main.c:96
static int xsltProcessUserParamInternal(xsltTransformContextPtr ctxt, const xmlChar *name, const xmlChar *value, int eval)
Definition: variables.c:1462

Referenced by xsltEvalUserParams().

◆ xsltEvalUserParams()

int xsltEvalUserParams ( xsltTransformContextPtr  ctxt,
const char **  params 
)

xsltEvalUserParams:

@ctxt: the XSLT transformation context @params: a NULL terminated array of parameters name/value tuples

Evaluate the global variables of a stylesheet. This needs to be done on parsed stylesheets before starting to apply transformations. Each of the parameters is evaluated as an XPath expression and stored in the global variables/parameter hash table. If you want your parameter used literally, use xsltQuoteUserParams.

Returns 0 in case of success, -1 in case of error

Definition at line 1686 of file variables.c.

1686 {
1687 size_t indx = 0;
1688 const xmlChar *name;
1689 const xmlChar *value;
1690
1691 if (params == NULL)
1692 return(0);
1693 while (params[indx] != NULL) {
1694 name = (const xmlChar *) params[indx++];
1695 value = (const xmlChar *) params[indx++];
1696 if (xsltEvalOneUserParam(ctxt, name, value) != 0)
1697 return(-1);
1698 }
1699 return 0;
1700}
GLenum const GLfloat * params
Definition: glext.h:5645
int xsltEvalOneUserParam(xsltTransformContextPtr ctxt, const xmlChar *name, const xmlChar *value)
Definition: variables.c:1751

Referenced by xsltApplyStylesheetInternal().

◆ xsltEvalVariable()

static xmlXPathObjectPtr xsltEvalVariable ( xsltTransformContextPtr  ctxt,
xsltStackElemPtr  variable,
xsltStylePreCompPtr  castedComp 
)
static

xsltEvalVariable: @ctxt: the XSLT transformation context @variable: the variable or parameter item @comp: the compiled XSLT instruction

Evaluate a variable value.

Returns the XPath Object value or NULL in case of error

Definition at line 814 of file variables.c.

816{
817#ifdef XSLT_REFACTORED
818 xsltStyleItemVariablePtr comp =
819 (xsltStyleItemVariablePtr) castedComp;
820#else
821 xsltStylePreCompPtr comp = castedComp;
822#endif
823 xmlXPathObjectPtr result = NULL;
824 xmlNodePtr oldInst;
825
826 if ((ctxt == NULL) || (variable == NULL))
827 return(NULL);
828
829 /*
830 * A variable or parameter are evaluated on demand; thus the
831 * context (of XSLT and XPath) need to be temporarily adjusted and
832 * restored on exit.
833 */
834 oldInst = ctxt->inst;
835
836#ifdef WITH_XSLT_DEBUG_VARIABLE
838 "Evaluating variable '%s'\n", variable->name));
839#endif
840 if (variable->select != NULL) {
841 xmlXPathCompExprPtr xpExpr = NULL;
842 xmlDocPtr oldXPDoc;
843 xmlNodePtr oldXPContextNode;
844 int oldXPProximityPosition, oldXPContextSize, oldXPNsNr;
845 xmlNsPtr *oldXPNamespaces;
846 xmlXPathContextPtr xpctxt = ctxt->xpathCtxt;
847 xsltStackElemPtr oldVar = ctxt->contextVariable;
848
849 if ((comp != NULL) && (comp->comp != NULL)) {
850 xpExpr = comp->comp;
851 } else {
852 xpExpr = xmlXPathCtxtCompile(ctxt->xpathCtxt, variable->select);
853 }
854 if (xpExpr == NULL)
855 return(NULL);
856 /*
857 * Save context states.
858 */
859 oldXPDoc = xpctxt->doc;
860 oldXPContextNode = xpctxt->node;
861 oldXPProximityPosition = xpctxt->proximityPosition;
862 oldXPContextSize = xpctxt->contextSize;
863 oldXPNamespaces = xpctxt->namespaces;
864 oldXPNsNr = xpctxt->nsNr;
865
866 xpctxt->node = ctxt->node;
867 /*
868 * OPTIMIZE TODO: Lame try to set the context doc.
869 * Get rid of this somehow in xpath.c.
870 */
871 if ((ctxt->node->type != XML_NAMESPACE_DECL) &&
872 ctxt->node->doc)
873 xpctxt->doc = ctxt->node->doc;
874 /*
875 * BUG TODO: The proximity position and the context size will
876 * potentially be wrong.
877 * Example:
878 * <xsl:template select="foo">
879 * <xsl:variable name="pos" select="position()"/>
880 * <xsl:for-each select="bar">
881 * <xsl:value-of select="$pos"/>
882 * </xsl:for-each>
883 * </xsl:template>
884 * Here the proximity position and context size are changed
885 * to the context of <xsl:for-each select="bar">, but
886 * the variable needs to be evaluated in the context of
887 * <xsl:template select="foo">.
888 */
889 if (comp != NULL) {
890
891#ifdef XSLT_REFACTORED
892 if (comp->inScopeNs != NULL) {
893 xpctxt->namespaces = comp->inScopeNs->list;
894 xpctxt->nsNr = comp->inScopeNs->xpathNumber;
895 } else {
896 xpctxt->namespaces = NULL;
897 xpctxt->nsNr = 0;
898 }
899#else
900 xpctxt->namespaces = comp->nsList;
901 xpctxt->nsNr = comp->nsNr;
902#endif
903 } else {
904 xpctxt->namespaces = NULL;
905 xpctxt->nsNr = 0;
906 }
907
908 /*
909 * We need to mark that we are "selecting" a var's value;
910 * if any tree fragments are created inside the expression,
911 * then those need to be stored inside the variable; otherwise
912 * we'll eventually free still referenced fragments, before
913 * we leave the scope of the variable.
914 */
917
918 result = xmlXPathCompiledEval(xpExpr, xpctxt);
919
921 /*
922 * Restore Context states.
923 */
924 ctxt->contextVariable = oldVar;
925
926 xpctxt->doc = oldXPDoc;
927 xpctxt->node = oldXPContextNode;
928 xpctxt->contextSize = oldXPContextSize;
929 xpctxt->proximityPosition = oldXPProximityPosition;
930 xpctxt->namespaces = oldXPNamespaces;
931 xpctxt->nsNr = oldXPNsNr;
932
933 if ((comp == NULL) || (comp->comp == NULL))
934 xmlXPathFreeCompExpr(xpExpr);
935 if (result == NULL) {
937 (comp != NULL) ? comp->inst : NULL,
938 "Failed to evaluate the expression of variable '%s'.\n",
939 variable->name);
941
942#ifdef WITH_XSLT_DEBUG_VARIABLE
943#ifdef LIBXML_DEBUG_ENABLED
944 } else {
947 xmlXPathDebugDumpObject((FILE *)xsltGenericDebugContext,
948 result, 0);
949#endif
950#endif
951 }
952 } else {
953 if (variable->tree == NULL) {
954 result = xmlXPathNewCString("");
955 } else {
956 if (variable->tree) {
957 xmlDocPtr container;
958 xmlNodePtr oldInsert;
959 xmlDocPtr oldOutput;
960 const xmlChar *oldLastText;
961 int oldLastTextSize, oldLastTextUse;
962 xsltStackElemPtr oldVar = ctxt->contextVariable;
963
964 /*
965 * Generate a result tree fragment.
966 */
967 container = xsltCreateRVT(ctxt);
968 if (container == NULL)
969 goto error;
970 /*
971 * NOTE: Local Result Tree Fragments of params/variables
972 * are not registered globally anymore; the life-time
973 * is not directly dependant of the param/variable itself.
974 *
975 * OLD: xsltRegisterTmpRVT(ctxt, container);
976 */
977 /*
978 * Attach the Result Tree Fragment to the variable;
979 * when the variable is freed, it will also free
980 * the Result Tree Fragment.
981 */
982 variable->fragment = container;
983 container->compression = XSLT_RVT_LOCAL;
984
985 oldOutput = ctxt->output;
986 oldInsert = ctxt->insert;
987 oldLastText = ctxt->lasttext;
988 oldLastTextSize = ctxt->lasttsize;
989 oldLastTextUse = ctxt->lasttuse;
990
991 ctxt->output = container;
992 ctxt->insert = (xmlNodePtr) container;
994 /*
995 * Process the sequence constructor (variable->tree).
996 * The resulting tree will be held by @container.
997 */
998 xsltApplyOneTemplate(ctxt, ctxt->node, variable->tree,
999 NULL, NULL);
1000
1001 ctxt->contextVariable = oldVar;
1002 ctxt->insert = oldInsert;
1003 ctxt->output = oldOutput;
1004 ctxt->lasttext = oldLastText;
1005 ctxt->lasttsize = oldLastTextSize;
1006 ctxt->lasttuse = oldLastTextUse;
1007
1008 result = xmlXPathNewValueTree((xmlNodePtr) container);
1009 }
1010 if (result == NULL) {
1011 result = xmlXPathNewCString("");
1012 } else {
1013 /*
1014 * This stops older libxml2 versions from freeing the nodes
1015 * in the tree.
1016 */
1017 result->boolval = 0;
1018 }
1019#ifdef WITH_XSLT_DEBUG_VARIABLE
1020#ifdef LIBXML_DEBUG_ENABLED
1021
1024 xmlXPathDebugDumpObject((FILE *)xsltGenericDebugContext,
1025 result, 0);
1026#endif
1027#endif
1028 }
1029 }
1030
1031error:
1032 ctxt->inst = oldInst;
1033 return(result);
1034}
GLenum GLenum variable
Definition: glext.h:9031
const xmlChar * lasttext
char * name
Definition: compiler.c:66
#define XSLT_VAR_IN_SELECT
Definition: variables.c:47
#define XSLT_RVT_LOCAL
Definition: variables.h:46

Referenced by xsltBuildVariable(), xsltVariableLookup(), and xsltXPathVariableLookup().

◆ xsltExtensionInstructionResultFinalize()

int xsltExtensionInstructionResultFinalize ( xsltTransformContextPtr ctxt  ATTRIBUTE_UNUSED)

xsltExtensionInstructionResultFinalize: @ctxt: an XSLT transformation context

Finalizes the data (e.g. result tree fragments) created within a value-returning process (e.g. EXSLT's function). Tree fragments marked as being returned by a function are set to normal state, which means that the fragment garbage collector will free them after the function-calling process exits.

Returns 0 in case of success and -1 in case of API or internal errors.

This function is unsupported in newer releases of libxslt.

Definition at line 208 of file variables.c.

210{
212 "xsltExtensionInstructionResultFinalize is unsupported "
213 "in this release of libxslt.\n");
214 return(-1);
215}

◆ xsltExtensionInstructionResultRegister()

int xsltExtensionInstructionResultRegister ( xsltTransformContextPtr ctxt  ATTRIBUTE_UNUSED,
xmlXPathObjectPtr obj  ATTRIBUTE_UNUSED 
)

xsltExtensionInstructionResultRegister: @ctxt: an XSLT transformation context @obj: an XPath object to be inspected for result tree fragments

Marks the result of a value-returning extension instruction in order to avoid it being garbage collected before the extension instruction exits. Note that one still has to additionally register any newly created tree fragments (via xsltCreateRVT()) with xsltRegisterLocalRVT().

Returns 0 in case of success and -1 in case of error.

It isn't necessary to call this function in newer releases of libxslt.

Definition at line 234 of file variables.c.

237{
238 return(0);
239}

◆ xsltFlagRVTs()

int xsltFlagRVTs ( xsltTransformContextPtr  ctxt,
xmlXPathObjectPtr  obj,
int  val 
)

xsltFlagRVTs: @ctxt: an XSLT transformation context @obj: an XPath object to be inspected for result tree fragments @val: the flag value

Updates ownership information of RVTs in @obj according to @val.

@val = XSLT_RVT_FUNC_RESULT for the result of an extension function, so its RVTs won't be destroyed after leaving the returning scope. @val = XSLT_RVT_LOCAL for the result of an extension function to reset the state of its RVTs after it was returned to a new scope. @val = XSLT_RVT_GLOBAL for parts of global variables.

Returns 0 in case of success and -1 in case of error.

Definition at line 258 of file variables.c.

258 {
259 int i;
260 xmlNodePtr cur;
261 xmlDocPtr doc;
262
263 if ((ctxt == NULL) || (obj == NULL))
264 return(-1);
265
266 /*
267 * OPTIMIZE TODO: If no local variables/params and no local tree
268 * fragments were created, then we don't need to analyse the XPath
269 * objects for tree fragments.
270 */
271
272 if ((obj->type != XPATH_NODESET) && (obj->type != XPATH_XSLT_TREE))
273 return(0);
274 if ((obj->nodesetval == NULL) || (obj->nodesetval->nodeNr == 0))
275 return(0);
276
277 for (i = 0; i < obj->nodesetval->nodeNr; i++) {
278 cur = obj->nodesetval->nodeTab[i];
279 if (cur->type == XML_NAMESPACE_DECL) {
280 /*
281 * The XPath module sets the owner element of a ns-node on
282 * the ns->next field.
283 */
284 if ((((xmlNsPtr) cur)->next != NULL) &&
285 (((xmlNsPtr) cur)->next->type == XML_ELEMENT_NODE))
286 {
287 cur = (xmlNodePtr) ((xmlNsPtr) cur)->next;
288 doc = cur->doc;
289 } else {
290 xsltTransformError(ctxt, NULL, ctxt->inst,
291 "Internal error in xsltFlagRVTs(): "
292 "Cannot retrieve the doc of a namespace node.\n");
293 return(-1);
294 }
295 } else {
296 doc = cur->doc;
297 }
298 if (doc == NULL) {
299 xsltTransformError(ctxt, NULL, ctxt->inst,
300 "Internal error in xsltFlagRVTs(): "
301 "Cannot retrieve the doc of a node.\n");
302 return(-1);
303 }
304 if (doc->name && (doc->name[0] == ' ') &&
305 doc->compression != XSLT_RVT_GLOBAL) {
306 /*
307 * This is a result tree fragment.
308 * We store ownership information in the @compression field.
309 * TODO: How do we know if this is a doc acquired via the
310 * document() function?
311 */
312#ifdef WITH_XSLT_DEBUG_VARIABLE
315 "Flagging RVT %p: %d -> %d\n",
316 (void *) doc, doc->compression, val));
317#endif
318
319 if (val == XSLT_RVT_LOCAL) {
320 if (doc->compression == XSLT_RVT_FUNC_RESULT)
321 doc->compression = XSLT_RVT_LOCAL;
322 } else if (val == XSLT_RVT_GLOBAL) {
323 if (doc->compression != XSLT_RVT_LOCAL) {
325 "xsltFlagRVTs: Invalid transition %d => GLOBAL\n",
326 doc->compression);
327 doc->compression = XSLT_RVT_GLOBAL;
328 return(-1);
329 }
330
331 /* Will be registered as persistant in xsltReleaseLocalRVTs. */
332 doc->compression = XSLT_RVT_GLOBAL;
333 } else if (val == XSLT_RVT_FUNC_RESULT) {
334 doc->compression = val;
335 }
336 }
337 }
338
339 return(0);
340}
GLuint GLfloat * val
Definition: glext.h:7180
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble const GLfloat const GLdouble const GLfloat GLint i
Definition: glfuncs.h:248
static unsigned __int64 next
Definition: rand_nt.c:6
#define XSLT_RVT_FUNC_RESULT
Definition: variables.h:55

Referenced by xsltEvalGlobalVariable().

◆ xsltFreeGlobalVariables()

void xsltFreeGlobalVariables ( xsltTransformContextPtr  ctxt)

xsltFreeGlobalVariables: @ctxt: the XSLT transformation context

Free up the data associated to the global variables its value.

Definition at line 2254 of file variables.c.

2254 {
2256}
void xmlHashFree(xmlHashTablePtr hash, xmlHashDeallocator dealloc)
Definition: hash.c:229
static void xsltFreeStackElemEntry(void *payload, const xmlChar *name ATTRIBUTE_UNUSED)
Definition: variables.c:614

Referenced by xsltFreeTransformContext().

◆ xsltFreeRVTs()

void xsltFreeRVTs ( xsltTransformContextPtr  ctxt)

xsltFreeRVTs: @ctxt: an XSLT transformation context

Frees all registered result value trees (Result Tree Fragments) of the transformation. Internal function; should not be called by user-code.

Definition at line 439 of file variables.c.

440{
441 xmlDocPtr cur, next;
442
443 if (ctxt == NULL)
444 return;
445 /*
446 * Local fragments.
447 */
448 cur = ctxt->localRVT;
449 while (cur != NULL) {
450 next = (xmlDocPtr) cur->next;
451 if (cur->_private != NULL) {
452 xsltFreeDocumentKeys(cur->_private);
453 xmlFree(cur->_private);
454 }
455 xmlFreeDoc(cur);
456 cur = next;
457 }
458 ctxt->localRVT = NULL;
459 /*
460 * User-created per-template fragments.
461 */
462 cur = ctxt->tmpRVT;
463 while (cur != NULL) {
464 next = (xmlDocPtr) cur->next;
465 if (cur->_private != NULL) {
466 xsltFreeDocumentKeys(cur->_private);
467 xmlFree(cur->_private);
468 }
469 xmlFreeDoc(cur);
470 cur = next;
471 }
472 ctxt->tmpRVT = NULL;
473 /*
474 * Global fragments.
475 */
476 cur = ctxt->persistRVT;
477 while (cur != NULL) {
478 next = (xmlDocPtr) cur->next;
479 if (cur->_private != NULL) {
480 xsltFreeDocumentKeys(cur->_private);
481 xmlFree(cur->_private);
482 }
483 xmlFreeDoc(cur);
484 cur = next;
485 }
486 ctxt->persistRVT = NULL;
487}
void xsltFreeDocumentKeys(xsltDocumentPtr idoc)
Definition: keys.c:931
xmlFreeFunc xmlFree
Definition: globals.c:184

Referenced by xsltApplyStylesheetInternal(), and xsltFreeTransformContext().

◆ xsltFreeStackElem()

static void xsltFreeStackElem ( xsltStackElemPtr  elem)
static

xsltFreeStackElem: @elem: an XSLT stack element

Free up the memory allocated by @elem

Definition at line 565 of file variables.c.

565 {
566 if (elem == NULL)
567 return;
568 if (elem->value != NULL)
569 xmlXPathFreeObject(elem->value);
570 /*
571 * Release the list of temporary Result Tree Fragments.
572 */
573 if (elem->context) {
574 xmlDocPtr cur;
575
576 while (elem->fragment != NULL) {
577 cur = elem->fragment;
578 elem->fragment = (xmlDocPtr) cur->next;
579
580 if (cur->compression == XSLT_RVT_LOCAL) {
581 xsltReleaseRVT(elem->context, cur);
582 } else if (cur->compression == XSLT_RVT_FUNC_RESULT) {
583 xsltRegisterLocalRVT(elem->context, cur);
584 cur->compression = XSLT_RVT_FUNC_RESULT;
585 } else {
587 "xsltFreeStackElem: Unexpected RVT flag %d\n",
588 cur->compression);
589 }
590 }
591 }
592 /*
593 * Cache or free the variable structure.
594 */
595 if (elem->context && (elem->context->cache->nbStackItems < 50)) {
596 /*
597 * Store the item in the cache.
598 */
599 xsltTransformContextPtr ctxt = elem->context;
600 memset(elem, 0, sizeof(xsltStackElem));
601 elem->context = ctxt;
602 elem->next = ctxt->cache->stackItems;
603 ctxt->cache->stackItems = elem;
604 ctxt->cache->nbStackItems++;
605#ifdef XSLT_DEBUG_PROFILE_CACHE
606 ctxt->cache->dbgCachedVars++;
607#endif
608 return;
609 }
610 xmlFree(elem);
611}
xsltStackElemPtr stackItems
int xsltRegisterLocalRVT(xsltTransformContextPtr ctxt, xmlDocPtr RVT)
Definition: variables.c:159
void xsltReleaseRVT(xsltTransformContextPtr ctxt, xmlDocPtr RVT)
Definition: variables.c:351

Referenced by xsltEvalGlobalVariables(), xsltFreeStackElemEntry(), xsltFreeStackElemList(), xsltProcessUserParamInternal(), and xsltRegisterVariable().

◆ xsltFreeStackElemEntry()

static void xsltFreeStackElemEntry ( void payload,
const xmlChar *name  ATTRIBUTE_UNUSED 
)
static

Definition at line 614 of file variables.c.

614 {
616}

Referenced by xsltFreeGlobalVariables().

◆ xsltFreeStackElemList()

void xsltFreeStackElemList ( xsltStackElemPtr  elem)

xsltFreeStackElemList: @elem: an XSLT stack element

Free up the memory allocated by @elem

Definition at line 626 of file variables.c.

626 {
628
629 while (elem != NULL) {
630 next = elem->next;
632 elem = next;
633 }
634}

Referenced by xsltApplyStylesheetInternal(), xsltApplyTemplates(), xsltCallTemplate(), xsltFreeStylesheet(), xsltLocalVariablePop(), and xsltTemplateParamsCleanup().

◆ xsltGlobalVariableLookup()

static xmlXPathObjectPtr xsltGlobalVariableLookup ( xsltTransformContextPtr  ctxt,
const xmlChar name,
const xmlChar ns_uri 
)
static

Definition at line 1900 of file variables.c.

1901 {
1903 xmlXPathObjectPtr ret = NULL;
1904
1905 /*
1906 * Lookup the global variables in XPath global variable hash table
1907 */
1908 if ((ctxt->xpathCtxt == NULL) || (ctxt->globalVars == NULL))
1909 return(NULL);
1911 xmlHashLookup2(ctxt->globalVars, name, ns_uri);
1912 if (elem == NULL) {
1913#ifdef WITH_XSLT_DEBUG_VARIABLE
1915 "global variable not found %s\n", name));
1916#endif
1917 return(NULL);
1918 }
1919 /*
1920 * URGENT TODO: Move the detection of recursive definitions
1921 * to compile-time.
1922 */
1923 if (elem->computed == 0) {
1924 if (elem->name == xsltComputingGlobalVarMarker) {
1925 xsltTransformError(ctxt, NULL, elem->comp->inst,
1926 "Recursive definition of %s\n", name);
1927 return(NULL);
1928 }
1930 } else
1931 ret = elem->value;
1932 return(xmlXPathObjectCopy(ret));
1933}
return ret
Definition: mutex.c:146

Referenced by xsltVariableLookup(), and xsltXPathVariableLookup().

◆ xsltNewStackElem()

static xsltStackElemPtr xsltNewStackElem ( xsltTransformContextPtr  ctxt)
static

xsltNewStackElem:

Create a new XSLT ParserContext

Returns the newly allocated xsltParserStackElem or NULL in case of error

Definition at line 503 of file variables.c.

504{
506 /*
507 * Reuse a stack item from the cache if available.
508 */
509 if (ctxt && ctxt->cache->stackItems) {
510 ret = ctxt->cache->stackItems;
511 ctxt->cache->stackItems = ret->next;
512 ret->next = NULL;
513 ctxt->cache->nbStackItems--;
514#ifdef XSLT_DEBUG_PROFILE_CACHE
515 ctxt->cache->dbgReusedVars++;
516#endif
517 return(ret);
518 }
520 if (ret == NULL) {
522 "xsltNewStackElem : malloc failed\n");
523 return(NULL);
524 }
525 memset(ret, 0, sizeof(xsltStackElem));
526 ret->context = ctxt;
527 return(ret);
528}

Referenced by xsltBuildVariable(), xsltProcessUserParamInternal(), and xsltRegisterGlobalVariable().

◆ xsltParseGlobalParam()

void xsltParseGlobalParam ( xsltStylesheetPtr  style,
xmlNodePtr  cur 
)

xsltParseGlobalParam: @style: the XSLT stylesheet @cur: the "param" element

parse an XSLT transformation param declaration and record its value.

Definition at line 2114 of file variables.c.

2114 {
2115#ifdef XSLT_REFACTORED
2116 xsltStyleItemParamPtr comp;
2117#else
2119#endif
2120
2121 if ((cur == NULL) || (style == NULL) || (cur->type != XML_ELEMENT_NODE))
2122 return;
2123
2124#ifdef XSLT_REFACTORED
2125 /*
2126 * Note that xsltStylePreCompute() will be called from
2127 * xslt.c only.
2128 */
2129 comp = (xsltStyleItemParamPtr) cur->psvi;
2130#else
2132 comp = (xsltStylePreCompPtr) cur->psvi;
2133#endif
2134 if (comp == NULL) {
2136 "xsl:param : compilation failed\n");
2137 return;
2138 }
2139
2140 if (comp->name == NULL) {
2142 "xsl:param : missing name attribute\n");
2143 return;
2144 }
2145
2146 /*
2147 * Parse the content (a sequence constructor) of xsl:param.
2148 */
2149 if (cur->children != NULL) {
2150#ifdef XSLT_REFACTORED
2151 xsltParseSequenceConstructor(XSLT_CCTXT(style), cur->children);
2152#else
2154#endif
2155 }
2156
2157#ifdef WITH_XSLT_DEBUG_VARIABLE
2159 "Registering global param %s\n", comp->name);
2160#endif
2161
2162 xsltRegisterGlobalVariable(style, comp->name, comp->ns,
2163 comp->select, cur->children, (xsltStylePreCompPtr) comp,
2164 NULL);
2165}
void xsltStylePreCompute(xsltStylesheetPtr style, xmlNodePtr inst)
Definition: preproc.c:2191
static int xsltRegisterGlobalVariable(xsltStylesheetPtr style, const xmlChar *name, const xmlChar *ns_uri, const xmlChar *sel, xmlNodePtr tree, xsltStylePreCompPtr comp, const xmlChar *value)
Definition: variables.c:1369
void xsltParseTemplateContent(xsltStylesheetPtr style, xmlNodePtr templ)
Definition: xslt.c:4894

Referenced by xsltParseStylesheetTop().

◆ xsltParseGlobalVariable()

void xsltParseGlobalVariable ( xsltStylesheetPtr  style,
xmlNodePtr  cur 
)

xsltParseGlobalVariable: @style: the XSLT stylesheet @cur: the "variable" element

Parses a global XSLT 'variable' declaration at compilation time and registers it

Definition at line 2051 of file variables.c.

2052{
2053#ifdef XSLT_REFACTORED
2054 xsltStyleItemVariablePtr comp;
2055#else
2057#endif
2058
2059 if ((cur == NULL) || (style == NULL) || (cur->type != XML_ELEMENT_NODE))
2060 return;
2061
2062#ifdef XSLT_REFACTORED
2063 /*
2064 * Note that xsltStylePreCompute() will be called from
2065 * xslt.c only.
2066 */
2067 comp = (xsltStyleItemVariablePtr) cur->psvi;
2068#else
2070 comp = (xsltStylePreCompPtr) cur->psvi;
2071#endif
2072 if (comp == NULL) {
2074 "xsl:variable : compilation failed\n");
2075 return;
2076 }
2077
2078 if (comp->name == NULL) {
2080 "xsl:variable : missing name attribute\n");
2081 return;
2082 }
2083
2084 /*
2085 * Parse the content (a sequence constructor) of xsl:variable.
2086 */
2087 if (cur->children != NULL) {
2088#ifdef XSLT_REFACTORED
2089 xsltParseSequenceConstructor(XSLT_CCTXT(style), cur->children);
2090#else
2092#endif
2093 }
2094#ifdef WITH_XSLT_DEBUG_VARIABLE
2096 "Registering global variable %s\n", comp->name);
2097#endif
2098
2099 xsltRegisterGlobalVariable(style, comp->name, comp->ns,
2100 comp->select, cur->children, (xsltStylePreCompPtr) comp,
2101 NULL);
2102}

Referenced by xsltParseStylesheetTop().

◆ xsltParseStylesheetCallerParam()

xsltStackElemPtr xsltParseStylesheetCallerParam ( xsltTransformContextPtr  ctxt,
xmlNodePtr  inst 
)

xsltParseStylesheetCallerParam: @ctxt: the XSLT transformation context @inst: the xsl:with-param instruction element

Processes an xsl:with-param instruction at transformation time. The value is computed, but not recorded. NOTE that this is also called with an xsl:param element from exsltFuncFunctionFunction().

Returns the new xsltStackElemPtr or NULL

Definition at line 1989 of file variables.c.

1990{
1991#ifdef XSLT_REFACTORED
1992 xsltStyleBasicItemVariablePtr comp;
1993#else
1995#endif
1996 xmlNodePtr tree = NULL; /* The first child node of the instruction or
1997 the instruction itself. */
1999
2000 if ((ctxt == NULL) || (inst == NULL) || (inst->type != XML_ELEMENT_NODE))
2001 return(NULL);
2002
2003#ifdef XSLT_REFACTORED
2004 comp = (xsltStyleBasicItemVariablePtr) inst->psvi;
2005#else
2006 comp = (xsltStylePreCompPtr) inst->psvi;
2007#endif
2008
2009 if (comp == NULL) {
2010 xsltTransformError(ctxt, NULL, inst,
2011 "Internal error in xsltParseStylesheetCallerParam(): "
2012 "The XSLT 'with-param' instruction was not compiled.\n");
2013 return(NULL);
2014 }
2015 if (comp->name == NULL) {
2016 xsltTransformError(ctxt, NULL, inst,
2017 "Internal error in xsltParseStylesheetCallerParam(): "
2018 "XSLT 'with-param': The attribute 'name' was not compiled.\n");
2019 return(NULL);
2020 }
2021
2022#ifdef WITH_XSLT_DEBUG_VARIABLE
2024 "Handling xsl:with-param %s\n", comp->name));
2025#endif
2026
2027 if (comp->select == NULL) {
2028 tree = inst->children;
2029 } else {
2030#ifdef WITH_XSLT_DEBUG_VARIABLE
2032 " select %s\n", comp->select));
2033#endif
2034 tree = inst;
2035 }
2036
2038
2039 return(param);
2040}
GLfloat param
Definition: glext.h:5796
static xsltStackElemPtr xsltBuildVariable(xsltTransformContextPtr ctxt, xsltStylePreCompPtr castedComp, xmlNodePtr tree)
Definition: variables.c:1790

Referenced by xsltApplyTemplates(), and xsltCallTemplate().

◆ xsltParseStylesheetParam()

void xsltParseStylesheetParam ( xsltTransformContextPtr  ctxt,
xmlNodePtr  cur 
)

xsltParseStylesheetParam: @ctxt: the XSLT transformation context @cur: the XSLT 'param' element

Registers a local XSLT 'param' declaration at transformation time and evaluates its value.

Definition at line 2218 of file variables.c.

2219{
2220#ifdef XSLT_REFACTORED
2221 xsltStyleItemParamPtr comp;
2222#else
2224#endif
2225
2226 if ((cur == NULL) || (ctxt == NULL) || (cur->type != XML_ELEMENT_NODE))
2227 return;
2228
2229 comp = cur->psvi;
2230 if ((comp == NULL) || (comp->name == NULL)) {
2232 "Internal error in xsltParseStylesheetParam(): "
2233 "The XSLT 'param' declaration was not compiled correctly.\n");
2234 return;
2235 }
2236
2237#ifdef WITH_XSLT_DEBUG_VARIABLE
2239 "Registering param %s\n", comp->name));
2240#endif
2241
2242 xsltRegisterVariable(ctxt, (xsltStylePreCompPtr) comp, cur->children, 1);
2243}
static int xsltRegisterVariable(xsltTransformContextPtr ctxt, xsltStylePreCompPtr castedComp, xmlNodePtr tree, int isParam)
Definition: variables.c:1837

Referenced by xsltApplyXSLTTemplate().

◆ xsltParseStylesheetVariable()

void xsltParseStylesheetVariable ( xsltTransformContextPtr  ctxt,
xmlNodePtr  inst 
)

xsltParseStylesheetVariable: @ctxt: the XSLT transformation context @inst: the xsl:variable instruction element

Registers a local XSLT 'variable' instruction at transformation time and evaluates its value.

Definition at line 2176 of file variables.c.

2177{
2178#ifdef XSLT_REFACTORED
2179 xsltStyleItemVariablePtr comp;
2180#else
2182#endif
2183
2184 if ((inst == NULL) || (ctxt == NULL) || (inst->type != XML_ELEMENT_NODE))
2185 return;
2186
2187 comp = inst->psvi;
2188 if (comp == NULL) {
2189 xsltTransformError(ctxt, NULL, inst,
2190 "Internal error in xsltParseStylesheetVariable(): "
2191 "The XSLT 'variable' instruction was not compiled.\n");
2192 return;
2193 }
2194 if (comp->name == NULL) {
2195 xsltTransformError(ctxt, NULL, inst,
2196 "Internal error in xsltParseStylesheetVariable(): "
2197 "The attribute 'name' was not compiled.\n");
2198 return;
2199 }
2200
2201#ifdef WITH_XSLT_DEBUG_VARIABLE
2203 "Registering variable '%s'\n", comp->name));
2204#endif
2205
2206 xsltRegisterVariable(ctxt, (xsltStylePreCompPtr) comp, inst->children, 0);
2207}

Referenced by xsltApplySequenceConstructor().

◆ xsltProcessUserParamInternal()

static int xsltProcessUserParamInternal ( xsltTransformContextPtr  ctxt,
const xmlChar name,
const xmlChar value,
int  eval 
)
static

Definition at line 1462 of file variables.c.

1465 {
1466
1468 const xmlChar *prefix;
1469 const xmlChar *href;
1470 xmlXPathCompExprPtr xpExpr;
1471 xmlXPathObjectPtr result;
1472
1474 int res;
1475 void *res_ptr;
1476
1477 if (ctxt == NULL)
1478 return(-1);
1479 if (name == NULL)
1480 return(0);
1481 if (value == NULL)
1482 return(0);
1483
1484 style = ctxt->style;
1485
1486#ifdef WITH_XSLT_DEBUG_VARIABLE
1488 "Evaluating user parameter %s=%s\n", name, value));
1489#endif
1490
1491 /*
1492 * Name lookup
1493 */
1494 href = NULL;
1495
1496 if (name[0] == '{') {
1497 int len = 0;
1498
1499 while ((name[len] != 0) && (name[len] != '}')) len++;
1500 if (name[len] == 0) {
1502 "user param : malformed parameter name : %s\n", name);
1503 } else {
1504 href = xmlDictLookup(ctxt->dict, &name[1], len-1);
1505 name = xmlDictLookup(ctxt->dict, &name[len + 1], -1);
1506 }
1507 }
1508 else {
1509 name = xsltSplitQName(ctxt->dict, name, &prefix);
1510 if (prefix != NULL) {
1511 xmlNsPtr ns;
1512
1513 ns = xmlSearchNs(style->doc, xmlDocGetRootElement(style->doc),
1514 prefix);
1515 if (ns == NULL) {
1517 "user param : no namespace bound to prefix %s\n", prefix);
1518 href = NULL;
1519 } else {
1520 href = ns->href;
1521 }
1522 }
1523 }
1524
1525 if (name == NULL)
1526 return (-1);
1527
1528 res_ptr = xmlHashLookup2(ctxt->globalVars, name, href);
1529 if (res_ptr != 0) {
1531 "Global parameter %s already defined\n", name);
1532 }
1533 if (ctxt->globalVars == NULL)
1534 ctxt->globalVars = xmlHashCreate(20);
1535
1536 /*
1537 * do not overwrite variables with parameters from the command line
1538 */
1539 while (style != NULL) {
1540 elem = ctxt->style->variables;
1541 while (elem != NULL) {
1542 if ((elem->comp != NULL) &&
1543 (elem->comp->type == XSLT_FUNC_VARIABLE) &&
1544 (xmlStrEqual(elem->name, name)) &&
1545 (xmlStrEqual(elem->nameURI, href))) {
1546 return(0);
1547 }
1548 elem = elem->next;
1549 }
1551 }
1552 style = ctxt->style;
1553 elem = NULL;
1554
1555 /*
1556 * Do the evaluation if @eval is non-zero.
1557 */
1558
1559 result = NULL;
1560 if (eval != 0) {
1561 xpExpr = xmlXPathCtxtCompile(ctxt->xpathCtxt, value);
1562 if (xpExpr != NULL) {
1563 xmlDocPtr oldXPDoc;
1564 xmlNodePtr oldXPContextNode;
1565 int oldXPProximityPosition, oldXPContextSize, oldXPNsNr;
1566 xmlNsPtr *oldXPNamespaces;
1567 xmlXPathContextPtr xpctxt = ctxt->xpathCtxt;
1568
1569 /*
1570 * Save context states.
1571 */
1572 oldXPDoc = xpctxt->doc;
1573 oldXPContextNode = xpctxt->node;
1574 oldXPProximityPosition = xpctxt->proximityPosition;
1575 oldXPContextSize = xpctxt->contextSize;
1576 oldXPNamespaces = xpctxt->namespaces;
1577 oldXPNsNr = xpctxt->nsNr;
1578
1579 /*
1580 * SPEC XSLT 1.0:
1581 * "At top-level, the expression or template specifying the
1582 * variable value is evaluated with the same context as that used
1583 * to process the root node of the source document: the current
1584 * node is the root node of the source document and the current
1585 * node list is a list containing just the root node of the source
1586 * document."
1587 */
1588 xpctxt->doc = ctxt->initialContextDoc;
1589 xpctxt->node = ctxt->initialContextNode;
1590 xpctxt->contextSize = 1;
1591 xpctxt->proximityPosition = 1;
1592 /*
1593 * There is really no in scope namespace for parameters on the
1594 * command line.
1595 */
1596 xpctxt->namespaces = NULL;
1597 xpctxt->nsNr = 0;
1598
1599 result = xmlXPathCompiledEval(xpExpr, xpctxt);
1600
1601 /*
1602 * Restore Context states.
1603 */
1604 xpctxt->doc = oldXPDoc;
1605 xpctxt->node = oldXPContextNode;
1606 xpctxt->contextSize = oldXPContextSize;
1607 xpctxt->proximityPosition = oldXPProximityPosition;
1608 xpctxt->namespaces = oldXPNamespaces;
1609 xpctxt->nsNr = oldXPNsNr;
1610
1611 xmlXPathFreeCompExpr(xpExpr);
1612 }
1613 if (result == NULL) {
1615 "Evaluating user parameter %s failed\n", name);
1616 ctxt->state = XSLT_STATE_STOPPED;
1617 return(-1);
1618 }
1619 }
1620
1621 /*
1622 * If @eval is 0 then @value is to be taken literally and result is NULL
1623 *
1624 * If @eval is not 0, then @value is an XPath expression and has been
1625 * successfully evaluated and result contains the resulting value and
1626 * is not NULL.
1627 *
1628 * Now create an xsltStackElemPtr for insertion into the context's
1629 * global variable/parameter hash table.
1630 */
1631
1632#ifdef WITH_XSLT_DEBUG_VARIABLE
1633#ifdef LIBXML_DEBUG_ENABLED
1636 xmlXPathDebugDumpObject((FILE *)xsltGenericDebugContext,
1637 result, 0);
1638#endif
1639#endif
1640
1642 if (elem != NULL) {
1643 elem->name = name;
1644 elem->select = xmlDictLookup(ctxt->dict, value, -1);
1645 if (href != NULL)
1646 elem->nameURI = xmlDictLookup(ctxt->dict, href, -1);
1647 elem->tree = NULL;
1648 elem->computed = 1;
1649 if (eval == 0) {
1650 elem->value = xmlXPathNewString(value);
1651 }
1652 else {
1653 elem->value = result;
1654 }
1655 }
1656
1657 /*
1658 * Global parameters are stored in the XPath context variables pool.
1659 */
1660
1661 res = xmlHashAddEntry2(ctxt->globalVars, name, href, elem);
1662 if (res != 0) {
1665 "Global parameter %s already defined\n", name);
1666 }
1667 return(0);
1668}
GLuint res
Definition: glext.h:9613
GLenum GLsizei len
Definition: glext.h:6722
const xmlChar * xmlDictLookup(xmlDictPtr dict, const xmlChar *name, int len)
Definition: dict.c:824
xmlHashTablePtr xmlHashCreate(int size)
Definition: hash.c:160
xsltStackElemPtr variables
Definition: mxnamespace.c:38
Character const *const prefix
Definition: tempnam.cpp:195
XMLPUBFUN int xmlStrEqual(const xmlChar *str1, const xmlChar *str2)
Definition: xmlstring.c:162
const xmlChar * xsltSplitQName(xmlDictPtr dict, const xmlChar *name, const xmlChar **prefix)
Definition: xsltutils.c:804

Referenced by xsltEvalOneUserParam(), and xsltQuoteOneUserParam().

◆ xsltQuoteOneUserParam()

int xsltQuoteOneUserParam ( xsltTransformContextPtr  ctxt,
const xmlChar name,
const xmlChar value 
)

Definition at line 1772 of file variables.c.

1774 {
1776 0 /* xpath eval ? */);
1777}

Referenced by xsltQuoteUserParams().

◆ xsltQuoteUserParams()

int xsltQuoteUserParams ( xsltTransformContextPtr  ctxt,
const char **  params 
)

xsltQuoteUserParams:

@ctxt: the XSLT transformation context @params: a NULL terminated arry of parameters names/values tuples

Similar to xsltEvalUserParams, but the values are treated literally and are * not evaluated as XPath expressions. This should be done on parsed stylesheets before starting to apply transformations.

Returns 0 in case of success, -1 in case of error.

Definition at line 1716 of file variables.c.

1716 {
1717 size_t indx = 0;
1718 const xmlChar *name;
1719 const xmlChar *value;
1720
1721 if (params == NULL)
1722 return(0);
1723 while (params[indx] != NULL) {
1724 name = (const xmlChar *) params[indx++];
1725 value = (const xmlChar *) params[indx++];
1726 if (xsltQuoteOneUserParam(ctxt, name, value) != 0)
1727 return(-1);
1728 }
1729 return 0;
1730}
int xsltQuoteOneUserParam(xsltTransformContextPtr ctxt, const xmlChar *name, const xmlChar *value)
Definition: variables.c:1772

Referenced by node_transform_node_params().

◆ xsltRegisterGlobalVariable()

static int xsltRegisterGlobalVariable ( xsltStylesheetPtr  style,
const xmlChar name,
const xmlChar ns_uri,
const xmlChar sel,
xmlNodePtr  tree,
xsltStylePreCompPtr  comp,
const xmlChar value 
)
static

Definition at line 1369 of file variables.c.

1372 {
1374 if (style == NULL)
1375 return(-1);
1376 if (name == NULL)
1377 return(-1);
1378 if (comp == NULL)
1379 return(-1);
1380
1381#ifdef WITH_XSLT_DEBUG_VARIABLE
1382 if (comp->type == XSLT_FUNC_PARAM)
1384 "Defining global param %s\n", name);
1385 else
1387 "Defining global variable %s\n", name);
1388#endif
1389
1391 if (elem == NULL)
1392 return(-1);
1393 elem->comp = comp;
1394 elem->name = xmlDictLookup(style->dict, name, -1);
1395 elem->select = xmlDictLookup(style->dict, sel, -1);
1396 if (ns_uri)
1397 elem->nameURI = xmlDictLookup(style->dict, ns_uri, -1);
1398 elem->tree = tree;
1399 tmp = style->variables;
1400 if (tmp == NULL) {
1401 elem->next = NULL;
1402 style->variables = elem;
1403 } else {
1404 while (tmp != NULL) {
1405 if ((elem->comp->type == XSLT_FUNC_VARIABLE) &&
1406 (tmp->comp->type == XSLT_FUNC_VARIABLE) &&
1407 (xmlStrEqual(elem->name, tmp->name)) &&
1408 ((elem->nameURI == tmp->nameURI) ||
1409 (xmlStrEqual(elem->nameURI, tmp->nameURI))))
1410 {
1412 "redefinition of global variable %s\n", elem->name);
1413 style->errors++;
1414 }
1415 if (tmp->next == NULL)
1416 break;
1417 tmp = tmp->next;
1418 }
1419 elem->next = NULL;
1420 tmp->next = elem;
1421 }
1422 if (value != NULL) {
1423 elem->computed = 1;
1424 elem->value = xmlXPathNewString(value);
1425 }
1426 return(0);
1427}
struct _xsltStackElem * next
const xmlChar * nameURI
const xmlChar * name
xsltStyleType type

Referenced by xsltParseGlobalParam(), and xsltParseGlobalVariable().

◆ xsltRegisterLocalRVT()

int xsltRegisterLocalRVT ( xsltTransformContextPtr  ctxt,
xmlDocPtr  RVT 
)

xsltRegisterLocalRVT: @ctxt: an XSLT transformation context @RVT: a result value tree (Result Tree Fragment; xmlDocPtr)

Registers a result value tree (XSLT 1.0 term: Result Tree Fragment) in the RVT garbage collector. The fragment will be freed when the instruction which created the fragment exits.

Returns 0 in case of success and -1 in case of API or internal errors.

Definition at line 159 of file variables.c.

161{
162 if ((ctxt == NULL) || (RVT == NULL))
163 return(-1);
164
165 RVT->prev = NULL;
166 RVT->compression = XSLT_RVT_LOCAL;
167
168 /*
169 * When evaluating "select" expressions of xsl:variable
170 * and xsl:param, we need to bind newly created tree fragments
171 * to the variable itself; otherwise the fragment will be
172 * freed before we leave the scope of a var.
173 */
174 if ((ctxt->contextVariable != NULL) &&
176 {
177 RVT->next = (xmlNodePtr) XSLT_TCTXT_VARIABLE(ctxt)->fragment;
178 XSLT_TCTXT_VARIABLE(ctxt)->fragment = RVT;
179 return(0);
180 }
181 /*
182 * Store the fragment in the scope of the current instruction.
183 * If not reference by a returning instruction (like EXSLT's function),
184 * then this fragment will be freed, when the instruction exits.
185 */
186 RVT->next = (xmlNodePtr) ctxt->localRVT;
187 if (ctxt->localRVT != NULL)
188 ctxt->localRVT->prev = (xmlNodePtr) RVT;
189 ctxt->localRVT = RVT;
190 return(0);
191}
GLbitfield flags
Definition: glext.h:7161
struct define * next
Definition: compiler.c:65
#define XSLT_TCTXT_VARIABLE(c)
Definition: variables.c:48

Referenced by xsltFreeStackElem(), and xsltReleaseLocalRVTs().

◆ xsltRegisterPersistRVT()

int xsltRegisterPersistRVT ( xsltTransformContextPtr  ctxt,
xmlDocPtr  RVT 
)

xsltRegisterPersistRVT: @ctxt: an XSLT transformation context @RVT: a result value tree (Result Tree Fragment)

Register the result value tree (XSLT 1.0 term: Result Tree Fragment) in the fragment garbage collector. The fragment will be freed when the transformation context is freed.

Returns 0 in case of success and -1 in case of error.

Definition at line 417 of file variables.c.

418{
419 if ((ctxt == NULL) || (RVT == NULL)) return(-1);
420
421 RVT->compression = XSLT_RVT_GLOBAL;
422 RVT->prev = NULL;
423 RVT->next = (xmlNodePtr) ctxt->persistRVT;
424 if (ctxt->persistRVT != NULL)
425 ctxt->persistRVT->prev = (xmlNodePtr) RVT;
426 ctxt->persistRVT = RVT;
427 return(0);
428}

Referenced by xsltEvalGlobalVariable(), and xsltReleaseLocalRVTs().

◆ xsltRegisterTmpRVT()

int xsltRegisterTmpRVT ( xsltTransformContextPtr  ctxt,
xmlDocPtr  RVT 
)

xsltRegisterTmpRVT: @ctxt: an XSLT transformation context @RVT: a result value tree (Result Tree Fragment)

Registers the result value tree (XSLT 1.0 term: Result Tree Fragment) in the garbage collector. The fragment will be freed at the exit of the currently instantiated xsl:template. Obsolete; this function might produce massive memory overhead, since the fragment is only freed when the current xsl:template exits. Use xsltRegisterLocalRVT() instead.

Returns 0 in case of success and -1 in case of API or internal errors.

Definition at line 120 of file variables.c.

121{
122 if ((ctxt == NULL) || (RVT == NULL))
123 return(-1);
124
125 RVT->prev = NULL;
126 RVT->compression = XSLT_RVT_LOCAL;
127
128 /*
129 * We'll restrict the lifetime of user-created fragments
130 * insinde an xsl:variable and xsl:param to the lifetime of the
131 * var/param itself.
132 */
133 if (ctxt->contextVariable != NULL) {
134 RVT->next = (xmlNodePtr) XSLT_TCTXT_VARIABLE(ctxt)->fragment;
135 XSLT_TCTXT_VARIABLE(ctxt)->fragment = RVT;
136 return(0);
137 }
138
139 RVT->next = (xmlNodePtr) ctxt->tmpRVT;
140 if (ctxt->tmpRVT != NULL)
141 ctxt->tmpRVT->prev = (xmlNodePtr) RVT;
142 ctxt->tmpRVT = RVT;
143 return(0);
144}

◆ xsltRegisterVariable()

static int xsltRegisterVariable ( xsltTransformContextPtr  ctxt,
xsltStylePreCompPtr  castedComp,
xmlNodePtr  tree,
int  isParam 
)
static

xsltRegisterVariable: @ctxt: the XSLT transformation context @comp: the compiled XSLT-variable (or param) instruction @tree: the tree if select is NULL @isParam: indicates if this is a parameter

Computes and registers a new variable.

Returns 0 in case of success, -1 in case of error

Definition at line 1837 of file variables.c.

1840{
1841#ifdef XSLT_REFACTORED
1842 xsltStyleBasicItemVariablePtr comp =
1843 (xsltStyleBasicItemVariablePtr) castedComp;
1844#else
1845 xsltStylePreCompPtr comp = castedComp;
1846 int present;
1847#endif
1849
1850#ifdef XSLT_REFACTORED
1851 /*
1852 * REFACTORED NOTE: Redefinitions of vars/params are checked
1853 * at compilation time in the refactored code.
1854 * xsl:with-param parameters are checked in xsltApplyXSLTTemplate().
1855 */
1856#else
1857 present = xsltCheckStackElem(ctxt, comp->name, comp->ns);
1858 if (isParam == 0) {
1859 if ((present != 0) && (present != 3)) {
1860 /* TODO: report QName. */
1861 xsltTransformError(ctxt, NULL, comp->inst,
1862 "XSLT-variable: Redefinition of variable '%s'.\n", comp->name);
1863 return(0);
1864 }
1865 } else if (present != 0) {
1866 if ((present == 1) || (present == 2)) {
1867 /* TODO: report QName. */
1868 xsltTransformError(ctxt, NULL, comp->inst,
1869 "XSLT-param: Redefinition of parameter '%s'.\n", comp->name);
1870 return(0);
1871 }
1872#ifdef WITH_XSLT_DEBUG_VARIABLE
1874 "param %s defined by caller\n", comp->name));
1875#endif
1876 return(0);
1877 }
1878#endif /* else of XSLT_REFACTORED */
1879
1881 if (xsltAddStackElem(ctxt, variable) < 0) {
1883 return(-1);
1884 }
1885 return(0);
1886}
static int xsltCheckStackElem(xsltTransformContextPtr ctxt, const xmlChar *name, const xmlChar *nameURI)
Definition: variables.c:719

Referenced by xsltParseStylesheetParam(), and xsltParseStylesheetVariable().

◆ xsltReleaseRVT()

void xsltReleaseRVT ( xsltTransformContextPtr  ctxt,
xmlDocPtr  RVT 
)

xsltReleaseRVT: @ctxt: an XSLT transformation context @RVT: a result value tree (Result Tree Fragment)

Either frees the RVT (which is an xmlDoc) or stores it in the context's cache for later reuse.

Definition at line 351 of file variables.c.

352{
353 if (RVT == NULL)
354 return;
355
356 if (ctxt && (ctxt->cache->nbRVT < 40)) {
357 /*
358 * Store the Result Tree Fragment.
359 * Free the document info.
360 */
361 if (RVT->_private != NULL) {
362 xsltFreeDocumentKeys((xsltDocumentPtr) RVT->_private);
363 xmlFree(RVT->_private);
364 RVT->_private = NULL;
365 }
366 /*
367 * Clear the document tree.
368 */
369 if (RVT->children != NULL) {
370 xmlFreeNodeList(RVT->children);
371 RVT->children = NULL;
372 RVT->last = NULL;
373 }
374 if (RVT->ids != NULL) {
375 xmlFreeIDTable((xmlIDTablePtr) RVT->ids);
376 RVT->ids = NULL;
377 }
378
379 /*
380 * Reset the ownership information.
381 */
382 RVT->compression = 0;
383
384 RVT->next = (xmlNodePtr) ctxt->cache->RVT;
385 ctxt->cache->RVT = RVT;
386
387 ctxt->cache->nbRVT++;
388
389#ifdef XSLT_DEBUG_PROFILE_CACHE
390 ctxt->cache->dbgCachedRVTs++;
391#endif
392 return;
393 }
394 /*
395 * Free it.
396 */
397 if (RVT->_private != NULL) {
398 xsltFreeDocumentKeys((xsltDocumentPtr) RVT->_private);
399 xmlFree(RVT->_private);
400 }
401 xmlFreeDoc(RVT);
402}
XMLPUBFUN void xmlFreeIDTable(xmlIDTablePtr table)
Definition: valid.c:2601

Referenced by xsltApplyXSLTTemplate(), xsltFreeStackElem(), and xsltReleaseLocalRVTs().

◆ xsltStackLookup()

static xsltStackElemPtr xsltStackLookup ( xsltTransformContextPtr  ctxt,
const xmlChar name,
const xmlChar nameURI 
)
static

Definition at line 650 of file variables.c.

651 {
652 int i;
654
655 if ((ctxt == NULL) || (name == NULL) || (ctxt->varsNr == 0))
656 return(NULL);
657
658 /*
659 * Do the lookup from the top of the stack, but
660 * don't use params being computed in a call-param
661 * First lookup expects the variable name and URI to
662 * come from the disctionnary and hence pointer comparison.
663 */
664 for (i = ctxt->varsNr; i > ctxt->varsBase; i--) {
665 cur = ctxt->varsTab[i-1];
666 while (cur != NULL) {
667 if ((cur->name == name) && (cur->nameURI == nameURI)) {
668#if 0
669 stack_addr++;
670#endif
671 return(cur);
672 }
673 cur = cur->next;
674 }
675 }
676
677 /*
678 * Redo the lookup with interned string compares
679 * to avoid string compares.
680 */
681 name = xmlDictLookup(ctxt->dict, name, -1);
682 if (nameURI != NULL)
683 nameURI = xmlDictLookup(ctxt->dict, nameURI, -1);
684
685 for (i = ctxt->varsNr; i > ctxt->varsBase; i--) {
686 cur = ctxt->varsTab[i-1];
687 while (cur != NULL) {
688 if ((cur->name == name) && (cur->nameURI == nameURI)) {
689#if 0
690 stack_cmp++;
691#endif
692 return(cur);
693 }
694 cur = cur->next;
695 }
696 }
697
698 return(NULL);
699}

Referenced by xsltCheckStackElem(), and xsltVariableLookup().

◆ xsltVariableLookup()

xmlXPathObjectPtr xsltVariableLookup ( xsltTransformContextPtr  ctxt,
const xmlChar name,
const xmlChar ns_uri 
)

Definition at line 1947 of file variables.c.

1948 {
1950
1951 if (ctxt == NULL)
1952 return(NULL);
1953
1954 elem = xsltStackLookup(ctxt, name, ns_uri);
1955 if (elem == NULL) {
1956 return(xsltGlobalVariableLookup(ctxt, name, ns_uri));
1957 }
1958 if (elem->computed == 0) {
1959#ifdef WITH_XSLT_DEBUG_VARIABLE
1961 "uncomputed variable %s\n", name));
1962#endif
1963 elem->value = xsltEvalVariable(ctxt, elem, NULL);
1964 elem->computed = 1;
1965 }
1966 if (elem->value != NULL)
1967 return(xmlXPathObjectCopy(elem->value));
1968#ifdef WITH_XSLT_DEBUG_VARIABLE
1970 "variable not found %s\n", name));
1971#endif
1972 return(NULL);
1973}
static xmlXPathObjectPtr xsltGlobalVariableLookup(xsltTransformContextPtr ctxt, const xmlChar *name, const xmlChar *ns_uri)
Definition: variables.c:1900

◆ xsltXPathVariableLookup()

xmlXPathObjectPtr xsltXPathVariableLookup ( void ctxt,
const xmlChar name,
const xmlChar ns_uri 
)

Definition at line 2270 of file variables.c.

2271 {
2273 xmlXPathObjectPtr valueObj = NULL;
2274
2275 if ((ctxt == NULL) || (name == NULL))
2276 return(NULL);
2277
2278#ifdef WITH_XSLT_DEBUG_VARIABLE
2280 "Lookup variable '%s'\n", name));
2281#endif
2282
2283 tctxt = (xsltTransformContextPtr) ctxt;
2284 /*
2285 * Local variables/params ---------------------------------------------
2286 *
2287 * Do the lookup from the top of the stack, but
2288 * don't use params being computed in a call-param
2289 * First lookup expects the variable name and URI to
2290 * come from the disctionnary and hence pointer comparison.
2291 */
2292 if (tctxt->varsNr != 0) {
2293 int i;
2295
2296 for (i = tctxt->varsNr; i > tctxt->varsBase; i--) {
2297 cur = tctxt->varsTab[i-1];
2298 if ((cur->name == name) && (cur->nameURI == ns_uri)) {
2299#if 0
2300 stack_addr++;
2301#endif
2302 variable = cur;
2303 goto local_variable_found;
2304 }
2305 cur = cur->next;
2306 }
2307 /*
2308 * Redo the lookup with interned strings to avoid string comparison.
2309 *
2310 * OPTIMIZE TODO: The problem here is, that if we request a
2311 * global variable, then this will be also executed.
2312 */
2313 {
2314 const xmlChar *tmpName = name, *tmpNsName = ns_uri;
2315
2316 name = xmlDictLookup(tctxt->dict, name, -1);
2317 if (ns_uri)
2318 ns_uri = xmlDictLookup(tctxt->dict, ns_uri, -1);
2319 if ((tmpName != name) || (tmpNsName != ns_uri)) {
2320 for (i = tctxt->varsNr; i > tctxt->varsBase; i--) {
2321 cur = tctxt->varsTab[i-1];
2322 if ((cur->name == name) && (cur->nameURI == ns_uri)) {
2323#if 0
2324 stack_cmp++;
2325#endif
2326 variable = cur;
2327 goto local_variable_found;
2328 }
2329 }
2330 }
2331 }
2332
2333local_variable_found:
2334
2335 if (variable) {
2336 if (variable->computed == 0) {
2337
2338#ifdef WITH_XSLT_DEBUG_VARIABLE
2340 "uncomputed variable '%s'\n", name));
2341#endif
2342 variable->value = xsltEvalVariable(tctxt, variable, NULL);
2343 variable->computed = 1;
2344 }
2345 if (variable->value != NULL) {
2346 valueObj = xmlXPathObjectCopy(variable->value);
2347 }
2348 return(valueObj);
2349 }
2350 }
2351 /*
2352 * Global variables/params --------------------------------------------
2353 */
2354 if (tctxt->globalVars) {
2355 valueObj = xsltGlobalVariableLookup(tctxt, name, ns_uri);
2356 }
2357
2358 if (valueObj == NULL) {
2359
2360#ifdef WITH_XSLT_DEBUG_VARIABLE
2362 "variable not found '%s'\n", name));
2363#endif
2364
2365 if (ns_uri) {
2366 xsltTransformError(tctxt, NULL, tctxt->inst,
2367 "Variable '{%s}%s' has not been declared.\n", ns_uri, name);
2368 } else {
2369 xsltTransformError(tctxt, NULL, tctxt->inst,
2370 "Variable '%s' has not been declared.\n", name);
2371 }
2372 } else {
2373
2374#ifdef WITH_XSLT_DEBUG_VARIABLE
2376 "found variable '%s'\n", name));
2377#endif
2378 }
2379
2380 return(valueObj);
2381}
xsltTransformContext * xsltTransformContextPtr

Variable Documentation

◆ xsltComputingGlobalVarMarker

const xmlChar* xsltComputingGlobalVarMarker
static
Initial value:
=
(const xmlChar *) " var/param being computed"

Definition at line 43 of file variables.c.

Referenced by xsltEvalGlobalVariable(), and xsltGlobalVariableLookup().