if (kind != Type.NODE && !Axis.containsNodeKind(axis, kind)) {
test = EmptySequenceTest.getInstance();
}
result = new NodeTestPattern(test);
} else {
throw new XPathException("Only downwards axes are allowed in a pattern", "XTSE0340");
}
// TODO: //A only matches an A element in a tree rooted at a document
} else if (expression instanceof FilterExpression) {
Expression base = ((FilterExpression)expression).getControllingExpression();
Expression filter = ((FilterExpression)expression).getFilter();
Pattern basePattern = fromExpression(base, config);
if (basePattern instanceof NodeTestPattern) {
LocationPathPattern path = new LocationPathPattern();
path.setNodeTest(basePattern.getNodeTest());
basePattern = path;
}
if (!(basePattern instanceof LocationPathPattern)) {
throw new XPathException("The filtered expression in a pattern must be a simple step");
}
((LocationPathPattern)basePattern).addFilter(filter);
result = basePattern;
} else if (expression instanceof SlashExpression) {
Expression head = ((SlashExpression)expression).getLeadingSteps();
Expression tail = ((SlashExpression)expression).getLastStep();
Pattern tailPattern = fromExpression(tail, config);
if (tailPattern instanceof NodeTestPattern) {
LocationPathPattern path = new LocationPathPattern();
path.setNodeTest(tailPattern.getNodeTest());
tailPattern = path;
}
if (!(tailPattern instanceof LocationPathPattern)) {
throw new XPathException("The path in a pattern must contain simple steps: found " + tailPattern.toString());
}
if (((LocationPathPattern)tailPattern).getUpperPattern() != null) {
throw new XPathException("The path in a pattern must contain simple steps");
}
byte axis = getAxisForPathStep(tail);
Pattern headPattern = fromExpression(head, config);
((LocationPathPattern)tailPattern).setUpperPattern(axis, headPattern);
result = tailPattern;
} else if (expression instanceof RootExpression) {
result = new NodeTestPattern(NodeKindTest.DOCUMENT);
} else if (expression instanceof IXSLFunction) {
result = new JSObjectPattern(expression, config);
} else {
TypeHierarchy th = config.getTypeHierarchy();
ItemType type = expression.getItemType(th);
if (((expression.getDependencies() & StaticProperty.DEPENDS_ON_NON_DOCUMENT_FOCUS) == 0) &&
(type instanceof NodeTest || expression instanceof VariableReference)) {
result = new NodeSetPattern(expression, config);
}
}
if (result == null) {
throw new XPathException("Cannot convert the expression {" + expression.toString() + "} to a pattern");
} else {
result.setOriginalText(expression.toString());
return result;
}
}