| 10880 | } |
| 10881 | |
| 10882 | xpath_node_set_raw eval_node_set(const xpath_context& c, const xpath_stack& stack, nodeset_eval_t eval) |
| 10883 | { |
| 10884 | switch (_type) |
| 10885 | { |
| 10886 | case ast_op_union: |
| 10887 | { |
| 10888 | xpath_allocator_capture cr(stack.temp); |
| 10889 | |
| 10890 | xpath_stack swapped_stack = {stack.temp, stack.result}; |
| 10891 | |
| 10892 | xpath_node_set_raw ls = _left->eval_node_set(c, stack, eval); |
| 10893 | xpath_node_set_raw rs = _right->eval_node_set(c, swapped_stack, eval); |
| 10894 | |
| 10895 | // we can optimize merging two sorted sets, but this is a very rare operation, so don't bother |
| 10896 | ls.set_type(xpath_node_set::type_unsorted); |
| 10897 | |
| 10898 | ls.append(rs.begin(), rs.end(), stack.result); |
| 10899 | ls.remove_duplicates(stack.temp); |
| 10900 | |
| 10901 | return ls; |
| 10902 | } |
| 10903 | |
| 10904 | case ast_filter: |
| 10905 | { |
| 10906 | xpath_node_set_raw set = _left->eval_node_set(c, stack, _test == predicate_constant_one ? nodeset_eval_first : nodeset_eval_all); |
| 10907 | |
| 10908 | // either expression is a number or it contains position() call; sort by document order |
| 10909 | if (_test != predicate_posinv) set.sort_do(); |
| 10910 | |
| 10911 | bool once = eval_once(set.type(), eval); |
| 10912 | |
| 10913 | apply_predicate(set, 0, stack, once); |
| 10914 | |
| 10915 | return set; |
| 10916 | } |
| 10917 | |
| 10918 | case ast_func_id: |
| 10919 | return xpath_node_set_raw(); |
| 10920 | |
| 10921 | case ast_step: |
| 10922 | { |
| 10923 | switch (_axis) |
| 10924 | { |
| 10925 | case axis_ancestor: |
| 10926 | return step_do(c, stack, eval, axis_to_type<axis_ancestor>()); |
| 10927 | |
| 10928 | case axis_ancestor_or_self: |
| 10929 | return step_do(c, stack, eval, axis_to_type<axis_ancestor_or_self>()); |
| 10930 | |
| 10931 | case axis_attribute: |
| 10932 | return step_do(c, stack, eval, axis_to_type<axis_attribute>()); |
| 10933 | |
| 10934 | case axis_child: |
| 10935 | return step_do(c, stack, eval, axis_to_type<axis_child>()); |
| 10936 | |
| 10937 | case axis_descendant: |
| 10938 | return step_do(c, stack, eval, axis_to_type<axis_descendant>()); |
| 10939 |
no test coverage detected