Sat, 11 Oct 2025 11:55:46 +0200
changes the compare function wrapper for pointer lists so that it no longer invokes the actual compare function for NULL pointers
1348
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
1 | /* |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
2 | * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER. |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
3 | * |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
4 | * Copyright 2025 Mike Becker, Olaf Wintermann All rights reserved. |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
5 | * |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
6 | * Redistribution and use in source and binary forms, with or without |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
7 | * modification, are permitted provided that the following conditions are met: |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
8 | * |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
9 | * 1. Redistributions of source code must retain the above copyright |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
10 | * notice, this list of conditions and the following disclaimer. |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
11 | * |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
12 | * 2. Redistributions in binary form must reproduce the above copyright |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
13 | * notice, this list of conditions and the following disclaimer in the |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
14 | * documentation and/or other materials provided with the distribution. |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
15 | * |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
16 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
17 | * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
18 | * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
19 | * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
20 | * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
21 | * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
22 | * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
23 | * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
24 | * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
25 | * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
26 | * POSSIBILITY OF SUCH DAMAGE. |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
27 | */ |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
28 | |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
29 | #include "cx/kv_list.h" |
1350
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
30 | #include "cx/hash_map.h" |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
31 | #include "cx/linked_list.h" |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
32 | |
1360
8b29d732f97b
implement cx_kvl_map_remove()
Mike Becker <universe@uap-core.de>
parents:
1358
diff
changeset
|
33 | #include <string.h> |
1384
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
34 | #include <assert.h> |
1360
8b29d732f97b
implement cx_kvl_map_remove()
Mike Becker <universe@uap-core.de>
parents:
1358
diff
changeset
|
35 | |
1350
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
36 | typedef struct cx_kv_list_s cx_kv_list; |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
37 | |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
38 | struct cx_kv_list_map_s { |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
39 | struct cx_hash_map_s map_base; |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
40 | /** Back-reference to the list. */ |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
41 | cx_kv_list *list; |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
42 | }; |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
43 | |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
44 | struct cx_kv_list_s { |
1367
6b3d52dd176e
change linked_list.c to allow custom data in nodes + implement cx_kv_list_set_key()
Mike Becker <universe@uap-core.de>
parents:
1365
diff
changeset
|
45 | struct cx_linked_list_s list; |
1350
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
46 | /** The lookup map - stores pointers to the nodes. */ |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
47 | struct cx_kv_list_map_s *map; |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
48 | const cx_list_class *list_methods; |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
49 | const cx_map_class *map_methods; |
1365
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
50 | cx_destructor_func list_destr; |
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
51 | cx_destructor_func2 list_destr2; |
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
52 | void *list_destr_data; |
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
53 | cx_destructor_func map_destr; |
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
54 | cx_destructor_func2 map_destr2; |
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
55 | void *map_destr_data; |
1350
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
56 | }; |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
57 | |
1375
e0ba5e20e77a
implement cx_kvl_find_remove()
Mike Becker <universe@uap-core.de>
parents:
1373
diff
changeset
|
58 | static void cx_kv_list_destructor_wrapper(void *list_ptr, void *elem) { |
1365
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
59 | const cx_kv_list *kv_list = list_ptr; |
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
60 | // list destructor is already called with proper deref of the elem |
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
61 | if (kv_list->list_destr) { |
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
62 | kv_list->list_destr(elem); |
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
63 | } |
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
64 | if (kv_list->list_destr2) { |
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
65 | kv_list->list_destr2(kv_list->list_destr_data, elem); |
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
66 | } |
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
67 | if (kv_list->map_destr) { |
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
68 | kv_list->map_destr(elem); |
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
69 | } |
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
70 | if (kv_list->map_destr2) { |
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
71 | kv_list->map_destr2(kv_list->map_destr_data, elem); |
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
72 | } |
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
73 | } |
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
74 | |
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
75 | static void cx_kv_list_update_destructors(cx_kv_list *list) { |
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
76 | // we copy the destructors to our custom fields and register |
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
77 | // an own destructor function which invokes all these |
1367
6b3d52dd176e
change linked_list.c to allow custom data in nodes + implement cx_kv_list_set_key()
Mike Becker <universe@uap-core.de>
parents:
1365
diff
changeset
|
78 | if (list->list.base.collection.simple_destructor != NULL) { |
6b3d52dd176e
change linked_list.c to allow custom data in nodes + implement cx_kv_list_set_key()
Mike Becker <universe@uap-core.de>
parents:
1365
diff
changeset
|
79 | list->list_destr = list->list.base.collection.simple_destructor; |
6b3d52dd176e
change linked_list.c to allow custom data in nodes + implement cx_kv_list_set_key()
Mike Becker <universe@uap-core.de>
parents:
1365
diff
changeset
|
80 | list->list.base.collection.simple_destructor = NULL; |
1365
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
81 | } |
1375
e0ba5e20e77a
implement cx_kvl_find_remove()
Mike Becker <universe@uap-core.de>
parents:
1373
diff
changeset
|
82 | if (list->list.base.collection.advanced_destructor != cx_kv_list_destructor_wrapper) { |
1367
6b3d52dd176e
change linked_list.c to allow custom data in nodes + implement cx_kv_list_set_key()
Mike Becker <universe@uap-core.de>
parents:
1365
diff
changeset
|
83 | list->list_destr2 = list->list.base.collection.advanced_destructor; |
6b3d52dd176e
change linked_list.c to allow custom data in nodes + implement cx_kv_list_set_key()
Mike Becker <universe@uap-core.de>
parents:
1365
diff
changeset
|
84 | list->list_destr_data = list->list.base.collection.destructor_data; |
1375
e0ba5e20e77a
implement cx_kvl_find_remove()
Mike Becker <universe@uap-core.de>
parents:
1373
diff
changeset
|
85 | list->list.base.collection.advanced_destructor = cx_kv_list_destructor_wrapper; |
1367
6b3d52dd176e
change linked_list.c to allow custom data in nodes + implement cx_kv_list_set_key()
Mike Becker <universe@uap-core.de>
parents:
1365
diff
changeset
|
86 | list->list.base.collection.destructor_data = list; |
1365
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
87 | } |
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
88 | if (list->map->map_base.base.collection.simple_destructor != NULL) { |
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
89 | list->map_destr = list->map->map_base.base.collection.simple_destructor; |
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
90 | list->map->map_base.base.collection.simple_destructor = NULL; |
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
91 | } |
1368
19025ca34caa
change kv-list destructor strategy to only use the list destructors
Mike Becker <universe@uap-core.de>
parents:
1367
diff
changeset
|
92 | if (list->map->map_base.base.collection.advanced_destructor != NULL) { |
1365
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
93 | list->map_destr2 = list->map->map_base.base.collection.advanced_destructor; |
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
94 | list->map_destr_data = list->map->map_base.base.collection.destructor_data; |
1368
19025ca34caa
change kv-list destructor strategy to only use the list destructors
Mike Becker <universe@uap-core.de>
parents:
1367
diff
changeset
|
95 | list->map->map_base.base.collection.advanced_destructor = NULL; |
19025ca34caa
change kv-list destructor strategy to only use the list destructors
Mike Becker <universe@uap-core.de>
parents:
1367
diff
changeset
|
96 | list->map->map_base.base.collection.destructor_data = NULL; |
1365
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
97 | } |
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
98 | } |
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
99 | |
1373
a6aaa77b6809
make cx_kvl_remove() also remove the keys from the map
Mike Becker <universe@uap-core.de>
parents:
1372
diff
changeset
|
100 | static CxHashKey *cx_kv_list_loc_key(cx_kv_list *list, void *node_data) { |
a6aaa77b6809
make cx_kvl_remove() also remove the keys from the map
Mike Becker <universe@uap-core.de>
parents:
1372
diff
changeset
|
101 | return (CxHashKey*)((char*)node_data + list->list.base.collection.elem_size); |
a6aaa77b6809
make cx_kvl_remove() also remove the keys from the map
Mike Becker <universe@uap-core.de>
parents:
1372
diff
changeset
|
102 | } |
a6aaa77b6809
make cx_kvl_remove() also remove the keys from the map
Mike Becker <universe@uap-core.de>
parents:
1372
diff
changeset
|
103 | |
1350
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
104 | static void cx_kvl_deallocate(struct cx_list_s *list) { |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
105 | cx_kv_list *kv_list = (cx_kv_list*)list; |
1365
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
106 | // patch the destructors |
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
107 | cx_kv_list_update_destructors(kv_list); |
1350
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
108 | kv_list->map_methods->deallocate(&kv_list->map->map_base.base); |
1367
6b3d52dd176e
change linked_list.c to allow custom data in nodes + implement cx_kv_list_set_key()
Mike Becker <universe@uap-core.de>
parents:
1365
diff
changeset
|
109 | // then free the list, now the destructors may be called |
1350
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
110 | kv_list->list_methods->deallocate(list); |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
111 | } |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
112 | |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
113 | static void *cx_kvl_insert_element( |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
114 | struct cx_list_s *list, |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
115 | size_t index, |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
116 | const void *data |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
117 | ) { |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
118 | cx_kv_list *kv_list = (cx_kv_list*)list; |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
119 | return kv_list->list_methods->insert_element(list, index, data); |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
120 | } |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
121 | |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
122 | static size_t cx_kvl_insert_array( |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
123 | struct cx_list_s *list, |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
124 | size_t index, |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
125 | const void *data, |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
126 | size_t n |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
127 | ) { |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
128 | cx_kv_list *kv_list = (cx_kv_list*)list; |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
129 | return kv_list->list_methods->insert_array(list, index, data, n); |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
130 | } |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
131 | |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
132 | static size_t cx_kvl_insert_sorted( |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
133 | struct cx_list_s *list, |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
134 | const void *sorted_data, |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
135 | size_t n |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
136 | ) { |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
137 | cx_kv_list *kv_list = (cx_kv_list*)list; |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
138 | return kv_list->list_methods->insert_sorted(list, sorted_data, n); |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
139 | } |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
140 | |
1419
e46406fd1b3c
add functions to insert elements into lists/arrays without duplicates - resolves #557
Mike Becker <universe@uap-core.de>
parents:
1405
diff
changeset
|
141 | static size_t cx_kvl_insert_unique( |
e46406fd1b3c
add functions to insert elements into lists/arrays without duplicates - resolves #557
Mike Becker <universe@uap-core.de>
parents:
1405
diff
changeset
|
142 | struct cx_list_s *list, |
e46406fd1b3c
add functions to insert elements into lists/arrays without duplicates - resolves #557
Mike Becker <universe@uap-core.de>
parents:
1405
diff
changeset
|
143 | const void *sorted_data, |
e46406fd1b3c
add functions to insert elements into lists/arrays without duplicates - resolves #557
Mike Becker <universe@uap-core.de>
parents:
1405
diff
changeset
|
144 | size_t n |
e46406fd1b3c
add functions to insert elements into lists/arrays without duplicates - resolves #557
Mike Becker <universe@uap-core.de>
parents:
1405
diff
changeset
|
145 | ) { |
e46406fd1b3c
add functions to insert elements into lists/arrays without duplicates - resolves #557
Mike Becker <universe@uap-core.de>
parents:
1405
diff
changeset
|
146 | cx_kv_list *kv_list = (cx_kv_list*)list; |
e46406fd1b3c
add functions to insert elements into lists/arrays without duplicates - resolves #557
Mike Becker <universe@uap-core.de>
parents:
1405
diff
changeset
|
147 | return kv_list->list_methods->insert_unique(list, sorted_data, n); |
e46406fd1b3c
add functions to insert elements into lists/arrays without duplicates - resolves #557
Mike Becker <universe@uap-core.de>
parents:
1405
diff
changeset
|
148 | } |
e46406fd1b3c
add functions to insert elements into lists/arrays without duplicates - resolves #557
Mike Becker <universe@uap-core.de>
parents:
1405
diff
changeset
|
149 | |
1350
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
150 | static int cx_kvl_insert_iter( |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
151 | struct cx_iterator_s *iter, |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
152 | const void *elem, |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
153 | int prepend |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
154 | ) { |
1362
d886626a9526
add several fixme and todo comments regarding invoking destructors
Mike Becker <universe@uap-core.de>
parents:
1361
diff
changeset
|
155 | cx_kv_list *kv_list = iter->src_handle.m; |
1350
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
156 | return kv_list->list_methods->insert_iter(iter, elem, prepend); |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
157 | } |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
158 | |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
159 | static size_t cx_kvl_remove( |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
160 | struct cx_list_s *list, |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
161 | size_t index, |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
162 | size_t num, |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
163 | void *targetbuf |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
164 | ) { |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
165 | cx_kv_list *kv_list = (cx_kv_list*)list; |
1365
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
166 | // patch the destructors |
1373
a6aaa77b6809
make cx_kvl_remove() also remove the keys from the map
Mike Becker <universe@uap-core.de>
parents:
1372
diff
changeset
|
167 | // we also have to do that when targetbuf is NULL, |
a6aaa77b6809
make cx_kvl_remove() also remove the keys from the map
Mike Becker <universe@uap-core.de>
parents:
1372
diff
changeset
|
168 | // because we do not want wrong destructors to be called when we remove keys from the map |
1365
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
169 | cx_kv_list_update_destructors(kv_list); |
1373
a6aaa77b6809
make cx_kvl_remove() also remove the keys from the map
Mike Becker <universe@uap-core.de>
parents:
1372
diff
changeset
|
170 | // iterate through the elements first and remove their keys from the map |
a6aaa77b6809
make cx_kvl_remove() also remove the keys from the map
Mike Becker <universe@uap-core.de>
parents:
1372
diff
changeset
|
171 | CxIterator iter = kv_list->list_methods->iterator(list, index, false); |
a6aaa77b6809
make cx_kvl_remove() also remove the keys from the map
Mike Becker <universe@uap-core.de>
parents:
1372
diff
changeset
|
172 | for (size_t i = 0; i < num && cxIteratorValid(iter); i++) { |
a6aaa77b6809
make cx_kvl_remove() also remove the keys from the map
Mike Becker <universe@uap-core.de>
parents:
1372
diff
changeset
|
173 | void *node_data = cxIteratorCurrent(iter); |
a6aaa77b6809
make cx_kvl_remove() also remove the keys from the map
Mike Becker <universe@uap-core.de>
parents:
1372
diff
changeset
|
174 | CxHashKey *key = cx_kv_list_loc_key(kv_list, node_data); |
a6aaa77b6809
make cx_kvl_remove() also remove the keys from the map
Mike Becker <universe@uap-core.de>
parents:
1372
diff
changeset
|
175 | // when the hash is zero, there is no key assigned to that element |
a6aaa77b6809
make cx_kvl_remove() also remove the keys from the map
Mike Becker <universe@uap-core.de>
parents:
1372
diff
changeset
|
176 | if (key->hash != 0) { |
a6aaa77b6809
make cx_kvl_remove() also remove the keys from the map
Mike Becker <universe@uap-core.de>
parents:
1372
diff
changeset
|
177 | kv_list->map_methods->remove(&kv_list->map->map_base.base, *key, NULL); |
a6aaa77b6809
make cx_kvl_remove() also remove the keys from the map
Mike Becker <universe@uap-core.de>
parents:
1372
diff
changeset
|
178 | } |
a6aaa77b6809
make cx_kvl_remove() also remove the keys from the map
Mike Becker <universe@uap-core.de>
parents:
1372
diff
changeset
|
179 | cxIteratorNext(iter); |
a6aaa77b6809
make cx_kvl_remove() also remove the keys from the map
Mike Becker <universe@uap-core.de>
parents:
1372
diff
changeset
|
180 | } |
1350
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
181 | return kv_list->list_methods->remove(list, index, num, targetbuf); |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
182 | } |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
183 | |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
184 | static void cx_kvl_clear(struct cx_list_s *list) { |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
185 | cx_kv_list *kv_list = (cx_kv_list*)list; |
1365
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
186 | // patch the destructors |
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
187 | cx_kv_list_update_destructors(kv_list); |
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
188 | // clear the list |
1350
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
189 | kv_list->list_methods->clear(list); |
1365
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
190 | // then clear the map |
1367
6b3d52dd176e
change linked_list.c to allow custom data in nodes + implement cx_kv_list_set_key()
Mike Becker <universe@uap-core.de>
parents:
1365
diff
changeset
|
191 | kv_list->map_methods->clear(&kv_list->map->map_base.base); |
1350
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
192 | } |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
193 | |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
194 | static int cx_kvl_swap( |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
195 | struct cx_list_s *list, |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
196 | size_t i, |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
197 | size_t j |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
198 | ) { |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
199 | cx_kv_list *kv_list = (cx_kv_list*)list; |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
200 | return kv_list->list_methods->swap(list, i, j); |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
201 | } |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
202 | |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
203 | static void *cx_kvl_at( |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
204 | const struct cx_list_s *list, |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
205 | size_t index |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
206 | ) { |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
207 | const cx_kv_list *kv_list = (const cx_kv_list*)list; |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
208 | return kv_list->list_methods->at(list, index); |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
209 | } |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
210 | |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
211 | static size_t cx_kvl_find_remove( |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
212 | struct cx_list_s *list, |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
213 | const void *elem, |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
214 | bool remove |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
215 | ) { |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
216 | cx_kv_list *kv_list = (cx_kv_list*)list; |
1375
e0ba5e20e77a
implement cx_kvl_find_remove()
Mike Becker <universe@uap-core.de>
parents:
1373
diff
changeset
|
217 | // we do not use the original list methods, |
e0ba5e20e77a
implement cx_kvl_find_remove()
Mike Becker <universe@uap-core.de>
parents:
1373
diff
changeset
|
218 | // because that would need two passes for removal |
e0ba5e20e77a
implement cx_kvl_find_remove()
Mike Becker <universe@uap-core.de>
parents:
1373
diff
changeset
|
219 | // (the first to find the index, the second to get a pointer) |
e0ba5e20e77a
implement cx_kvl_find_remove()
Mike Becker <universe@uap-core.de>
parents:
1373
diff
changeset
|
220 | if (list->collection.size == 0) return 0; |
e0ba5e20e77a
implement cx_kvl_find_remove()
Mike Becker <universe@uap-core.de>
parents:
1373
diff
changeset
|
221 | |
e0ba5e20e77a
implement cx_kvl_find_remove()
Mike Becker <universe@uap-core.de>
parents:
1373
diff
changeset
|
222 | size_t index; |
e0ba5e20e77a
implement cx_kvl_find_remove()
Mike Becker <universe@uap-core.de>
parents:
1373
diff
changeset
|
223 | cx_linked_list *ll = &kv_list->list; |
e0ba5e20e77a
implement cx_kvl_find_remove()
Mike Becker <universe@uap-core.de>
parents:
1373
diff
changeset
|
224 | char *node = cx_linked_list_find( |
e0ba5e20e77a
implement cx_kvl_find_remove()
Mike Becker <universe@uap-core.de>
parents:
1373
diff
changeset
|
225 | ll->begin, |
e0ba5e20e77a
implement cx_kvl_find_remove()
Mike Becker <universe@uap-core.de>
parents:
1373
diff
changeset
|
226 | ll->loc_next, ll->loc_data, |
e0ba5e20e77a
implement cx_kvl_find_remove()
Mike Becker <universe@uap-core.de>
parents:
1373
diff
changeset
|
227 | list->collection.cmpfunc, elem, |
e0ba5e20e77a
implement cx_kvl_find_remove()
Mike Becker <universe@uap-core.de>
parents:
1373
diff
changeset
|
228 | &index |
e0ba5e20e77a
implement cx_kvl_find_remove()
Mike Becker <universe@uap-core.de>
parents:
1373
diff
changeset
|
229 | ); |
e0ba5e20e77a
implement cx_kvl_find_remove()
Mike Becker <universe@uap-core.de>
parents:
1373
diff
changeset
|
230 | if (node == NULL) { |
e0ba5e20e77a
implement cx_kvl_find_remove()
Mike Becker <universe@uap-core.de>
parents:
1373
diff
changeset
|
231 | return list->collection.size; |
e0ba5e20e77a
implement cx_kvl_find_remove()
Mike Becker <universe@uap-core.de>
parents:
1373
diff
changeset
|
232 | } |
e0ba5e20e77a
implement cx_kvl_find_remove()
Mike Becker <universe@uap-core.de>
parents:
1373
diff
changeset
|
233 | if (remove) { |
e0ba5e20e77a
implement cx_kvl_find_remove()
Mike Becker <universe@uap-core.de>
parents:
1373
diff
changeset
|
234 | cx_kv_list_update_destructors(kv_list); |
e0ba5e20e77a
implement cx_kvl_find_remove()
Mike Becker <universe@uap-core.de>
parents:
1373
diff
changeset
|
235 | cx_invoke_advanced_destructor(list, node + ll->loc_data); |
e0ba5e20e77a
implement cx_kvl_find_remove()
Mike Becker <universe@uap-core.de>
parents:
1373
diff
changeset
|
236 | cx_linked_list_remove(&ll->begin, &ll->end, |
e0ba5e20e77a
implement cx_kvl_find_remove()
Mike Becker <universe@uap-core.de>
parents:
1373
diff
changeset
|
237 | ll->loc_prev, ll->loc_next, node); |
e0ba5e20e77a
implement cx_kvl_find_remove()
Mike Becker <universe@uap-core.de>
parents:
1373
diff
changeset
|
238 | CxHashKey *key = cx_kv_list_loc_key(kv_list, node + ll->loc_data); |
e0ba5e20e77a
implement cx_kvl_find_remove()
Mike Becker <universe@uap-core.de>
parents:
1373
diff
changeset
|
239 | if (key->hash != 0) { |
e0ba5e20e77a
implement cx_kvl_find_remove()
Mike Becker <universe@uap-core.de>
parents:
1373
diff
changeset
|
240 | kv_list->map_methods->remove(&kv_list->map->map_base.base, *key, NULL); |
e0ba5e20e77a
implement cx_kvl_find_remove()
Mike Becker <universe@uap-core.de>
parents:
1373
diff
changeset
|
241 | } |
e0ba5e20e77a
implement cx_kvl_find_remove()
Mike Becker <universe@uap-core.de>
parents:
1373
diff
changeset
|
242 | list->collection.size--; |
e0ba5e20e77a
implement cx_kvl_find_remove()
Mike Becker <universe@uap-core.de>
parents:
1373
diff
changeset
|
243 | cxFree(list->collection.allocator, node); |
e0ba5e20e77a
implement cx_kvl_find_remove()
Mike Becker <universe@uap-core.de>
parents:
1373
diff
changeset
|
244 | } |
e0ba5e20e77a
implement cx_kvl_find_remove()
Mike Becker <universe@uap-core.de>
parents:
1373
diff
changeset
|
245 | return index; |
1350
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
246 | } |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
247 | |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
248 | static void cx_kvl_sort(struct cx_list_s *list) { |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
249 | cx_kv_list *kv_list = (cx_kv_list*)list; |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
250 | kv_list->list_methods->sort(list); |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
251 | } |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
252 | |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
253 | static void cx_kvl_reverse(struct cx_list_s *list) { |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
254 | cx_kv_list *kv_list = (cx_kv_list*)list; |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
255 | kv_list->list_methods->reverse(list); |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
256 | } |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
257 | |
1386
748d0d40881e
kv-list: implement mutating iterator support
Mike Becker <universe@uap-core.de>
parents:
1384
diff
changeset
|
258 | static void cx_kvl_list_iter_next(void *it) { |
748d0d40881e
kv-list: implement mutating iterator support
Mike Becker <universe@uap-core.de>
parents:
1384
diff
changeset
|
259 | struct cx_iterator_s *iter = it; |
748d0d40881e
kv-list: implement mutating iterator support
Mike Becker <universe@uap-core.de>
parents:
1384
diff
changeset
|
260 | if (iter->base.remove) { |
748d0d40881e
kv-list: implement mutating iterator support
Mike Becker <universe@uap-core.de>
parents:
1384
diff
changeset
|
261 | // remove the assigned key from the map before calling the actual function |
748d0d40881e
kv-list: implement mutating iterator support
Mike Becker <universe@uap-core.de>
parents:
1384
diff
changeset
|
262 | cx_kv_list *kv_list = iter->src_handle.m; |
748d0d40881e
kv-list: implement mutating iterator support
Mike Becker <universe@uap-core.de>
parents:
1384
diff
changeset
|
263 | cx_kv_list_update_destructors(kv_list); |
748d0d40881e
kv-list: implement mutating iterator support
Mike Becker <universe@uap-core.de>
parents:
1384
diff
changeset
|
264 | char *node = iter->elem_handle; |
748d0d40881e
kv-list: implement mutating iterator support
Mike Becker <universe@uap-core.de>
parents:
1384
diff
changeset
|
265 | CxHashKey *key = cx_kv_list_loc_key(kv_list, node + kv_list->list.loc_data); |
748d0d40881e
kv-list: implement mutating iterator support
Mike Becker <universe@uap-core.de>
parents:
1384
diff
changeset
|
266 | if (key->hash != 0) { |
748d0d40881e
kv-list: implement mutating iterator support
Mike Becker <universe@uap-core.de>
parents:
1384
diff
changeset
|
267 | kv_list->map_methods->remove(&kv_list->map->map_base.base, *key, NULL); |
748d0d40881e
kv-list: implement mutating iterator support
Mike Becker <universe@uap-core.de>
parents:
1384
diff
changeset
|
268 | } |
748d0d40881e
kv-list: implement mutating iterator support
Mike Becker <universe@uap-core.de>
parents:
1384
diff
changeset
|
269 | } |
748d0d40881e
kv-list: implement mutating iterator support
Mike Becker <universe@uap-core.de>
parents:
1384
diff
changeset
|
270 | iter->base.next_impl(it); |
748d0d40881e
kv-list: implement mutating iterator support
Mike Becker <universe@uap-core.de>
parents:
1384
diff
changeset
|
271 | } |
748d0d40881e
kv-list: implement mutating iterator support
Mike Becker <universe@uap-core.de>
parents:
1384
diff
changeset
|
272 | |
1350
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
273 | static struct cx_iterator_s cx_kvl_iterator( |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
274 | const struct cx_list_s *list, |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
275 | size_t index, |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
276 | bool backward |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
277 | ) { |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
278 | const cx_kv_list *kv_list = (const cx_kv_list*)list; |
1386
748d0d40881e
kv-list: implement mutating iterator support
Mike Becker <universe@uap-core.de>
parents:
1384
diff
changeset
|
279 | struct cx_iterator_s iter = kv_list->list_methods->iterator(list, index, backward); |
748d0d40881e
kv-list: implement mutating iterator support
Mike Becker <universe@uap-core.de>
parents:
1384
diff
changeset
|
280 | iter.base.next_impl = iter.base.next; |
748d0d40881e
kv-list: implement mutating iterator support
Mike Becker <universe@uap-core.de>
parents:
1384
diff
changeset
|
281 | iter.base.next = cx_kvl_list_iter_next; |
748d0d40881e
kv-list: implement mutating iterator support
Mike Becker <universe@uap-core.de>
parents:
1384
diff
changeset
|
282 | return iter; |
1350
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
283 | } |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
284 | |
1358
dda9c330e3e5
make test_kv_list_map_put() pass
Mike Becker <universe@uap-core.de>
parents:
1353
diff
changeset
|
285 | static void cx_kvl_map_deallocate(struct cx_map_s *map) { |
dda9c330e3e5
make test_kv_list_map_put() pass
Mike Becker <universe@uap-core.de>
parents:
1353
diff
changeset
|
286 | cx_kv_list *kv_list = ((struct cx_kv_list_map_s*)map)->list; |
dda9c330e3e5
make test_kv_list_map_put() pass
Mike Becker <universe@uap-core.de>
parents:
1353
diff
changeset
|
287 | kv_list->map_methods->deallocate(map); |
1367
6b3d52dd176e
change linked_list.c to allow custom data in nodes + implement cx_kv_list_set_key()
Mike Becker <universe@uap-core.de>
parents:
1365
diff
changeset
|
288 | kv_list->list_methods->deallocate(&kv_list->list.base); |
1358
dda9c330e3e5
make test_kv_list_map_put() pass
Mike Becker <universe@uap-core.de>
parents:
1353
diff
changeset
|
289 | } |
dda9c330e3e5
make test_kv_list_map_put() pass
Mike Becker <universe@uap-core.de>
parents:
1353
diff
changeset
|
290 | |
dda9c330e3e5
make test_kv_list_map_put() pass
Mike Becker <universe@uap-core.de>
parents:
1353
diff
changeset
|
291 | static void cx_kvl_map_clear(struct cx_map_s *map) { |
dda9c330e3e5
make test_kv_list_map_put() pass
Mike Becker <universe@uap-core.de>
parents:
1353
diff
changeset
|
292 | cx_kv_list *kv_list = ((struct cx_kv_list_map_s*)map)->list; |
1365
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
293 | cx_kv_list_update_destructors(kv_list); |
1368
19025ca34caa
change kv-list destructor strategy to only use the list destructors
Mike Becker <universe@uap-core.de>
parents:
1367
diff
changeset
|
294 | kv_list->list_methods->clear(&kv_list->list.base); |
1358
dda9c330e3e5
make test_kv_list_map_put() pass
Mike Becker <universe@uap-core.de>
parents:
1353
diff
changeset
|
295 | kv_list->map_methods->clear(map); |
dda9c330e3e5
make test_kv_list_map_put() pass
Mike Becker <universe@uap-core.de>
parents:
1353
diff
changeset
|
296 | } |
dda9c330e3e5
make test_kv_list_map_put() pass
Mike Becker <universe@uap-core.de>
parents:
1353
diff
changeset
|
297 | |
dda9c330e3e5
make test_kv_list_map_put() pass
Mike Becker <universe@uap-core.de>
parents:
1353
diff
changeset
|
298 | static void *cx_kvl_map_put(CxMap *map, CxHashKey key, void *value) { |
dda9c330e3e5
make test_kv_list_map_put() pass
Mike Becker <universe@uap-core.de>
parents:
1353
diff
changeset
|
299 | cx_kv_list *kv_list = ((struct cx_kv_list_map_s*)map)->list; |
1381
ee421d6b95ef
consider the edge case that either list or map operation fails when adding an element
Mike Becker <universe@uap-core.de>
parents:
1379
diff
changeset
|
300 | // if the hash has not yet been computed, do it now |
ee421d6b95ef
consider the edge case that either list or map operation fails when adding an element
Mike Becker <universe@uap-core.de>
parents:
1379
diff
changeset
|
301 | if (key.hash == 0) { |
ee421d6b95ef
consider the edge case that either list or map operation fails when adding an element
Mike Becker <universe@uap-core.de>
parents:
1379
diff
changeset
|
302 | cx_hash_murmur(&key); |
ee421d6b95ef
consider the edge case that either list or map operation fails when adding an element
Mike Becker <universe@uap-core.de>
parents:
1379
diff
changeset
|
303 | } |
ee421d6b95ef
consider the edge case that either list or map operation fails when adding an element
Mike Becker <universe@uap-core.de>
parents:
1379
diff
changeset
|
304 | |
ee421d6b95ef
consider the edge case that either list or map operation fails when adding an element
Mike Becker <universe@uap-core.de>
parents:
1379
diff
changeset
|
305 | // reserve memory in the map first |
ee421d6b95ef
consider the edge case that either list or map operation fails when adding an element
Mike Becker <universe@uap-core.de>
parents:
1379
diff
changeset
|
306 | void **map_data = kv_list->map_methods->put(map, key, NULL); |
ee421d6b95ef
consider the edge case that either list or map operation fails when adding an element
Mike Becker <universe@uap-core.de>
parents:
1379
diff
changeset
|
307 | if (map_data == NULL) return NULL; // LCOV_EXCL_LINE |
ee421d6b95ef
consider the edge case that either list or map operation fails when adding an element
Mike Becker <universe@uap-core.de>
parents:
1379
diff
changeset
|
308 | |
ee421d6b95ef
consider the edge case that either list or map operation fails when adding an element
Mike Becker <universe@uap-core.de>
parents:
1379
diff
changeset
|
309 | // insert the data into the list (which most likely destroys the sorted property) |
1367
6b3d52dd176e
change linked_list.c to allow custom data in nodes + implement cx_kv_list_set_key()
Mike Becker <universe@uap-core.de>
parents:
1365
diff
changeset
|
310 | kv_list->list.base.collection.sorted = false; |
1358
dda9c330e3e5
make test_kv_list_map_put() pass
Mike Becker <universe@uap-core.de>
parents:
1353
diff
changeset
|
311 | void *node_data = kv_list->list_methods->insert_element( |
1370
607f822c79fe
kv-list: fix support for CX_STORE_POINTERS when using the map interface
Mike Becker <universe@uap-core.de>
parents:
1369
diff
changeset
|
312 | &kv_list->list.base, kv_list->list.base.collection.size, |
607f822c79fe
kv-list: fix support for CX_STORE_POINTERS when using the map interface
Mike Becker <universe@uap-core.de>
parents:
1369
diff
changeset
|
313 | kv_list->list.base.collection.store_pointer ? &value : value); |
1381
ee421d6b95ef
consider the edge case that either list or map operation fails when adding an element
Mike Becker <universe@uap-core.de>
parents:
1379
diff
changeset
|
314 | if (node_data == NULL) { // LCOV_EXCL_START |
ee421d6b95ef
consider the edge case that either list or map operation fails when adding an element
Mike Becker <universe@uap-core.de>
parents:
1379
diff
changeset
|
315 | // non-destructively remove the key again |
ee421d6b95ef
consider the edge case that either list or map operation fails when adding an element
Mike Becker <universe@uap-core.de>
parents:
1379
diff
changeset
|
316 | kv_list->map_methods->remove(&kv_list->map->map_base.base, key, &map_data); |
ee421d6b95ef
consider the edge case that either list or map operation fails when adding an element
Mike Becker <universe@uap-core.de>
parents:
1379
diff
changeset
|
317 | return NULL; |
ee421d6b95ef
consider the edge case that either list or map operation fails when adding an element
Mike Becker <universe@uap-core.de>
parents:
1379
diff
changeset
|
318 | } // LCOV_EXCL_STOP |
ee421d6b95ef
consider the edge case that either list or map operation fails when adding an element
Mike Becker <universe@uap-core.de>
parents:
1379
diff
changeset
|
319 | |
ee421d6b95ef
consider the edge case that either list or map operation fails when adding an element
Mike Becker <universe@uap-core.de>
parents:
1379
diff
changeset
|
320 | // write the node pointer to the map entry |
ee421d6b95ef
consider the edge case that either list or map operation fails when adding an element
Mike Becker <universe@uap-core.de>
parents:
1379
diff
changeset
|
321 | *map_data = node_data; |
ee421d6b95ef
consider the edge case that either list or map operation fails when adding an element
Mike Becker <universe@uap-core.de>
parents:
1379
diff
changeset
|
322 | |
1373
a6aaa77b6809
make cx_kvl_remove() also remove the keys from the map
Mike Becker <universe@uap-core.de>
parents:
1372
diff
changeset
|
323 | // copy the key to the node data |
a6aaa77b6809
make cx_kvl_remove() also remove the keys from the map
Mike Becker <universe@uap-core.de>
parents:
1372
diff
changeset
|
324 | CxHashKey *key_ptr = cx_kv_list_loc_key(kv_list, node_data); |
a6aaa77b6809
make cx_kvl_remove() also remove the keys from the map
Mike Becker <universe@uap-core.de>
parents:
1372
diff
changeset
|
325 | *key_ptr = key; |
1397
a5c7d63b064d
fix cx_kvl_map_put() returning the wrong pointer
Mike Becker <universe@uap-core.de>
parents:
1394
diff
changeset
|
326 | |
a5c7d63b064d
fix cx_kvl_map_put() returning the wrong pointer
Mike Becker <universe@uap-core.de>
parents:
1394
diff
changeset
|
327 | // we must return node_data here and not map_data, |
a5c7d63b064d
fix cx_kvl_map_put() returning the wrong pointer
Mike Becker <universe@uap-core.de>
parents:
1394
diff
changeset
|
328 | // because the node_data is the actual element of this collection |
a5c7d63b064d
fix cx_kvl_map_put() returning the wrong pointer
Mike Becker <universe@uap-core.de>
parents:
1394
diff
changeset
|
329 | return node_data; |
1358
dda9c330e3e5
make test_kv_list_map_put() pass
Mike Becker <universe@uap-core.de>
parents:
1353
diff
changeset
|
330 | } |
dda9c330e3e5
make test_kv_list_map_put() pass
Mike Becker <universe@uap-core.de>
parents:
1353
diff
changeset
|
331 | |
dda9c330e3e5
make test_kv_list_map_put() pass
Mike Becker <universe@uap-core.de>
parents:
1353
diff
changeset
|
332 | void *cx_kvl_map_get(const CxMap *map, CxHashKey key) { |
dda9c330e3e5
make test_kv_list_map_put() pass
Mike Becker <universe@uap-core.de>
parents:
1353
diff
changeset
|
333 | cx_kv_list *kv_list = ((struct cx_kv_list_map_s*)map)->list; |
1370
607f822c79fe
kv-list: fix support for CX_STORE_POINTERS when using the map interface
Mike Becker <universe@uap-core.de>
parents:
1369
diff
changeset
|
334 | void *node_data = kv_list->map_methods->get(map, key); |
607f822c79fe
kv-list: fix support for CX_STORE_POINTERS when using the map interface
Mike Becker <universe@uap-core.de>
parents:
1369
diff
changeset
|
335 | if (node_data == NULL) return NULL; // LCOV_EXCL_LINE |
607f822c79fe
kv-list: fix support for CX_STORE_POINTERS when using the map interface
Mike Becker <universe@uap-core.de>
parents:
1369
diff
changeset
|
336 | // return the node data |
607f822c79fe
kv-list: fix support for CX_STORE_POINTERS when using the map interface
Mike Becker <universe@uap-core.de>
parents:
1369
diff
changeset
|
337 | return kv_list->list.base.collection.store_pointer ? *(void**)node_data : node_data; |
1358
dda9c330e3e5
make test_kv_list_map_put() pass
Mike Becker <universe@uap-core.de>
parents:
1353
diff
changeset
|
338 | } |
dda9c330e3e5
make test_kv_list_map_put() pass
Mike Becker <universe@uap-core.de>
parents:
1353
diff
changeset
|
339 | |
dda9c330e3e5
make test_kv_list_map_put() pass
Mike Becker <universe@uap-core.de>
parents:
1353
diff
changeset
|
340 | int cx_kvl_map_remove(CxMap *map, CxHashKey key, void *targetbuf) { |
dda9c330e3e5
make test_kv_list_map_put() pass
Mike Becker <universe@uap-core.de>
parents:
1353
diff
changeset
|
341 | cx_kv_list *kv_list = ((struct cx_kv_list_map_s*)map)->list; |
1365
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
342 | |
1360
8b29d732f97b
implement cx_kvl_map_remove()
Mike Becker <universe@uap-core.de>
parents:
1358
diff
changeset
|
343 | void *node_data; |
8b29d732f97b
implement cx_kvl_map_remove()
Mike Becker <universe@uap-core.de>
parents:
1358
diff
changeset
|
344 | if (kv_list->map_methods->remove(map, key, &node_data)) { |
8b29d732f97b
implement cx_kvl_map_remove()
Mike Becker <universe@uap-core.de>
parents:
1358
diff
changeset
|
345 | return 1; |
8b29d732f97b
implement cx_kvl_map_remove()
Mike Becker <universe@uap-core.de>
parents:
1358
diff
changeset
|
346 | } |
8b29d732f97b
implement cx_kvl_map_remove()
Mike Becker <universe@uap-core.de>
parents:
1358
diff
changeset
|
347 | // we cannot just call a list method (because we don't have the index) |
8b29d732f97b
implement cx_kvl_map_remove()
Mike Becker <universe@uap-core.de>
parents:
1358
diff
changeset
|
348 | // and tbh. we also don't want to (because it's not performant when we |
8b29d732f97b
implement cx_kvl_map_remove()
Mike Becker <universe@uap-core.de>
parents:
1358
diff
changeset
|
349 | // can have the node ptr directly instead) |
8b29d732f97b
implement cx_kvl_map_remove()
Mike Becker <universe@uap-core.de>
parents:
1358
diff
changeset
|
350 | // therefore, we re-implement the logic ourselves |
8b29d732f97b
implement cx_kvl_map_remove()
Mike Becker <universe@uap-core.de>
parents:
1358
diff
changeset
|
351 | |
8b29d732f97b
implement cx_kvl_map_remove()
Mike Becker <universe@uap-core.de>
parents:
1358
diff
changeset
|
352 | // check if the outside caller want's us to return or to destroy the element |
8b29d732f97b
implement cx_kvl_map_remove()
Mike Becker <universe@uap-core.de>
parents:
1358
diff
changeset
|
353 | if (targetbuf == NULL) { |
1365
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
354 | // patch the destructors and invoke them through the wrapper |
e4135791687e
implement a patch function that results in (almost) always calling the correct destructors
Mike Becker <universe@uap-core.de>
parents:
1362
diff
changeset
|
355 | cx_kv_list_update_destructors(kv_list); |
1367
6b3d52dd176e
change linked_list.c to allow custom data in nodes + implement cx_kv_list_set_key()
Mike Becker <universe@uap-core.de>
parents:
1365
diff
changeset
|
356 | cx_invoke_advanced_destructor(&kv_list->list.base, node_data); |
1360
8b29d732f97b
implement cx_kvl_map_remove()
Mike Becker <universe@uap-core.de>
parents:
1358
diff
changeset
|
357 | } else { |
8b29d732f97b
implement cx_kvl_map_remove()
Mike Becker <universe@uap-core.de>
parents:
1358
diff
changeset
|
358 | // copy the element to the target buffer |
1367
6b3d52dd176e
change linked_list.c to allow custom data in nodes + implement cx_kv_list_set_key()
Mike Becker <universe@uap-core.de>
parents:
1365
diff
changeset
|
359 | memcpy(targetbuf, node_data, kv_list->list.base.collection.elem_size); |
1360
8b29d732f97b
implement cx_kvl_map_remove()
Mike Becker <universe@uap-core.de>
parents:
1358
diff
changeset
|
360 | } |
8b29d732f97b
implement cx_kvl_map_remove()
Mike Becker <universe@uap-core.de>
parents:
1358
diff
changeset
|
361 | |
8b29d732f97b
implement cx_kvl_map_remove()
Mike Becker <universe@uap-core.de>
parents:
1358
diff
changeset
|
362 | // calculate the address of the node |
1367
6b3d52dd176e
change linked_list.c to allow custom data in nodes + implement cx_kv_list_set_key()
Mike Becker <universe@uap-core.de>
parents:
1365
diff
changeset
|
363 | void *node_ptr = (char*)node_data - kv_list->list.loc_data; |
1360
8b29d732f97b
implement cx_kvl_map_remove()
Mike Becker <universe@uap-core.de>
parents:
1358
diff
changeset
|
364 | |
8b29d732f97b
implement cx_kvl_map_remove()
Mike Becker <universe@uap-core.de>
parents:
1358
diff
changeset
|
365 | // unlink the node |
8b29d732f97b
implement cx_kvl_map_remove()
Mike Becker <universe@uap-core.de>
parents:
1358
diff
changeset
|
366 | cx_linked_list_remove( |
8b29d732f97b
implement cx_kvl_map_remove()
Mike Becker <universe@uap-core.de>
parents:
1358
diff
changeset
|
367 | &kv_list->list.begin, |
8b29d732f97b
implement cx_kvl_map_remove()
Mike Becker <universe@uap-core.de>
parents:
1358
diff
changeset
|
368 | &kv_list->list.end, |
1367
6b3d52dd176e
change linked_list.c to allow custom data in nodes + implement cx_kv_list_set_key()
Mike Becker <universe@uap-core.de>
parents:
1365
diff
changeset
|
369 | kv_list->list.loc_prev, |
6b3d52dd176e
change linked_list.c to allow custom data in nodes + implement cx_kv_list_set_key()
Mike Becker <universe@uap-core.de>
parents:
1365
diff
changeset
|
370 | kv_list->list.loc_next, |
1360
8b29d732f97b
implement cx_kvl_map_remove()
Mike Becker <universe@uap-core.de>
parents:
1358
diff
changeset
|
371 | node_ptr |
8b29d732f97b
implement cx_kvl_map_remove()
Mike Becker <universe@uap-core.de>
parents:
1358
diff
changeset
|
372 | ); |
8b29d732f97b
implement cx_kvl_map_remove()
Mike Becker <universe@uap-core.de>
parents:
1358
diff
changeset
|
373 | |
8b29d732f97b
implement cx_kvl_map_remove()
Mike Becker <universe@uap-core.de>
parents:
1358
diff
changeset
|
374 | // decrement the list's size |
1367
6b3d52dd176e
change linked_list.c to allow custom data in nodes + implement cx_kv_list_set_key()
Mike Becker <universe@uap-core.de>
parents:
1365
diff
changeset
|
375 | kv_list->list.base.collection.size--; |
1360
8b29d732f97b
implement cx_kvl_map_remove()
Mike Becker <universe@uap-core.de>
parents:
1358
diff
changeset
|
376 | |
8b29d732f97b
implement cx_kvl_map_remove()
Mike Becker <universe@uap-core.de>
parents:
1358
diff
changeset
|
377 | // deallocate the node |
1367
6b3d52dd176e
change linked_list.c to allow custom data in nodes + implement cx_kv_list_set_key()
Mike Becker <universe@uap-core.de>
parents:
1365
diff
changeset
|
378 | cxFree(kv_list->list.base.collection.allocator, node_ptr); |
1360
8b29d732f97b
implement cx_kvl_map_remove()
Mike Becker <universe@uap-core.de>
parents:
1358
diff
changeset
|
379 | |
8b29d732f97b
implement cx_kvl_map_remove()
Mike Becker <universe@uap-core.de>
parents:
1358
diff
changeset
|
380 | return 0; |
1358
dda9c330e3e5
make test_kv_list_map_put() pass
Mike Becker <universe@uap-core.de>
parents:
1353
diff
changeset
|
381 | } |
dda9c330e3e5
make test_kv_list_map_put() pass
Mike Becker <universe@uap-core.de>
parents:
1353
diff
changeset
|
382 | |
1384
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
383 | static void *cx_kvl_iter_current_entry(const void *it) { |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
384 | const CxMapIterator *iter = it; |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
385 | return (void*)&iter->entry; |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
386 | } |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
387 | |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
388 | static void *cx_kvl_iter_current_key(const void *it) { |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
389 | const CxMapEntry *entry = cx_kvl_iter_current_entry(it); |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
390 | return (void*)entry->key; |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
391 | } |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
392 | |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
393 | static void *cx_kvl_iter_current_value(const void *it) { |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
394 | const CxMapEntry *entry = cx_kvl_iter_current_entry(it); |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
395 | return entry->value; |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
396 | } |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
397 | |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
398 | static void cx_kvl_iter_next(void *it) { |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
399 | CxMapIterator *iter = it; |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
400 | cx_kv_list *kv_list = ((struct cx_kv_list_map_s*)iter->map.m)->list; |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
401 | |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
402 | // find the next list entry that has a key assigned |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
403 | CxHashKey *key = NULL; |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
404 | char *next = iter->elem; |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
405 | while (true) { |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
406 | next = *(char**)(next + kv_list->list.loc_next); |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
407 | if (next == NULL) break; |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
408 | key = cx_kv_list_loc_key(kv_list, next + kv_list->list.loc_data); |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
409 | if (key->hash != 0) break; |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
410 | } |
1386
748d0d40881e
kv-list: implement mutating iterator support
Mike Becker <universe@uap-core.de>
parents:
1384
diff
changeset
|
411 | |
748d0d40881e
kv-list: implement mutating iterator support
Mike Becker <universe@uap-core.de>
parents:
1384
diff
changeset
|
412 | // remove previous element if requested |
748d0d40881e
kv-list: implement mutating iterator support
Mike Becker <universe@uap-core.de>
parents:
1384
diff
changeset
|
413 | if (iter->base.remove) { |
748d0d40881e
kv-list: implement mutating iterator support
Mike Becker <universe@uap-core.de>
parents:
1384
diff
changeset
|
414 | iter->base.remove = false; |
748d0d40881e
kv-list: implement mutating iterator support
Mike Becker <universe@uap-core.de>
parents:
1384
diff
changeset
|
415 | cx_kv_list_update_destructors(kv_list); |
748d0d40881e
kv-list: implement mutating iterator support
Mike Becker <universe@uap-core.de>
parents:
1384
diff
changeset
|
416 | char *elem = iter->elem; |
748d0d40881e
kv-list: implement mutating iterator support
Mike Becker <universe@uap-core.de>
parents:
1384
diff
changeset
|
417 | char *elem_data = elem + kv_list->list.loc_data; |
748d0d40881e
kv-list: implement mutating iterator support
Mike Becker <universe@uap-core.de>
parents:
1384
diff
changeset
|
418 | CxHashKey *elem_key = cx_kv_list_loc_key(kv_list, elem_data); |
748d0d40881e
kv-list: implement mutating iterator support
Mike Becker <universe@uap-core.de>
parents:
1384
diff
changeset
|
419 | // key is guaranteed to exist because iterator only iterates over elems with a key |
748d0d40881e
kv-list: implement mutating iterator support
Mike Becker <universe@uap-core.de>
parents:
1384
diff
changeset
|
420 | kv_list->map_methods->remove(&kv_list->map->map_base.base, *elem_key, NULL); |
748d0d40881e
kv-list: implement mutating iterator support
Mike Becker <universe@uap-core.de>
parents:
1384
diff
changeset
|
421 | cx_invoke_advanced_destructor(&kv_list->list.base, elem_data); |
748d0d40881e
kv-list: implement mutating iterator support
Mike Becker <universe@uap-core.de>
parents:
1384
diff
changeset
|
422 | cx_linked_list_remove( |
748d0d40881e
kv-list: implement mutating iterator support
Mike Becker <universe@uap-core.de>
parents:
1384
diff
changeset
|
423 | &kv_list->list.begin, |
748d0d40881e
kv-list: implement mutating iterator support
Mike Becker <universe@uap-core.de>
parents:
1384
diff
changeset
|
424 | &kv_list->list.end, |
748d0d40881e
kv-list: implement mutating iterator support
Mike Becker <universe@uap-core.de>
parents:
1384
diff
changeset
|
425 | kv_list->list.loc_prev, |
748d0d40881e
kv-list: implement mutating iterator support
Mike Becker <universe@uap-core.de>
parents:
1384
diff
changeset
|
426 | kv_list->list.loc_next, |
748d0d40881e
kv-list: implement mutating iterator support
Mike Becker <universe@uap-core.de>
parents:
1384
diff
changeset
|
427 | elem |
748d0d40881e
kv-list: implement mutating iterator support
Mike Becker <universe@uap-core.de>
parents:
1384
diff
changeset
|
428 | ); |
748d0d40881e
kv-list: implement mutating iterator support
Mike Becker <universe@uap-core.de>
parents:
1384
diff
changeset
|
429 | cxFree(kv_list->list.base.collection.allocator, elem); |
748d0d40881e
kv-list: implement mutating iterator support
Mike Becker <universe@uap-core.de>
parents:
1384
diff
changeset
|
430 | kv_list->list.base.collection.size--; |
748d0d40881e
kv-list: implement mutating iterator support
Mike Becker <universe@uap-core.de>
parents:
1384
diff
changeset
|
431 | iter->index--; |
748d0d40881e
kv-list: implement mutating iterator support
Mike Becker <universe@uap-core.de>
parents:
1384
diff
changeset
|
432 | iter->elem_count--; |
748d0d40881e
kv-list: implement mutating iterator support
Mike Becker <universe@uap-core.de>
parents:
1384
diff
changeset
|
433 | } |
748d0d40881e
kv-list: implement mutating iterator support
Mike Becker <universe@uap-core.de>
parents:
1384
diff
changeset
|
434 | |
748d0d40881e
kv-list: implement mutating iterator support
Mike Becker <universe@uap-core.de>
parents:
1384
diff
changeset
|
435 | // advance to the next element, if any |
1384
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
436 | if (next == NULL) { |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
437 | iter->index = kv_list->list.base.collection.size; |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
438 | iter->elem = NULL; |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
439 | iter->entry = (CxMapEntry){NULL, NULL}; |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
440 | return; |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
441 | } |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
442 | iter->index++; |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
443 | iter->elem = next; |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
444 | iter->entry.key = key; |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
445 | if (kv_list->list.base.collection.store_pointer) { |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
446 | iter->entry.value = *(void**)(next + kv_list->list.loc_data); |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
447 | } else { |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
448 | iter->entry.value = (void*)(next + kv_list->list.loc_data); |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
449 | } |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
450 | } |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
451 | |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
452 | static bool cx_kvl_iter_valid(const void *it) { |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
453 | const CxMapIterator *iter = it; |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
454 | return iter->elem != NULL; |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
455 | } |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
456 | |
1358
dda9c330e3e5
make test_kv_list_map_put() pass
Mike Becker <universe@uap-core.de>
parents:
1353
diff
changeset
|
457 | CxMapIterator cx_kvl_map_iterator(const CxMap *map, enum cx_map_iterator_type type) { |
1405
0f6515875a09
fix using empty initializer, which is a C23 extension
Mike Becker <universe@uap-core.de>
parents:
1397
diff
changeset
|
458 | CxMapIterator iter = {0}; |
1384
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
459 | |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
460 | iter.type = type; |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
461 | iter.map.c = map; |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
462 | // although we iterate over the list, we only report that many elements that have a key in the map |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
463 | iter.elem_count = map->collection.size; |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
464 | |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
465 | switch (type) { |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
466 | case CX_MAP_ITERATOR_PAIRS: |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
467 | iter.elem_size = sizeof(CxMapEntry); |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
468 | iter.base.current = cx_kvl_iter_current_entry; |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
469 | break; |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
470 | case CX_MAP_ITERATOR_KEYS: |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
471 | iter.elem_size = sizeof(CxHashKey); |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
472 | iter.base.current = cx_kvl_iter_current_key; |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
473 | break; |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
474 | case CX_MAP_ITERATOR_VALUES: |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
475 | iter.elem_size = map->collection.elem_size; |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
476 | iter.base.current = cx_kvl_iter_current_value; |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
477 | break; |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
478 | default: |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
479 | assert(false); // LCOV_EXCL_LINE |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
480 | } |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
481 | |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
482 | iter.base.next = cx_kvl_iter_next; |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
483 | iter.base.valid = cx_kvl_iter_valid; |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
484 | |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
485 | // find the first list entry that has a key assigned |
1358
dda9c330e3e5
make test_kv_list_map_put() pass
Mike Becker <universe@uap-core.de>
parents:
1353
diff
changeset
|
486 | cx_kv_list *kv_list = ((struct cx_kv_list_map_s*)map)->list; |
1384
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
487 | CxHashKey *key = NULL; |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
488 | char *next = kv_list->list.begin; |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
489 | while (next != NULL) { |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
490 | key = cx_kv_list_loc_key(kv_list, next + kv_list->list.loc_data); |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
491 | if (key->hash != 0) break; |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
492 | next = *(char**)(next + kv_list->list.loc_next); |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
493 | } |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
494 | if (next == NULL) { |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
495 | iter.elem = NULL; |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
496 | iter.entry = (CxMapEntry){NULL, NULL}; |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
497 | } else { |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
498 | iter.elem = next; |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
499 | iter.entry.key = key; |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
500 | if (kv_list->list.base.collection.store_pointer) { |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
501 | iter.entry.value = *(void**)(next + kv_list->list.loc_data); |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
502 | } else { |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
503 | iter.entry.value = (void*)(next + kv_list->list.loc_data); |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
504 | } |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
505 | } |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
506 | |
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
507 | return iter; |
1358
dda9c330e3e5
make test_kv_list_map_put() pass
Mike Becker <universe@uap-core.de>
parents:
1353
diff
changeset
|
508 | } |
dda9c330e3e5
make test_kv_list_map_put() pass
Mike Becker <universe@uap-core.de>
parents:
1353
diff
changeset
|
509 | |
1350
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
510 | static cx_list_class cx_kv_list_class = { |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
511 | cx_kvl_deallocate, |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
512 | cx_kvl_insert_element, |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
513 | cx_kvl_insert_array, |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
514 | cx_kvl_insert_sorted, |
1419
e46406fd1b3c
add functions to insert elements into lists/arrays without duplicates - resolves #557
Mike Becker <universe@uap-core.de>
parents:
1405
diff
changeset
|
515 | cx_kvl_insert_unique, |
1350
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
516 | cx_kvl_insert_iter, |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
517 | cx_kvl_remove, |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
518 | cx_kvl_clear, |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
519 | cx_kvl_swap, |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
520 | cx_kvl_at, |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
521 | cx_kvl_find_remove, |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
522 | cx_kvl_sort, |
1352
8428516137dd
make comparisons between kv_list and linked_list optimizable
Mike Becker <universe@uap-core.de>
parents:
1350
diff
changeset
|
523 | NULL, |
1350
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
524 | cx_kvl_reverse, |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
525 | cx_kvl_iterator, |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
526 | }; |
1348
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
527 | |
1358
dda9c330e3e5
make test_kv_list_map_put() pass
Mike Becker <universe@uap-core.de>
parents:
1353
diff
changeset
|
528 | static cx_map_class cx_kv_map_class = { |
dda9c330e3e5
make test_kv_list_map_put() pass
Mike Becker <universe@uap-core.de>
parents:
1353
diff
changeset
|
529 | cx_kvl_map_deallocate, |
dda9c330e3e5
make test_kv_list_map_put() pass
Mike Becker <universe@uap-core.de>
parents:
1353
diff
changeset
|
530 | cx_kvl_map_clear, |
dda9c330e3e5
make test_kv_list_map_put() pass
Mike Becker <universe@uap-core.de>
parents:
1353
diff
changeset
|
531 | cx_kvl_map_put, |
dda9c330e3e5
make test_kv_list_map_put() pass
Mike Becker <universe@uap-core.de>
parents:
1353
diff
changeset
|
532 | cx_kvl_map_get, |
dda9c330e3e5
make test_kv_list_map_put() pass
Mike Becker <universe@uap-core.de>
parents:
1353
diff
changeset
|
533 | cx_kvl_map_remove, |
dda9c330e3e5
make test_kv_list_map_put() pass
Mike Becker <universe@uap-core.de>
parents:
1353
diff
changeset
|
534 | cx_kvl_map_iterator, |
dda9c330e3e5
make test_kv_list_map_put() pass
Mike Becker <universe@uap-core.de>
parents:
1353
diff
changeset
|
535 | }; |
dda9c330e3e5
make test_kv_list_map_put() pass
Mike Becker <universe@uap-core.de>
parents:
1353
diff
changeset
|
536 | |
1348
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
537 | CxList *cxKvListCreate( |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
538 | const CxAllocator *allocator, |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
539 | cx_compare_func comparator, |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
540 | size_t elem_size |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
541 | ) { |
1350
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
542 | if (allocator == NULL) { |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
543 | allocator = cxDefaultAllocator; |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
544 | } |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
545 | |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
546 | // create a normal linked list and a normal hash map, first |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
547 | CxList *list = cxLinkedListCreate(allocator, comparator, elem_size); |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
548 | if (list == NULL) return NULL; // LCOV_EXCL_LINE |
1367
6b3d52dd176e
change linked_list.c to allow custom data in nodes + implement cx_kv_list_set_key()
Mike Becker <universe@uap-core.de>
parents:
1365
diff
changeset
|
549 | cx_linked_list *ll = (cx_linked_list*)list; |
6b3d52dd176e
change linked_list.c to allow custom data in nodes + implement cx_kv_list_set_key()
Mike Becker <universe@uap-core.de>
parents:
1365
diff
changeset
|
550 | ll->extra_data_len = sizeof(CxHashKey); |
1350
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
551 | CxMap *map = cxHashMapCreate(allocator, CX_STORE_POINTERS, 0); |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
552 | if (map == NULL) { // LCOV_EXCL_START |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
553 | cxListFree(list); |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
554 | return NULL; |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
555 | } // LCOV_EXCL_STOP |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
556 | |
1352
8428516137dd
make comparisons between kv_list and linked_list optimizable
Mike Becker <universe@uap-core.de>
parents:
1350
diff
changeset
|
557 | // patch the kv-list class with the compare function of the linked list |
8428516137dd
make comparisons between kv_list and linked_list optimizable
Mike Becker <universe@uap-core.de>
parents:
1350
diff
changeset
|
558 | // this allows cxListCompare() to optimize comparisons between linked lists and kv-list |
8428516137dd
make comparisons between kv_list and linked_list optimizable
Mike Becker <universe@uap-core.de>
parents:
1350
diff
changeset
|
559 | cx_kv_list_class.compare = list->cl->compare; |
8428516137dd
make comparisons between kv_list and linked_list optimizable
Mike Becker <universe@uap-core.de>
parents:
1350
diff
changeset
|
560 | |
1350
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
561 | // reallocate the map to add memory for the list back-reference |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
562 | struct cx_kv_list_map_s *kv_map = cxRealloc(allocator, map, sizeof(struct cx_kv_list_map_s)); |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
563 | |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
564 | // reallocate the list to add memory for storing the metadata |
1358
dda9c330e3e5
make test_kv_list_map_put() pass
Mike Becker <universe@uap-core.de>
parents:
1353
diff
changeset
|
565 | cx_kv_list *kv_list = cxRealloc(allocator, list, sizeof(struct cx_kv_list_s)); |
1350
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
566 | |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
567 | // if any of the reallocations failed, we bail out |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
568 | if (kv_map != NULL && kv_list != NULL) { |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
569 | map = (CxMap*) kv_map; |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
570 | list = (CxList*) kv_list; |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
571 | } else { // LCOV_EXCL_START |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
572 | cxListFree(list); |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
573 | cxMapFree(map); |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
574 | return NULL; |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
575 | } // LCOV_EXCL_STOP |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
576 | |
1371
37dcaeebe5ca
kv-list: fix a possible source of UB when allocation fails during list creation
Mike Becker <universe@uap-core.de>
parents:
1370
diff
changeset
|
577 | // zero the custom destructor information |
37dcaeebe5ca
kv-list: fix a possible source of UB when allocation fails during list creation
Mike Becker <universe@uap-core.de>
parents:
1370
diff
changeset
|
578 | memset((char*)kv_list + offsetof(cx_kv_list, list_destr), 0, sizeof(void*)*6); |
37dcaeebe5ca
kv-list: fix a possible source of UB when allocation fails during list creation
Mike Becker <universe@uap-core.de>
parents:
1370
diff
changeset
|
579 | |
1350
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
580 | // combine the list and the map aspect |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
581 | kv_list->map = kv_map; |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
582 | kv_map->list = kv_list; |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
583 | |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
584 | // remember the base methods and override them |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
585 | kv_list->map_methods = map->cl; |
1358
dda9c330e3e5
make test_kv_list_map_put() pass
Mike Becker <universe@uap-core.de>
parents:
1353
diff
changeset
|
586 | map->cl = &cx_kv_map_class; |
1353
5a13b9c1c57b
fix that the wrong vtable is patched when CX_STORE_POINTERS is used
Mike Becker <universe@uap-core.de>
parents:
1352
diff
changeset
|
587 | if (list->climpl == NULL) { |
5a13b9c1c57b
fix that the wrong vtable is patched when CX_STORE_POINTERS is used
Mike Becker <universe@uap-core.de>
parents:
1352
diff
changeset
|
588 | kv_list->list_methods = list->cl; |
5a13b9c1c57b
fix that the wrong vtable is patched when CX_STORE_POINTERS is used
Mike Becker <universe@uap-core.de>
parents:
1352
diff
changeset
|
589 | list->cl = &cx_kv_list_class; |
5a13b9c1c57b
fix that the wrong vtable is patched when CX_STORE_POINTERS is used
Mike Becker <universe@uap-core.de>
parents:
1352
diff
changeset
|
590 | } else { |
5a13b9c1c57b
fix that the wrong vtable is patched when CX_STORE_POINTERS is used
Mike Becker <universe@uap-core.de>
parents:
1352
diff
changeset
|
591 | kv_list->list_methods = list->climpl; |
5a13b9c1c57b
fix that the wrong vtable is patched when CX_STORE_POINTERS is used
Mike Becker <universe@uap-core.de>
parents:
1352
diff
changeset
|
592 | list->climpl = &cx_kv_list_class; |
5a13b9c1c57b
fix that the wrong vtable is patched when CX_STORE_POINTERS is used
Mike Becker <universe@uap-core.de>
parents:
1352
diff
changeset
|
593 | } |
1350
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
594 | |
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
595 | return list; |
1348
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
596 | } |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
597 | |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
598 | CxMap *cxKvListCreateAsMap( |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
599 | const CxAllocator *allocator, |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
600 | cx_compare_func comparator, |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
601 | size_t elem_size |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
602 | ) { |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
603 | CxList *list = cxKvListCreate(allocator, comparator, elem_size); |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
604 | return list == NULL ? NULL : cxKvListAsMap(list); |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
605 | } |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
606 | |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
607 | CxList *cxKvListAsList(CxMap *map) { |
1367
6b3d52dd176e
change linked_list.c to allow custom data in nodes + implement cx_kv_list_set_key()
Mike Becker <universe@uap-core.de>
parents:
1365
diff
changeset
|
608 | return &((struct cx_kv_list_map_s*)map)->list->list.base; |
1348
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
609 | } |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
610 | |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
611 | CxMap *cxKvListAsMap(CxList *list) { |
1350
189756516eaa
implement kv-list to a point where it correctly behaves like a list
Mike Becker <universe@uap-core.de>
parents:
1348
diff
changeset
|
612 | return &((cx_kv_list*)list)->map->map_base.base; |
1348
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
613 | } |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
614 | |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
615 | int cx_kv_list_set_key(CxList *list, size_t index, CxHashKey key) { |
1367
6b3d52dd176e
change linked_list.c to allow custom data in nodes + implement cx_kv_list_set_key()
Mike Becker <universe@uap-core.de>
parents:
1365
diff
changeset
|
616 | cx_kv_list *kv_list = (cx_kv_list*)list; |
1373
a6aaa77b6809
make cx_kvl_remove() also remove the keys from the map
Mike Becker <universe@uap-core.de>
parents:
1372
diff
changeset
|
617 | void *node_data = kv_list->list_methods->at(list, index); |
a6aaa77b6809
make cx_kvl_remove() also remove the keys from the map
Mike Becker <universe@uap-core.de>
parents:
1372
diff
changeset
|
618 | if (node_data == NULL) { |
a6aaa77b6809
make cx_kvl_remove() also remove the keys from the map
Mike Becker <universe@uap-core.de>
parents:
1372
diff
changeset
|
619 | return 1; |
a6aaa77b6809
make cx_kvl_remove() also remove the keys from the map
Mike Becker <universe@uap-core.de>
parents:
1372
diff
changeset
|
620 | } |
a6aaa77b6809
make cx_kvl_remove() also remove the keys from the map
Mike Becker <universe@uap-core.de>
parents:
1372
diff
changeset
|
621 | // if the hash has not yet been computed, do it now |
a6aaa77b6809
make cx_kvl_remove() also remove the keys from the map
Mike Becker <universe@uap-core.de>
parents:
1372
diff
changeset
|
622 | if (key.hash == 0) { |
a6aaa77b6809
make cx_kvl_remove() also remove the keys from the map
Mike Becker <universe@uap-core.de>
parents:
1372
diff
changeset
|
623 | cx_hash_murmur(&key); |
a6aaa77b6809
make cx_kvl_remove() also remove the keys from the map
Mike Becker <universe@uap-core.de>
parents:
1372
diff
changeset
|
624 | } |
1376
0698e573936f
add error handling to cx_kv_list_set_key()
Mike Becker <universe@uap-core.de>
parents:
1375
diff
changeset
|
625 | |
1382
f61119884dcd
disallow setting a key that already exists
Mike Becker <universe@uap-core.de>
parents:
1381
diff
changeset
|
626 | // check if the key is already assigned |
1383
3db28cb1e5ec
allow setting the key again on the same node
Mike Becker <universe@uap-core.de>
parents:
1382
diff
changeset
|
627 | void *existing = kv_list->map_methods->get(&kv_list->map->map_base.base, key); |
3db28cb1e5ec
allow setting the key again on the same node
Mike Becker <universe@uap-core.de>
parents:
1382
diff
changeset
|
628 | if (existing == node_data) { |
3db28cb1e5ec
allow setting the key again on the same node
Mike Becker <universe@uap-core.de>
parents:
1382
diff
changeset
|
629 | return 0; // nothing to do |
3db28cb1e5ec
allow setting the key again on the same node
Mike Becker <universe@uap-core.de>
parents:
1382
diff
changeset
|
630 | } |
3db28cb1e5ec
allow setting the key again on the same node
Mike Becker <universe@uap-core.de>
parents:
1382
diff
changeset
|
631 | if (existing != NULL) { |
3db28cb1e5ec
allow setting the key again on the same node
Mike Becker <universe@uap-core.de>
parents:
1382
diff
changeset
|
632 | // the key is already assigned to another node, we disallow re-assignment |
1382
f61119884dcd
disallow setting a key that already exists
Mike Becker <universe@uap-core.de>
parents:
1381
diff
changeset
|
633 | return 1; |
f61119884dcd
disallow setting a key that already exists
Mike Becker <universe@uap-core.de>
parents:
1381
diff
changeset
|
634 | } |
f61119884dcd
disallow setting a key that already exists
Mike Becker <universe@uap-core.de>
parents:
1381
diff
changeset
|
635 | |
f61119884dcd
disallow setting a key that already exists
Mike Becker <universe@uap-core.de>
parents:
1381
diff
changeset
|
636 | // add the key to the map; |
1376
0698e573936f
add error handling to cx_kv_list_set_key()
Mike Becker <universe@uap-core.de>
parents:
1375
diff
changeset
|
637 | if (NULL == kv_list->map_methods->put(&kv_list->map->map_base.base, key, node_data)) { |
1384
a2cfbff39e5d
implement non-mutating iterator
Mike Becker <universe@uap-core.de>
parents:
1383
diff
changeset
|
638 | return 1; // LCOV_EXCL_LINE |
1376
0698e573936f
add error handling to cx_kv_list_set_key()
Mike Becker <universe@uap-core.de>
parents:
1375
diff
changeset
|
639 | } |
0698e573936f
add error handling to cx_kv_list_set_key()
Mike Becker <universe@uap-core.de>
parents:
1375
diff
changeset
|
640 | |
0698e573936f
add error handling to cx_kv_list_set_key()
Mike Becker <universe@uap-core.de>
parents:
1375
diff
changeset
|
641 | // write the key to the list's node |
1373
a6aaa77b6809
make cx_kvl_remove() also remove the keys from the map
Mike Becker <universe@uap-core.de>
parents:
1372
diff
changeset
|
642 | CxHashKey *loc_key = cx_kv_list_loc_key(kv_list, node_data); |
a6aaa77b6809
make cx_kvl_remove() also remove the keys from the map
Mike Becker <universe@uap-core.de>
parents:
1372
diff
changeset
|
643 | *loc_key = key; |
1367
6b3d52dd176e
change linked_list.c to allow custom data in nodes + implement cx_kv_list_set_key()
Mike Becker <universe@uap-core.de>
parents:
1365
diff
changeset
|
644 | |
6b3d52dd176e
change linked_list.c to allow custom data in nodes + implement cx_kv_list_set_key()
Mike Becker <universe@uap-core.de>
parents:
1365
diff
changeset
|
645 | return 0; |
1348
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
646 | } |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
647 | |
1377
1562bdf948da
implement cxKvListRemoveKey()
Mike Becker <universe@uap-core.de>
parents:
1376
diff
changeset
|
648 | int cxKvListRemoveKey(CxList *list, size_t index) { |
1562bdf948da
implement cxKvListRemoveKey()
Mike Becker <universe@uap-core.de>
parents:
1376
diff
changeset
|
649 | cx_kv_list *kv_list = (cx_kv_list*)list; |
1562bdf948da
implement cxKvListRemoveKey()
Mike Becker <universe@uap-core.de>
parents:
1376
diff
changeset
|
650 | void *node_data = kv_list->list_methods->at(list, index); |
1562bdf948da
implement cxKvListRemoveKey()
Mike Becker <universe@uap-core.de>
parents:
1376
diff
changeset
|
651 | if (node_data == NULL) { |
1562bdf948da
implement cxKvListRemoveKey()
Mike Becker <universe@uap-core.de>
parents:
1376
diff
changeset
|
652 | return 1; |
1562bdf948da
implement cxKvListRemoveKey()
Mike Becker <universe@uap-core.de>
parents:
1376
diff
changeset
|
653 | } |
1562bdf948da
implement cxKvListRemoveKey()
Mike Becker <universe@uap-core.de>
parents:
1376
diff
changeset
|
654 | CxHashKey *loc_key = cx_kv_list_loc_key(kv_list, node_data); |
1562bdf948da
implement cxKvListRemoveKey()
Mike Becker <universe@uap-core.de>
parents:
1376
diff
changeset
|
655 | if (loc_key->hash == 0) { |
1562bdf948da
implement cxKvListRemoveKey()
Mike Becker <universe@uap-core.de>
parents:
1376
diff
changeset
|
656 | return 0; |
1562bdf948da
implement cxKvListRemoveKey()
Mike Becker <universe@uap-core.de>
parents:
1376
diff
changeset
|
657 | } |
1562bdf948da
implement cxKvListRemoveKey()
Mike Becker <universe@uap-core.de>
parents:
1376
diff
changeset
|
658 | kv_list->map_methods->remove(&kv_list->map->map_base.base, *loc_key, NULL); |
1562bdf948da
implement cxKvListRemoveKey()
Mike Becker <universe@uap-core.de>
parents:
1376
diff
changeset
|
659 | // also zero the memory in the list node, |
1562bdf948da
implement cxKvListRemoveKey()
Mike Becker <universe@uap-core.de>
parents:
1376
diff
changeset
|
660 | // but don't free the key data (that was done by the map remove) |
1562bdf948da
implement cxKvListRemoveKey()
Mike Becker <universe@uap-core.de>
parents:
1376
diff
changeset
|
661 | memset(loc_key, 0, sizeof(CxHashKey)); |
1562bdf948da
implement cxKvListRemoveKey()
Mike Becker <universe@uap-core.de>
parents:
1376
diff
changeset
|
662 | return 0; |
1348
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
663 | } |
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
664 | |
1394 | 665 | const CxHashKey *cxKvListGetKey(CxList *list, size_t index) { |
666 | cx_kv_list *kv_list = (cx_kv_list*)list; | |
667 | void *node_data = kv_list->list_methods->at(list, index); | |
668 | if (node_data == NULL) { | |
669 | return NULL; | |
670 | } | |
671 | CxHashKey *key = cx_kv_list_loc_key(kv_list, node_data); | |
672 | if (key->hash == 0) { | |
673 | return NULL; | |
674 | } | |
675 | return key; | |
676 | } | |
677 | ||
1348
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
678 | int cx_kv_list_insert(CxList *list, size_t index, CxHashKey key, void *value) { |
1393
461d256e32c6
fix that cxKvListInsert() did not lose the sorted property
Mike Becker <universe@uap-core.de>
parents:
1386
diff
changeset
|
679 | // assume we are losing the sorted property |
461d256e32c6
fix that cxKvListInsert() did not lose the sorted property
Mike Becker <universe@uap-core.de>
parents:
1386
diff
changeset
|
680 | list->collection.sorted = false; |
461d256e32c6
fix that cxKvListInsert() did not lose the sorted property
Mike Becker <universe@uap-core.de>
parents:
1386
diff
changeset
|
681 | |
1378
1b4fa55f7caa
implement cx_kv_list_insert()
Mike Becker <universe@uap-core.de>
parents:
1377
diff
changeset
|
682 | cx_kv_list *kv_list = (cx_kv_list*)list; |
1b4fa55f7caa
implement cx_kv_list_insert()
Mike Becker <universe@uap-core.de>
parents:
1377
diff
changeset
|
683 | |
1381
ee421d6b95ef
consider the edge case that either list or map operation fails when adding an element
Mike Becker <universe@uap-core.de>
parents:
1379
diff
changeset
|
684 | // reserve memory in the map |
ee421d6b95ef
consider the edge case that either list or map operation fails when adding an element
Mike Becker <universe@uap-core.de>
parents:
1379
diff
changeset
|
685 | void **map_data = kv_list->map_methods->put(&kv_list->map->map_base.base, key, NULL); |
ee421d6b95ef
consider the edge case that either list or map operation fails when adding an element
Mike Becker <universe@uap-core.de>
parents:
1379
diff
changeset
|
686 | if (map_data == NULL) return 1; // LCOV_EXCL_LINE |
ee421d6b95ef
consider the edge case that either list or map operation fails when adding an element
Mike Becker <universe@uap-core.de>
parents:
1379
diff
changeset
|
687 | |
1379
9ad4a7011528
improve cx_kv_list_insert() by using low level access to the list method
Mike Becker <universe@uap-core.de>
parents:
1378
diff
changeset
|
688 | // insert the node |
9ad4a7011528
improve cx_kv_list_insert() by using low level access to the list method
Mike Becker <universe@uap-core.de>
parents:
1378
diff
changeset
|
689 | void *node_data = kv_list->list_methods->insert_element(&kv_list->list.base, index, |
9ad4a7011528
improve cx_kv_list_insert() by using low level access to the list method
Mike Becker <universe@uap-core.de>
parents:
1378
diff
changeset
|
690 | kv_list->list.base.collection.store_pointer ? &value : value); |
1381
ee421d6b95ef
consider the edge case that either list or map operation fails when adding an element
Mike Becker <universe@uap-core.de>
parents:
1379
diff
changeset
|
691 | if (node_data == NULL) { // LCOV_EXCL_START |
ee421d6b95ef
consider the edge case that either list or map operation fails when adding an element
Mike Becker <universe@uap-core.de>
parents:
1379
diff
changeset
|
692 | // non-destructively remove the key again |
ee421d6b95ef
consider the edge case that either list or map operation fails when adding an element
Mike Becker <universe@uap-core.de>
parents:
1379
diff
changeset
|
693 | kv_list->map_methods->remove(&kv_list->map->map_base.base, key, &map_data); |
ee421d6b95ef
consider the edge case that either list or map operation fails when adding an element
Mike Becker <universe@uap-core.de>
parents:
1379
diff
changeset
|
694 | return 1; |
ee421d6b95ef
consider the edge case that either list or map operation fails when adding an element
Mike Becker <universe@uap-core.de>
parents:
1379
diff
changeset
|
695 | } // LCOV_EXCL_STOP |
ee421d6b95ef
consider the edge case that either list or map operation fails when adding an element
Mike Becker <universe@uap-core.de>
parents:
1379
diff
changeset
|
696 | *map_data = node_data; |
1378
1b4fa55f7caa
implement cx_kv_list_insert()
Mike Becker <universe@uap-core.de>
parents:
1377
diff
changeset
|
697 | |
1b4fa55f7caa
implement cx_kv_list_insert()
Mike Becker <universe@uap-core.de>
parents:
1377
diff
changeset
|
698 | // write the key to the node |
1b4fa55f7caa
implement cx_kv_list_insert()
Mike Becker <universe@uap-core.de>
parents:
1377
diff
changeset
|
699 | CxHashKey *loc_key = cx_kv_list_loc_key(kv_list, node_data); |
1b4fa55f7caa
implement cx_kv_list_insert()
Mike Becker <universe@uap-core.de>
parents:
1377
diff
changeset
|
700 | *loc_key = key; |
1b4fa55f7caa
implement cx_kv_list_insert()
Mike Becker <universe@uap-core.de>
parents:
1377
diff
changeset
|
701 | |
1b4fa55f7caa
implement cx_kv_list_insert()
Mike Becker <universe@uap-core.de>
parents:
1377
diff
changeset
|
702 | return 0; |
1348
a1da355ed3b8
roll out the function stubs for the kv-list
Mike Becker <universe@uap-core.de>
parents:
diff
changeset
|
703 | } |