| 9339 | } |
| 9340 | |
| 9341 | xpath_node_set_raw eval_node_set(const xpath_context& c, const xpath_stack& stack) |
| 9342 | { |
| 9343 | switch (_type) |
| 9344 | { |
| 9345 | case ast_op_union: |
| 9346 | { |
| 9347 | xpath_allocator_capture cr(stack.temp); |
| 9348 | |
| 9349 | xpath_stack swapped_stack = {stack.temp, stack.result}; |
| 9350 | |
| 9351 | xpath_node_set_raw ls = _left->eval_node_set(c, swapped_stack); |
| 9352 | xpath_node_set_raw rs = _right->eval_node_set(c, stack); |
| 9353 | |
| 9354 | // we can optimize merging two sorted sets, but this is a very rare operation, so don't bother |
| 9355 | rs.set_type(xpath_node_set::type_unsorted); |
| 9356 | |
| 9357 | rs.append(ls.begin(), ls.end(), stack.result); |
| 9358 | rs.remove_duplicates(); |
| 9359 | |
| 9360 | return rs; |
| 9361 | } |
| 9362 | |
| 9363 | case ast_filter: |
| 9364 | case ast_filter_posinv: |
| 9365 | { |
| 9366 | xpath_node_set_raw set = _left->eval_node_set(c, stack); |
| 9367 | |
| 9368 | // either expression is a number or it contains position() call; sort by document order |
| 9369 | if (_type == ast_filter) |
| 9370 | set.sort_do(); |
| 9371 | |
| 9372 | apply_predicate(set, 0, _right, stack); |
| 9373 | |
| 9374 | return set; |
| 9375 | } |
| 9376 | |
| 9377 | case ast_func_id: return xpath_node_set_raw(); |
| 9378 | |
| 9379 | case ast_step: |
| 9380 | { |
| 9381 | switch (_axis) |
| 9382 | { |
| 9383 | case axis_ancestor: return step_do(c, stack, axis_to_type<axis_ancestor>()); |
| 9384 | |
| 9385 | case axis_ancestor_or_self: return step_do(c, stack, axis_to_type<axis_ancestor_or_self>()); |
| 9386 | |
| 9387 | case axis_attribute: return step_do(c, stack, axis_to_type<axis_attribute>()); |
| 9388 | |
| 9389 | case axis_child: return step_do(c, stack, axis_to_type<axis_child>()); |
| 9390 | |
| 9391 | case axis_descendant: return step_do(c, stack, axis_to_type<axis_descendant>()); |
| 9392 | |
| 9393 | case axis_descendant_or_self: return step_do(c, stack, axis_to_type<axis_descendant_or_self>()); |
| 9394 | |
| 9395 | case axis_following: return step_do(c, stack, axis_to_type<axis_following>()); |
| 9396 | |
| 9397 | case axis_following_sibling: return step_do(c, stack, axis_to_type<axis_following_sibling>()); |
| 9398 |
no test coverage detected