protected string AppendStep(string basePath, XPathAxis stepAxis, string stepNodeTest, string predicate) { return String.Concat( EnsureTrailingSlash(basePath), GetAxisString(stepAxis), stepNodeTest, EnsureBracketedPredicate(predicate)); }
public object Axis(XPathAxis xpathAxis, System.Xml.XPath.XPathNodeType nodeType, string prefix, string name) { if (xpathAxis == XPathAxis.Root) { return(Root); } if (nodeType == System.Xml.XPath.XPathNodeType.Element) { if (name != "ui") { throw new NotSupportedException($"{name} element is not supported."); } } if (xpathAxis == XPathAxis.Descendant) { FindElementFunc func = FindDescendant; return(func); } if (xpathAxis == XPathAxis.DescendantOrSelf) { FindElementFunc func = FindDescendantOrSelf; return(func); } if (xpathAxis == XPathAxis.FollowingSibling) { FindElementFunc func = FindFollowingSibling; return(func); } if (xpathAxis == XPathAxis.Child) { FindElementFunc func = FindChild; return(func); } if (xpathAxis == XPathAxis.Attribute) { string lowerCaseName = name.ToLower(); if (lowerCaseName == "id") { return(AutomationElement.AutomationIdProperty); } if (lowerCaseName == "name") { return(AutomationElement.NameProperty); } if (lowerCaseName == "class") { return(AutomationElement.ClassNameProperty); } if (lowerCaseName == "type") { return(UiAutomationElement.ProgrammaticName); } if (lowerCaseName == "typeid") { return(UiAutomationElement.Id); } throw new NotSupportedException($"Attribute {name} is not supportet."); } return(null); }
private static bool IsReverseAxis(XPathAxis axis) { return( axis == XPathAxis.Ancestor || axis == XPathAxis.Preceding || axis == XPathAxis.AncestorOrSelf || axis == XPathAxis.PrecedingSibling ); }
public AxisElement(XPathAxis xpathAxis, System.Xml.XPath.XPathNodeType nodeType, string prefix, string name) { _xpathAxis = xpathAxis; _nodeType = nodeType; _prefix = prefix; _name = name; }
private static XPathNodeType PrincipalNodeType(XPathAxis axis) { return( axis == XPathAxis.Attribute ? XPathNodeType.Attribute : axis == XPathAxis.Namespace ? XPathNodeType.Namespace : /*else*/ XPathNodeType.Element ); }
protected string AppendStep(string basePath, XPathAxis stepAxis, string stepNodeTest, string predicate) { return(String.Concat( EnsureTrailingSlash(basePath), GetAxisString(stepAxis), stepNodeTest, EnsureBracketedPredicate(predicate))); }
public XElement Axis(XPathAxis xpathAxis, System.Xml.XPath.XPathNodeType nodeType, string prefix, string name) { return(new XElement(xpathAxis.ToString(), new XAttribute("nodeType", nodeType.ToString()), new XAttribute("prefix", prefix ?? "(null)"), new XAttribute("name", name ?? "(null)") )); }
private QilNode BuildAxis(XPathAxis xpathAxis, XPathNodeType nodeType, string nsUri, string name) { QilNode currentNode = GetCurrentNode(); QilNode qilAxis; switch (xpathAxis) { case XPathAxis.Ancestor: qilAxis = _f.Ancestor(currentNode); break; case XPathAxis.AncestorOrSelf: qilAxis = _f.AncestorOrSelf(currentNode); break; case XPathAxis.Attribute: qilAxis = _f.Content(currentNode); break; case XPathAxis.Child: qilAxis = _f.Content(currentNode); break; case XPathAxis.Descendant: qilAxis = _f.Descendant(currentNode); break; case XPathAxis.DescendantOrSelf: qilAxis = _f.DescendantOrSelf(currentNode); break; case XPathAxis.Following: qilAxis = _f.XPathFollowing(currentNode); break; case XPathAxis.FollowingSibling: qilAxis = _f.FollowingSibling(currentNode); break; case XPathAxis.Namespace: qilAxis = _f.XPathNamespace(currentNode); break; case XPathAxis.Parent: qilAxis = _f.Parent(currentNode); break; case XPathAxis.Preceding: qilAxis = _f.XPathPreceding(currentNode); break; case XPathAxis.PrecedingSibling: qilAxis = _f.PrecedingSibling(currentNode); break; case XPathAxis.Self: qilAxis = (currentNode); break; // Can be done using BuildAxisFilter() but f.Root() sets wrong XmlNodeKindFlags case XPathAxis.Root: return(_f.Root(currentNode)); default: qilAxis = null; Debug.Fail("Invalid EnumValue 'XPathAxis'"); break; } QilNode result = BuildAxisFilter(qilAxis, xpathAxis, nodeType, name, nsUri); if ( xpathAxis == XPathAxis.Ancestor || xpathAxis == XPathAxis.Preceding || xpathAxis == XPathAxis.AncestorOrSelf || xpathAxis == XPathAxis.PrecedingSibling ) { result = _f.BaseFactory.DocOrderDistinct(result); // To make grouping operator NOP we should always return path expressions in DOD. // I can't use Pattern factory here becasue Predicate() depends on fact that DOD() is // outmost node in reverse steps } return(result); }
public string Axis(XPathAxis xpathAxis, XPathNodeType nodeType, string prefix, string name) { string nodeTest; switch (nodeType) { case XPathNodeType.ProcessingInstruction: Debug.Assert(prefix == ""); nodeTest = "processing-instruction(" + name + ")"; break; case XPathNodeType.Text: Debug.Assert(prefix == null && name == null); nodeTest = "text()"; break; case XPathNodeType.Comment: Debug.Assert(prefix == null && name == null); nodeTest = "comment()"; break; case XPathNodeType.All: nodeTest = "node()"; break; case XPathNodeType.Attribute: lastAttribute = name; nodeTest = QNameOrWildcard(prefix, name); break; case XPathNodeType.Element: if (lastElement != null) { CreateElement(); } lastElement = name; nodeTest = QNameOrWildcard(prefix, name); break; case XPathNodeType.Namespace: nodeTest = QNameOrWildcard(prefix, name); break; default: throw new ArgumentException("unexpected XPathNodeType", "XPathNodeType"); } return(axisStrings[(int)xpathAxis] + nodeTest); }
/* * NodeTest ::= NameTest | ('comment' | 'text' | 'node') '(' ')' | 'processing-instruction' '(' Literal? ')' * NameTest ::= '*' | NCName ':' '*' | QName */ private Node ParseNodeTest(XPathAxis axis) { XPathNodeType nodeType; string nodePrefix, nodeName; int startChar = scanner.LexStart; InternalParseNodeTest(scanner, axis, out nodeType, out nodePrefix, out nodeName); PushPosInfo(startChar, scanner.PrevLexEnd); Node result = builder.Axis(axis, nodeType, nodePrefix, nodeName); PopPosInfo(); return(result); }
public IXPathNode Axis(XPathAxis axis, XPathNodeType type, string prefix, string name) { string label = name; if ((prefix ?? "") != "") { label = prefix + ":" + name; } return(new XPathAxisNode { Axis = axis, Type = type, Label = label, }); }
QilNode BuildAxisFilter(QilNode qilAxis, XPathAxis xpathAxis, XPathNodeType nodeType, string name, string nsUri) { XmlNodeKindFlags original = qilAxis.XmlType.NodeKinds; XmlNodeKindFlags required = AxisTypeMask(original, nodeType, xpathAxis); QilIterator itr; if (required == 0) { return(f.Sequence()); } else if (required == original) { } else { qilAxis = f.Filter(itr = f.For(qilAxis), f.IsType(itr, T.NodeChoice(required))); qilAxis.XmlType = T.PrimeProduct(T.NodeChoice(required), qilAxis.XmlType.Cardinality); // Without code bellow IlGeneragion gives stack overflow exception for the following passage. //<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> // <xsl:template match="/"> // <xsl:value-of select="descendant::author/@id | comment()" /> // </xsl:template> //</xsl:stylesheet> // ToDo: remove this code when IlGen bug will be fixed. if (qilAxis.NodeType == QilNodeType.Filter) { QilLoop filter = (QilLoop)qilAxis; filter.Body = f.And(filter.Body, name != null && nsUri != null ? f.Eq(f.NameOf(itr), f.QName(name, nsUri)) : // ns:bar || bar nsUri != null ? f.Eq(f.NamespaceUriOf(itr), f.String(nsUri)) : // ns:* name != null ? f.Eq(f.LocalNameOf(itr), f.String(name)) : // *:foo /*name == nsUri == null*/ f.True() // * ); return(filter); } } return(f.Filter(itr = f.For(qilAxis), name != null && nsUri != null ? f.Eq(f.NameOf(itr), f.QName(name, nsUri)) : // ns:bar || bar nsUri != null ? f.Eq(f.NamespaceUriOf(itr), f.String(nsUri)) : // ns:* name != null ? f.Eq(f.LocalNameOf(itr), f.String(name)) : // *:foo /*name == nsUri == null*/ f.True() // * )); }
public bool TryGetAxis(out XPathAxis axis) { axis = XPathAxis.Self; if (Type == XPathTokenType.AxisName) { if (Value == "@") { axis = XPathAxis.Attribute; return(true); } if (Enum.TryParse(Value.Replace("-", ""), true, out axis)) { return(true); } } return(false); }
private string GetAxisString(XPathAxis stepAxis) { switch (stepAxis) { case XPathAxis.Child: return(String.Empty); case XPathAxis.Descendant: return("descendant::"); case XPathAxis.Parent: return("parent::"); case XPathAxis.Ancestor: return("ancestor::"); case XPathAxis.FollowingSibling: return("following-sibling::"); case XPathAxis.PrecedingSibling: return("preceding-sibling::"); case XPathAxis.Following: return("following::"); case XPathAxis.Preceding: return("preceding::"); case XPathAxis.Self: return("self::"); case XPathAxis.DescendantOrSelf: return("/"); case XPathAxis.AncestorOrSelf: return("ancestor-or-self::"); default: Debug.Fail("There should be no XPathAxis enum value that isn't handled in this switch statement"); return(String.Empty); } }
private string GetAxisString(XPathAxis stepAxis) { switch (stepAxis) { case XPathAxis.Child: return(string.Empty); case XPathAxis.Descendant: return("descendant::"); case XPathAxis.Parent: return("parent::"); case XPathAxis.Ancestor: return("ancestor::"); case XPathAxis.FollowingSibling: return("following-sibling::"); case XPathAxis.PrecedingSibling: return("preceding-sibling::"); case XPathAxis.Following: return("following::"); case XPathAxis.Preceding: return("preceding::"); case XPathAxis.Self: return("self::"); case XPathAxis.DescendantOrSelf: return("/"); case XPathAxis.AncestorOrSelf: return("ancestor-or-self::"); default: return(string.Empty); } }
QilNode BuildAxisFilter(QilNode qilAxis, XPathAxis xpathAxis, XPathNodeType nodeType, string name, string nsUri) { XmlNodeKindFlags original = qilAxis.XmlType.NodeKinds; XmlNodeKindFlags required = AxisTypeMask(original, nodeType, xpathAxis); QilIterator itr; if (required == 0) { return(f.Sequence()); } else if (required == original) { } else { qilAxis = f.Filter(itr = f.For(qilAxis), f.IsType(itr, T.NodeChoice(required))); qilAxis.XmlType = T.PrimeProduct(T.NodeChoice(required), qilAxis.XmlType.Cardinality); if (qilAxis.NodeType == QilNodeType.Filter) { QilLoop filter = (QilLoop)qilAxis; filter.Body = f.And(filter.Body, name != null && nsUri != null ? f.Eq(f.NameOf(itr), f.QName(name, nsUri)) : // ns:bar || bar nsUri != null ? f.Eq(f.NamespaceUriOf(itr), f.String(nsUri)) : // ns:* name != null ? f.Eq(f.LocalNameOf(itr), f.String(name)) : // *:foo /*name == nsUri == null*/ f.True() // * ); return(filter); } } return(f.Filter(itr = f.For(qilAxis), name != null && nsUri != null ? f.Eq(f.NameOf(itr), f.QName(name, nsUri)) : // ns:bar || bar nsUri != null ? f.Eq(f.NamespaceUriOf(itr), f.String(nsUri)) : // ns:* name != null ? f.Eq(f.LocalNameOf(itr), f.String(name)) : // *:foo /*name == nsUri == null*/ f.True() // * )); }
private static QilLoop BuildAxisFilter(QilPatternFactory f, QilIterator itr, XPathAxis xpathAxis, XPathNodeType nodeType, string name, string nsUri) { QilNode nameTest = ( name != null && nsUri != null ? f.Eq(f.NameOf(itr), f.QName(name, nsUri)) : // ns:bar || bar nsUri != null ? f.Eq(f.NamespaceUriOf(itr), f.String(nsUri)) : // ns:* name != null ? f.Eq(f.LocalNameOf(itr), f.String(name)) : // *:foo /*name == nsUri == null*/ f.True() // * ); XmlNodeKindFlags intersection = XPathBuilder.AxisTypeMask(itr.XmlType.NodeKinds, nodeType, xpathAxis); QilNode typeTest = ( intersection == 0 ? f.False() : // input & required doesn't intersect intersection == itr.XmlType.NodeKinds ? f.True() : // input is subset of required /*else*/ f.IsType(itr, T.NodeChoice(intersection)) ); QilLoop filter = f.BaseFactory.Filter(itr, f.And(typeTest, nameTest)); filter.XmlType = T.PrimeProduct(T.NodeChoice(intersection), filter.XmlType.Cardinality); return(filter); }
public virtual QilNode Axis(XPathAxis xpathAxis, XPathNodeType nodeType, string prefix, string name) { string nsUri = prefix == null ? null : _environment.ResolvePrefix(prefix); return(BuildAxis(xpathAxis, nodeType, nsUri, name)); }
private string GetAxisString(XPathAxis stepAxis) { switch (stepAxis) { case XPathAxis.Child: return string.Empty; case XPathAxis.Descendant: return "descendant::"; case XPathAxis.Parent: return "parent::"; case XPathAxis.Ancestor: return "ancestor::"; case XPathAxis.FollowingSibling: return "following-sibling::"; case XPathAxis.PrecedingSibling: return "preceding-sibling::"; case XPathAxis.Following: return "following::"; case XPathAxis.Preceding: return "preceding::"; case XPathAxis.Self: return "self::"; case XPathAxis.DescendantOrSelf: return "/"; case XPathAxis.AncestorOrSelf: return "ancestor-or-self::"; default: return string.Empty; } }
// also called by XPathPatternBuilder public static XmlNodeKindFlags AxisTypeMask(XmlNodeKindFlags inputTypeMask, XPathNodeType nodeType, XPathAxis xpathAxis) { return((XmlNodeKindFlags)( (int)inputTypeMask & (int)s_XPathNodeType2QilXmlNodeKind[(int)nodeType] & (int)s_XPathAxisMask[(int)xpathAxis] )); }
public QilNode Axis(XPathAxis xpathAxis, XPathNodeType nodeType, string prefix, string name) { Debug.Assert( xpathAxis == XPathAxis.Child || xpathAxis == XPathAxis.Attribute || xpathAxis == XPathAxis.DescendantOrSelf || xpathAxis == XPathAxis.Root ); QilLoop result; double priority; switch (xpathAxis) { case XPathAxis.DescendantOrSelf : Debug.Assert(nodeType == XPathNodeType.All && prefix == null && name == null, " // is the only d-o-s axes that we can have in pattern"); return f.Nop(this.fixupNode); // We using Nop as a flag that DescendantOrSelf exis was used between steps. case XPathAxis.Root : QilIterator i; result = f.BaseFactory.Filter(i = f.For(fixupNode), f.IsType(i, T.Document)); priority = 0.5; break; default : string nsUri = prefix == null ? null : this.environment.ResolvePrefix(prefix); result = BuildAxisFilter(f, f.For(fixupNode), xpathAxis, nodeType, name, nsUri); switch (nodeType) { case XPathNodeType.Element : case XPathNodeType.Attribute : if (name != null) { priority = 0; } else { if (prefix != null) { priority = -0.25; } else { priority = -0.5; } } break; case XPathNodeType.ProcessingInstruction : priority = name != null ? 0 : -0.5; break; default: priority = -0.5; break; } break; } SetPriority(result, priority); SetLastParent(result, result); return result; }
public void NextLex() { prevLexEnd = curIndex; prevKind = kind; SkipSpace(); lexStart = curIndex; switch (curChar) { case '\0': kind = LexKind.Eof; return; case '(': case ')': case '[': case ']': case '@': case ',': case '$': case '}': kind = (LexKind)curChar; NextChar(); break; case '.': NextChar(); if (curChar == '.') { kind = LexKind.DotDot; NextChar(); } else if (IsAsciiDigit(curChar)) { SetSourceIndex(lexStart); goto case '0'; } else { kind = LexKind.Dot; } break; case ':': NextChar(); if (curChar == ':') { kind = LexKind.ColonColon; NextChar(); } else { kind = LexKind.Unknown; } break; case '*': kind = LexKind.Star; NextChar(); CheckOperator(true); break; case '/': NextChar(); if (curChar == '/') { kind = LexKind.SlashSlash; NextChar(); } else { kind = LexKind.Slash; } break; case '|': kind = LexKind.Union; NextChar(); break; case '+': kind = LexKind.Plus; NextChar(); break; case '-': kind = LexKind.Minus; NextChar(); break; case '=': kind = LexKind.Eq; NextChar(); break; case '!': NextChar(); if (curChar == '=') { kind = LexKind.Ne; NextChar(); } else { kind = LexKind.Unknown; } break; case '<': NextChar(); if (curChar == '=') { kind = LexKind.Le; NextChar(); } else { kind = LexKind.Lt; } break; case '>': NextChar(); if (curChar == '=') { kind = LexKind.Ge; NextChar(); } else { kind = LexKind.Gt; } break; case '"': case '\'': kind = LexKind.String; ScanString(); break; case '0': case '1': case '2': case '3': case '4': case '5': case '6': case '7': case '8': case '9': kind = LexKind.Number; ScanNumber(); break; default: this.name = ScanNCName(); if (this.name != null) { kind = LexKind.Name; this.prefix = string.Empty; this.canBeFunction = false; this.axis = XPathAxis.Unknown; bool colonColon = false; int saveSourceIndex = curIndex; // "foo:bar" or "foo:*" -- one lexeme (no spaces allowed) // "foo::" or "foo ::" -- two lexemes, reported as one (AxisName) // "foo:?" or "foo :?" -- lexeme "foo" reported if (curChar == ':') { NextChar(); if (curChar == ':') { // "foo::" -> OperatorName, AxisName NextChar(); colonColon = true; SetSourceIndex(saveSourceIndex); } else { // "foo:bar", "foo:*" or "foo:?" if (curChar == '*') { NextChar(); this.prefix = this.name; this.name = "*"; } else { string ncName = ScanNCName(); if (ncName != null) { this.prefix = this.name; this.name = ncName; // Look ahead for '(' to determine whether QName can be a FunctionName saveSourceIndex = curIndex; SkipSpace(); this.canBeFunction = (curChar == '('); SetSourceIndex(saveSourceIndex); } else { // "foo:?" -> OperatorName, NameTest // Return "foo" and leave ":" to be reported later as an unknown lexeme SetSourceIndex(saveSourceIndex); } } } } else { SkipSpace(); if (curChar == ':') { // "foo ::" or "foo :?" NextChar(); if (curChar == ':') { NextChar(); colonColon = true; } SetSourceIndex(saveSourceIndex); } else { this.canBeFunction = (curChar == '('); } } if (!CheckOperator(false) && colonColon) { this.axis = CheckAxis(); } } else { kind = LexKind.Unknown; NextChar(); } break; } }
public IControlWalkerElement Axis(XPathAxis xpathAxis, System.Xml.XPath.XPathNodeType nodeType, string prefix, string name) { return(new AxisElement(xpathAxis, nodeType, prefix, name)); }
public override object EvaluateInternal(XPathNodeIterator iterator) #line 36 "./XPath/Private/XPathEvaluate.tc" { NodeTest node = this; // TODO handle various axes XPathSimpleIterator axis = null; switch(node.axis) { case XPathAxis.Self: { axis = new XPathSelfIterator( (XPathBaseIterator)iterator); } break; case XPathAxis.Child: { axis = new XPathChildIterator( (XPathBaseIterator)iterator); } break; case XPathAxis.Parent: { axis = new XPathParentIterator( (XPathBaseIterator)iterator); } break; case XPathAxis.Attribute: { axis = new XPathAttributeIterator( (XPathBaseIterator)iterator); } break; case XPathAxis.Ancestor: { axis = new XPathAncestorIterator( (XPathBaseIterator)iterator); } break; case XPathAxis.AncestorOrSelf: { axis = new XPathAncestorOrSelfIterator( (XPathBaseIterator)iterator); } break; case XPathAxis.Descendant: { axis = new XPathDescendantIterator( (XPathBaseIterator)iterator); } break; case XPathAxis.DescendantOrSelf: { axis = new XPathDescendantOrSelfIterator( (XPathBaseIterator)iterator); } break; case XPathAxis.Following: { axis = new XPathFollowingIterator( (XPathBaseIterator)iterator); } break; case XPathAxis.FollowingSibling: { axis = new XPathFollowingSiblingIterator( (XPathBaseIterator)iterator); } break; case XPathAxis.Preceding: { axis = new XPathPrecedingIterator( (XPathBaseIterator)iterator); } break; case XPathAxis.PrecedingSibling: { axis = new XPathPrecedingSiblingIterator( (XPathBaseIterator)iterator); } break; case XPathAxis.Namespace: { axis = new XPathNamespaceIterator( (XPathBaseIterator)iterator); } break; default: { throw new NotImplementedException(node.axis + " is not implemented"); } break; } return new XPathAxisIterator(axis, this); }
protected string AppendStep(string basePath, XPathAxis stepAxis, string stepNodeTest) => AppendStep(basePath, stepAxis, stepNodeTest, string.Empty);
public void NextLex() { _prevLexEnd = _curIndex; _prevKind = _kind; SkipSpace(); _lexStart = _curIndex; switch (_curChar) { case '\0': _kind = LexKind.Eof; return; case '(': case ')': case '[': case ']': case '@': case ',': case '$': case '}': _kind = (LexKind)_curChar; NextChar(); break; case '.': NextChar(); if (_curChar == '.') { _kind = LexKind.DotDot; NextChar(); } else if (IsAsciiDigit(_curChar)) { SetSourceIndex(_lexStart); goto case '0'; } else { _kind = LexKind.Dot; } break; case ':': NextChar(); if (_curChar == ':') { _kind = LexKind.ColonColon; NextChar(); } else { _kind = LexKind.Unknown; } break; case '*': _kind = LexKind.Star; NextChar(); CheckOperator(true); break; case '/': NextChar(); if (_curChar == '/') { _kind = LexKind.SlashSlash; NextChar(); } else { _kind = LexKind.Slash; } break; case '|': _kind = LexKind.Union; NextChar(); break; case '+': _kind = LexKind.Plus; NextChar(); break; case '-': _kind = LexKind.Minus; NextChar(); break; case '=': _kind = LexKind.Eq; NextChar(); break; case '!': NextChar(); if (_curChar == '=') { _kind = LexKind.Ne; NextChar(); } else { _kind = LexKind.Unknown; } break; case '<': NextChar(); if (_curChar == '=') { _kind = LexKind.Le; NextChar(); } else { _kind = LexKind.Lt; } break; case '>': NextChar(); if (_curChar == '=') { _kind = LexKind.Ge; NextChar(); } else { _kind = LexKind.Gt; } break; case '"': case '\'': _kind = LexKind.String; ScanString(); break; case '0': case '1': case '2': case '3': case '4': case '5': case '6': case '7': case '8': case '9': _kind = LexKind.Number; ScanNumber(); break; default: if (_xmlCharType.IsStartNCNameSingleChar(_curChar) #if XML10_FIFTH_EDITION || xmlCharType.IsNCNameHighSurrogateChar(curChar) #endif ) { _kind = LexKind.Name; _name = ScanNCName(); _prefix = string.Empty; _canBeFunction = false; _axis = XPathAxis.Unknown; bool colonColon = false; int saveSourceIndex = _curIndex; // "foo:bar" or "foo:*" -- one lexeme (no spaces allowed) // "foo::" or "foo ::" -- two lexemes, reported as one (AxisName) // "foo:?" or "foo :?" -- lexeme "foo" reported if (_curChar == ':') { NextChar(); if (_curChar == ':') { // "foo::" -> OperatorName, AxisName NextChar(); colonColon = true; SetSourceIndex(saveSourceIndex); } else { // "foo:bar", "foo:*" or "foo:?" if (_curChar == '*') { NextChar(); _prefix = _name; _name = "*"; } else if (_xmlCharType.IsStartNCNameSingleChar(_curChar) #if XML10_FIFTH_EDITION || xmlCharType.IsNCNameHighSurrogateChar(curChar) #endif ) { _prefix = _name; _name = ScanNCName(); // Look ahead for '(' to determine whether QName can be a FunctionName saveSourceIndex = _curIndex; SkipSpace(); _canBeFunction = (_curChar == '('); SetSourceIndex(saveSourceIndex); } else { // "foo:?" -> OperatorName, NameTest // Return "foo" and leave ":" to be reported later as an unknown lexeme SetSourceIndex(saveSourceIndex); } } } else { SkipSpace(); if (_curChar == ':') { // "foo ::" or "foo :?" NextChar(); if (_curChar == ':') { NextChar(); colonColon = true; } SetSourceIndex(saveSourceIndex); } else { _canBeFunction = (_curChar == '('); } } if (!CheckOperator(false) && colonColon) { _axis = CheckAxis(); } } else { _kind = LexKind.Unknown; NextChar(); } break; } }
protected string AppendStep(string basePath, XPathAxis stepAxis, string stepNodeTest) { return(AppendStep(basePath, stepAxis, stepNodeTest, String.Empty)); }
public NodeTest(XPathAxis axis, XPathNodeType nodeType, XmlQualifiedName name) : base() { this.kind__ = KIND; this.axis = axis; this.nodeType = nodeType; this.name = name; }
public void NextLex() { prevLexEnd = curIndex; prevKind = kind; SkipSpace(); lexStart = curIndex; switch (curChar) { case '\0': kind = LexKind.Eof; return; case '(': case ')': case '[': case ']': case '@': case ',': case '$': case '}': kind = (LexKind)curChar; NextChar(); break; case '.': NextChar(); if (curChar == '.') { kind = LexKind.DotDot; NextChar(); } else if (IsAsciiDigit(curChar)) { SetSourceIndex(lexStart); goto case '0'; } else { kind = LexKind.Dot; } break; case ':': NextChar(); if (curChar == ':') { kind = LexKind.ColonColon; NextChar(); } else { kind = LexKind.Unknown; } break; case '*': kind = LexKind.Star; NextChar(); CheckOperator(true); break; case '/': NextChar(); if (curChar == '/') { kind = LexKind.SlashSlash; NextChar(); } else { kind = LexKind.Slash; } break; case '|': kind = LexKind.Union; NextChar(); break; case '+': kind = LexKind.Plus; NextChar(); break; case '-': kind = LexKind.Minus; NextChar(); break; case '=': kind = LexKind.Eq; NextChar(); break; case '!': NextChar(); if (curChar == '=') { kind = LexKind.Ne; NextChar(); } else { kind = LexKind.Unknown; } break; case '<': NextChar(); if (curChar == '=') { kind = LexKind.Le; NextChar(); } else { kind = LexKind.Lt; } break; case '>': NextChar(); if (curChar == '=') { kind = LexKind.Ge; NextChar(); } else { kind = LexKind.Gt; } break; case '"': case '\'': kind = LexKind.String; ScanString(); break; case '0': case '1': case '2': case '3': case '4': case '5': case '6': case '7': case '8': case '9': kind = LexKind.Number; ScanNumber(); break; default: if (xmlCharType.IsStartNCNameSingleChar(curChar) #if XML10_FIFTH_EDITION || xmlCharType.IsNCNameHighSurrogateChar(curChar) #endif ) { kind = LexKind.Name; this.name = ScanNCName(); this.prefix = string.Empty; this.canBeFunction = false; this.axis = XPathAxis.Unknown; bool colonColon = false; int saveSourceIndex = curIndex; // "foo:bar" or "foo:*" -- one lexeme (no spaces allowed) // "foo::" or "foo ::" -- two lexemes, reported as one (AxisName) // "foo:?" or "foo :?" -- lexeme "foo" reported if (curChar == ':') { NextChar(); if (curChar == ':') // "foo::" -> OperatorName, AxisName { NextChar(); colonColon = true; SetSourceIndex(saveSourceIndex); } else // "foo:bar", "foo:*" or "foo:?" { if (curChar == '*') { NextChar(); this.prefix = this.name; this.name = "*"; } else if (xmlCharType.IsStartNCNameSingleChar(curChar) #if XML10_FIFTH_EDITION || xmlCharType.IsNCNameHighSurrogateChar(curChar) #endif ) { this.prefix = this.name; this.name = ScanNCName(); // Look ahead for '(' to determine whether QName can be a FunctionName saveSourceIndex = curIndex; SkipSpace(); this.canBeFunction = (curChar == '('); SetSourceIndex(saveSourceIndex); } else // "foo:?" -> OperatorName, NameTest // Return "foo" and leave ":" to be reported later as an unknown lexeme { SetSourceIndex(saveSourceIndex); } } } else { SkipSpace(); if (curChar == ':') // "foo ::" or "foo :?" { NextChar(); if (curChar == ':') { NextChar(); colonColon = true; } SetSourceIndex(saveSourceIndex); } else { this.canBeFunction = (curChar == '('); } } if (!CheckOperator(false) && colonColon) { this.axis = CheckAxis(); } } else { kind = LexKind.Unknown; NextChar(); } break; } }
protected string AppendStep(string basePath, XPathAxis stepAxis, string stepNodeTest) { return AppendStep(basePath, stepAxis, stepNodeTest, String.Empty); }
protected string AppendStep(string basePath, XPathAxis stepAxis, string stepNodeTest, string predicate) { return this.EnsureTrailingSlash(basePath) + this.GetAxisString(stepAxis) + stepNodeTest + this.EnsureBracketedPredicate(predicate); }
private static QilLoop BuildAxisFilter(QilPatternFactory f, QilIterator itr, XPathAxis xpathAxis, XPathNodeType nodeType, string name, string nsUri) { QilNode nameTest = ( name != null && nsUri != null ? f.Eq(f.NameOf(itr), f.QName(name, nsUri)) : // ns:bar || bar nsUri != null ? f.Eq(f.NamespaceUriOf(itr), f.String(nsUri)) : // ns:* name != null ? f.Eq(f.LocalNameOf(itr), f.String(name)) : // *:foo /*name == nsUri == null*/ f.True() // * ); XmlNodeKindFlags intersection = XPathBuilder.AxisTypeMask(itr.XmlType.NodeKinds, nodeType, xpathAxis); QilNode typeTest = ( intersection == 0 ? f.False() : // input & required doesn't intersect intersection == itr.XmlType.NodeKinds ? f.True() : // input is subset of required /*else*/ f.IsType(itr, T.NodeChoice(intersection)) ); QilLoop filter = f.BaseFactory.Filter(itr, f.And(typeTest, nameTest)); filter.XmlType = T.PrimeProduct(T.NodeChoice(intersection), filter.XmlType.Cardinality); return filter; }
private string GetAxisString(XPathAxis stepAxis) { switch (stepAxis) { case XPathAxis.Child: return String.Empty; case XPathAxis.Descendant: return "descendant::"; case XPathAxis.Parent: return "parent::"; case XPathAxis.Ancestor: return "ancestor::"; case XPathAxis.FollowingSibling: return "following-sibling::"; case XPathAxis.PrecedingSibling: return "preceding-sibling::"; case XPathAxis.Following: return "following::"; case XPathAxis.Preceding: return "preceding::"; case XPathAxis.Self: return "self::"; case XPathAxis.DescendantOrSelf: return "/"; case XPathAxis.AncestorOrSelf: return "ancestor-or-self::"; default: Debug.Fail("There should be no XPathAxis enum value that isn't handled in this switch statement"); return String.Empty; } }
protected string AppendStep(string basePath, XPathAxis stepAxis, string stepNodeTest, string predicate) { return(this.EnsureTrailingSlash(basePath) + this.GetAxisString(stepAxis) + stepNodeTest + this.EnsureBracketedPredicate(predicate)); }
private static void InternalParseNodeTest(XPathScanner scanner, XPathAxis axis, out XPathNodeType nodeType, out string nodePrefix, out string nodeName) { switch (scanner.Kind) { case LexKind.Name: if (scanner.CanBeFunction && IsNodeType(scanner)) { nodePrefix = null; nodeName = null; switch (scanner.Name) { case "comment": nodeType = XPathNodeType.Comment; break; case "text": nodeType = XPathNodeType.Text; break; case "node": nodeType = XPathNodeType.All; break; default: Debug.Assert(scanner.Name == "processing-instruction"); nodeType = XPathNodeType.ProcessingInstruction; break; } scanner.NextLex(); scanner.PassToken(LexKind.LParens); if (nodeType == XPathNodeType.ProcessingInstruction) { if (scanner.Kind != LexKind.RParens) // 'processing-instruction' '(' Literal ')' { scanner.CheckToken(LexKind.String); // It is not needed to set nodePrefix here, but for our current implementation // comparing whole QNames is faster than comparing just local names nodePrefix = string.Empty; nodeName = scanner.StringValue; scanner.NextLex(); } } scanner.PassToken(LexKind.RParens); } else { nodePrefix = scanner.Prefix; nodeName = scanner.Name; nodeType = PrincipalNodeType(axis); scanner.NextLex(); if (nodeName == "*") { nodeName = null; } } break; case LexKind.Star: nodePrefix = null; nodeName = null; nodeType = PrincipalNodeType(axis); scanner.NextLex(); break; default: throw scanner.NodeTestExpectedException(scanner.RawValue); } }
public IXPathExpression Axis(XPathAxis xpathAxis, System.Xml.XPath.XPathNodeType nodeType, string prefix, string name) { return(new AxisElement(xpathAxis, nodeType, prefix, name)); }
public QilNode Axis(XPathAxis xpathAxis, XPathNodeType nodeType, string prefix, string name) { Debug.Assert( xpathAxis == XPathAxis.Child || xpathAxis == XPathAxis.Attribute || xpathAxis == XPathAxis.DescendantOrSelf || xpathAxis == XPathAxis.Root ); QilLoop result; double priority; switch (xpathAxis) { case XPathAxis.DescendantOrSelf: Debug.Assert(nodeType == XPathNodeType.All && prefix == null && name == null, " // is the only d-o-s axes that we can have in pattern"); return(_f.Nop(_fixupNode)); // We using Nop as a flag that DescendantOrSelf exis was used between steps. case XPathAxis.Root: QilIterator i; result = _f.BaseFactory.Filter(i = _f.For(_fixupNode), _f.IsType(i, T.Document)); priority = 0.5; break; default: string nsUri = prefix == null ? null : _environment.ResolvePrefix(prefix); result = BuildAxisFilter(_f, _f.For(_fixupNode), xpathAxis, nodeType, name, nsUri); switch (nodeType) { case XPathNodeType.Element: case XPathNodeType.Attribute: if (name != null) { priority = 0; } else { if (prefix != null) { priority = -0.25; } else { priority = -0.5; } } break; case XPathNodeType.ProcessingInstruction: priority = name != null ? 0 : -0.5; break; default: priority = -0.5; break; } break; } SetPriority(result, priority); SetLastParent(result, result); return(result); }
public StepExpression(XPathAxis axis, Expression filter) : base() { this.kind__ = KIND; this.axis = axis; this.filter = filter; }