| line |
true |
false |
branch |
|
41
|
0 |
23 |
if (!sv) return false; |
|
42
|
0 |
23 |
if (SvMAGICAL(sv)) |
|
44
|
0 |
23 |
if (SvIOK(sv) || SvUOK(sv)) |
|
|
0 |
0 |
if (SvIOK(sv) || SvUOK(sv)) |
|
46
|
0 |
0 |
if (SvNOK(sv) && (SvNV(sv) == (NV)(IV)SvNV(sv))) |
|
|
0 |
0 |
if (SvNOK(sv) && (SvNV(sv) == (NV)(IV)SvNV(sv))) |
|
48
|
0 |
0 |
if (SvPOK(sv)) { |
|
51
|
0 |
0 |
if (len == 0 || !((str[0] >= '0' && str[0] <= '9') || str[0] == '-' || str[0] == '+')) |
|
|
0 |
0 |
if (len == 0 || !((str[0] >= '0' && str[0] <= '9') || str[0] == '-' || str[0] == '+')) |
|
|
0 |
0 |
if (len == 0 || !((str[0] >= '0' && str[0] <= '9') || str[0] == '-' || str[0] == '+')) |
|
|
0 |
0 |
if (len == 0 || !((str[0] >= '0' && str[0] <= '9') || str[0] == '-' || str[0] == '+')) |
|
|
0 |
0 |
if (len == 0 || !((str[0] >= '0' && str[0] <= '9') || str[0] == '-' || str[0] == '+')) |
|
53
|
0 |
0 |
while (--len > 0) { |
|
54
|
0 |
0 |
if (str[len] < '0' || str[len] > '9') |
|
|
0 |
0 |
if (str[len] < '0' || str[len] > '9') |
|
65
|
16 |
8 |
if (SvIOK(type_sv)) { |
|
67
|
16 |
0 |
if (key_type < 1 || key_type > KEY_TYPE_MAX) |
|
|
0 |
16 |
if (key_type < 1 || key_type > KEY_TYPE_MAX) |
|
70
|
8 |
0 |
else if (SvPOK(type_sv)) { |
|
73
|
2 |
6 |
if (len > 9 && foldEQ(str, "KEY_TYPE_", 9)) { |
|
|
2 |
0 |
if (len > 9 && foldEQ(str, "KEY_TYPE_", 9)) { |
|
77
|
7 |
0 |
key_type= (len == 3 && foldEQ(str, "ANY", 3))? KEY_TYPE_ANY |
|
78
|
7 |
1 |
: (len == 5 && foldEQ(str, "CLAIM", 5))? KEY_TYPE_CLAIM |
|
|
0 |
8 |
: (len == 5 && foldEQ(str, "CLAIM", 5))? KEY_TYPE_CLAIM |
|
|
0 |
0 |
: (len == 5 && foldEQ(str, "CLAIM", 5))? KEY_TYPE_CLAIM |
|
79
|
7 |
1 |
: (len == 3 && foldEQ(str, "INT", 3))? KEY_TYPE_INT |
|
|
0 |
7 |
: (len == 3 && foldEQ(str, "INT", 3))? KEY_TYPE_INT |
|
80
|
0 |
1 |
: (len == 5 && foldEQ(str, "FLOAT", 5))? KEY_TYPE_FLOAT |
|
|
0 |
0 |
: (len == 5 && foldEQ(str, "FLOAT", 5))? KEY_TYPE_FLOAT |
|
81
|
1 |
0 |
: (len == 4 && foldEQ(str, "BSTR", 4))? KEY_TYPE_BSTR |
|
|
0 |
1 |
: (len == 4 && foldEQ(str, "BSTR", 4))? KEY_TYPE_BSTR |
|
82
|
0 |
0 |
: (len == 4 && foldEQ(str, "USTR", 4))? KEY_TYPE_USTR |
|
|
0 |
0 |
: (len == 4 && foldEQ(str, "USTR", 4))? KEY_TYPE_USTR |
|
128
|
8 |
48 |
if (SvROK(cmp_sv) && SvTYPE(SvRV(cmp_sv)) == SVt_PVCV) |
|
|
8 |
0 |
if (SvROK(cmp_sv) && SvTYPE(SvRV(cmp_sv)) == SVt_PVCV) |
|
130
|
28 |
20 |
else if (SvIOK(cmp_sv)) { |
|
132
|
28 |
0 |
cmp_id= (i < 1 || i > CMP_MAX || i == CMP_SUB)? -1 : (int) i; |
|
|
28 |
0 |
cmp_id= (i < 1 || i > CMP_MAX || i == CMP_SUB)? -1 : (int) i; |
|
|
28 |
0 |
cmp_id= (i < 1 || i > CMP_MAX || i == CMP_SUB)? -1 : (int) i; |
|
134
|
20 |
0 |
else if (SvPOK(cmp_sv)) { |
|
137
|
10 |
10 |
if (len > 4 && foldEQ(str, "CMP_", 4)) { |
|
|
1 |
9 |
if (len > 4 && foldEQ(str, "CMP_", 4)) { |
|
141
|
1 |
9 |
cmp_id= (len == 3 && foldEQ(str, "INT", 3))? CMP_INT |
|
142
|
10 |
10 |
: (len == 3 && foldEQ(str, "STR", 3))? CMP_STR |
|
|
0 |
1 |
: (len == 3 && foldEQ(str, "STR", 3))? CMP_STR |
|
143
|
1 |
10 |
: (len == 4 && foldEQ(str, "UTF8", 4))? CMP_STR // back-compat name |
|
|
0 |
0 |
: (len == 4 && foldEQ(str, "UTF8", 4))? CMP_STR // back-compat name |
|
144
|
0 |
10 |
: (len == 4 && foldEQ(str, "PERL", 4))? CMP_PERL |
|
|
0 |
0 |
: (len == 4 && foldEQ(str, "PERL", 4))? CMP_PERL |
|
145
|
0 |
10 |
: (len == 5 && foldEQ(str, "FLOAT", 5))? CMP_FLOAT |
|
|
0 |
1 |
: (len == 5 && foldEQ(str, "FLOAT", 5))? CMP_FLOAT |
|
146
|
1 |
9 |
: (len == 6 && foldEQ(str, "MEMCMP", 6))? CMP_MEMCMP |
|
|
0 |
0 |
: (len == 6 && foldEQ(str, "MEMCMP", 6))? CMP_MEMCMP |
|
147
|
0 |
9 |
: (len == 8 && foldEQ(str, "FOLDCASE", 8))? CMP_FOLDCASE |
|
|
2 |
5 |
: (len == 8 && foldEQ(str, "FOLDCASE", 8))? CMP_FOLDCASE |
|
148
|
7 |
2 |
: (len == 8 && foldEQ(str, "NUMSPLIT", 8))? CMP_NUMSPLIT |
|
|
0 |
2 |
: (len == 8 && foldEQ(str, "NUMSPLIT", 8))? CMP_NUMSPLIT |
|
149
|
2 |
2 |
: (len ==17 && foldEQ(str, "NUMSPLIT_FOLDCASE", 17))? CMP_NUMSPLIT_FOLDCASE |
|
|
2 |
0 |
: (len ==17 && foldEQ(str, "NUMSPLIT_FOLDCASE", 17))? CMP_NUMSPLIT_FOLDCASE |
|
151
|
2 |
0 |
: -1; |
|
185
|
61 |
0 |
if (SvIOK(mode_sv)) { |
|
187
|
61 |
0 |
mode= (i < 0 || i > GET_MAX)? -1 : (int) i; |
|
|
61 |
0 |
mode= (i < 0 || i > GET_MAX)? -1 : (int) i; |
|
188
|
0 |
0 |
} else if (SvPOK(mode_sv)) { |
|
191
|
0 |
0 |
if (len > 4 && foldEQ(mode_str, "GET_", 4)) { |
|
|
0 |
0 |
if (len > 4 && foldEQ(mode_str, "GET_", 4)) { |
|
197
|
0 |
0 |
case '<': mode= len == 1? GET_LT : len == 2 && mode_str[1] == '='? GET_LE : -1; break; |
|
|
0 |
0 |
case '<': mode= len == 1? GET_LT : len == 2 && mode_str[1] == '='? GET_LE : -1; break; |
|
|
0 |
0 |
case '<': mode= len == 1? GET_LT : len == 2 && mode_str[1] == '='? GET_LE : -1; break; |
|
198
|
0 |
0 |
case '>': mode= len == 1? GET_GT : len == 2 && mode_str[1] == '='? GET_GE : -1; break; |
|
|
0 |
0 |
case '>': mode= len == 1? GET_GT : len == 2 && mode_str[1] == '='? GET_GE : -1; break; |
|
|
0 |
0 |
case '>': mode= len == 1? GET_GT : len == 2 && mode_str[1] == '='? GET_GE : -1; break; |
|
199
|
0 |
0 |
case '=': mode= len == 2 && mode_str[1] == '='? GET_EQ : -1; break; |
|
|
0 |
0 |
case '=': mode= len == 2 && mode_str[1] == '='? GET_EQ : -1; break; |
|
200
|
0 |
0 |
case '-': mode= len == 2 && mode_str[1] == '-'? GET_PREV : -1; break; |
|
|
0 |
0 |
case '-': mode= len == 2 && mode_str[1] == '-'? GET_PREV : -1; break; |
|
201
|
0 |
0 |
case '+': mode= len == 2 && mode_str[1] == '+'? GET_NEXT : -1; break; |
|
|
0 |
0 |
case '+': mode= len == 2 && mode_str[1] == '+'? GET_NEXT : -1; break; |
|
203
|
0 |
0 |
mode= len == 2 && (mode_str[1] == 'q' || mode_str[1] == 'Q')? GET_EQ |
|
|
0 |
0 |
mode= len == 2 && (mode_str[1] == 'q' || mode_str[1] == 'Q')? GET_EQ |
|
204
|
0 |
0 |
: len == 7 && foldEQ(mode_str, "EQ_LAST", 7)? GET_EQ_LAST |
|
|
0 |
0 |
: len == 7 && foldEQ(mode_str, "EQ_LAST", 7)? GET_EQ_LAST |
|
205
|
0 |
0 |
: -1; |
|
208
|
0 |
0 |
mode= len == 2 && (mode_str[1] == 't' || mode_str[1] == 'T')? GET_GT |
|
|
0 |
0 |
mode= len == 2 && (mode_str[1] == 't' || mode_str[1] == 'T')? GET_GT |
|
209
|
0 |
0 |
: len == 2 && (mode_str[1] == 'e' || mode_str[1] == 'E')? GET_GE |
|
|
0 |
0 |
: len == 2 && (mode_str[1] == 'e' || mode_str[1] == 'E')? GET_GE |
|
|
0 |
0 |
: len == 2 && (mode_str[1] == 'e' || mode_str[1] == 'E')? GET_GE |
|
210
|
0 |
0 |
: -1; |
|
213
|
0 |
0 |
mode= len == 2 && (mode_str[1] == 't' || mode_str[1] == 'T')? GET_LT |
|
|
0 |
0 |
mode= len == 2 && (mode_str[1] == 't' || mode_str[1] == 'T')? GET_LT |
|
214
|
0 |
0 |
: len == 2 && (mode_str[1] == 'e' || mode_str[1] == 'E')? GET_LE |
|
|
0 |
0 |
: len == 2 && (mode_str[1] == 'e' || mode_str[1] == 'E')? GET_LE |
|
|
0 |
0 |
: len == 2 && (mode_str[1] == 'e' || mode_str[1] == 'E')? GET_LE |
|
215
|
0 |
0 |
: len == 7 && foldEQ(mode_str, "LE_LAST", 7)? GET_LE_LAST |
|
|
0 |
0 |
: len == 7 && foldEQ(mode_str, "LE_LAST", 7)? GET_LE_LAST |
|
216
|
0 |
0 |
: -1; |
|
218
|
0 |
0 |
case 'P': case 'p': mode= foldEQ(mode_str, "PREV", 4)? GET_PREV : -1; break; |
|
219
|
0 |
0 |
case 'N': case 'n': mode= foldEQ(mode_str, "NEXT", 4)? GET_NEXT : -1; break; |
|
220
|
0 |
0 |
case 'o': case 'O': mode= foldEQ(mode_str, "OR_ADD", 6)? GET_OR_ADD : -1; break; |
|
230
|
0 |
0 |
if (!sv) |
|
232
|
0 |
0 |
else if (!SvPOK(sv)) |
|
235
|
0 |
0 |
if (len < size || ((intptr_t)p) & (align-1)) { |
|
|
0 |
0 |
if (len < size || ((intptr_t)p) & (align-1)) { |
|
236
|
0 |
0 |
SvGROW(sv, size+align-1); |
|
|
0 |
0 |
SvGROW(sv, size+align-1); |
|
239
|
0 |
0 |
if ((intptr_t)p & (align-1)) { |
|
333
|
20213 |
0 |
if (item->orig_key_stored) |
|
433
|
0 |
19 |
if (!tree) croak("tree is NULL"); |
|
434
|
0 |
19 |
if (!tree->owner) croak("no owner"); |
|
435
|
19 |
0 |
if (tree->key_type < 0 || tree->key_type > KEY_TYPE_MAX) croak("bad key_type"); |
|
|
0 |
19 |
if (tree->key_type < 0 || tree->key_type > KEY_TYPE_MAX) croak("bad key_type"); |
|
436
|
0 |
19 |
if (!tree->compare) croak("no compare function"); |
|
437
|
0 |
19 |
if ((err= rbtree_check_structure(&tree->root_sentinel, (int(*)(void*,void*,void*)) tree->compare, tree, -OFS_TreeRBXS_item_FIELD_rbnode))) |
|
439
|
19 |
0 |
if (TreeRBXS_get_count(tree)) { |
|
441
|
500010 |
19 |
while (node) { |
|
443
|
0 |
500010 |
if (item->key_type != tree->key_type) |
|
445
|
0 |
500010 |
if (!item->value) |
|
447
|
0 |
500010 |
if (item->iter) { |
|
449
|
0 |
0 |
while (iter) { |
|
450
|
0 |
0 |
if (!iter->owner) croak("Iterator lacks owner reference"); |
|
451
|
0 |
0 |
if (iter->item != item) croak("Iterator referenced by wrong item"); |
|
458
|
19 |
0 |
if (!tree->recent_count) { |
|
459
|
19 |
0 |
if (tree->recent.prev != &tree->recent || tree->recent.next != &tree->recent) |
|
|
0 |
19 |
if (tree->recent.prev != &tree->recent || tree->recent.next != &tree->recent) |
|
462
|
0 |
0 |
if (tree->recent.prev == &tree->recent || tree->recent.next == &tree->recent) |
|
|
0 |
0 |
if (tree->recent.prev == &tree->recent || tree->recent.next == &tree->recent) |
|
464
|
0 |
0 |
if (tree->recent_limit >= 0 && tree->recent_count > tree->recent_limit) |
|
|
0 |
0 |
if (tree->recent_limit >= 0 && tree->recent_count > tree->recent_limit) |
|
472
|
5 |
74 |
if (!tree->hashiter) { |
|
495
|
20079 |
481391 |
if (tree->transform) { |
|
518
|
0 |
140231 |
if (len > CKEYLEN_MAX) |
|
537
|
44 |
3 |
if (cmp != 0) { |
|
538
|
9 |
35 |
rbtree_node_t *node= cmp < 0? rbtree_node_prev(&item->rbnode) : rbtree_node_next(&item->rbnode); |
|
540
|
44 |
0 |
int neighbor_cmp= neighbor? tree->compare(tree, new_value, neighbor) : 0; |
|
541
|
14 |
30 |
IV new_extra= ITEM_EXTRA_BYTES_NEEDED(new_value); |
|
|
0 |
14 |
IV new_extra= ITEM_EXTRA_BYTES_NEEDED(new_value); |
|
542
|
14 |
30 |
if (IS_ITEM_KEY_STORED_IN_EXTRA(item)) { |
|
|
0 |
14 |
if (IS_ITEM_KEY_STORED_IN_EXTRA(item)) { |
|
543
|
0 |
30 |
IV cur_extra= ITEM_EXTRA_BYTES_NEEDED(item); |
|
|
0 |
0 |
IV cur_extra= ITEM_EXTRA_BYTES_NEEDED(item); |
|
544
|
2 |
28 |
if (new_extra > cur_extra) { |
|
554
|
35 |
9 |
if ((cmp > 0 && neighbor_cmp > 0) || (cmp < 0 && neighbor_cmp < 0) |
|
|
32 |
3 |
if ((cmp > 0 && neighbor_cmp > 0) || (cmp < 0 && neighbor_cmp < 0) |
|
|
9 |
32 |
if ((cmp > 0 && neighbor_cmp > 0) || (cmp < 0 && neighbor_cmp < 0) |
|
|
6 |
3 |
if ((cmp > 0 && neighbor_cmp > 0) || (cmp < 0 && neighbor_cmp < 0) |
|
555
|
33 |
5 |
|| (neighbor_cmp == 0 && !tree->allow_duplicates) |
|
|
33 |
0 |
|| (neighbor_cmp == 0 && !tree->allow_duplicates) |
|
560
|
0 |
39 |
if (item->iter) |
|
563
|
0 |
39 |
if (tree->prev_inserted_item == item) { |
|
589
|
36 |
3 |
if (found_identical) { |
|
591
|
30 |
6 |
if (cmp > 0) |
|
596
|
36 |
0 |
if (!tree->allow_duplicates) { |
|
600
|
0 |
36 |
rm_node= (rm_node == search[1])? NULL : rbtree_node_next(rm_node); |
|
601
|
0 |
36 |
ASSUME(rm_item != item); |
|
603
|
0 |
36 |
} while (rm_node); |
|
606
|
3 |
0 |
else if (search[0]) |
|
616
|
0 |
14 |
if (item->key_type == KEY_TYPE_CLAIM) |
|
638
|
16 |
31 |
if (item->orig_key_stored) { |
|
642
|
0 |
16 |
ASSUME(new_value->orig_key_stored); |
|
658
|
470907 |
30077 |
bool is_buffered_key= IS_ITEM_KEY_STORED_IN_EXTRA(src); |
|
|
110025 |
360882 |
bool is_buffered_key= IS_ITEM_KEY_STORED_IN_EXTRA(src); |
|
666
|
480952 |
20032 |
if (src->orig_key_stored || is_buffered_key) { |
|
|
120070 |
360882 |
if (src->orig_key_stored || is_buffered_key) { |
|
668
|
140102 |
0 |
strbuf_len= is_buffered_key? src->ckeylen+1 : 0; |
|
672
|
20032 |
120070 |
if (keyptr_len) { |
|
675
|
0 |
20032 |
kept= src->key_type == KEY_TYPE_CLAIM? SvREFCNT_inc(kept) : newSVsv(kept); |
|
680
|
140102 |
0 |
if (is_buffered_key) { |
|
729
|
149 |
26 |
return node? GET_TreeRBXS_FROM_root_sentinel(node) : NULL; |
|
734
|
6 |
0 |
while (node && node->parent) |
|
|
4 |
2 |
while (node && node->parent) |
|
747
|
2 |
0 |
struct TreeRBXS *tree= root_sentinel? GET_TreeRBXS_FROM_root_sentinel(root_sentinel) : NULL; |
|
753
|
2 |
0 |
if (item != orig_item) { |
|
755
|
2 |
0 |
if (tree) { |
|
756
|
2 |
0 |
if (item->rbnode.left->count) { |
|
757
|
0 |
2 |
ASSUME(item->rbnode.left->parent == orig_rbnode); |
|
760
|
2 |
0 |
if (item->rbnode.right->count) { |
|
761
|
0 |
2 |
ASSUME(item->rbnode.right->parent == orig_rbnode); |
|
764
|
2 |
0 |
if (item->rbnode.parent == root_sentinel) { |
|
765
|
0 |
2 |
ASSUME(root_sentinel->left == orig_rbnode); |
|
768
|
0 |
0 |
else if (item->rbnode.parent->left == orig_rbnode) |
|
771
|
0 |
0 |
ASSUME(item->rbnode.parent->right == orig_rbnode); |
|
775
|
2 |
0 |
if (item->recent.next) { |
|
776
|
0 |
2 |
ASSUME(item->recent.next->prev == orig_llnode); |
|
777
|
0 |
2 |
ASSUME(item->recent.prev->next == orig_llnode); |
|
782
|
0 |
2 |
if (tree->prev_inserted_item == orig_item) |
|
786
|
0 |
2 |
if (item->iter) { |
|
788
|
0 |
0 |
for (; cur; cur= cur->next_iter) { |
|
789
|
0 |
0 |
ASSUME(cur->item == orig_item); |
|
794
|
2 |
0 |
if (item->owner) { |
|
796
|
0 |
2 |
ASSUME(magic != NULL); |
|
797
|
0 |
2 |
ASSUME(magic->mg_ptr == (char*) orig_item); |
|
801
|
0 |
2 |
if (IS_ITEM_KEY_STORED_IN_EXTRA(item)) { |
|
|
0 |
0 |
if (IS_ITEM_KEY_STORED_IN_EXTRA(item)) { |
|
802
|
2 |
0 |
ASSUME(orig_ckey_ofs >= 0 && orig_ckey_ofs <= sizeof(void*)); |
|
|
0 |
2 |
ASSUME(orig_ckey_ofs >= 0 && orig_ckey_ofs <= sizeof(void*)); |
|
811
|
140767 |
360218 |
switch (item->key_type) { |
|
815
|
20032 |
480953 |
if (item->orig_key_stored) { |
|
819
|
500985 |
0 |
if (item->value) |
|
837
|
25 |
178 |
if (!rbtree_node_is_in_tree(&item->rbnode)) |
|
847
|
16813 |
0 |
for (cur= &item->iter; *cur; cur= &((*cur)->next_iter)) { |
|
848
|
1659 |
15154 |
if (*cur == iter) { |
|
865
|
3 |
12 |
if (iter->recent) { |
|
866
|
0 |
3 |
lnode= iter->reverse? tree->recent.prev : tree->recent.next; |
|
867
|
3 |
0 |
item= (lnode == &tree->recent)? NULL : GET_TreeRBXS_item_FROM_recent(lnode); |
|
873
|
2 |
10 |
: rbtree_node_left_leaf(root); |
|
882
|
13 |
1917 |
if (iter->item == item) |
|
885
|
1640 |
277 |
if (iter->item) |
|
888
|
1692 |
225 |
if (item) { |
|
890
|
106 |
1586 |
if (iter->recent && !item->recent.next) |
|
|
0 |
106 |
if (iter->recent && !item->recent.next) |
|
907
|
0 |
1667 |
if (!iter->tree) |
|
910
|
103 |
1564 |
if (iter->recent) { |
|
913
|
1 |
102 |
if (ofs < 0 && !item) { |
|
|
0 |
1 |
if (ofs < 0 && !item) { |
|
914
|
0 |
0 |
cur= iter->reverse? iter->tree->recent.prev : iter->tree->recent.next; |
|
919
|
16 |
87 |
if (iter->reverse) |
|
921
|
86 |
17 |
if (ofs > 0) { |
|
922
|
88 |
86 |
while (ofs-- > 0 && cur && cur != end) |
|
|
88 |
0 |
while (ofs-- > 0 && cur && cur != end) |
|
|
88 |
0 |
while (ofs-- > 0 && cur && cur != end) |
|
924
|
17 |
0 |
} else if (ofs < 0) { |
|
925
|
17 |
17 |
while (ofs++ < 0 && cur && cur != end) |
|
|
17 |
0 |
while (ofs++ < 0 && cur && cur != end) |
|
|
17 |
0 |
while (ofs++ < 0 && cur && cur != end) |
|
928
|
103 |
0 |
item= cur && cur != end? GET_TreeRBXS_item_FROM_recent(cur) : NULL; |
|
|
88 |
15 |
item= cur && cur != end? GET_TreeRBXS_item_FROM_recent(cur) : NULL; |
|
932
|
810 |
754 |
else if (ofs == 1) { |
|
934
|
798 |
12 |
if (item) { |
|
936
|
392 |
406 |
node= iter->reverse? rbtree_node_prev(node) : rbtree_node_next(node); |
|
950
|
737 |
17 |
: !iter->reverse? rbtree_node_index(&item->rbnode) |
|
952
|
387 |
350 |
: cnt - 1 - rbtree_node_index(&item->rbnode); |
|
953
|
750 |
4 |
if (ofs > 0) { |
|
954
|
601 |
149 |
newpos= (UV)ofs < (cnt-pos)? pos + ofs : cnt; |
|
957
|
4 |
0 |
newpos= (pos < o)? 0 : pos - o; |
|
960
|
360 |
394 |
if (iter->reverse) newpos= cnt - 1 - newpos; |
|
982
|
70 |
18 |
for (iter= item->iter, item->iter= NULL; iter; iter= next) { |
|
984
|
8 |
62 |
if (iter->recent) { // iterating insertion order? |
|
985
|
3 |
5 |
if (iter->reverse) { // newest to oldest? |
|
986
|
3 |
0 |
if (!prev_recent) { |
|
988
|
3 |
0 |
if (lnode == NULL || lnode == &iter->tree->recent) { |
|
|
1 |
2 |
if (lnode == NULL || lnode == &iter->tree->recent) { |
|
1001
|
3 |
2 |
if (!next_recent) { |
|
1003
|
3 |
0 |
if (lnode == NULL || lnode == &iter->tree->recent) { |
|
|
0 |
3 |
if (lnode == NULL || lnode == &iter->tree->recent) { |
|
1015
|
3 |
59 |
else if (flags & ONLY_ADVANCE_RECENT) { |
|
1021
|
31 |
28 |
if (iter->reverse) { // iterating high to low |
|
1022
|
22 |
9 |
if (!prev_item) { |
|
1024
|
17 |
5 |
if (!node) { |
|
1038
|
18 |
10 |
if (!next_item) { |
|
1040
|
9 |
9 |
if (!node) { |
|
1062
|
97 |
0 |
if (rbtree_node_is_in_tree(&item->rbnode)) { |
|
1063
|
14 |
83 |
if (tree->prev_inserted_item == item) { |
|
1068
|
16 |
81 |
if (item->iter) |
|
1071
|
25 |
72 |
if (item->recent.next) |
|
1078
|
85 |
12 |
if (!item->owner) |
|
1088
|
6 |
500887 |
while (iter) { |
|
1097
|
0 |
500887 |
if (rbtree_node_is_in_tree(&item->rbnode)) |
|
1100
|
500875 |
12 |
if (!item->owner) |
|
1105
|
19 |
243 |
if (iter->item) |
|
1107
|
262 |
0 |
if (iter->tree) { |
|
1108
|
5 |
257 |
if (iter->tree->hashiter == iter) |
|
1119
|
8 |
103 |
if (tree->compare_callback) |
|
1121
|
5 |
106 |
if (tree->hashiter) |
|
1152
|
369 |
5 |
if (node && cmp == 0) { |
|
|
327 |
42 |
if (node && cmp == 0) { |
|
1163
|
2 |
310 |
if (tree->allowed_duplicates) |
|
1166
|
8 |
304 |
if (step) |
|
1175
|
1 |
14 |
if (tree->allowed_duplicates) |
|
1178
|
10 |
5 |
if (step) |
|
1193
|
7 |
0 |
if (node && cmp > 0) |
|
|
2 |
5 |
if (node && cmp > 0) |
|
1199
|
7 |
0 |
if (node && cmp < 0) |
|
|
6 |
1 |
if (node && cmp < 0) |
|
1204
|
3 |
3 |
TREERBXS_INSERT_ITEM_AT_NODE(tree, item, node, cmp); |
|
|
0 |
3 |
TREERBXS_INSERT_ITEM_AT_NODE(tree, item, node, cmp); |
|
|
0 |
6 |
TREERBXS_INSERT_ITEM_AT_NODE(tree, item, node, cmp); |
|
1220
|
500671 |
339 |
if (tree->prev_inserted_trend >= INSERT_TREND_TRIGGER) { |
|
1221
|
470541 |
30130 |
if (tree->prev_inserted_trend > INSERT_TREND_CAP) |
|
1225
|
14 |
500657 |
if (cmp == 0) { |
|
1227
|
1 |
13 |
if (overwrite) { |
|
1228
|
1 |
0 |
if (tree->prev_inserted_dup) { |
|
1231
|
1 |
1 |
&& tree->compare(tree, stack_item, GET_TreeRBXS_item_FROM_rbnode(hint->parent)) == 0) |
|
|
1 |
0 |
&& tree->compare(tree, stack_item, GET_TreeRBXS_item_FROM_rbnode(hint->parent)) == 0) |
|
1237
|
13 |
0 |
} else if (tree->allow_duplicates) |
|
1242
|
500607 |
50 |
else if (cmp > 0) { |
|
1244
|
149791 |
350816 |
if (!tmpnode || tree->compare(tree, stack_item, GET_TreeRBXS_item_FROM_rbnode(tmpnode)) < 0) { |
|
|
134802 |
14989 |
if (!tmpnode || tree->compare(tree, stack_item, GET_TreeRBXS_item_FROM_rbnode(tmpnode)) < 0) { |
|
1252
|
47 |
3 |
if (!tmpnode || tree->compare(tree, stack_item, GET_TreeRBXS_item_FROM_rbnode(tmpnode)) > 0) { |
|
|
9 |
38 |
if (!tmpnode || tree->compare(tree, stack_item, GET_TreeRBXS_item_FROM_rbnode(tmpnode)) > 0) { |
|
1266
|
15271 |
95 |
if (hint && cmp == 0) { |
|
|
15219 |
52 |
if (hint && cmp == 0) { |
|
1267
|
25 |
27 |
if (overwrite) { |
|
1269
|
23 |
2 |
if (tree->allowed_duplicates) { |
|
1271
|
0 |
3 |
if (!rbtree_find_all( |
|
1280
|
6 |
3 |
while (last != first) { |
|
1291
|
23 |
3 |
if (oldval_out) |
|
1297
|
6 |
20 |
if (item->orig_key_stored) { |
|
1300
|
6 |
0 |
if (sv_cmp(orig_key, new_key)) { |
|
1307
|
25 |
1 |
if (tree->track_recent || item->recent.next) |
|
|
0 |
25 |
if (tree->track_recent || item->recent.next) |
|
1310
|
21 |
6 |
} else if (tree->allow_duplicates) { |
|
1316
|
8 |
26 |
if (tree->track_recent) |
|
1322
|
3 |
3 |
if (item == tree->prev_inserted_item) |
|
1330
|
95 |
500849 |
TREERBXS_INSERT_ITEM_AT_NODE(tree, item, hint, cmp); |
|
|
493311 |
7538 |
TREERBXS_INSERT_ITEM_AT_NODE(tree, item, hint, cmp); |
|
|
72 |
500872 |
TREERBXS_INSERT_ITEM_AT_NODE(tree, item, hint, cmp); |
|
1334
|
341 |
500663 |
if (tree->prev_inserted_trend < INSERT_TREND_TRIGGER && tree->prev_inserted_item) { |
|
|
242 |
99 |
if (tree->prev_inserted_trend < INSERT_TREND_TRIGGER && tree->prev_inserted_item) { |
|
1336
|
234 |
8 |
if (item == tree->prev_inserted_item |
|
1337
|
57 |
177 |
|| item->rbnode.parent == &tree->prev_inserted_item->rbnode |
|
1338
|
50 |
7 |
|| item->rbnode.left == &tree->prev_inserted_item->rbnode |
|
1339
|
11 |
39 |
|| item->rbnode.right == &tree->prev_inserted_item->rbnode |
|
1342
|
24 |
15 |
} else if (tree->prev_inserted_trend) |
|
1354
|
110 |
1 |
if (item->recent.next != node_after) { |
|
1355
|
6 |
104 |
if (item->recent.next) { |
|
1368
|
19 |
91 |
if (tree->recent_limit >= 0 && tree->recent_count > tree->recent_limit) |
|
|
14 |
5 |
if (tree->recent_limit >= 0 && tree->recent_count > tree->recent_limit) |
|
1377
|
35 |
0 |
if (item->recent.next) { |
|
1379
|
2 |
33 |
if (item->iter) |
|
1394
|
15 |
0 |
if (lim >= 0 && tree->recent_count > lim) { |
|
|
15 |
0 |
if (lim >= 0 && tree->recent_count > lim) { |
|
1397
|
17 |
15 |
for (i= 0; i < n && cur && cur != &tree->recent; i++) { |
|
|
17 |
0 |
for (i= 0; i < n && cur && cur != &tree->recent; i++) { |
|
|
17 |
0 |
for (i= 0; i < n && cur && cur != &tree->recent; i++) { |
|
1399
|
0 |
17 |
if (nodes_out) |
|
1405
|
0 |
15 |
if (i != n) |
|
1423
|
165671 |
55399 |
return diff < 0? -1 : diff > 0? 1 : 0; /* shrink from IV to int might lose upper bits */ |
|
1429
|
55330 |
165491 |
return diff < 0? -1 : diff > 0? 1 : 0; |
|
1437
|
39507 |
632784 |
return cmp? cmp : alen < blen? -1 : alen > blen? 1 : 0; |
|
|
35663 |
3844 |
return cmp? cmp : alen < blen? -1 : alen > blen? 1 : 0; |
|
1448
|
40307 |
1 |
while (apos < alim && bpos < blim) { |
|
|
40293 |
14 |
while (apos < alim && bpos < blim) { |
|
1450
|
40413 |
4 |
while (apos < alim && bpos < blim && *apos == *bpos && !isdigit(*apos)) |
|
|
40413 |
0 |
while (apos < alim && bpos < blim && *apos == *bpos && !isdigit(*apos)) |
|
|
39920 |
493 |
while (apos < alim && bpos < blim && *apos == *bpos && !isdigit(*apos)) |
|
|
124 |
39796 |
while (apos < alim && bpos < blim && *apos == *bpos && !isdigit(*apos)) |
|
1454
|
40627 |
9 |
while (apos < alim && !isdigit(*apos)) apos++; |
|
|
343 |
40284 |
while (apos < alim && !isdigit(*apos)) apos++; |
|
1456
|
40478 |
9 |
while (bpos < blim && !isdigit(*bpos)) bpos++; |
|
|
194 |
40284 |
while (bpos < blim && !isdigit(*bpos)) bpos++; |
|
1460
|
40211 |
82 |
if (alen || blen) { |
|
|
10 |
40201 |
if (alen || blen) { |
|
1463
|
10 |
82 |
if (alen == 0) return -1; |
|
1464
|
46 |
36 |
if (blen == 0) return 1; |
|
1467
|
0 |
36 |
if (a_utf8 != b_utf8) { |
|
1469
|
0 |
0 |
: bytes_cmp_utf8((const U8*) amark, alen, (const U8*) bmark, blen); |
|
1470
|
0 |
0 |
if (cmp) return cmp; |
|
1475
|
36 |
0 |
if (cmp) return cmp; |
|
1476
|
0 |
0 |
if (alen < blen) return -1; |
|
1477
|
0 |
0 |
if (alen > blen) return -1; |
|
1481
|
40197 |
4 |
if (!(apos < alim && bpos < blim)) break; |
|
|
40197 |
0 |
if (!(apos < alim && bpos < blim)) break; |
|
1484
|
40387 |
0 |
while (apos < alim && *apos == '0') apos++; |
|
|
190 |
40197 |
while (apos < alim && *apos == '0') apos++; |
|
1485
|
40325 |
0 |
while (bpos < blim && *bpos == '0') bpos++; |
|
|
128 |
40197 |
while (bpos < blim && *bpos == '0') bpos++; |
|
1489
|
147627 |
2 |
while (apos < alim && bpos < blim && *apos == *bpos && isdigit(*apos)) |
|
|
147613 |
14 |
while (apos < alim && bpos < blim && *apos == *bpos && isdigit(*apos)) |
|
|
107472 |
40141 |
while (apos < alim && bpos < blim && *apos == *bpos && isdigit(*apos)) |
|
|
107432 |
40 |
while (apos < alim && bpos < blim && *apos == *bpos && isdigit(*apos)) |
|
1493
|
40195 |
2 |
if ((apos < alim && isdigit(*apos)) || (bpos < blim && isdigit(*bpos))) { |
|
|
59 |
40136 |
if ((apos < alim && isdigit(*apos)) || (bpos < blim && isdigit(*bpos))) { |
|
|
47 |
14 |
if ((apos < alim && isdigit(*apos)) || (bpos < blim && isdigit(*bpos))) { |
|
|
6 |
41 |
if ((apos < alim && isdigit(*apos)) || (bpos < blim && isdigit(*bpos))) { |
|
1494
|
1 |
40141 |
if (apos == alim) return -1; |
|
1495
|
0 |
40141 |
if (bpos == blim) return 1; |
|
1499
|
48642 |
40018 |
while (apos < alim && isdigit(*apos)) apos++; |
|
|
48519 |
123 |
while (apos < alim && isdigit(*apos)) apos++; |
|
1500
|
48606 |
40039 |
while (bpos < blim && isdigit(*bpos)) bpos++; |
|
|
48504 |
102 |
while (bpos < blim && isdigit(*bpos)) bpos++; |
|
1504
|
52 |
40089 |
if (alen < blen) return -1; |
|
1505
|
67 |
40022 |
if (alen > blen) return 1; |
|
1512
|
1 |
18 |
if (bpos < blim) return -1; |
|
1513
|
14 |
4 |
if (apos < alim) return 1; |
|
1568
|
0 |
221372 |
PUSHMARK(SP); |
|
1569
|
0 |
221372 |
EXTEND(SP, 2); |
|
1573
|
0 |
221372 |
if (call_sv(tree->compare_callback, G_SCALAR) != 1) |
|
1580
|
166015 |
55357 |
return (int)(ret < 0? -1 : ret > 0? 1 : 0); |
|
1593
|
0 |
20079 |
PUSHMARK(SP); |
|
1594
|
0 |
20079 |
XPUSHs(orig_key); |
|
1616
|
111 |
0 |
if (mg->mg_ptr) { |
|
1626
|
203 |
0 |
if (mg->mg_ptr) { |
|
1635
|
257 |
0 |
if (mg->mg_ptr) |
|
1660
|
0 |
501531 |
if (!sv_isobject(obj)) { |
|
1661
|
0 |
0 |
if (flags & OR_DIE) |
|
1666
|
501420 |
111 |
if (SvMAGICAL(sv) && (magic= mg_findext(sv, PERL_MAGIC_ext, &TreeRBXS_magic_vt))) |
|
|
501420 |
0 |
if (SvMAGICAL(sv) && (magic= mg_findext(sv, PERL_MAGIC_ext, &TreeRBXS_magic_vt))) |
|
1669
|
111 |
0 |
if (flags & AUTOCREATE) { |
|
1678
|
0 |
0 |
else if (flags & OR_DIE) |
|
1689
|
34 |
694 |
if (!sv_isobject(obj)) { |
|
1690
|
0 |
34 |
if (flags & OR_DIE) |
|
1695
|
694 |
0 |
if (SvMAGICAL(sv) && (magic= mg_findext(sv, PERL_MAGIC_ext, &TreeRBXS_item_magic_vt))) |
|
|
452 |
242 |
if (SvMAGICAL(sv) && (magic= mg_findext(sv, PERL_MAGIC_ext, &TreeRBXS_item_magic_vt))) |
|
1698
|
0 |
242 |
if (flags & OR_DIE) |
|
1710
|
75 |
221 |
if (!item) |
|
1713
|
21 |
200 |
if (item->owner) |
|
1729
|
24 |
902 |
if (!item) |
|
1731
|
159 |
743 |
if (item->orig_key_stored) { |
|
1781
|
0 |
2210 |
if (!sv_isobject(obj)) { |
|
1782
|
0 |
0 |
if (flags & OR_DIE) |
|
1787
|
2210 |
0 |
if (SvMAGICAL(sv) && (magic= mg_findext(sv, PERL_MAGIC_ext, &TreeRBXS_iter_magic_vt))) |
|
|
1696 |
514 |
if (SvMAGICAL(sv) && (magic= mg_findext(sv, PERL_MAGIC_ext, &TreeRBXS_iter_magic_vt))) |
|
1790
|
257 |
257 |
if (flags & AUTOCREATE) { |
|
1799
|
0 |
257 |
else if (flags & OR_DIE) |
|
1808
|
65 |
0 |
if (!(method_gv= gv_fetchmethod(stash, name)) |
|
1809
|
0 |
65 |
|| !(method_cv= GvCV(method_gv))) |
|
1816
|
348 |
0 |
SvUPGRADE(name, SVt_PVNV); |
|
1830
|
39 |
0 |
if (array && SvTYPE(array) == SVt_PVAV) |
|
|
3 |
36 |
if (array && SvTYPE(array) == SVt_PVAV) |
|
1832
|
36 |
0 |
else if (array && SvROK(array) && SvTYPE(SvRV(array)) == SVt_PVAV) |
|
|
36 |
0 |
else if (array && SvROK(array) && SvTYPE(SvRV(array)) == SVt_PVAV) |
|
|
36 |
0 |
else if (array && SvROK(array) && SvTYPE(SvRV(array)) == SVt_PVAV) |
|
1839
|
1 |
38 |
if (!vec) { |
|
1840
|
0 |
1 |
if (n == 0) /* don't return a NULL for an empty array, but doesn't need to be a real pointer */ |
|
1845
|
0 |
1 |
Newx(vec, n, SV*); |
|
1847
|
10 |
1 |
for (i= 0; i < n; i++) { |
|
1849
|
10 |
0 |
vec[i]= el? *el : NULL; |
|
1853
|
39 |
0 |
if (len) *len= n; |
|
1886
|
138 |
111 |
for (i= out_i= 0; i < attr_list_len; i += 2) { |
|
1891
|
0 |
138 |
if (i + 1 == attr_list_len) |
|
1894
|
0 |
138 |
if (!SvOK(val)) |
|
1897
|
27 |
0 |
case 2: if (strcmp("kv", attrname) == 0) { kv_sv= val; break; } |
|
1899
|
5 |
0 |
case 4: if (strcmp("keys", attrname) == 0) { keys_sv= val; break; } |
|
1901
|
2 |
1 |
case 6: if (strcmp("values", attrname) == 0) { values_sv= val; break; } |
|
1902
|
1 |
0 |
else if (strcmp("recent", attrname) == 0) { recent_sv= val; break; } |
|
1904
|
24 |
0 |
case 8: if (strcmp("key_type", attrname) == 0) { key_type_sv= val; break; } |
|
1905
|
0 |
0 |
else if (strcmp("hashiter", attrname) == 0) { hashiter_sv= val; break; } |
|
1907
|
56 |
0 |
case 10: if (strcmp("compare_fn", attrname) == 0) { compare_fn_sv= val; break; } |
|
1909
|
9 |
1 |
case 12: if (strcmp("track_recent", attrname) == 0) { tree->track_recent= val && SvTRUE(val); break; } |
|
|
9 |
0 |
case 12: if (strcmp("track_recent", attrname) == 0) { tree->track_recent= val && SvTRUE(val); break; } |
|
|
9 |
0 |
case 12: if (strcmp("track_recent", attrname) == 0) { tree->track_recent= val && SvTRUE(val); break; } |
|
1910
|
1 |
0 |
else if (strcmp("recent_limit", attrname) == 0) { |
|
1911
|
1 |
0 |
tree->recent_limit= val && SvOK(val) && SvIV(val) >= 0? SvIV(val) : -1; |
|
|
1 |
0 |
tree->recent_limit= val && SvOK(val) && SvIV(val) >= 0? SvIV(val) : -1; |
|
|
1 |
0 |
tree->recent_limit= val && SvOK(val) && SvIV(val) >= 0? SvIV(val) : -1; |
|
1915
|
0 |
0 |
case 15: if (strcmp("compat_list_get", attrname) == 0) { tree->compat_list_get= val && SvTRUE(val); break; } |
|
|
0 |
0 |
case 15: if (strcmp("compat_list_get", attrname) == 0) { tree->compat_list_get= val && SvTRUE(val); break; } |
|
|
0 |
0 |
case 15: if (strcmp("compat_list_get", attrname) == 0) { tree->compat_list_get= val && SvTRUE(val); break; } |
|
1917
|
10 |
0 |
case 16: if (strcmp("allow_duplicates", attrname) == 0) { tree->allow_duplicates= val && SvTRUE(val); break; } |
|
|
10 |
0 |
case 16: if (strcmp("allow_duplicates", attrname) == 0) { tree->allow_duplicates= val && SvTRUE(val); break; } |
|
|
10 |
0 |
case 16: if (strcmp("allow_duplicates", attrname) == 0) { tree->allow_duplicates= val && SvTRUE(val); break; } |
|
1919
|
3 |
0 |
case 20: if (strcmp("keys_in_recent_order", attrname) == 0) { tree->keys_in_recent_order= val && SvTRUE(val); break; } |
|
|
3 |
0 |
case 20: if (strcmp("keys_in_recent_order", attrname) == 0) { tree->keys_in_recent_order= val && SvTRUE(val); break; } |
|
|
3 |
0 |
case 20: if (strcmp("keys_in_recent_order", attrname) == 0) { tree->keys_in_recent_order= val && SvTRUE(val); break; } |
|
1921
|
0 |
0 |
case 21: if (strcmp("lookup_updates_recent", attrname) == 0) { tree->lookup_updates_recent= val && SvTRUE(val); break; } |
|
|
0 |
0 |
case 21: if (strcmp("lookup_updates_recent", attrname) == 0) { tree->lookup_updates_recent= val && SvTRUE(val); break; } |
|
|
0 |
0 |
case 21: if (strcmp("lookup_updates_recent", attrname) == 0) { tree->lookup_updates_recent= val && SvTRUE(val); break; } |
|
1925
|
0 |
0 |
if (i > out_i) { |
|
1934
|
24 |
87 |
if (key_type_sv) { |
|
1936
|
0 |
24 |
if (key_type < 0) |
|
1942
|
56 |
55 |
if (compare_fn_sv) { |
|
1944
|
0 |
56 |
if (cmp_id < 0) |
|
1947
|
21 |
34 |
} else if (key_type_sv) { |
|
1950
|
10 |
11 |
: key_type == KEY_TYPE_FLOAT? CMP_FLOAT |
|
1951
|
7 |
3 |
: key_type == KEY_TYPE_BSTR? CMP_MEMCMP |
|
1952
|
4 |
3 |
: key_type == KEY_TYPE_USTR? CMP_STR |
|
1953
|
2 |
2 |
: key_type == KEY_TYPE_ANY? CMP_PERL /* use Perl's cmp operator */ |
|
1960
|
8 |
0 |
if (!compare_fn_sv || !SvRV(compare_fn_sv) || SvTYPE(SvRV(compare_fn_sv)) != SVt_PVCV) |
|
|
8 |
0 |
if (!compare_fn_sv || !SvRV(compare_fn_sv) || SvTYPE(SvRV(compare_fn_sv)) != SVt_PVCV) |
|
|
0 |
8 |
if (!compare_fn_sv || !SvRV(compare_fn_sv) || SvTYPE(SvRV(compare_fn_sv)) != SVt_PVCV) |
|
1964
|
8 |
0 |
if (key_type != KEY_TYPE_CLAIM) tree->key_type= KEY_TYPE_ANY; |
|
1974
|
37 |
1 |
if (key_type != KEY_TYPE_CLAIM) tree->key_type= KEY_TYPE_ANY; |
|
1995
|
4 |
1 |
if (key_type != KEY_TYPE_USTR && key_type != KEY_TYPE_ANY && key_type != KEY_TYPE_CLAIM) |
|
|
1 |
3 |
if (key_type != KEY_TYPE_USTR && key_type != KEY_TYPE_ANY && key_type != KEY_TYPE_CLAIM) |
|
|
1 |
0 |
if (key_type != KEY_TYPE_USTR && key_type != KEY_TYPE_ANY && key_type != KEY_TYPE_CLAIM) |
|
2004
|
84 |
27 |
if (kv_sv || keys_sv || values_sv) { |
|
|
79 |
5 |
if (kv_sv || keys_sv || values_sv) { |
|
|
0 |
79 |
if (kv_sv || keys_sv || values_sv) { |
|
2009
|
27 |
5 |
if (kv_sv) { |
|
2010
|
27 |
0 |
if (keys_sv || values_sv) |
|
|
0 |
27 |
if (keys_sv || values_sv) |
|
2012
|
0 |
27 |
if (!(key_vec= unwrap_array(kv_sv, &num_kv))) |
|
2014
|
0 |
27 |
if (num_kv & 1) |
|
2020
|
5 |
27 |
if (keys_sv) { |
|
2021
|
0 |
5 |
if (!(key_vec= unwrap_array(keys_sv, &num_kv))) |
|
2025
|
2 |
30 |
if (values_sv) { |
|
2027
|
0 |
2 |
if (!key_vec) |
|
2029
|
0 |
2 |
if (!(val_vec= unwrap_array(values_sv, &nvals))) |
|
2031
|
0 |
2 |
if (nvals != num_kv) |
|
2036
|
1 |
31 |
if (recent_sv) |
|
2038
|
154 |
32 |
for (key_lim= key_vec + num_kv * key_step; key_vec < key_lim; key_vec += key_step, val_vec += val_step) { |
|
2039
|
136 |
18 |
TreeRBXS_init_tmp_item(&stack_item, tree, (*key_vec? *key_vec : &PL_sv_undef), (val_vec? *val_vec : &PL_sv_undef)); |
|
|
154 |
0 |
TreeRBXS_init_tmp_item(&stack_item, tree, (*key_vec? *key_vec : &PL_sv_undef), (val_vec? *val_vec : &PL_sv_undef)); |
|
2048
|
1 |
110 |
if (recent_sv) { |
|
2051
|
0 |
1 |
if (!rvec) croak("'recent' must be an arrayref"); |
|
2052
|
23 |
1 |
for (i= 0; i < n; i++) { |
|
2053
|
0 |
23 |
if (!looks_like_integer(rvec[i])) |
|
2056
|
23 |
0 |
if (idx < 0 || idx >= nodecount) |
|
|
0 |
23 |
if (idx < 0 || idx >= nodecount) |
|
2059
|
0 |
23 |
if (!node) croak("BUG: access node[idx]"); |
|
2065
|
0 |
111 |
if (hashiter_sv) { |
|
2068
|
0 |
0 |
if (!looks_like_integer(hashiter_sv)) |
|
2071
|
0 |
0 |
if (idx < 0 || idx >= nodecount) |
|
|
0 |
0 |
if (idx < 0 || idx >= nodecount) |
|
2074
|
0 |
0 |
if (!node) croak("BUG: access node[idx]"); |
|
2085
|
7 |
0 |
if (!version || !SvOK(version)) |
|
|
0 |
7 |
if (!version || !SvOK(version)) |
|
2108
|
0 |
108 |
if (sv_isobject(obj_or_pkg) && SvTYPE(SvRV(obj_or_pkg)) == SVt_PVHV) { |
|
|
0 |
0 |
if (sv_isobject(obj_or_pkg) && SvTYPE(SvRV(obj_or_pkg)) == SVt_PVHV) { |
|
2112
|
108 |
0 |
else if (SvPOK(obj_or_pkg) && (pkg= gv_stashsv(obj_or_pkg, 0))) { |
|
|
108 |
0 |
else if (SvPOK(obj_or_pkg) && (pkg= gv_stashsv(obj_or_pkg, 0))) { |
|
2113
|
0 |
108 |
if (!sv_derived_from(obj_or_pkg, "Tree::RB::XS")) |
|
2121
|
0 |
0 |
croak("%s: first arg must be package name or blessed object", ix == 1? "_init_tree":"new"); |
|
2124
|
4 |
104 |
if (items == 2) { |
|
2127
|
1 |
3 |
if (!SvROK(first) || SvTYPE(SvRV(first)) == SVt_PVCV) { |
|
|
0 |
1 |
if (!SvROK(first) || SvTYPE(SvRV(first)) == SVt_PVCV) { |
|
2134
|
1 |
0 |
else if (SvTYPE(SvRV(first)) == SVt_PVHV) { |
|
2139
|
0 |
1 |
Newx(attr_list, attr_len, SV*); |
|
2142
|
3 |
1 |
while ((ent= hv_iternext(attrhv)) && i < attr_len) { |
|
|
3 |
0 |
while ((ent= hv_iternext(attrhv)) && i < attr_len) { |
|
2155
|
0 |
108 |
if (tree->owner != (SV*) obj_hv) |
|
2159
|
0 |
108 |
if (n_unknown) { |
|
2161
|
0 |
0 |
if (ix == 0) |
|
2164
|
0 |
0 |
if (attr_list != PL_stack_base+ax+1) { |
|
2165
|
0 |
0 |
EXTEND(SP, n_unknown); |
|
|
0 |
0 |
EXTEND(SP, n_unknown); |
|
2166
|
0 |
0 |
for (i= 0; i < n_unknown; i++) |
|
2170
|
0 |
108 |
i= ix == 0? 1 : n_unknown; |
|
2197
|
0 |
4 |
while ((pos= hv_iternext(treehv))) { |
|
2201
|
0 |
4 |
if (tree->recent_limit >= 0) { |
|
2207
|
2 |
2 |
if (nodecount) { |
|
2233
|
34 |
2 |
for (i= 0; i < nodecount && node; i++, node=rbtree_node_next(node)) { |
|
|
34 |
0 |
for (i= 0; i < nodecount && node; i++, node=rbtree_node_next(node)) { |
|
2255
|
0 |
2 |
if (i < nodecount) croak("BUG: too few nodes in tree"); |
|
2256
|
0 |
2 |
if (node) croak("BUG: too many nodes in tree"); |
|
2267
|
1 |
1 |
if (tree->recent_count) { |
|
2273
|
23 |
1 |
for (i= tree->recent_count; i > 0 && pos != root; --i, pos= pos->next) { |
|
|
23 |
0 |
for (i= tree->recent_count; i > 0 && pos != root; --i, pos= pos->next) { |
|
2278
|
0 |
1 |
if (i != 0) croak("BUG: too few recent-tracked nodes"); |
|
2279
|
0 |
1 |
if (pos != root) croak("BUG: too many recent-tracked nodes"); |
|
2282
|
0 |
2 |
if (tree->hashiter && tree->hashiter->item) { |
|
|
0 |
0 |
if (tree->hashiter && tree->hashiter->item) { |
|
2286
|
0 |
0 |
if (pointing_at) { |
|
2296
|
2 |
2 |
if (cmp_id == CMP_SUB) { |
|
2297
|
0 |
2 |
if (!cloning) |
|
2305
|
2 |
0 |
if (!stash || !name || !(re_gv= gv_fetchmethod(stash, name)) || GvCV(re_gv) != cv) |
|
|
2 |
0 |
if (!stash || !name || !(re_gv= gv_fetchmethod(stash, name)) || GvCV(re_gv) != cv) |
|
|
1 |
1 |
if (!stash || !name || !(re_gv= gv_fetchmethod(stash, name)) || GvCV(re_gv) != cv) |
|
|
0 |
1 |
if (!stash || !name || !(re_gv= gv_fetchmethod(stash, name)) || GvCV(re_gv) != cv) |
|
2306
|
1 |
0 |
croak("Comparison function (%s::%s) for Tree::RB::XS instance cannot be serialized unless it exists as a global package function", |
|
|
1 |
0 |
croak("Comparison function (%s::%s) for Tree::RB::XS instance cannot be serialized unless it exists as a global package function", |
|
|
1 |
0 |
croak("Comparison function (%s::%s) for Tree::RB::XS instance cannot be serialized unless it exists as a global package function", |
|
|
1 |
0 |
croak("Comparison function (%s::%s) for Tree::RB::XS instance cannot be serialized unless it exists as a global package function", |
|
|
0 |
1 |
croak("Comparison function (%s::%s) for Tree::RB::XS instance cannot be serialized unless it exists as a global package function", |
|
|
0 |
0 |
croak("Comparison function (%s::%s) for Tree::RB::XS instance cannot be serialized unless it exists as a global package function", |
|
|
1 |
0 |
croak("Comparison function (%s::%s) for Tree::RB::XS instance cannot be serialized unless it exists as a global package function", |
|
|
0 |
1 |
croak("Comparison function (%s::%s) for Tree::RB::XS instance cannot be serialized unless it exists as a global package function", |
|
2311
|
1 |
0 |
av_push(attrs, newSVpvf("%s::%s", HvNAME(stash), name)); |
|
|
1 |
0 |
av_push(attrs, newSVpvf("%s::%s", HvNAME(stash), name)); |
|
|
0 |
1 |
av_push(attrs, newSVpvf("%s::%s", HvNAME(stash), name)); |
|
|
0 |
0 |
av_push(attrs, newSVpvf("%s::%s", HvNAME(stash), name)); |
|
|
1 |
0 |
av_push(attrs, newSVpvf("%s::%s", HvNAME(stash), name)); |
|
|
0 |
1 |
av_push(attrs, newSVpvf("%s::%s", HvNAME(stash), name)); |
|
2315
|
0 |
3 |
if (version < 0 || version > 0x7FFFFFFF) |
|
2321
|
3 |
0 |
if (key_type < 1 || key_type > 255) |
|
|
0 |
3 |
if (key_type < 1 || key_type > 255) |
|
2325
|
3 |
0 |
if (cmp_id < 1 || cmp_id > 255) |
|
|
0 |
3 |
if (cmp_id < 1 || cmp_id > 255) |
|
2330
|
0 |
3 |
| (tree->compat_list_get? 2 : 0) |
|
2331
|
1 |
2 |
| (tree->track_recent? 4 : 0) |
|
2332
|
0 |
3 |
| (tree->lookup_updates_recent? 8 : 0) |
|
2333
|
0 |
3 |
| (tree->keys_in_recent_order? 0x10 : 0); |
|
2337
|
0 |
3 |
EXTEND(SP, 2); |
|
2356
|
3 |
0 |
if (!SvROK(objref) || SvTYPE(SvRV(objref)) != SVt_PVHV) |
|
|
0 |
3 |
if (!SvROK(objref) || SvTYPE(SvRV(objref)) != SVt_PVHV) |
|
2359
|
0 |
3 |
if (tree->owner != SvRV(objref)) |
|
2364
|
0 |
3 |
if (sb_len < 10) |
|
2371
|
0 |
3 |
if (version <= 0) |
|
2373
|
0 |
3 |
if (version > get_integer_version()) |
|
2383
|
3 |
0 |
if (key_type <= 0 || key_type > KEY_TYPE_MAX) |
|
|
0 |
3 |
if (key_type <= 0 || key_type > KEY_TYPE_MAX) |
|
2387
|
3 |
0 |
if (cmp_id <= 0 || cmp_id > CMP_MAX) |
|
|
0 |
3 |
if (cmp_id <= 0 || cmp_id > CMP_MAX) |
|
2391
|
3 |
0 |
if (cmp_id == CMP_FOLDCASE || cmp_id == CMP_NUMSPLIT_FOLDCASE) |
|
|
0 |
3 |
if (cmp_id == CMP_FOLDCASE || cmp_id == CMP_NUMSPLIT_FOLDCASE) |
|
2395
|
0 |
3 |
Newx(attr_list, attr_len, SV*); |
|
2400
|
1 |
2 |
if (cmp_id == CMP_SUB) { |
|
2401
|
0 |
1 |
if (!cloning) croak("compare_fn lookup is forbidden unless cloning"); |
|
2403
|
1 |
0 |
for (i= attr_len-2; i >= 0; i-= 2) { |
|
2404
|
1 |
0 |
if (strcmp(SvPV_nolen(attr_list[i]), "compare_fn") == 0) { |
|
2407
|
1 |
0 |
if (gv && GvCV(gv)) |
|
|
1 |
0 |
if (gv && GvCV(gv)) |
|
2414
|
0 |
1 |
if (i < 0) |
|
2419
|
0 |
3 |
if (n_unknown) { |
|
2422
|
0 |
0 |
for (i= 0; i < n_unknown-1; i += 2) |
|
2423
|
0 |
0 |
if (!hv_store_ent(obj, attr_list[i], (tmpsv= newSVsv(attr_list[i+1])), 0)) |
|
2445
|
2 |
16 |
: sv_2mortal(new_enum_dualvar(aTHX_ id, newSVpv(get_cmp_name(id), 0))); |
|
2453
|
4 |
11 |
if (items > 1) { |
|
2466
|
0 |
2 |
if (items > 1) { |
|
2470
|
0 |
2 |
ST(0)= tree->compat_list_get? &PL_sv_yes : &PL_sv_no; |
|
2479
|
0 |
2 |
if (items > 1) { |
|
2483
|
2 |
0 |
ST(0)= tree->track_recent? &PL_sv_yes : &PL_sv_no; |
|
2492
|
1 |
2 |
if (items > 1) { |
|
2496
|
0 |
2 |
ST(0)= tree->lookup_updates_recent? &PL_sv_yes : &PL_sv_no; |
|
2505
|
1 |
0 |
if (items > 1) { |
|
2509
|
0 |
0 |
ST(0)= tree->keys_in_recent_order? &PL_sv_yes : &PL_sv_no; |
|
2517
|
0 |
56 |
RETVAL= TreeRBXS_get_count(tree); |
|
2525
|
0 |
9 |
RETVAL= tree->recent_count; |
|
2534
|
2 |
2 |
if (newval) { |
|
2535
|
1 |
1 |
if (!SvOK(newval)) { |
|
2537
|
1 |
0 |
} else if (!looks_like_number(newval) || SvIV(newval) < 0) { |
|
|
0 |
1 |
} else if (!looks_like_number(newval) || SvIV(newval) < 0) { |
|
2546
|
1 |
1 |
: sv_2mortal(newSViv(tree->recent_limit)); |
|
2554
|
0 |
1 |
EXTEND(SP, 5); |
|
2575
|
0 |
500341 |
if (!SvOK(key)) |
|
2579
|
100132 |
1 |
ST(0)= ix == 0? sv_2mortal(newSViv(inserted? rbtree_node_index(&inserted->rbnode) : -1)) |
|
2580
|
100133 |
400208 |
: ix == 1? (oldval? oldval : &PL_sv_undef) |
|
|
17 |
400185 |
: ix == 1? (oldval? oldval : &PL_sv_undef) |
|
2581
|
400202 |
6 |
: (inserted? sv_2mortal(TreeRBXS_wrap_item(inserted)) : &PL_sv_undef); |
|
|
4 |
2 |
: (inserted? sv_2mortal(TreeRBXS_wrap_item(inserted)) : &PL_sv_undef); |
|
2596
|
0 |
4 |
if (items == 2 && SvROK(ST(1)) && SvTYPE(SvRV(ST(1))) == SVt_PVAV && !sv_isobject(ST(1))) { |
|
|
0 |
0 |
if (items == 2 && SvROK(ST(1)) && SvTYPE(SvRV(ST(1))) == SVt_PVAV && !sv_isobject(ST(1))) { |
|
|
0 |
0 |
if (items == 2 && SvROK(ST(1)) && SvTYPE(SvRV(ST(1))) == SVt_PVAV && !sv_isobject(ST(1))) { |
|
|
0 |
0 |
if (items == 2 && SvROK(ST(1)) && SvTYPE(SvRV(ST(1))) == SVt_PVAV && !sv_isobject(ST(1))) { |
|
2605
|
515 |
4 |
while (i < lim) { |
|
2608
|
0 |
515 |
if (av) { |
|
2610
|
0 |
0 |
if (!el) croak("Tree->insert_multi does not support tied or sparse arrays"); |
|
2613
|
0 |
0 |
if (i < lim) { |
|
2615
|
0 |
0 |
if (!el) croak("Tree->insert_multi does not support tied or sparse arrays"); |
|
2621
|
515 |
0 |
if (++i < lim) { |
|
2626
|
0 |
515 |
if (!SvOK(key)) |
|
2633
|
5 |
510 |
if (ix == 0? (inserted != NULL) : (oldval == NULL)) |
|
|
507 |
8 |
if (ix == 0? (inserted != NULL) : (oldval == NULL)) |
|
2636
|
0 |
4 |
RETVAL= added; |
|
2653
|
4 |
4 |
for (i= 1; i < items; i++) { |
|
2656
|
1 |
3 |
if (tree->allowed_duplicates) { |
|
2671
|
2 |
1 |
if (node && cmp == 0) |
|
|
2 |
0 |
if (node && cmp == 0) |
|
2675
|
0 |
4 |
RETVAL= total; |
|
2706
|
0 |
368 |
if (!SvOK(key)) |
|
2709
|
6 |
362 |
if (ix >> 4) { |
|
2712
|
0 |
6 |
if (mode_sv) |
|
2715
|
61 |
301 |
mode= mode_sv? parse_lookup_mode(mode_sv) : GET_EQ; |
|
2716
|
0 |
362 |
if (mode < 0) |
|
2721
|
249 |
119 |
if (ix >= 3) |
|
2722
|
24 |
225 |
ix= (GIMME_V == G_SCALAR || (ix == 4 && !tree->compat_list_get))? 2 : 3; |
|
|
3 |
21 |
ix= (GIMME_V == G_SCALAR || (ix == 4 && !tree->compat_list_get))? 2 : 3; |
|
|
3 |
0 |
ix= (GIMME_V == G_SCALAR || (ix == 4 && !tree->compat_list_get))? 2 : 3; |
|
2732
|
337 |
31 |
if (item) { |
|
2733
|
1 |
336 |
if (tree->lookup_updates_recent) |
|
2735
|
0 |
337 |
if (GIMME_V == G_VOID) |
|
2737
|
48 |
289 |
else if (ix <= 1) { |
|
2738
|
38 |
10 |
if (ix == 0) { // return node |
|
2745
|
273 |
16 |
} else if (ix == 2) { // return value |
|
2768
|
0 |
1 |
if (!SvOK(key)) |
|
2771
|
1 |
0 |
if (rbtree_find_all( |
|
2778
|
0 |
1 |
EXTEND(SP, count); |
|
2779
|
6 |
1 |
for (i= 0; i < count; i++) { |
|
2782
|
0 |
6 |
if (tree->lookup_updates_recent) |
|
2800
|
0 |
24 |
if (!SvOK(key1)) |
|
2803
|
0 |
24 |
if ((item= TreeRBXS_get_magic_item(key1, 0))) { |
|
2804
|
0 |
0 |
if (!TreeRBXS_is_member(tree, item)) |
|
2809
|
21 |
3 |
if (rbtree_find_all( |
|
2816
|
1 |
20 |
if (key2) |
|
2822
|
2 |
1 |
if (key2) { |
|
2830
|
3 |
21 |
if (key2 && first) { |
|
|
3 |
0 |
if (key2 && first) { |
|
2831
|
0 |
3 |
if ((item= TreeRBXS_get_magic_item(key2, 0))) { |
|
2832
|
0 |
0 |
if (!TreeRBXS_is_member(tree, item)) |
|
2837
|
2 |
1 |
if (rbtree_find_all( |
|
2851
|
3 |
0 |
if (last && rbtree_node_index(first) > rbtree_node_index(last)) |
|
|
1 |
2 |
if (last && rbtree_node_index(first) > rbtree_node_index(last)) |
|
2856
|
24 |
0 |
if (first && last) { |
|
|
22 |
2 |
if (first && last) { |
|
2859
|
3 |
22 |
first= (first == last)? NULL : rbtree_node_next(first); |
|
2862
|
3 |
22 |
} while (first); |
|
2864
|
6 |
18 |
RETVAL= i; |
|
2881
|
33 |
23 |
for (i= 1; i < items; i++) { |
|
2884
|
0 |
33 |
if (++i >= items) |
|
2889
|
3 |
0 |
case 'a': if (strncmp(opt_name, "max", len) == 0) { max_sv= ST(i); continue; } |
|
2890
|
7 |
0 |
case 'i': if (strncmp(opt_name, "min", len) == 0) { min_sv= ST(i); continue; } |
|
2894
|
23 |
0 |
if (strncmp(opt_name, "offset", len) == 0) { offset_sv= ST(i); continue; } |
|
2899
|
1 |
22 |
if (!TreeRBXS_get_count(tree)) |
|
2902
|
7 |
15 |
if (min_sv) { |
|
2904
|
6 |
1 |
if (!min_item) { |
|
2906
|
1 |
5 |
if (SvROK(min_sv) && (it= TreeRBXS_get_magic_iter(min_sv, 0))) { |
|
|
1 |
0 |
if (SvROK(min_sv) && (it= TreeRBXS_get_magic_iter(min_sv, 0))) { |
|
2908
|
0 |
1 |
if (!min_item) croak("Iterator for 'min' is not referencing a tree node"); |
|
2917
|
3 |
19 |
if (max_sv) { |
|
2919
|
2 |
1 |
if (!max_item) { |
|
2921
|
1 |
1 |
if (SvROK(max_sv) && (it= TreeRBXS_get_magic_iter(max_sv, 0))) { |
|
|
1 |
0 |
if (SvROK(max_sv) && (it= TreeRBXS_get_magic_iter(max_sv, 0))) { |
|
2923
|
0 |
1 |
if (!max_item) croak("Iterator for 'max' is not referencing a tree node"); |
|
2932
|
22 |
0 |
if (offset_sv) { |
|
2942
|
18 |
4 |
if (tree->key_type == KEY_TYPE_INT) { |
|
2945
|
1 |
17 |
if (SvUOK(offset_sv) && SvUV(offset_sv) > IV_MAX) |
|
|
1 |
0 |
if (SvUOK(offset_sv) && SvUV(offset_sv) > IV_MAX) |
|
2948
|
0 |
17 |
if (offset_iv == 0) |
|
2953
|
11 |
6 |
if (positive) { |
|
2954
|
3 |
8 |
IV max_key= (max_item? max_item : last_item)->keyunion.ikey; |
|
2955
|
1 |
10 |
if (IV_MAX - offset_iv < max_key) |
|
2958
|
3 |
3 |
IV min_key= (min_item? min_item : first_item)->keyunion.ikey; |
|
2959
|
1 |
5 |
if (IV_MIN - offset_iv > min_key) |
|
2963
|
2 |
2 |
else if (tree->key_type == KEY_TYPE_FLOAT) { |
|
2965
|
0 |
2 |
if (offset_nv == 0.0) |
|
2978
|
12 |
5 |
edge_item= positive? max_item : min_item; |
|
2979
|
6 |
11 |
if (edge_item && (boundary_node= node_seek[positive](&edge_item->rbnode))) { |
|
|
4 |
2 |
if (edge_item && (boundary_node= node_seek[positive](&edge_item->rbnode))) { |
|
2984
|
1 |
0 |
*final_item= (positive? (min_item? min_item : first_item) |
|
2985
|
1 |
3 |
: (max_item? max_item : last_item)), |
|
|
0 |
3 |
: (max_item? max_item : last_item)), |
|
2989
|
9 |
0 |
if (intmode) { |
|
2991
|
1 |
8 |
if (positive? (newval < boundary_item->keyunion.ikey) |
|
|
4 |
5 |
if (positive? (newval < boundary_item->keyunion.ikey) |
|
2997
|
0 |
0 |
if (positive? (newval < boundary_item->keyunion.nkey) |
|
|
0 |
0 |
if (positive? (newval < boundary_item->keyunion.nkey) |
|
3027
|
5 |
0 |
if (intmode) edge_item->keyunion.ikey= stack_item.keyunion.ikey; |
|
3029
|
1 |
4 |
if (found_identical) { |
|
3033
|
1 |
0 |
if (!tree->allow_duplicates) { |
|
3037
|
0 |
1 |
node= (node == search[1])? NULL : rbtree_node_next(node); |
|
3038
|
1 |
0 |
if (item != edge_item) |
|
3040
|
0 |
1 |
} while (node); |
|
3045
|
3 |
1 |
else if (search[0]) |
|
3049
|
5 |
0 |
if (!next || edge_item == final_item) |
|
|
0 |
5 |
if (!next || edge_item == final_item) |
|
3058
|
1 |
3 |
*(positive? &max_item : &min_item)= edge_item; |
|
3061
|
7 |
10 |
rbtree_node_t *node= min_item? &min_item->rbnode : &first_item->rbnode; |
|
3062
|
3 |
14 |
rbtree_node_t *end= max_item? &max_item->rbnode : &last_item->rbnode; |
|
3064
|
36 |
5 |
if (intmode) |
|
3068
|
17 |
24 |
if (node == end) break; |
|
3088
|
0 |
0 |
bool keep= !(GIMME_V == G_VOID || GIMME_V == G_SCALAR); |
|
|
0 |
0 |
bool keep= !(GIMME_V == G_VOID || GIMME_V == G_SCALAR); |
|
3092
|
0 |
0 |
if (max_count >= 0 && tree->recent_count > max_count) { |
|
|
0 |
0 |
if (max_count >= 0 && tree->recent_count > max_count) { |
|
3094
|
0 |
0 |
if (keep) { |
|
3095
|
0 |
0 |
EXTEND(SP, n); |
|
|
0 |
0 |
EXTEND(SP, n); |
|
3102
|
0 |
0 |
if (GIMME_V == G_SCALAR) |
|
3145
|
1 |
14 |
if (ofs < 0) ofs += TreeRBXS_get_count(tree); |
|
3156
|
8 |
0 |
: GET_TreeRBXS_item_FROM_rbnode(TreeRBXS_get_root(tree)); |
|
3165
|
1 |
12 |
if (newval) { |
|
3166
|
0 |
1 |
if (!TreeRBXS_is_member(tree, newval)) |
|
3171
|
9 |
4 |
: GET_TreeRBXS_item_FROM_recent(tree->recent.next); |
|
3180
|
1 |
18 |
if (newval) { |
|
3181
|
0 |
1 |
if (!TreeRBXS_is_member(tree, newval)) |
|
3186
|
15 |
4 |
: GET_TreeRBXS_item_FROM_recent(tree->recent.prev); |
|
3200
|
8 |
72 |
size_t n_ret, i, node_count= tree->keys_in_recent_order? tree->recent_count : TreeRBXS_get_count(tree); |
|
3206
|
0 |
80 |
if (GIMME_V == G_VOID) { |
|
3209
|
0 |
80 |
else if (GIMME_V == G_SCALAR) { |
|
3214
|
19 |
61 |
n_ret= want_kv? node_count*2 : node_count; |
|
3215
|
0 |
80 |
EXTEND(SP, n_ret); |
|
3216
|
8 |
72 |
if (tree->keys_in_recent_order) { |
|
3217
|
3 |
5 |
struct dllist_node *node= reverse? tree->recent.prev : tree->recent.next; |
|
3219
|
3 |
5 |
if (keys_only) { |
|
3220
|
8 |
3 |
for (i= 0; i < n_ret && node != limit; i++, node= reverse? node->prev : node->next) |
|
|
8 |
0 |
for (i= 0; i < n_ret && node != limit; i++, node= reverse? node->prev : node->next) |
|
3221
|
3 |
5 |
ST(i)= sv_2mortal(TreeRBXS_item_wrap_key(GET_TreeRBXS_item_FROM_recent(node))); |
|
3223
|
2 |
3 |
else if (values_only) { |
|
3224
|
6 |
2 |
for (i= 0; i < n_ret && node != limit; i++, node= reverse? node->prev : node->next) |
|
|
6 |
0 |
for (i= 0; i < n_ret && node != limit; i++, node= reverse? node->prev : node->next) |
|
3225
|
3 |
3 |
ST(i)= GET_TreeRBXS_item_FROM_recent(node)->value; |
|
3228
|
8 |
3 |
for (i= 0; i < n_ret && node != limit; node= reverse? node->prev : node->next) { |
|
|
8 |
0 |
for (i= 0; i < n_ret && node != limit; node= reverse? node->prev : node->next) { |
|
3232
|
3 |
5 |
i++; |
|
3235
|
0 |
8 |
if (node != limit) i++; // for error reporting |
|
3238
|
0 |
72 |
rbtree_node_t *node= (reverse? rbtree_node_right_leaf : rbtree_node_left_leaf)(TreeRBXS_get_root(tree)); |
|
3239
|
0 |
72 |
rbtree_node_t *(*step)(rbtree_node_t *)= reverse? rbtree_node_prev : rbtree_node_next; |
|
3240
|
56 |
16 |
if (keys_only) { |
|
3241
|
374 |
56 |
for (i= 0; i < n_ret && node; i++, node= step(node)) |
|
|
374 |
0 |
for (i= 0; i < n_ret && node; i++, node= step(node)) |
|
3244
|
0 |
16 |
else if (values_only) { |
|
3245
|
0 |
0 |
for (i= 0; i < n_ret && node; i++, node= step(node)) |
|
|
0 |
0 |
for (i= 0; i < n_ret && node; i++, node= step(node)) |
|
3249
|
56 |
16 |
for (i= 0; i < n_ret && node; node= step(node)) { |
|
|
56 |
0 |
for (i= 0; i < n_ret && node; node= step(node)) { |
|
3256
|
0 |
72 |
if (node) i++; // for error reporting |
|
3258
|
0 |
80 |
if (i != n_ret) |
|
3259
|
0 |
0 |
croak("BUG: expected %ld nodes but found %ld", |
|
3271
|
1 |
14 |
if (tree->hashiterset) |
|
3288
|
2 |
59 |
if (tree->hashiterset) |
|
3306
|
2 |
1 |
if (item && (TreeRBXS_item_get_tree(item) != tree)) |
|
|
0 |
2 |
if (item && (TreeRBXS_item_get_tree(item) != tree)) |
|
3311
|
1 |
2 |
if (!item) TreeRBXS_iter_rewind(iter); |
|
3331
|
0 |
3 |
if (!SvOK(key)) |
|
3334
|
2 |
1 |
if (rbtree_find_all( |
|
3344
|
0 |
2 |
first= (first == last)? NULL : rbtree_node_next(first); |
|
3346
|
0 |
2 |
} while (first); |
|
3377
|
66 |
1 |
RETVAL= cmp_numsplit(apos, apos+alen, a_utf8, bpos, bpos+blen, b_utf8); |
|
3392
|
47 |
155 |
if (newval) { |
|
3400
|
155 |
47 |
: TreeRBXS_item_wrap_key(item); |
|
3409
|
0 |
51 |
if (newval) |
|
3419
|
0 |
0 |
RETVAL= rbtree_node_index(&item->rbnode); |
|
3451
|
1 |
11 |
if (newval) { |
|
3452
|
0 |
1 |
if (!next) |
|
3454
|
0 |
1 |
if (!tree) croak("Node was removed from tree"); |
|
3458
|
5 |
0 |
RETVAL= (!next || !tree || next == &tree->recent)? NULL |
|
|
5 |
0 |
RETVAL= (!next || !tree || next == &tree->recent)? NULL |
|
3459
|
5 |
7 |
: GET_TreeRBXS_item_FROM_recent(next); |
|
3471
|
1 |
13 |
if (newval) { |
|
3472
|
0 |
1 |
if (!prev) |
|
3474
|
0 |
1 |
if (!tree) croak("Node was removed from tree"); |
|
3478
|
7 |
0 |
RETVAL= (!prev || !tree || prev == &tree->recent)? NULL |
|
|
7 |
0 |
RETVAL= (!prev || !tree || prev == &tree->recent)? NULL |
|
3479
|
7 |
7 |
: GET_TreeRBXS_item_FROM_recent(prev); |
|
3487
|
0 |
1 |
RETVAL= rbtree_node_is_in_tree(&item->rbnode) && item->rbnode.parent->count? |
|
3488
|
1 |
4 |
GET_TreeRBXS_item_FROM_rbnode(item->rbnode.parent) : NULL; |
|
3498
|
1 |
14 |
ST(0)= tree && tree->owner? sv_2mortal(newRV_inc(tree->owner)) : &PL_sv_undef; |
|
|
1 |
0 |
ST(0)= tree && tree->owner? sv_2mortal(newRV_inc(tree->owner)) : &PL_sv_undef; |
|
3505
|
4 |
4 |
RETVAL= rbtree_node_is_in_tree(&item->rbnode) && item->rbnode.left->count? |
|
3506
|
8 |
4 |
GET_TreeRBXS_item_FROM_rbnode(item->rbnode.left) : NULL; |
|
3514
|
4 |
4 |
RETVAL= rbtree_node_is_in_tree(&item->rbnode) && item->rbnode.right->count? |
|
3515
|
8 |
4 |
GET_TreeRBXS_item_FROM_rbnode(item->rbnode.right) : NULL; |
|
3543
|
1 |
4 |
RETVAL= item->rbnode.color; |
|
3551
|
0 |
5 |
RETVAL= item->rbnode.count; |
|
3562
|
5 |
1 |
if (tree) { |
|
3576
|
10 |
4 |
if (items > 1) { |
|
3578
|
0 |
10 |
if (!tree) croak("Node was removed from tree"); |
|
3579
|
0 |
10 |
if (SvTRUE(newval)) |
|
3595
|
0 |
2 |
if (!tree) croak("Node was removed from tree"); |
|
3605
|
0 |
0 |
if (!tree) croak("Node was removed from tree"); |
|
3618
|
2 |
1 |
if (tree) { |
|
3642
|
1 |
2 |
if (idx == -1) { |
|
3645
|
1 |
0 |
if (!svec || n != 2 || !svec[0] || !svec[1]) |
|
|
1 |
0 |
if (!svec || n != 2 || !svec[0] || !svec[1]) |
|
|
1 |
0 |
if (!svec || n != 2 || !svec[0] || !svec[1]) |
|
|
0 |
1 |
if (!svec || n != 2 || !svec[0] || !svec[1]) |
|
3654
|
0 |
2 |
if (!(node= rbtree_node_child_at_index(TreeRBXS_get_root(tree), idx))) |
|
3657
|
0 |
2 |
if (item->owner) { |
|
3658
|
0 |
0 |
if (item->owner != SvRV(item_sv)) |
|
3690
|
257 |
0 |
if (iter->item || iter->tree) |
|
|
0 |
257 |
if (iter->item || iter->tree) |
|
3701
|
0 |
257 |
if ((iter2= TreeRBXS_get_magic_iter(target, 0))) { |
|
3703
|
0 |
0 |
if (items < 2) { |
|
3710
|
17 |
240 |
else if ((item= TreeRBXS_get_magic_item(target, 0))) { |
|
3713
|
240 |
0 |
else if ((tree= TreeRBXS_get_magic_tree(target, 0))) { |
|
3714
|
13 |
227 |
if (iter->recent) { |
|
3715
|
4 |
9 |
lnode= iter->reverse? tree->recent.prev : tree->recent.next; |
|
3717
|
13 |
0 |
: GET_TreeRBXS_item_FROM_recent(lnode); |
|
3721
|
227 |
0 |
: iter->reverse? rbtree_node_right_leaf(TreeRBXS_get_root(tree)) |
|
3722
|
104 |
123 |
: rbtree_node_left_leaf(TreeRBXS_get_root(tree)); |
|
3723
|
227 |
0 |
if (node) |
|
3727
|
0 |
257 |
if (!tree) |
|
3729
|
15 |
242 |
if (iter->recent && item && !item->recent.next) |
|
|
15 |
0 |
if (iter->recent && item && !item->recent.next) |
|
|
0 |
15 |
if (iter->recent && item && !item->recent.next) |
|
3732
|
257 |
0 |
if (tree->owner) |
|
3751
|
25 |
10 |
RETVAL= iter->item? SvREFCNT_inc_simple_NN(iter->item->value) : &PL_sv_undef; |
|
3767
|
0 |
0 |
RETVAL= !iter->item || !rbtree_node_is_in_tree(&iter->item->rbnode)? &PL_sv_undef |
|
3768
|
0 |
1 |
: newSViv(rbtree_node_index(&iter->item->rbnode)); |
|
3776
|
0 |
0 |
RETVAL= iter->tree && iter->tree->owner? newRV_inc(iter->tree->owner) : &PL_sv_undef; |
|
|
0 |
0 |
RETVAL= iter->tree && iter->tree->owner? newRV_inc(iter->tree->owner) : &PL_sv_undef; |
|
3784
|
19 |
27 |
RETVAL= !iter->item; |
|
3800
|
22 |
24 |
size_t pos, n, nret, i, max_count= iter->recent? iter->tree->recent_count : TreeRBXS_get_count(iter->tree); |
|
3803
|
8 |
38 |
rbtree_node_t *(*step)(rbtree_node_t *)= iter->reverse? &rbtree_node_prev : rbtree_node_next; |
|
3805
|
38 |
8 |
if (iter->item) { |
|
3807
|
28 |
10 |
: ((SvPOK(count_sv) && *SvPV_nolen(count_sv) == '*') |
|
|
15 |
13 |
: ((SvPOK(count_sv) && *SvPV_nolen(count_sv) == '*') |
|
|
0 |
15 |
: ((SvPOK(count_sv) && *SvPV_nolen(count_sv) == '*') |
|
3808
|
6 |
7 |
|| (SvNOK(count_sv) && SvNV(count_sv) > (NV)PERL_INT_MAX))? max_count |
|
|
0 |
6 |
|| (SvNOK(count_sv) && SvNV(count_sv) > (NV)PERL_INT_MAX))? max_count |
|
3810
|
1 |
37 |
if (request < 1) { |
|
3815
|
1 |
36 |
else if (GIMME_V == G_VOID) { |
|
3821
|
26 |
10 |
else if (request == 1 || iter->recent) { // un-optimized loop |
|
|
10 |
16 |
else if (request == 1 || iter->recent) { // un-optimized loop |
|
3822
|
2 |
18 |
nret= ix == 3? request<<1 : request; |
|
3823
|
0 |
20 |
EXTEND(SP, nret); |
|
3824
|
86 |
20 |
for (i= 0; i < nret && iter->item; ) { |
|
|
86 |
0 |
for (i= 0; i < nret && iter->item; ) { |
|
3826
|
6 |
80 |
: ix == 2? iter->item->value |
|
3827
|
0 |
80 |
: sv_2mortal(TreeRBXS_item_wrap_key(iter->item)); |
|
3828
|
46 |
40 |
if (ix == 3) |
|
3837
|
1 |
15 |
n= iter->reverse? 1 + pos : max_count - pos; |
|
3838
|
3 |
13 |
if (n > request) n= request; |
|
3840
|
6 |
10 |
nret= (ix == 3)? n<<1 : n; |
|
3841
|
0 |
16 |
EXTEND(SP, nret); // EXTEND macro declares a temp 'ix' internally - GitHub #2 |
|
3842
|
1 |
15 |
if (ix == 0) { |
|
3843
|
2 |
1 |
for (i= 0; i < nret && node; i++, node= step(node)) |
|
|
2 |
0 |
for (i= 0; i < nret && node; i++, node= step(node)) |
|
3846
|
4 |
11 |
else if (ix == 1) { |
|
3847
|
16 |
4 |
for (i= 0; i < nret && node; i++, node= step(node)) |
|
|
16 |
0 |
for (i= 0; i < nret && node; i++, node= step(node)) |
|
3850
|
5 |
6 |
else if (ix == 2) { |
|
3851
|
91 |
5 |
for (i= 0; i < nret && node; i++, node= step(node)) |
|
|
91 |
0 |
for (i= 0; i < nret && node; i++, node= step(node)) |
|
3855
|
70 |
6 |
for (i= 0; i < nret && node; node= step(node)) { |
|
|
70 |
0 |
for (i= 0; i < nret && node; node= step(node)) { |
|
3862
|
0 |
16 |
if (i != nret) |
|
3863
|
0 |
0 |
croak("BUG: expected %ld nodes but found %ld", (long) n, (long) (ix == 3? i>>1 : i)); |
|
3881
|
1295 |
210 |
RETVAL= !!iter->item; |
|
3889
|
5 |
0 |
if (iter->item) { |
|
3911
|
0 |
0 |
av_push(refs, iter->item? newSViv(rbtree_node_index(&iter->item->rbnode)) : newSV(0)); |