19f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson/* 29f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * Licensed to the Apache Software Foundation (ASF) under one 39f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * or more contributor license agreements. See the NOTICE file 49f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * distributed with this work for additional information 59f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * regarding copyright ownership. The ASF licenses this file 69f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * to you under the Apache License, Version 2.0 (the "License"); 79f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * you may not use this file except in compliance with the License. 89f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * You may obtain a copy of the License at 99f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 109f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * http://www.apache.org/licenses/LICENSE-2.0 119f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 129f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * Unless required by applicable law or agreed to in writing, software 139f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * distributed under the License is distributed on an "AS IS" BASIS, 149f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 159f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * See the License for the specific language governing permissions and 169f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * limitations under the License. 179f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 189f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson/* 199f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * $Id: XPathParser.java 468655 2006-10-28 07:12:06Z minchau $ 209f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 219f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilsonpackage org.apache.xpath.compiler; 229f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 239f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilsonimport javax.xml.transform.ErrorListener; 249f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilsonimport javax.xml.transform.TransformerException; 259f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 269f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilsonimport org.apache.xalan.res.XSLMessages; 279f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilsonimport org.apache.xml.utils.PrefixResolver; 289f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilsonimport org.apache.xpath.XPathProcessorException; 299f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilsonimport org.apache.xpath.domapi.XPathStylesheetDOM3Exception; 309f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilsonimport org.apache.xpath.objects.XNumber; 319f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilsonimport org.apache.xpath.objects.XString; 329f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilsonimport org.apache.xpath.res.XPATHErrorResources; 339f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 349f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson/** 359f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * Tokenizes and parses XPath expressions. This should really be named 369f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * XPathParserImpl, and may be renamed in the future. 379f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @xsl.usage general 389f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 399f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilsonpublic class XPathParser 409f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson{ 419f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // %REVIEW% Is there a better way of doing this? 429f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // Upside is minimum object churn. Downside is that we don't have a useful 439f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // backtrace in the exception itself -- but we don't expect to need one. 449f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson static public final String CONTINUE_AFTER_FATAL_ERROR="CONTINUE_AFTER_FATAL_ERROR"; 459f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 469f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 479f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * The XPath to be processed. 489f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 499f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson private OpMap m_ops; 509f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 519f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 529f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * The next token in the pattern. 539f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 549f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson transient String m_token; 559f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 569f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 579f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * The first char in m_token, the theory being that this 589f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * is an optimization because we won't have to do charAt(0) as 599f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * often. 609f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 619f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson transient char m_tokenChar = 0; 629f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 639f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 649f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * The position in the token queue is tracked by m_queueMark. 659f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 669f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int m_queueMark = 0; 679f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 689f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 699f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * Results from checking FilterExpr syntax 709f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 719f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson protected final static int FILTER_MATCH_FAILED = 0; 729f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson protected final static int FILTER_MATCH_PRIMARY = 1; 739f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson protected final static int FILTER_MATCH_PREDICATES = 2; 749f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 759f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 769f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * The parser constructor. 779f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 789f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson public XPathParser(ErrorListener errorListener, javax.xml.transform.SourceLocator sourceLocator) 799f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 809f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_errorListener = errorListener; 819f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_sourceLocator = sourceLocator; 829f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 839f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 849f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 859f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * The prefix resolver to map prefixes to namespaces in the OpMap. 869f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 879f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson PrefixResolver m_namespaceContext; 889f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 899f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 909f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * Given an string, init an XPath object for selections, 919f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * in order that a parse doesn't 929f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * have to be done each time the expression is evaluated. 939f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 949f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @param compiler The compiler object. 959f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @param expression A string conforming to the XPath grammar. 969f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @param namespaceContext An object that is able to resolve prefixes in 979f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * the XPath to namespaces. 989f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 999f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @throws javax.xml.transform.TransformerException 1009f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 1019f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson public void initXPath( 1029f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson Compiler compiler, String expression, PrefixResolver namespaceContext) 1039f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson throws javax.xml.transform.TransformerException 1049f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 1059f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 1069f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops = compiler; 1079f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_namespaceContext = namespaceContext; 1089f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_functionTable = compiler.getFunctionTable(); 1099f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 1109f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson Lexer lexer = new Lexer(compiler, namespaceContext, this); 1119f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 1129f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson lexer.tokenize(expression); 1139f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 1149f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(0,OpCodes.OP_XPATH); 1159f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(OpMap.MAPINDEX_LENGTH,2); 1169f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 1179f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 1189f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // Patch for Christine's gripe. She wants her errorHandler to return from 1199f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // a fatal error and continue trying to parse, rather than throwing an exception. 1209f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // Without the patch, that put us into an endless loop. 1219f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // 1229f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // %REVIEW% Is there a better way of doing this? 1239f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // %REVIEW% Are there any other cases which need the safety net? 1249f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // (and if so do we care right now, or should we rewrite the XPath 1259f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // grammar engine and can fix it at that time?) 1269f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson try { 1279f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 1289f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 1299f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson Expr(); 1309f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 1319f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (null != m_token) 1329f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 1339f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson String extraTokens = ""; 1349f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 1359f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson while (null != m_token) 1369f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 1379f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson extraTokens += "'" + m_token + "'"; 1389f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 1399f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 1409f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 1419f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (null != m_token) 1429f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson extraTokens += ", "; 1439f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 1449f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 1459f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson error(XPATHErrorResources.ER_EXTRA_ILLEGAL_TOKENS, 1469f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson new Object[]{ extraTokens }); //"Extra illegal tokens: "+extraTokens); 1479f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 1489f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 1499f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 1509f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson catch (org.apache.xpath.XPathProcessorException e) 1519f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 1529f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if(CONTINUE_AFTER_FATAL_ERROR.equals(e.getMessage())) 1539f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 1549f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // What I _want_ to do is null out this XPath. 1559f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // I doubt this has the desired effect, but I'm not sure what else to do. 1569f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // %REVIEW%!!! 1579f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson initXPath(compiler, "/..", namespaceContext); 1589f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 1599f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else 1609f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson throw e; 1619f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 1629f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 1639f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson compiler.shrink(); 1649f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 1659f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 1669f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 1679f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * Given an string, init an XPath object for pattern matches, 1689f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * in order that a parse doesn't 1699f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * have to be done each time the expression is evaluated. 1709f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @param compiler The XPath object to be initialized. 1719f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @param expression A String representing the XPath. 1729f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @param namespaceContext An object that is able to resolve prefixes in 1739f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * the XPath to namespaces. 1749f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 1759f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @throws javax.xml.transform.TransformerException 1769f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 1779f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson public void initMatchPattern( 1789f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson Compiler compiler, String expression, PrefixResolver namespaceContext) 1799f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson throws javax.xml.transform.TransformerException 1809f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 1819f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 1829f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops = compiler; 1839f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_namespaceContext = namespaceContext; 1849f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_functionTable = compiler.getFunctionTable(); 1859f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 1869f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson Lexer lexer = new Lexer(compiler, namespaceContext, this); 1879f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 1889f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson lexer.tokenize(expression); 1899f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 1909f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(0, OpCodes.OP_MATCHPATTERN); 1919f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(OpMap.MAPINDEX_LENGTH, 2); 1929f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 1939f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 1949f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson Pattern(); 1959f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 1969f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (null != m_token) 1979f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 1989f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson String extraTokens = ""; 1999f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 2009f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson while (null != m_token) 2019f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 2029f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson extraTokens += "'" + m_token + "'"; 2039f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 2049f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 2059f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 2069f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (null != m_token) 2079f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson extraTokens += ", "; 2089f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 2099f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 2109f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson error(XPATHErrorResources.ER_EXTRA_ILLEGAL_TOKENS, 2119f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson new Object[]{ extraTokens }); //"Extra illegal tokens: "+extraTokens); 2129f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 2139f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 2149f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // Terminate for safety. 2159f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(m_ops.getOp(OpMap.MAPINDEX_LENGTH), OpCodes.ENDOP); 2169f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(OpMap.MAPINDEX_LENGTH, m_ops.getOp(OpMap.MAPINDEX_LENGTH)+1); 2179f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 2189f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.shrink(); 2199f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 2209f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 2219f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** The error listener where syntax errors are to be sent. 2229f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 2239f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson private ErrorListener m_errorListener; 2249f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 2259f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** The source location of the XPath. */ 2269f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson javax.xml.transform.SourceLocator m_sourceLocator; 2279f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 2289f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** The table contains build-in functions and customized functions */ 2299f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson private FunctionTable m_functionTable; 2309f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 2319f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 2329f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * Allow an application to register an error event handler, where syntax 2339f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * errors will be sent. If the error listener is not set, syntax errors 2349f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * will be sent to System.err. 2359f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 2369f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @param handler Reference to error listener where syntax errors will be 2379f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * sent. 2389f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 2399f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson public void setErrorHandler(ErrorListener handler) 2409f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 2419f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_errorListener = handler; 2429f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 2439f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 2449f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 2459f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * Return the current error listener. 2469f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 2479f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @return The error listener, which should not normally be null, but may be. 2489f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 2499f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson public ErrorListener getErrorListener() 2509f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 2519f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson return m_errorListener; 2529f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 2539f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 2549f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 2559f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * Check whether m_token matches the target string. 2569f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 2579f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @param s A string reference or null. 2589f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 2599f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @return If m_token is null, returns false (or true if s is also null), or 2609f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * return true if the current token matches the string, else false. 2619f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 2629f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson final boolean tokenIs(String s) 2639f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 2649f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson return (m_token != null) ? (m_token.equals(s)) : (s == null); 2659f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 2669f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 2679f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 2689f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * Check whether m_tokenChar==c. 2699f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 2709f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @param c A character to be tested. 2719f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 2729f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @return If m_token is null, returns false, or return true if c matches 2739f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * the current token. 2749f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 2759f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson final boolean tokenIs(char c) 2769f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 2779f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson return (m_token != null) ? (m_tokenChar == c) : false; 2789f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 2799f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 2809f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 2819f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * Look ahead of the current token in order to 2829f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * make a branching decision. 2839f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 2849f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @param c the character to be tested for. 2859f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @param n number of tokens to look ahead. Must be 2869f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * greater than 1. 2879f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 2889f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @return true if the next token matches the character argument. 2899f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 2909f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson final boolean lookahead(char c, int n) 2919f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 2929f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 2939f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int pos = (m_queueMark + n); 2949f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson boolean b; 2959f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 2969f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if ((pos <= m_ops.getTokenQueueSize()) && (pos > 0) 2979f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson && (m_ops.getTokenQueueSize() != 0)) 2989f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 2999f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson String tok = ((String) m_ops.m_tokenQueue.elementAt(pos - 1)); 3009f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 3019f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson b = (tok.length() == 1) ? (tok.charAt(0) == c) : false; 3029f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 3039f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else 3049f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 3059f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson b = false; 3069f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 3079f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 3089f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson return b; 3099f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 3109f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 3119f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 3129f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * Look behind the first character of the current token in order to 3139f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * make a branching decision. 3149f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 3159f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @param c the character to compare it to. 3169f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @param n number of tokens to look behind. Must be 3179f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * greater than 1. Note that the look behind terminates 3189f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * at either the beginning of the string or on a '|' 3199f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * character. Because of this, this method should only 3209f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * be used for pattern matching. 3219f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 3229f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @return true if the token behind the current token matches the character 3239f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * argument. 3249f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 3259f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson private final boolean lookbehind(char c, int n) 3269f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 3279f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 3289f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson boolean isToken; 3299f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int lookBehindPos = m_queueMark - (n + 1); 3309f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 3319f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (lookBehindPos >= 0) 3329f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 3339f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson String lookbehind = (String) m_ops.m_tokenQueue.elementAt(lookBehindPos); 3349f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 3359f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (lookbehind.length() == 1) 3369f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 3379f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson char c0 = (lookbehind == null) ? '|' : lookbehind.charAt(0); 3389f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 3399f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson isToken = (c0 == '|') ? false : (c0 == c); 3409f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 3419f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else 3429f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 3439f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson isToken = false; 3449f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 3459f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 3469f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else 3479f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 3489f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson isToken = false; 3499f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 3509f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 3519f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson return isToken; 3529f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 3539f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 3549f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 3559f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * look behind the current token in order to 3569f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * see if there is a useable token. 3579f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 3589f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @param n number of tokens to look behind. Must be 3599f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * greater than 1. Note that the look behind terminates 3609f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * at either the beginning of the string or on a '|' 3619f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * character. Because of this, this method should only 3629f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * be used for pattern matching. 3639f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 3649f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @return true if look behind has a token, false otherwise. 3659f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 3669f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson private final boolean lookbehindHasToken(int n) 3679f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 3689f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 3699f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson boolean hasToken; 3709f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 3719f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if ((m_queueMark - n) > 0) 3729f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 3739f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson String lookbehind = (String) m_ops.m_tokenQueue.elementAt(m_queueMark - (n - 1)); 3749f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson char c0 = (lookbehind == null) ? '|' : lookbehind.charAt(0); 3759f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 3769f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson hasToken = (c0 == '|') ? false : true; 3779f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 3789f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else 3799f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 3809f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson hasToken = false; 3819f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 3829f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 3839f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson return hasToken; 3849f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 3859f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 3869f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 3879f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * Look ahead of the current token in order to 3889f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * make a branching decision. 3899f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 3909f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @param s the string to compare it to. 3919f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @param n number of tokens to lookahead. Must be 3929f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * greater than 1. 3939f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 3949f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @return true if the token behind the current token matches the string 3959f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * argument. 3969f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 3979f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson private final boolean lookahead(String s, int n) 3989f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 3999f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 4009f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson boolean isToken; 4019f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 4029f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if ((m_queueMark + n) <= m_ops.getTokenQueueSize()) 4039f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 4049f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson String lookahead = (String) m_ops.m_tokenQueue.elementAt(m_queueMark + (n - 1)); 4059f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 4069f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson isToken = (lookahead != null) ? lookahead.equals(s) : (s == null); 4079f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 4089f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else 4099f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 4109f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson isToken = (null == s); 4119f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 4129f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 4139f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson return isToken; 4149f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 4159f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 4169f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 4179f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * Retrieve the next token from the command and 4189f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * store it in m_token string. 4199f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 4209f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson private final void nextToken() 4219f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 4229f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 4239f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (m_queueMark < m_ops.getTokenQueueSize()) 4249f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 4259f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_token = (String) m_ops.m_tokenQueue.elementAt(m_queueMark++); 4269f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_tokenChar = m_token.charAt(0); 4279f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 4289f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else 4299f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 4309f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_token = null; 4319f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_tokenChar = 0; 4329f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 4339f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 4349f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 4359f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 4369f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * Retrieve a token relative to the current token. 4379f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 4389f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @param i Position relative to current token. 4399f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 4409f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @return The string at the given index, or null if the index is out 4419f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * of range. 4429f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 4439f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson private final String getTokenRelative(int i) 4449f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 4459f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 4469f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson String tok; 4479f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int relative = m_queueMark + i; 4489f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 4499f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if ((relative > 0) && (relative < m_ops.getTokenQueueSize())) 4509f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 4519f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson tok = (String) m_ops.m_tokenQueue.elementAt(relative); 4529f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 4539f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else 4549f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 4559f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson tok = null; 4569f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 4579f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 4589f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson return tok; 4599f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 4609f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 4619f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 4629f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * Retrieve the previous token from the command and 4639f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * store it in m_token string. 4649f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 4659f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson private final void prevToken() 4669f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 4679f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 4689f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (m_queueMark > 0) 4699f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 4709f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_queueMark--; 4719f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 4729f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_token = (String) m_ops.m_tokenQueue.elementAt(m_queueMark); 4739f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_tokenChar = m_token.charAt(0); 4749f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 4759f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else 4769f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 4779f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_token = null; 4789f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_tokenChar = 0; 4799f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 4809f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 4819f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 4829f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 4839f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * Consume an expected token, throwing an exception if it 4849f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * isn't there. 4859f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 4869f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @param expected The string to be expected. 4879f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 4889f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @throws javax.xml.transform.TransformerException 4899f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 4909f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson private final void consumeExpected(String expected) 4919f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson throws javax.xml.transform.TransformerException 4929f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 4939f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 4949f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (tokenIs(expected)) 4959f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 4969f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 4979f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 4989f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else 4999f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 5009f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson error(XPATHErrorResources.ER_EXPECTED_BUT_FOUND, new Object[]{ expected, 5019f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_token }); //"Expected "+expected+", but found: "+m_token); 5029f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 5039f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // Patch for Christina's gripe. She wants her errorHandler to return from 5049f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // this error and continue trying to parse, rather than throwing an exception. 5059f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // Without the patch, that put us into an endless loop. 5069f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson throw new XPathProcessorException(CONTINUE_AFTER_FATAL_ERROR); 5079f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 5089f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 5099f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 5109f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 5119f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * Consume an expected token, throwing an exception if it 5129f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * isn't there. 5139f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 5149f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @param expected the character to be expected. 5159f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 5169f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @throws javax.xml.transform.TransformerException 5179f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 5189f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson private final void consumeExpected(char expected) 5199f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson throws javax.xml.transform.TransformerException 5209f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 5219f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 5229f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (tokenIs(expected)) 5239f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 5249f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 5259f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 5269f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else 5279f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 5289f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson error(XPATHErrorResources.ER_EXPECTED_BUT_FOUND, 5299f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson new Object[]{ String.valueOf(expected), 5309f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_token }); //"Expected "+expected+", but found: "+m_token); 5319f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 5329f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // Patch for Christina's gripe. She wants her errorHandler to return from 5339f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // this error and continue trying to parse, rather than throwing an exception. 5349f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // Without the patch, that put us into an endless loop. 5359f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson throw new XPathProcessorException(CONTINUE_AFTER_FATAL_ERROR); 5369f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 5379f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 5389f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 5399f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 5409f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * Warn the user of a problem. 5419f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 5429f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @param msg An error msgkey that corresponds to one of the constants found 5439f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * in {@link org.apache.xpath.res.XPATHErrorResources}, which is 5449f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * a key for a format string. 5459f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @param args An array of arguments represented in the format string, which 5469f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * may be null. 5479f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 5489f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @throws TransformerException if the current ErrorListoner determines to 5499f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * throw an exception. 5509f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 5519f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson void warn(String msg, Object[] args) throws TransformerException 5529f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 5539f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 5549f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson String fmsg = XSLMessages.createXPATHWarning(msg, args); 5559f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson ErrorListener ehandler = this.getErrorListener(); 5569f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 5579f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (null != ehandler) 5589f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 5599f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // TO DO: Need to get stylesheet Locator from here. 5609f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson ehandler.warning(new TransformerException(fmsg, m_sourceLocator)); 5619f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 5629f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else 5639f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 5649f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // Should never happen. 5659f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson System.err.println(fmsg); 5669f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 5679f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 5689f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 5699f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 5709f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * Notify the user of an assertion error, and probably throw an 5719f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * exception. 5729f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 5739f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @param b If false, a runtime exception will be thrown. 5749f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @param msg The assertion message, which should be informative. 5759f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 5769f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @throws RuntimeException if the b argument is false. 5779f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 5789f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson private void assertion(boolean b, String msg) 5799f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 5809f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 5819f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (!b) 5829f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 5839f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson String fMsg = XSLMessages.createXPATHMessage( 5849f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson XPATHErrorResources.ER_INCORRECT_PROGRAMMER_ASSERTION, 5859f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson new Object[]{ msg }); 5869f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 5879f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson throw new RuntimeException(fMsg); 5889f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 5899f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 5909f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 5919f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 5929f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * Notify the user of an error, and probably throw an 5939f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * exception. 5949f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 5959f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @param msg An error msgkey that corresponds to one of the constants found 5969f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * in {@link org.apache.xpath.res.XPATHErrorResources}, which is 5979f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * a key for a format string. 5989f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @param args An array of arguments represented in the format string, which 5999f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * may be null. 6009f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 6019f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @throws TransformerException if the current ErrorListoner determines to 6029f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * throw an exception. 6039f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 6049f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson void error(String msg, Object[] args) throws TransformerException 6059f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 6069f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 6079f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson String fmsg = XSLMessages.createXPATHMessage(msg, args); 6089f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson ErrorListener ehandler = this.getErrorListener(); 6099f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 6109f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson TransformerException te = new TransformerException(fmsg, m_sourceLocator); 6119f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (null != ehandler) 6129f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 6139f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // TO DO: Need to get stylesheet Locator from here. 6149f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson ehandler.fatalError(te); 6159f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 6169f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else 6179f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 6189f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // System.err.println(fmsg); 6199f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson throw te; 6209f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 6219f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 6229f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 6239f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 6249f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * This method is added to support DOM 3 XPath API. 6259f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * <p> 6269f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * This method is exactly like error(String, Object[]); except that 6279f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * the underlying TransformerException is 6289f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * XpathStylesheetDOM3Exception (which extends TransformerException). 6299f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * <p> 6309f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * So older XPath code in Xalan is not affected by this. To older XPath code 6319f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * the behavior of whether error() or errorForDOM3() is called because it is 6329f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * always catching TransformerException objects and is oblivious to 6339f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * the new subclass of XPathStylesheetDOM3Exception. Older XPath code 6349f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * runs as before. 6359f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * <p> 6369f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * However, newer DOM3 XPath code upon catching a TransformerException can 6379f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * can check if the exception is an instance of XPathStylesheetDOM3Exception 6389f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * and take appropriate action. 6399f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 6409f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @param msg An error msgkey that corresponds to one of the constants found 6419f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * in {@link org.apache.xpath.res.XPATHErrorResources}, which is 6429f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * a key for a format string. 6439f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @param args An array of arguments represented in the format string, which 6449f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * may be null. 6459f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 6469f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @throws TransformerException if the current ErrorListoner determines to 6479f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * throw an exception. 6489f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 6499f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson void errorForDOM3(String msg, Object[] args) throws TransformerException 6509f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 6519f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 6529f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson String fmsg = XSLMessages.createXPATHMessage(msg, args); 6539f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson ErrorListener ehandler = this.getErrorListener(); 6549f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 6559f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson TransformerException te = new XPathStylesheetDOM3Exception(fmsg, m_sourceLocator); 6569f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (null != ehandler) 6579f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 6589f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // TO DO: Need to get stylesheet Locator from here. 6599f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson ehandler.fatalError(te); 6609f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 6619f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else 6629f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 6639f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // System.err.println(fmsg); 6649f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson throw te; 6659f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 6669f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 6679f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 6689f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * Dump the remaining token queue. 6699f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * Thanks to Craig for this. 6709f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 6719f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @return A dump of the remaining token queue, which may be appended to 6729f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * an error message. 6739f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 6749f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson protected String dumpRemainingTokenQueue() 6759f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 6769f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 6779f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int q = m_queueMark; 6789f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson String returnMsg; 6799f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 6809f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (q < m_ops.getTokenQueueSize()) 6819f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 6829f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson String msg = "\n Remaining tokens: ("; 6839f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 6849f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson while (q < m_ops.getTokenQueueSize()) 6859f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 6869f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson String t = (String) m_ops.m_tokenQueue.elementAt(q++); 6879f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 6889f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson msg += (" '" + t + "'"); 6899f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 6909f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 6919f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson returnMsg = msg + ")"; 6929f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 6939f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else 6949f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 6959f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson returnMsg = ""; 6969f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 6979f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 6989f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson return returnMsg; 6999f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 7009f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 7019f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 7029f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * Given a string, return the corresponding function token. 7039f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 7049f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @param key A local name of a function. 7059f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 7069f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @return The function ID, which may correspond to one of the FUNC_XXX 7079f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * values found in {@link org.apache.xpath.compiler.FunctionTable}, but may 7089f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * be a value installed by an external module. 7099f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 7109f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson final int getFunctionToken(String key) 7119f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 7129f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 7139f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int tok; 7149f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 7159f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson Object id; 7169f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 7179f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson try 7189f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 7199f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // These are nodetests, xpathparser treats them as functions when parsing 7209f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // a FilterExpr. 7219f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson id = Keywords.lookupNodeTest(key); 7229f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (null == id) id = m_functionTable.getFunctionID(key); 7239f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson tok = ((Integer) id).intValue(); 7249f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 7259f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson catch (NullPointerException npe) 7269f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 7279f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson tok = -1; 7289f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 7299f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson catch (ClassCastException cce) 7309f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 7319f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson tok = -1; 7329f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 7339f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 7349f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson return tok; 7359f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 7369f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 7379f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 7389f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * Insert room for operation. This will NOT set 7399f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * the length value of the operation, but will update 7409f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * the length value for the total expression. 7419f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 7429f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @param pos The position where the op is to be inserted. 7439f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @param length The length of the operation space in the op map. 7449f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @param op The op code to the inserted. 7459f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 7469f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson void insertOp(int pos, int length, int op) 7479f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 7489f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 7499f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int totalLen = m_ops.getOp(OpMap.MAPINDEX_LENGTH); 7509f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 7519f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson for (int i = totalLen - 1; i >= pos; i--) 7529f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 7539f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(i + length, m_ops.getOp(i)); 7549f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 7559f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 7569f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(pos,op); 7579f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(OpMap.MAPINDEX_LENGTH,totalLen + length); 7589f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 7599f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 7609f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 7619f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * Insert room for operation. This WILL set 7629f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * the length value of the operation, and will update 7639f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * the length value for the total expression. 7649f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 7659f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @param length The length of the operation. 7669f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @param op The op code to the inserted. 7679f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 7689f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson void appendOp(int length, int op) 7699f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 7709f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 7719f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int totalLen = m_ops.getOp(OpMap.MAPINDEX_LENGTH); 7729f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 7739f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(totalLen, op); 7749f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(totalLen + OpMap.MAPINDEX_LENGTH, length); 7759f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(OpMap.MAPINDEX_LENGTH, totalLen + length); 7769f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 7779f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 7789f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // ============= EXPRESSIONS FUNCTIONS ================= 7799f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 7809f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 7819f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 7829f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 7839f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * Expr ::= OrExpr 7849f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 7859f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 7869f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @throws javax.xml.transform.TransformerException 7879f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 7889f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson protected void Expr() throws javax.xml.transform.TransformerException 7899f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 7909f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson OrExpr(); 7919f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 7929f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 7939f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 7949f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 7959f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 7969f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * OrExpr ::= AndExpr 7979f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * | OrExpr 'or' AndExpr 7989f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 7999f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 8009f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @throws javax.xml.transform.TransformerException 8019f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 8029f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson protected void OrExpr() throws javax.xml.transform.TransformerException 8039f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 8049f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 8059f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int opPos = m_ops.getOp(OpMap.MAPINDEX_LENGTH); 8069f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 8079f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson AndExpr(); 8089f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 8099f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if ((null != m_token) && tokenIs("or")) 8109f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 8119f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 8129f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson insertOp(opPos, 2, OpCodes.OP_OR); 8139f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson OrExpr(); 8149f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 8159f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(opPos + OpMap.MAPINDEX_LENGTH, 8169f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.getOp(OpMap.MAPINDEX_LENGTH) - opPos); 8179f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 8189f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 8199f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 8209f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 8219f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 8229f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 8239f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * AndExpr ::= EqualityExpr 8249f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * | AndExpr 'and' EqualityExpr 8259f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 8269f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 8279f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @throws javax.xml.transform.TransformerException 8289f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 8299f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson protected void AndExpr() throws javax.xml.transform.TransformerException 8309f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 8319f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 8329f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int opPos = m_ops.getOp(OpMap.MAPINDEX_LENGTH); 8339f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 8349f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson EqualityExpr(-1); 8359f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 8369f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if ((null != m_token) && tokenIs("and")) 8379f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 8389f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 8399f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson insertOp(opPos, 2, OpCodes.OP_AND); 8409f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson AndExpr(); 8419f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 8429f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(opPos + OpMap.MAPINDEX_LENGTH, 8439f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.getOp(OpMap.MAPINDEX_LENGTH) - opPos); 8449f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 8459f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 8469f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 8479f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 8489f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 8499f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @returns an Object which is either a String, a Number, a Boolean, or a vector 8509f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * of nodes. 8519f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 8529f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * EqualityExpr ::= RelationalExpr 8539f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * | EqualityExpr '=' RelationalExpr 8549f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 8559f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 8569f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @param addPos Position where expression is to be added, or -1 for append. 8579f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 8589f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @return the position at the end of the equality expression. 8599f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 8609f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @throws javax.xml.transform.TransformerException 8619f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 8629f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson protected int EqualityExpr(int addPos) throws javax.xml.transform.TransformerException 8639f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 8649f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 8659f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int opPos = m_ops.getOp(OpMap.MAPINDEX_LENGTH); 8669f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 8679f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (-1 == addPos) 8689f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson addPos = opPos; 8699f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 8709f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson RelationalExpr(-1); 8719f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 8729f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (null != m_token) 8739f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 8749f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (tokenIs('!') && lookahead('=', 1)) 8759f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 8769f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 8779f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 8789f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson insertOp(addPos, 2, OpCodes.OP_NOTEQUALS); 8799f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 8809f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int opPlusLeftHandLen = m_ops.getOp(OpMap.MAPINDEX_LENGTH) - addPos; 8819f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 8829f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson addPos = EqualityExpr(addPos); 8839f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(addPos + OpMap.MAPINDEX_LENGTH, 8849f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.getOp(addPos + opPlusLeftHandLen + 1) + opPlusLeftHandLen); 8859f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson addPos += 2; 8869f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 8879f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else if (tokenIs('=')) 8889f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 8899f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 8909f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson insertOp(addPos, 2, OpCodes.OP_EQUALS); 8919f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 8929f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int opPlusLeftHandLen = m_ops.getOp(OpMap.MAPINDEX_LENGTH) - addPos; 8939f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 8949f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson addPos = EqualityExpr(addPos); 8959f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(addPos + OpMap.MAPINDEX_LENGTH, 8969f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.getOp(addPos + opPlusLeftHandLen + 1) + opPlusLeftHandLen); 8979f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson addPos += 2; 8989f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 8999f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 9009f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 9019f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson return addPos; 9029f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 9039f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 9049f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 9059f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * . 9069f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @returns an Object which is either a String, a Number, a Boolean, or a vector 9079f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * of nodes. 9089f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 9099f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * RelationalExpr ::= AdditiveExpr 9109f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * | RelationalExpr '<' AdditiveExpr 9119f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * | RelationalExpr '>' AdditiveExpr 9129f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * | RelationalExpr '<=' AdditiveExpr 9139f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * | RelationalExpr '>=' AdditiveExpr 9149f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 9159f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 9169f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @param addPos Position where expression is to be added, or -1 for append. 9179f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 9189f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @return the position at the end of the relational expression. 9199f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 9209f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @throws javax.xml.transform.TransformerException 9219f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 9229f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson protected int RelationalExpr(int addPos) throws javax.xml.transform.TransformerException 9239f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 9249f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 9259f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int opPos = m_ops.getOp(OpMap.MAPINDEX_LENGTH); 9269f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 9279f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (-1 == addPos) 9289f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson addPos = opPos; 9299f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 9309f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson AdditiveExpr(-1); 9319f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 9329f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (null != m_token) 9339f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 9349f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (tokenIs('<')) 9359f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 9369f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 9379f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 9389f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (tokenIs('=')) 9399f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 9409f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 9419f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson insertOp(addPos, 2, OpCodes.OP_LTE); 9429f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 9439f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else 9449f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 9459f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson insertOp(addPos, 2, OpCodes.OP_LT); 9469f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 9479f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 9489f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int opPlusLeftHandLen = m_ops.getOp(OpMap.MAPINDEX_LENGTH) - addPos; 9499f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 9509f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson addPos = RelationalExpr(addPos); 9519f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(addPos + OpMap.MAPINDEX_LENGTH, 9529f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.getOp(addPos + opPlusLeftHandLen + 1) + opPlusLeftHandLen); 9539f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson addPos += 2; 9549f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 9559f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else if (tokenIs('>')) 9569f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 9579f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 9589f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 9599f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (tokenIs('=')) 9609f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 9619f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 9629f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson insertOp(addPos, 2, OpCodes.OP_GTE); 9639f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 9649f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else 9659f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 9669f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson insertOp(addPos, 2, OpCodes.OP_GT); 9679f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 9689f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 9699f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int opPlusLeftHandLen = m_ops.getOp(OpMap.MAPINDEX_LENGTH) - addPos; 9709f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 9719f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson addPos = RelationalExpr(addPos); 9729f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(addPos + OpMap.MAPINDEX_LENGTH, 9739f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.getOp(addPos + opPlusLeftHandLen + 1) + opPlusLeftHandLen); 9749f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson addPos += 2; 9759f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 9769f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 9779f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 9789f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson return addPos; 9799f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 9809f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 9819f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 9829f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * This has to handle construction of the operations so that they are evaluated 9839f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * in pre-fix order. So, for 9+7-6, instead of |+|9|-|7|6|, this needs to be 9849f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * evaluated as |-|+|9|7|6|. 9859f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 9869f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * AdditiveExpr ::= MultiplicativeExpr 9879f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * | AdditiveExpr '+' MultiplicativeExpr 9889f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * | AdditiveExpr '-' MultiplicativeExpr 9899f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 9909f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 9919f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @param addPos Position where expression is to be added, or -1 for append. 9929f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 9939f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @return the position at the end of the equality expression. 9949f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 9959f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @throws javax.xml.transform.TransformerException 9969f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 9979f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson protected int AdditiveExpr(int addPos) throws javax.xml.transform.TransformerException 9989f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 9999f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 10009f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int opPos = m_ops.getOp(OpMap.MAPINDEX_LENGTH); 10019f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 10029f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (-1 == addPos) 10039f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson addPos = opPos; 10049f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 10059f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson MultiplicativeExpr(-1); 10069f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 10079f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (null != m_token) 10089f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 10099f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (tokenIs('+')) 10109f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 10119f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 10129f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson insertOp(addPos, 2, OpCodes.OP_PLUS); 10139f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 10149f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int opPlusLeftHandLen = m_ops.getOp(OpMap.MAPINDEX_LENGTH) - addPos; 10159f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 10169f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson addPos = AdditiveExpr(addPos); 10179f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(addPos + OpMap.MAPINDEX_LENGTH, 10189f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.getOp(addPos + opPlusLeftHandLen + 1) + opPlusLeftHandLen); 10199f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson addPos += 2; 10209f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 10219f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else if (tokenIs('-')) 10229f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 10239f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 10249f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson insertOp(addPos, 2, OpCodes.OP_MINUS); 10259f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 10269f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int opPlusLeftHandLen = m_ops.getOp(OpMap.MAPINDEX_LENGTH) - addPos; 10279f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 10289f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson addPos = AdditiveExpr(addPos); 10299f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(addPos + OpMap.MAPINDEX_LENGTH, 10309f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.getOp(addPos + opPlusLeftHandLen + 1) + opPlusLeftHandLen); 10319f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson addPos += 2; 10329f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 10339f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 10349f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 10359f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson return addPos; 10369f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 10379f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 10389f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 10399f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * This has to handle construction of the operations so that they are evaluated 10409f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * in pre-fix order. So, for 9+7-6, instead of |+|9|-|7|6|, this needs to be 10419f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * evaluated as |-|+|9|7|6|. 10429f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 10439f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * MultiplicativeExpr ::= UnaryExpr 10449f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * | MultiplicativeExpr MultiplyOperator UnaryExpr 10459f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * | MultiplicativeExpr 'div' UnaryExpr 10469f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * | MultiplicativeExpr 'mod' UnaryExpr 10479f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * | MultiplicativeExpr 'quo' UnaryExpr 10489f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 10499f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @param addPos Position where expression is to be added, or -1 for append. 10509f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 10519f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @return the position at the end of the equality expression. 10529f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 10539f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @throws javax.xml.transform.TransformerException 10549f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 10559f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson protected int MultiplicativeExpr(int addPos) throws javax.xml.transform.TransformerException 10569f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 10579f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 10589f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int opPos = m_ops.getOp(OpMap.MAPINDEX_LENGTH); 10599f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 10609f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (-1 == addPos) 10619f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson addPos = opPos; 10629f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 10639f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson UnaryExpr(); 10649f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 10659f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (null != m_token) 10669f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 10679f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (tokenIs('*')) 10689f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 10699f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 10709f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson insertOp(addPos, 2, OpCodes.OP_MULT); 10719f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 10729f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int opPlusLeftHandLen = m_ops.getOp(OpMap.MAPINDEX_LENGTH) - addPos; 10739f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 10749f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson addPos = MultiplicativeExpr(addPos); 10759f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(addPos + OpMap.MAPINDEX_LENGTH, 10769f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.getOp(addPos + opPlusLeftHandLen + 1) + opPlusLeftHandLen); 10779f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson addPos += 2; 10789f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 10799f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else if (tokenIs("div")) 10809f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 10819f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 10829f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson insertOp(addPos, 2, OpCodes.OP_DIV); 10839f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 10849f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int opPlusLeftHandLen = m_ops.getOp(OpMap.MAPINDEX_LENGTH) - addPos; 10859f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 10869f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson addPos = MultiplicativeExpr(addPos); 10879f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(addPos + OpMap.MAPINDEX_LENGTH, 10889f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.getOp(addPos + opPlusLeftHandLen + 1) + opPlusLeftHandLen); 10899f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson addPos += 2; 10909f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 10919f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else if (tokenIs("mod")) 10929f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 10939f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 10949f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson insertOp(addPos, 2, OpCodes.OP_MOD); 10959f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 10969f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int opPlusLeftHandLen = m_ops.getOp(OpMap.MAPINDEX_LENGTH) - addPos; 10979f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 10989f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson addPos = MultiplicativeExpr(addPos); 10999f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(addPos + OpMap.MAPINDEX_LENGTH, 11009f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.getOp(addPos + opPlusLeftHandLen + 1) + opPlusLeftHandLen); 11019f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson addPos += 2; 11029f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 11039f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else if (tokenIs("quo")) 11049f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 11059f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 11069f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson insertOp(addPos, 2, OpCodes.OP_QUO); 11079f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 11089f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int opPlusLeftHandLen = m_ops.getOp(OpMap.MAPINDEX_LENGTH) - addPos; 11099f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 11109f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson addPos = MultiplicativeExpr(addPos); 11119f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(addPos + OpMap.MAPINDEX_LENGTH, 11129f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.getOp(addPos + opPlusLeftHandLen + 1) + opPlusLeftHandLen); 11139f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson addPos += 2; 11149f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 11159f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 11169f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 11179f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson return addPos; 11189f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 11199f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 11209f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 11219f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 11229f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * UnaryExpr ::= UnionExpr 11239f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * | '-' UnaryExpr 11249f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 11259f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 11269f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @throws javax.xml.transform.TransformerException 11279f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 11289f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson protected void UnaryExpr() throws javax.xml.transform.TransformerException 11299f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 11309f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 11319f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int opPos = m_ops.getOp(OpMap.MAPINDEX_LENGTH); 11329f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson boolean isNeg = false; 11339f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 11349f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (m_tokenChar == '-') 11359f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 11369f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 11379f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson appendOp(2, OpCodes.OP_NEG); 11389f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 11399f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson isNeg = true; 11409f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 11419f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 11429f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson UnionExpr(); 11439f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 11449f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (isNeg) 11459f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(opPos + OpMap.MAPINDEX_LENGTH, 11469f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.getOp(OpMap.MAPINDEX_LENGTH) - opPos); 11479f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 11489f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 11499f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 11509f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 11519f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * StringExpr ::= Expr 11529f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 11539f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 11549f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @throws javax.xml.transform.TransformerException 11559f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 11569f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson protected void StringExpr() throws javax.xml.transform.TransformerException 11579f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 11589f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 11599f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int opPos = m_ops.getOp(OpMap.MAPINDEX_LENGTH); 11609f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 11619f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson appendOp(2, OpCodes.OP_STRING); 11629f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson Expr(); 11639f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 11649f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(opPos + OpMap.MAPINDEX_LENGTH, 11659f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.getOp(OpMap.MAPINDEX_LENGTH) - opPos); 11669f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 11679f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 11689f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 11699f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 11709f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 11719f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * StringExpr ::= Expr 11729f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 11739f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 11749f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @throws javax.xml.transform.TransformerException 11759f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 11769f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson protected void BooleanExpr() throws javax.xml.transform.TransformerException 11779f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 11789f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 11799f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int opPos = m_ops.getOp(OpMap.MAPINDEX_LENGTH); 11809f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 11819f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson appendOp(2, OpCodes.OP_BOOL); 11829f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson Expr(); 11839f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 11849f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int opLen = m_ops.getOp(OpMap.MAPINDEX_LENGTH) - opPos; 11859f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 11869f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (opLen == 2) 11879f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 11889f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson error(XPATHErrorResources.ER_BOOLEAN_ARG_NO_LONGER_OPTIONAL, null); //"boolean(...) argument is no longer optional with 19990709 XPath draft."); 11899f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 11909f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 11919f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(opPos + OpMap.MAPINDEX_LENGTH, opLen); 11929f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 11939f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 11949f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 11959f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 11969f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 11979f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * NumberExpr ::= Expr 11989f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 11999f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 12009f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @throws javax.xml.transform.TransformerException 12019f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 12029f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson protected void NumberExpr() throws javax.xml.transform.TransformerException 12039f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 12049f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 12059f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int opPos = m_ops.getOp(OpMap.MAPINDEX_LENGTH); 12069f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 12079f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson appendOp(2, OpCodes.OP_NUMBER); 12089f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson Expr(); 12099f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 12109f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(opPos + OpMap.MAPINDEX_LENGTH, 12119f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.getOp(OpMap.MAPINDEX_LENGTH) - opPos); 12129f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 12139f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 12149f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 12159f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * The context of the right hand side expressions is the context of the 12169f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * left hand side expression. The results of the right hand side expressions 12179f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * are node sets. The result of the left hand side UnionExpr is the union 12189f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * of the results of the right hand side expressions. 12199f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 12209f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 12219f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * UnionExpr ::= PathExpr 12229f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * | UnionExpr '|' PathExpr 12239f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 12249f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 12259f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @throws javax.xml.transform.TransformerException 12269f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 12279f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson protected void UnionExpr() throws javax.xml.transform.TransformerException 12289f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 12299f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 12309f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int opPos = m_ops.getOp(OpMap.MAPINDEX_LENGTH); 12319f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson boolean continueOrLoop = true; 12329f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson boolean foundUnion = false; 12339f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 12349f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson do 12359f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 12369f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson PathExpr(); 12379f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 12389f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (tokenIs('|')) 12399f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 12409f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (false == foundUnion) 12419f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 12429f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson foundUnion = true; 12439f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 12449f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson insertOp(opPos, 2, OpCodes.OP_UNION); 12459f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 12469f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 12479f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 12489f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 12499f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else 12509f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 12519f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson break; 12529f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 12539f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 12549f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // this.m_testForDocOrder = true; 12559f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 12569f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson while (continueOrLoop); 12579f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 12589f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(opPos + OpMap.MAPINDEX_LENGTH, 12599f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.getOp(OpMap.MAPINDEX_LENGTH) - opPos); 12609f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 12619f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 12629f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 12639f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * PathExpr ::= LocationPath 12649f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * | FilterExpr 12659f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * | FilterExpr '/' RelativeLocationPath 12669f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * | FilterExpr '//' RelativeLocationPath 12679f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 12689f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @throws XSLProcessorException thrown if the active ProblemListener and XPathContext decide 12699f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * the error condition is severe enough to halt processing. 12709f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 12719f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @throws javax.xml.transform.TransformerException 12729f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 12739f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson protected void PathExpr() throws javax.xml.transform.TransformerException 12749f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 12759f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 12769f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int opPos = m_ops.getOp(OpMap.MAPINDEX_LENGTH); 12779f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 12789f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int filterExprMatch = FilterExpr(); 12799f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 12809f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (filterExprMatch != FILTER_MATCH_FAILED) 12819f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 12829f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // If FilterExpr had Predicates, a OP_LOCATIONPATH opcode would already 12839f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // have been inserted. 12849f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson boolean locationPathStarted = (filterExprMatch==FILTER_MATCH_PREDICATES); 12859f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 12869f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (tokenIs('/')) 12879f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 12889f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 12899f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 12909f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (!locationPathStarted) 12919f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 12929f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // int locationPathOpPos = opPos; 12939f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson insertOp(opPos, 2, OpCodes.OP_LOCATIONPATH); 12949f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 12959f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson locationPathStarted = true; 12969f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 12979f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 12989f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (!RelativeLocationPath()) 12999f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 13009f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // "Relative location path expected following '/' or '//'" 13019f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson error(XPATHErrorResources.ER_EXPECTED_REL_LOC_PATH, null); 13029f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 13039f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 13049f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 13059f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 13069f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // Terminate for safety. 13079f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (locationPathStarted) 13089f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 13099f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(m_ops.getOp(OpMap.MAPINDEX_LENGTH), OpCodes.ENDOP); 13109f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(OpMap.MAPINDEX_LENGTH, m_ops.getOp(OpMap.MAPINDEX_LENGTH) + 1); 13119f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(opPos + OpMap.MAPINDEX_LENGTH, 13129f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.getOp(OpMap.MAPINDEX_LENGTH) - opPos); 13139f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 13149f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 13159f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else 13169f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 13179f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson LocationPath(); 13189f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 13199f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 13209f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 13219f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 13229f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 13239f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 13249f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * FilterExpr ::= PrimaryExpr 13259f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * | FilterExpr Predicate 13269f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 13279f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @throws XSLProcessorException thrown if the active ProblemListener and XPathContext decide 13289f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * the error condition is severe enough to halt processing. 13299f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 13309f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @return FILTER_MATCH_PREDICATES, if this method successfully matched a 13319f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * FilterExpr with one or more Predicates; 13329f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * FILTER_MATCH_PRIMARY, if this method successfully matched a 13339f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * FilterExpr that was just a PrimaryExpr; or 13349f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * FILTER_MATCH_FAILED, if this method did not match a FilterExpr 13359f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 13369f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @throws javax.xml.transform.TransformerException 13379f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 13389f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson protected int FilterExpr() throws javax.xml.transform.TransformerException 13399f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 13409f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 13419f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int opPos = m_ops.getOp(OpMap.MAPINDEX_LENGTH); 13429f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 13439f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int filterMatch; 13449f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 13459f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (PrimaryExpr()) 13469f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 13479f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (tokenIs('[')) 13489f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 13499f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 13509f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // int locationPathOpPos = opPos; 13519f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson insertOp(opPos, 2, OpCodes.OP_LOCATIONPATH); 13529f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 13539f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson while (tokenIs('[')) 13549f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 13559f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson Predicate(); 13569f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 13579f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 13589f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson filterMatch = FILTER_MATCH_PREDICATES; 13599f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 13609f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else 13619f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 13629f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson filterMatch = FILTER_MATCH_PRIMARY; 13639f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 13649f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 13659f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else 13669f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 13679f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson filterMatch = FILTER_MATCH_FAILED; 13689f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 13699f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 13709f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson return filterMatch; 13719f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 13729f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /* 13739f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * if(tokenIs('[')) 13749f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * { 13759f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * Predicate(); 13769f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * m_ops.m_opMap[opPos + OpMap.MAPINDEX_LENGTH] = m_ops.m_opMap[OpMap.MAPINDEX_LENGTH] - opPos; 13779f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * } 13789f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 13799f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 13809f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 13819f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 13829f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 13839f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * PrimaryExpr ::= VariableReference 13849f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * | '(' Expr ')' 13859f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * | Literal 13869f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * | Number 13879f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * | FunctionCall 13889f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 13899f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @return true if this method successfully matched a PrimaryExpr 13909f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 13919f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @throws javax.xml.transform.TransformerException 13929f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 13939f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 13949f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson protected boolean PrimaryExpr() throws javax.xml.transform.TransformerException 13959f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 13969f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 13979f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson boolean matchFound; 13989f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int opPos = m_ops.getOp(OpMap.MAPINDEX_LENGTH); 13999f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 14009f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if ((m_tokenChar == '\'') || (m_tokenChar == '"')) 14019f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 14029f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson appendOp(2, OpCodes.OP_LITERAL); 14039f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson Literal(); 14049f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 14059f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(opPos + OpMap.MAPINDEX_LENGTH, 14069f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.getOp(OpMap.MAPINDEX_LENGTH) - opPos); 14079f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 14089f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson matchFound = true; 14099f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 14109f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else if (m_tokenChar == '$') 14119f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 14129f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); // consume '$' 14139f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson appendOp(2, OpCodes.OP_VARIABLE); 14149f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson QName(); 14159f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 14169f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(opPos + OpMap.MAPINDEX_LENGTH, 14179f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.getOp(OpMap.MAPINDEX_LENGTH) - opPos); 14189f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 14199f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson matchFound = true; 14209f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 14219f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else if (m_tokenChar == '(') 14229f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 14239f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 14249f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson appendOp(2, OpCodes.OP_GROUP); 14259f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson Expr(); 14269f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson consumeExpected(')'); 14279f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 14289f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(opPos + OpMap.MAPINDEX_LENGTH, 14299f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.getOp(OpMap.MAPINDEX_LENGTH) - opPos); 14309f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 14319f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson matchFound = true; 14329f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 14339f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else if ((null != m_token) && ((('.' == m_tokenChar) && (m_token.length() > 1) && Character.isDigit( 14349f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_token.charAt(1))) || Character.isDigit(m_tokenChar))) 14359f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 14369f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson appendOp(2, OpCodes.OP_NUMBERLIT); 14379f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson Number(); 14389f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 14399f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(opPos + OpMap.MAPINDEX_LENGTH, 14409f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.getOp(OpMap.MAPINDEX_LENGTH) - opPos); 14419f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 14429f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson matchFound = true; 14439f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 14449f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else if (lookahead('(', 1) || (lookahead(':', 1) && lookahead('(', 3))) 14459f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 14469f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson matchFound = FunctionCall(); 14479f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 14489f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else 14499f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 14509f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson matchFound = false; 14519f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 14529f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 14539f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson return matchFound; 14549f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 14559f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 14569f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 14579f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 14589f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * Argument ::= Expr 14599f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 14609f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 14619f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @throws javax.xml.transform.TransformerException 14629f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 14639f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson protected void Argument() throws javax.xml.transform.TransformerException 14649f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 14659f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 14669f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int opPos = m_ops.getOp(OpMap.MAPINDEX_LENGTH); 14679f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 14689f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson appendOp(2, OpCodes.OP_ARGUMENT); 14699f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson Expr(); 14709f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 14719f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(opPos + OpMap.MAPINDEX_LENGTH, 14729f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.getOp(OpMap.MAPINDEX_LENGTH) - opPos); 14739f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 14749f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 14759f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 14769f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 14779f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * FunctionCall ::= FunctionName '(' ( Argument ( ',' Argument)*)? ')' 14789f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 14799f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @return true if, and only if, a FunctionCall was matched 14809f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 14819f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @throws javax.xml.transform.TransformerException 14829f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 14839f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson protected boolean FunctionCall() throws javax.xml.transform.TransformerException 14849f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 14859f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 14869f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int opPos = m_ops.getOp(OpMap.MAPINDEX_LENGTH); 14879f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 14889f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (lookahead(':', 1)) 14899f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 14909f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson appendOp(4, OpCodes.OP_EXTFUNCTION); 14919f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 14929f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(opPos + OpMap.MAPINDEX_LENGTH + 1, m_queueMark - 1); 14939f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 14949f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 14959f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson consumeExpected(':'); 14969f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 14979f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(opPos + OpMap.MAPINDEX_LENGTH + 2, m_queueMark - 1); 14989f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 14999f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 15009f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 15019f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else 15029f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 15039f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int funcTok = getFunctionToken(m_token); 15049f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 15059f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (-1 == funcTok) 15069f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 15079f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson error(XPATHErrorResources.ER_COULDNOT_FIND_FUNCTION, 15089f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson new Object[]{ m_token }); //"Could not find function: "+m_token+"()"); 15099f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 15109f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 15119f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson switch (funcTok) 15129f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 15139f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson case OpCodes.NODETYPE_PI : 15149f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson case OpCodes.NODETYPE_COMMENT : 15159f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson case OpCodes.NODETYPE_TEXT : 15169f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson case OpCodes.NODETYPE_NODE : 15179f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // Node type tests look like function calls, but they're not 15189f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson return false; 15199f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson default : 15209f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson appendOp(3, OpCodes.OP_FUNCTION); 15219f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 15229f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(opPos + OpMap.MAPINDEX_LENGTH + 1, funcTok); 15239f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 15249f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 15259f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 15269f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 15279f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 15289f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson consumeExpected('('); 15299f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 15309f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson while (!tokenIs(')') && m_token != null) 15319f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 15329f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (tokenIs(',')) 15339f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 15349f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson error(XPATHErrorResources.ER_FOUND_COMMA_BUT_NO_PRECEDING_ARG, null); //"Found ',' but no preceding argument!"); 15359f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 15369f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 15379f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson Argument(); 15389f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 15399f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (!tokenIs(')')) 15409f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 15419f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson consumeExpected(','); 15429f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 15439f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (tokenIs(')')) 15449f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 15459f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson error(XPATHErrorResources.ER_FOUND_COMMA_BUT_NO_FOLLOWING_ARG, 15469f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson null); //"Found ',' but no following argument!"); 15479f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 15489f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 15499f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 15509f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 15519f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson consumeExpected(')'); 15529f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 15539f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // Terminate for safety. 15549f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(m_ops.getOp(OpMap.MAPINDEX_LENGTH), OpCodes.ENDOP); 15559f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(OpMap.MAPINDEX_LENGTH,m_ops.getOp(OpMap.MAPINDEX_LENGTH) + 1); 15569f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(opPos + OpMap.MAPINDEX_LENGTH, 15579f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.getOp(OpMap.MAPINDEX_LENGTH) - opPos); 15589f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 15599f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson return true; 15609f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 15619f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 15629f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // ============= GRAMMAR FUNCTIONS ================= 15639f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 15649f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 15659f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 15669f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * LocationPath ::= RelativeLocationPath 15679f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * | AbsoluteLocationPath 15689f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 15699f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 15709f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @throws javax.xml.transform.TransformerException 15719f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 15729f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson protected void LocationPath() throws javax.xml.transform.TransformerException 15739f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 15749f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 15759f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int opPos = m_ops.getOp(OpMap.MAPINDEX_LENGTH); 15769f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 15779f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // int locationPathOpPos = opPos; 15789f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson appendOp(2, OpCodes.OP_LOCATIONPATH); 15799f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 15809f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson boolean seenSlash = tokenIs('/'); 15819f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 15829f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (seenSlash) 15839f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 15849f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson appendOp(4, OpCodes.FROM_ROOT); 15859f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 15869f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // Tell how long the step is without the predicate 15879f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(m_ops.getOp(OpMap.MAPINDEX_LENGTH) - 2, 4); 15889f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(m_ops.getOp(OpMap.MAPINDEX_LENGTH) - 1, OpCodes.NODETYPE_ROOT); 15899f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 15909f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 15919f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } else if (m_token == null) { 15929f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson error(XPATHErrorResources.ER_EXPECTED_LOC_PATH_AT_END_EXPR, null); 15939f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 15949f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 15959f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (m_token != null) 15969f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 15979f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (!RelativeLocationPath() && !seenSlash) 15989f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 15999f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // Neither a '/' nor a RelativeLocationPath - i.e., matched nothing 16009f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // "Location path expected, but found "+m_token+" was encountered." 16019f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson error(XPATHErrorResources.ER_EXPECTED_LOC_PATH, 16029f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson new Object [] {m_token}); 16039f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 16049f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 16059f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 16069f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // Terminate for safety. 16079f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(m_ops.getOp(OpMap.MAPINDEX_LENGTH), OpCodes.ENDOP); 16089f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(OpMap.MAPINDEX_LENGTH,m_ops.getOp(OpMap.MAPINDEX_LENGTH) + 1); 16099f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(opPos + OpMap.MAPINDEX_LENGTH, 16109f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.getOp(OpMap.MAPINDEX_LENGTH) - opPos); 16119f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 16129f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 16139f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 16149f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 16159f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * RelativeLocationPath ::= Step 16169f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * | RelativeLocationPath '/' Step 16179f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * | AbbreviatedRelativeLocationPath 16189f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 16199f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @returns true if, and only if, a RelativeLocationPath was matched 16209f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 16219f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @throws javax.xml.transform.TransformerException 16229f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 16239f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson protected boolean RelativeLocationPath() 16249f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson throws javax.xml.transform.TransformerException 16259f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 16269f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (!Step()) 16279f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 16289f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson return false; 16299f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 16309f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 16319f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson while (tokenIs('/')) 16329f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 16339f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 16349f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 16359f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (!Step()) 16369f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 16379f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // RelativeLocationPath can't end with a trailing '/' 16389f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // "Location step expected following '/' or '//'" 16399f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson error(XPATHErrorResources.ER_EXPECTED_LOC_STEP, null); 16409f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 16419f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 16429f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 16439f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson return true; 16449f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 16459f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 16469f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 16479f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 16489f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * Step ::= Basis Predicate 16499f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * | AbbreviatedStep 16509f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 16519f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @returns false if step was empty (or only a '/'); true, otherwise 16529f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 16539f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @throws javax.xml.transform.TransformerException 16549f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 16559f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson protected boolean Step() throws javax.xml.transform.TransformerException 16569f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 16579f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int opPos = m_ops.getOp(OpMap.MAPINDEX_LENGTH); 16589f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 16599f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson boolean doubleSlash = tokenIs('/'); 16609f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 16619f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // At most a single '/' before each Step is consumed by caller; if the 16629f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // first thing is a '/', that means we had '//' and the Step must not 16639f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // be empty. 16649f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (doubleSlash) 16659f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 16669f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 16679f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 16689f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson appendOp(2, OpCodes.FROM_DESCENDANTS_OR_SELF); 16699f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 16709f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // Have to fix up for patterns such as '//@foo' or '//attribute::foo', 16719f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // which translate to 'descendant-or-self::node()/attribute::foo'. 16729f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // notice I leave the '/' on the queue, so the next will be processed 16739f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // by a regular step pattern. 16749f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 16759f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // Make room for telling how long the step is without the predicate 16769f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(OpMap.MAPINDEX_LENGTH,m_ops.getOp(OpMap.MAPINDEX_LENGTH) + 1); 16779f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(m_ops.getOp(OpMap.MAPINDEX_LENGTH), OpCodes.NODETYPE_NODE); 16789f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(OpMap.MAPINDEX_LENGTH,m_ops.getOp(OpMap.MAPINDEX_LENGTH) + 1); 16799f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 16809f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // Tell how long the step is without the predicate 16819f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(opPos + OpMap.MAPINDEX_LENGTH + 1, 16829f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.getOp(OpMap.MAPINDEX_LENGTH) - opPos); 16839f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 16849f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // Tell how long the step is with the predicate 16859f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(opPos + OpMap.MAPINDEX_LENGTH, 16869f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.getOp(OpMap.MAPINDEX_LENGTH) - opPos); 16879f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 16889f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson opPos = m_ops.getOp(OpMap.MAPINDEX_LENGTH); 16899f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 16909f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 16919f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (tokenIs(".")) 16929f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 16939f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 16949f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 16959f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (tokenIs('[')) 16969f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 16979f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson error(XPATHErrorResources.ER_PREDICATE_ILLEGAL_SYNTAX, null); //"'..[predicate]' or '.[predicate]' is illegal syntax. Use 'self::node()[predicate]' instead."); 16989f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 16999f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 17009f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson appendOp(4, OpCodes.FROM_SELF); 17019f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 17029f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // Tell how long the step is without the predicate 17039f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(m_ops.getOp(OpMap.MAPINDEX_LENGTH) - 2,4); 17049f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(m_ops.getOp(OpMap.MAPINDEX_LENGTH) - 1, OpCodes.NODETYPE_NODE); 17059f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 17069f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else if (tokenIs("..")) 17079f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 17089f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 17099f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson appendOp(4, OpCodes.FROM_PARENT); 17109f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 17119f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // Tell how long the step is without the predicate 17129f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(m_ops.getOp(OpMap.MAPINDEX_LENGTH) - 2,4); 17139f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(m_ops.getOp(OpMap.MAPINDEX_LENGTH) - 1, OpCodes.NODETYPE_NODE); 17149f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 17159f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 17169f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // There is probably a better way to test for this 17179f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // transition... but it gets real hairy if you try 17189f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // to do it in basis(). 17199f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else if (tokenIs('*') || tokenIs('@') || tokenIs('_') 17209f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson || (m_token!= null && Character.isLetter(m_token.charAt(0)))) 17219f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 17229f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson Basis(); 17239f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 17249f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson while (tokenIs('[')) 17259f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 17269f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson Predicate(); 17279f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 17289f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 17299f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // Tell how long the entire step is. 17309f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(opPos + OpMap.MAPINDEX_LENGTH, 17319f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.getOp(OpMap.MAPINDEX_LENGTH) - opPos); 17329f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 17339f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else 17349f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 17359f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // No Step matched - that's an error if previous thing was a '//' 17369f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (doubleSlash) 17379f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 17389f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // "Location step expected following '/' or '//'" 17399f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson error(XPATHErrorResources.ER_EXPECTED_LOC_STEP, null); 17409f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 17419f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 17429f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson return false; 17439f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 17449f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 17459f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson return true; 17469f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 17479f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 17489f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 17499f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 17509f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * Basis ::= AxisName '::' NodeTest 17519f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * | AbbreviatedBasis 17529f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 17539f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @throws javax.xml.transform.TransformerException 17549f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 17559f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson protected void Basis() throws javax.xml.transform.TransformerException 17569f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 17579f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 17589f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int opPos = m_ops.getOp(OpMap.MAPINDEX_LENGTH); 17599f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int axesType; 17609f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 17619f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // The next blocks guarantee that a FROM_XXX will be added. 17629f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (lookahead("::", 1)) 17639f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 17649f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson axesType = AxisName(); 17659f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 17669f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 17679f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 17689f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 17699f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else if (tokenIs('@')) 17709f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 17719f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson axesType = OpCodes.FROM_ATTRIBUTES; 17729f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 17739f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson appendOp(2, axesType); 17749f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 17759f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 17769f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else 17779f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 17789f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson axesType = OpCodes.FROM_CHILDREN; 17799f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 17809f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson appendOp(2, axesType); 17819f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 17829f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 17839f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // Make room for telling how long the step is without the predicate 17849f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(OpMap.MAPINDEX_LENGTH, m_ops.getOp(OpMap.MAPINDEX_LENGTH) + 1); 17859f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 17869f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson NodeTest(axesType); 17879f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 17889f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // Tell how long the step is without the predicate 17899f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(opPos + OpMap.MAPINDEX_LENGTH + 1, 17909f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.getOp(OpMap.MAPINDEX_LENGTH) - opPos); 17919f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 17929f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 17939f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 17949f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 17959f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * Basis ::= AxisName '::' NodeTest 17969f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * | AbbreviatedBasis 17979f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 17989f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @return FROM_XXX axes type, found in {@link org.apache.xpath.compiler.Keywords}. 17999f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 18009f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @throws javax.xml.transform.TransformerException 18019f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 18029f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson protected int AxisName() throws javax.xml.transform.TransformerException 18039f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 18049f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 18059f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson Object val = Keywords.getAxisName(m_token); 18069f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 18079f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (null == val) 18089f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 18099f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson error(XPATHErrorResources.ER_ILLEGAL_AXIS_NAME, 18109f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson new Object[]{ m_token }); //"illegal axis name: "+m_token); 18119f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 18129f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 18139f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int axesType = ((Integer) val).intValue(); 18149f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 18159f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson appendOp(2, axesType); 18169f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 18179f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson return axesType; 18189f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 18199f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 18209f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 18219f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 18229f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * NodeTest ::= WildcardName 18239f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * | NodeType '(' ')' 18249f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * | 'processing-instruction' '(' Literal ')' 18259f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 18269f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @param axesType FROM_XXX axes type, found in {@link org.apache.xpath.compiler.Keywords}. 18279f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 18289f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @throws javax.xml.transform.TransformerException 18299f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 18309f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson protected void NodeTest(int axesType) throws javax.xml.transform.TransformerException 18319f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 18329f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 18339f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (lookahead('(', 1)) 18349f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 18359f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson Object nodeTestOp = Keywords.getNodeType(m_token); 18369f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 18379f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (null == nodeTestOp) 18389f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 18399f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson error(XPATHErrorResources.ER_UNKNOWN_NODETYPE, 18409f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson new Object[]{ m_token }); //"Unknown nodetype: "+m_token); 18419f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 18429f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else 18439f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 18449f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 18459f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 18469f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int nt = ((Integer) nodeTestOp).intValue(); 18479f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 18489f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(m_ops.getOp(OpMap.MAPINDEX_LENGTH), nt); 18499f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(OpMap.MAPINDEX_LENGTH, m_ops.getOp(OpMap.MAPINDEX_LENGTH) + 1); 18509f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 18519f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson consumeExpected('('); 18529f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 18539f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (OpCodes.NODETYPE_PI == nt) 18549f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 18559f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (!tokenIs(')')) 18569f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 18579f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson Literal(); 18589f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 18599f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 18609f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 18619f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson consumeExpected(')'); 18629f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 18639f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 18649f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else 18659f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 18669f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 18679f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // Assume name of attribute or element. 18689f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(m_ops.getOp(OpMap.MAPINDEX_LENGTH), OpCodes.NODENAME); 18699f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(OpMap.MAPINDEX_LENGTH, m_ops.getOp(OpMap.MAPINDEX_LENGTH) + 1); 18709f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 18719f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (lookahead(':', 1)) 18729f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 18739f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (tokenIs('*')) 18749f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 18759f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(m_ops.getOp(OpMap.MAPINDEX_LENGTH), OpCodes.ELEMWILDCARD); 18769f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 18779f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else 18789f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 18799f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(m_ops.getOp(OpMap.MAPINDEX_LENGTH), m_queueMark - 1); 18809f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 18819f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // Minimalist check for an NCName - just check first character 18829f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // to distinguish from other possible tokens 18839f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (!Character.isLetter(m_tokenChar) && !tokenIs('_')) 18849f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 18859f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // "Node test that matches either NCName:* or QName was expected." 18869f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson error(XPATHErrorResources.ER_EXPECTED_NODE_TEST, null); 18879f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 18889f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 18899f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 18909f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 18919f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson consumeExpected(':'); 18929f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 18939f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else 18949f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 18959f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(m_ops.getOp(OpMap.MAPINDEX_LENGTH), OpCodes.EMPTY); 18969f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 18979f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 18989f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(OpMap.MAPINDEX_LENGTH, m_ops.getOp(OpMap.MAPINDEX_LENGTH) + 1); 18999f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 19009f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (tokenIs('*')) 19019f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 19029f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(m_ops.getOp(OpMap.MAPINDEX_LENGTH), OpCodes.ELEMWILDCARD); 19039f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 19049f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else 19059f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 19069f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(m_ops.getOp(OpMap.MAPINDEX_LENGTH), m_queueMark - 1); 19079f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 19089f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // Minimalist check for an NCName - just check first character 19099f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // to distinguish from other possible tokens 19109f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (!Character.isLetter(m_tokenChar) && !tokenIs('_')) 19119f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 19129f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // "Node test that matches either NCName:* or QName was expected." 19139f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson error(XPATHErrorResources.ER_EXPECTED_NODE_TEST, null); 19149f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 19159f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 19169f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 19179f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(OpMap.MAPINDEX_LENGTH, m_ops.getOp(OpMap.MAPINDEX_LENGTH) + 1); 19189f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 19199f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 19209f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 19219f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 19229f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 19239f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 19249f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 19259f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * Predicate ::= '[' PredicateExpr ']' 19269f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 19279f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 19289f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @throws javax.xml.transform.TransformerException 19299f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 19309f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson protected void Predicate() throws javax.xml.transform.TransformerException 19319f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 19329f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 19339f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (tokenIs('[')) 19349f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 19359f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 19369f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson PredicateExpr(); 19379f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson consumeExpected(']'); 19389f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 19399f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 19409f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 19419f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 19429f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 19439f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * PredicateExpr ::= Expr 19449f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 19459f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 19469f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @throws javax.xml.transform.TransformerException 19479f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 19489f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson protected void PredicateExpr() throws javax.xml.transform.TransformerException 19499f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 19509f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 19519f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int opPos = m_ops.getOp(OpMap.MAPINDEX_LENGTH); 19529f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 19539f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson appendOp(2, OpCodes.OP_PREDICATE); 19549f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson Expr(); 19559f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 19569f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // Terminate for safety. 19579f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(m_ops.getOp(OpMap.MAPINDEX_LENGTH), OpCodes.ENDOP); 19589f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(OpMap.MAPINDEX_LENGTH, m_ops.getOp(OpMap.MAPINDEX_LENGTH) + 1); 19599f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(opPos + OpMap.MAPINDEX_LENGTH, 19609f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.getOp(OpMap.MAPINDEX_LENGTH) - opPos); 19619f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 19629f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 19639f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 19649f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * QName ::= (Prefix ':')? LocalPart 19659f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * Prefix ::= NCName 19669f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * LocalPart ::= NCName 19679f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 19689f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @throws javax.xml.transform.TransformerException 19699f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 19709f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson protected void QName() throws javax.xml.transform.TransformerException 19719f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 19729f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // Namespace 19739f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if(lookahead(':', 1)) 19749f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 19759f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(m_ops.getOp(OpMap.MAPINDEX_LENGTH), m_queueMark - 1); 19769f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(OpMap.MAPINDEX_LENGTH, m_ops.getOp(OpMap.MAPINDEX_LENGTH) + 1); 19779f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 19789f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 19799f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson consumeExpected(':'); 19809f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 19819f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else 19829f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 19839f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(m_ops.getOp(OpMap.MAPINDEX_LENGTH), OpCodes.EMPTY); 19849f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(OpMap.MAPINDEX_LENGTH, m_ops.getOp(OpMap.MAPINDEX_LENGTH) + 1); 19859f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 19869f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 19879f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // Local name 19889f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(m_ops.getOp(OpMap.MAPINDEX_LENGTH), m_queueMark - 1); 19899f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(OpMap.MAPINDEX_LENGTH, m_ops.getOp(OpMap.MAPINDEX_LENGTH) + 1); 19909f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 19919f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 19929f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 19939f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 19949f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 19959f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * NCName ::= (Letter | '_') (NCNameChar) 19969f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * NCNameChar ::= Letter | Digit | '.' | '-' | '_' | CombiningChar | Extender 19979f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 19989f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson protected void NCName() 19999f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 20009f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 20019f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(m_ops.getOp(OpMap.MAPINDEX_LENGTH), m_queueMark - 1); 20029f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(OpMap.MAPINDEX_LENGTH, m_ops.getOp(OpMap.MAPINDEX_LENGTH) + 1); 20039f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 20049f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 20059f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 20069f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 20079f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 20089f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * The value of the Literal is the sequence of characters inside 20099f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * the " or ' characters>. 20109f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 20119f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * Literal ::= '"' [^"]* '"' 20129f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * | "'" [^']* "'" 20139f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 20149f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 20159f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @throws javax.xml.transform.TransformerException 20169f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 20179f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson protected void Literal() throws javax.xml.transform.TransformerException 20189f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 20199f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 20209f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int last = m_token.length() - 1; 20219f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson char c0 = m_tokenChar; 20229f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson char cX = m_token.charAt(last); 20239f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 20249f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (((c0 == '\"') && (cX == '\"')) || ((c0 == '\'') && (cX == '\''))) 20259f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 20269f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 20279f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // Mutate the token to remove the quotes and have the XString object 20289f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // already made. 20299f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int tokenQueuePos = m_queueMark - 1; 20309f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 20319f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.m_tokenQueue.setElementAt(null,tokenQueuePos); 20329f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 20339f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson Object obj = new XString(m_token.substring(1, last)); 20349f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 20359f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.m_tokenQueue.setElementAt(obj,tokenQueuePos); 20369f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 20379f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // lit = m_token.substring(1, last); 20389f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(m_ops.getOp(OpMap.MAPINDEX_LENGTH), tokenQueuePos); 20399f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(OpMap.MAPINDEX_LENGTH, m_ops.getOp(OpMap.MAPINDEX_LENGTH) + 1); 20409f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 20419f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 20429f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 20439f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else 20449f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 20459f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson error(XPATHErrorResources.ER_PATTERN_LITERAL_NEEDS_BE_QUOTED, 20469f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson new Object[]{ m_token }); //"Pattern literal ("+m_token+") needs to be quoted!"); 20479f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 20489f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 20499f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 20509f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 20519f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 20529f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * Number ::= [0-9]+('.'[0-9]+)? | '.'[0-9]+ 20539f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 20549f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 20559f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @throws javax.xml.transform.TransformerException 20569f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 20579f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson protected void Number() throws javax.xml.transform.TransformerException 20589f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 20599f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 20609f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (null != m_token) 20619f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 20629f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 20639f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // Mutate the token to remove the quotes and have the XNumber object 20649f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // already made. 20659f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson double num; 20669f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 20679f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson try 20689f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 20699f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // XPath 1.0 does not support number in exp notation 20709f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if ((m_token.indexOf('e') > -1)||(m_token.indexOf('E') > -1)) 20719f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson throw new NumberFormatException(); 20729f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson num = Double.valueOf(m_token).doubleValue(); 20739f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 20749f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson catch (NumberFormatException nfe) 20759f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 20769f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson num = 0.0; // to shut up compiler. 20779f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 20789f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson error(XPATHErrorResources.ER_COULDNOT_BE_FORMATTED_TO_NUMBER, 20799f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson new Object[]{ m_token }); //m_token+" could not be formatted to a number!"); 20809f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 20819f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 20829f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.m_tokenQueue.setElementAt(new XNumber(num),m_queueMark - 1); 20839f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(m_ops.getOp(OpMap.MAPINDEX_LENGTH), m_queueMark - 1); 20849f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(OpMap.MAPINDEX_LENGTH, m_ops.getOp(OpMap.MAPINDEX_LENGTH) + 1); 20859f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 20869f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 20879f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 20889f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 20899f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 20909f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // ============= PATTERN FUNCTIONS ================= 20919f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 20929f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 20939f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 20949f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * Pattern ::= LocationPathPattern 20959f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * | Pattern '|' LocationPathPattern 20969f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 20979f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 20989f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @throws javax.xml.transform.TransformerException 20999f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 21009f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson protected void Pattern() throws javax.xml.transform.TransformerException 21019f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 21029f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 21039f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson while (true) 21049f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 21059f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson LocationPathPattern(); 21069f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 21079f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (tokenIs('|')) 21089f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 21099f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 21109f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 21119f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else 21129f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 21139f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson break; 21149f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 21159f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 21169f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 21179f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 21189f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 21199f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 21209f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 21219f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * LocationPathPattern ::= '/' RelativePathPattern? 21229f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * | IdKeyPattern (('/' | '//') RelativePathPattern)? 21239f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * | '//'? RelativePathPattern 21249f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 21259f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 21269f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @throws javax.xml.transform.TransformerException 21279f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 21289f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson protected void LocationPathPattern() throws javax.xml.transform.TransformerException 21299f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 21309f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 21319f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int opPos = m_ops.getOp(OpMap.MAPINDEX_LENGTH); 21329f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 21339f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson final int RELATIVE_PATH_NOT_PERMITTED = 0; 21349f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson final int RELATIVE_PATH_PERMITTED = 1; 21359f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson final int RELATIVE_PATH_REQUIRED = 2; 21369f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 21379f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int relativePathStatus = RELATIVE_PATH_NOT_PERMITTED; 21389f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 21399f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson appendOp(2, OpCodes.OP_LOCATIONPATHPATTERN); 21409f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 21419f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (lookahead('(', 1) 21429f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson && (tokenIs(Keywords.FUNC_ID_STRING) 21439f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson || tokenIs(Keywords.FUNC_KEY_STRING))) 21449f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 21459f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson IdKeyPattern(); 21469f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 21479f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (tokenIs('/')) 21489f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 21499f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 21509f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 21519f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (tokenIs('/')) 21529f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 21539f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson appendOp(4, OpCodes.MATCH_ANY_ANCESTOR); 21549f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 21559f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 21569f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 21579f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else 21589f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 21599f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson appendOp(4, OpCodes.MATCH_IMMEDIATE_ANCESTOR); 21609f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 21619f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 21629f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // Tell how long the step is without the predicate 21639f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(m_ops.getOp(OpMap.MAPINDEX_LENGTH) - 2, 4); 21649f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(m_ops.getOp(OpMap.MAPINDEX_LENGTH) - 1, OpCodes.NODETYPE_FUNCTEST); 21659f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 21669f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson relativePathStatus = RELATIVE_PATH_REQUIRED; 21679f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 21689f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 21699f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else if (tokenIs('/')) 21709f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 21719f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (lookahead('/', 1)) 21729f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 21739f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson appendOp(4, OpCodes.MATCH_ANY_ANCESTOR); 21749f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 21759f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // Added this to fix bug reported by Myriam for match="//x/a" 21769f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // patterns. If you don't do this, the 'x' step will think it's part 21779f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // of a '//' pattern, and so will cause 'a' to be matched when it has 21789f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // any ancestor that is 'x'. 21799f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 21809f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 21819f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson relativePathStatus = RELATIVE_PATH_REQUIRED; 21829f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 21839f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else 21849f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 21859f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson appendOp(4, OpCodes.FROM_ROOT); 21869f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 21879f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson relativePathStatus = RELATIVE_PATH_PERMITTED; 21889f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 21899f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 21909f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 21919f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // Tell how long the step is without the predicate 21929f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(m_ops.getOp(OpMap.MAPINDEX_LENGTH) - 2, 4); 21939f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(m_ops.getOp(OpMap.MAPINDEX_LENGTH) - 1, OpCodes.NODETYPE_ROOT); 21949f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 21959f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 21969f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 21979f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else 21989f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 21999f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson relativePathStatus = RELATIVE_PATH_REQUIRED; 22009f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 22019f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 22029f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (relativePathStatus != RELATIVE_PATH_NOT_PERMITTED) 22039f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 22049f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (!tokenIs('|') && (null != m_token)) 22059f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 22069f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson RelativePathPattern(); 22079f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 22089f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else if (relativePathStatus == RELATIVE_PATH_REQUIRED) 22099f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 22109f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // "A relative path pattern was expected." 22119f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson error(XPATHErrorResources.ER_EXPECTED_REL_PATH_PATTERN, null); 22129f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 22139f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 22149f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 22159f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // Terminate for safety. 22169f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(m_ops.getOp(OpMap.MAPINDEX_LENGTH), OpCodes.ENDOP); 22179f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(OpMap.MAPINDEX_LENGTH, m_ops.getOp(OpMap.MAPINDEX_LENGTH) + 1); 22189f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(opPos + OpMap.MAPINDEX_LENGTH, 22199f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.getOp(OpMap.MAPINDEX_LENGTH) - opPos); 22209f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 22219f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 22229f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 22239f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 22249f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * IdKeyPattern ::= 'id' '(' Literal ')' 22259f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * | 'key' '(' Literal ',' Literal ')' 22269f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * (Also handle doc()) 22279f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 22289f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 22299f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @throws javax.xml.transform.TransformerException 22309f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 22319f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson protected void IdKeyPattern() throws javax.xml.transform.TransformerException 22329f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 22339f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson FunctionCall(); 22349f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 22359f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 22369f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 22379f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 22389f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * RelativePathPattern ::= StepPattern 22399f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * | RelativePathPattern '/' StepPattern 22409f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * | RelativePathPattern '//' StepPattern 22419f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 22429f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @throws javax.xml.transform.TransformerException 22439f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 22449f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson protected void RelativePathPattern() 22459f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson throws javax.xml.transform.TransformerException 22469f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 22479f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 22489f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // Caller will have consumed any '/' or '//' preceding the 22499f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // RelativePathPattern, so let StepPattern know it can't begin with a '/' 22509f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson boolean trailingSlashConsumed = StepPattern(false); 22519f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 22529f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson while (tokenIs('/')) 22539f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 22549f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 22559f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 22569f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // StepPattern() may consume first slash of pair in "a//b" while 22579f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // processing StepPattern "a". On next iteration, let StepPattern know 22589f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // that happened, so it doesn't match ill-formed patterns like "a///b". 22599f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson trailingSlashConsumed = StepPattern(!trailingSlashConsumed); 22609f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 22619f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 22629f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 22639f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 22649f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 22659f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * StepPattern ::= AbbreviatedNodeTestStep 22669f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 22679f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @param isLeadingSlashPermitted a boolean indicating whether a slash can 22689f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * appear at the start of this step 22699f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 22709f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @return boolean indicating whether a slash following the step was consumed 22719f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 22729f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @throws javax.xml.transform.TransformerException 22739f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 22749f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson protected boolean StepPattern(boolean isLeadingSlashPermitted) 22759f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson throws javax.xml.transform.TransformerException 22769f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 22779f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson return AbbreviatedNodeTestStep(isLeadingSlashPermitted); 22789f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 22799f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 22809f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson /** 22819f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 22829f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * AbbreviatedNodeTestStep ::= '@'? NodeTest Predicate 22839f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 22849f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @param isLeadingSlashPermitted a boolean indicating whether a slash can 22859f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * appear at the start of this step 22869f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 22879f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @return boolean indicating whether a slash following the step was consumed 22889f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * 22899f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson * @throws javax.xml.transform.TransformerException 22909f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson */ 22919f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson protected boolean AbbreviatedNodeTestStep(boolean isLeadingSlashPermitted) 22929f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson throws javax.xml.transform.TransformerException 22939f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 22949f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 22959f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int opPos = m_ops.getOp(OpMap.MAPINDEX_LENGTH); 22969f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int axesType; 22979f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 22989f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // The next blocks guarantee that a MATCH_XXX will be added. 22999f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson int matchTypePos = -1; 23009f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 23019f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (tokenIs('@')) 23029f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 23039f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson axesType = OpCodes.MATCH_ATTRIBUTE; 23049f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 23059f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson appendOp(2, axesType); 23069f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 23079f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 23089f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else if (this.lookahead("::", 1)) 23099f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 23109f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (tokenIs("attribute")) 23119f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 23129f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson axesType = OpCodes.MATCH_ATTRIBUTE; 23139f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 23149f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson appendOp(2, axesType); 23159f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 23169f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else if (tokenIs("child")) 23179f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 23189f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson matchTypePos = m_ops.getOp(OpMap.MAPINDEX_LENGTH); 23199f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson axesType = OpCodes.MATCH_IMMEDIATE_ANCESTOR; 23209f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 23219f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson appendOp(2, axesType); 23229f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 23239f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else 23249f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 23259f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson axesType = -1; 23269f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 23279f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson this.error(XPATHErrorResources.ER_AXES_NOT_ALLOWED, 23289f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson new Object[]{ this.m_token }); 23299f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 23309f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 23319f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 23329f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 23339f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 23349f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else if (tokenIs('/')) 23359f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 23369f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if (!isLeadingSlashPermitted) 23379f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 23389f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // "A step was expected in the pattern, but '/' was encountered." 23399f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson error(XPATHErrorResources.ER_EXPECTED_STEP_PATTERN, null); 23409f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 23419f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson axesType = OpCodes.MATCH_ANY_ANCESTOR; 23429f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 23439f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson appendOp(2, axesType); 23449f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 23459f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 23469f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else 23479f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 23489f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson matchTypePos = m_ops.getOp(OpMap.MAPINDEX_LENGTH); 23499f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson axesType = OpCodes.MATCH_IMMEDIATE_ANCESTOR; 23509f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 23519f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson appendOp(2, axesType); 23529f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 23539f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 23549f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // Make room for telling how long the step is without the predicate 23559f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(OpMap.MAPINDEX_LENGTH, m_ops.getOp(OpMap.MAPINDEX_LENGTH) + 1); 23569f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 23579f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson NodeTest(axesType); 23589f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 23599f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // Tell how long the step is without the predicate 23609f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(opPos + OpMap.MAPINDEX_LENGTH + 1, 23619f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.getOp(OpMap.MAPINDEX_LENGTH) - opPos); 23629f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 23639f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson while (tokenIs('[')) 23649f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 23659f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson Predicate(); 23669f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 23679f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 23689f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson boolean trailingSlashConsumed; 23699f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 23709f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // For "a//b", where "a" is current step, we need to mark operation of 23719f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // current step as "MATCH_ANY_ANCESTOR". Then we'll consume the first 23729f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // slash and subsequent step will be treated as a MATCH_IMMEDIATE_ANCESTOR 23739f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // (unless it too is followed by '//'.) 23749f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // 23759f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // %REVIEW% Following is what happens today, but I'm not sure that's 23769f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // %REVIEW% correct behaviour. Perhaps no valid case could be constructed 23779f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // %REVIEW% where it would matter? 23789f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // 23799f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // If current step is on the attribute axis (e.g., "@x//b"), we won't 23809f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // change the current step, and let following step be marked as 23819f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // MATCH_ANY_ANCESTOR on next call instead. 23829f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson if ((matchTypePos > -1) && tokenIs('/') && lookahead('/', 1)) 23839f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 23849f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(matchTypePos, OpCodes.MATCH_ANY_ANCESTOR); 23859f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 23869f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson nextToken(); 23879f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 23889f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson trailingSlashConsumed = true; 23899f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 23909f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson else 23919f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson { 23929f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson trailingSlashConsumed = false; 23939f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 23949f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 23959f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson // Tell how long the entire step is. 23969f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.setOp(opPos + OpMap.MAPINDEX_LENGTH, 23979f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson m_ops.getOp(OpMap.MAPINDEX_LENGTH) - opPos); 23989f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson 23999f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson return trailingSlashConsumed; 24009f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson } 24019f8118474e9513f7a5b7d2a05e4a0fb15d1a6569Jesse Wilson} 2402