Tue, 04 Oct 2022 19:25:07 +0200
fix over-optimization of strstr
1. it's actually less performant to frequently read bytes
from an array instead of using the native word length
2. the SBO buffer should be local and not static to allow
multi-threading usage
264
24f5484bae97
web doc has now proper titles
Mike Becker <universe@uap-core.de>
parents:
259
diff
changeset
|
1 | --- |
390
d345541018fa
starts ucx 3.0 development
Mike Becker <universe@uap-core.de>
parents:
370
diff
changeset
|
2 | title: UCX 2.1 Modules |
264
24f5484bae97
web doc has now proper titles
Mike Becker <universe@uap-core.de>
parents:
259
diff
changeset
|
3 | --- |
259 | 4 | |
390
d345541018fa
starts ucx 3.0 development
Mike Becker <universe@uap-core.de>
parents:
370
diff
changeset
|
5 | UCX 2.1 provided several modules for data structures and algorithms. |
259 | 6 | You may choose to use specific modules by inclueding the corresponding header |
7 | file. | |
390
d345541018fa
starts ucx 3.0 development
Mike Becker <universe@uap-core.de>
parents:
370
diff
changeset
|
8 | Please note, that some modules make use of other UCX 2.1 modules. |
259 | 9 | For instance, the [Allocator](#allocator) module is used by many other modules |
10 | to allow flexible memory allocation. | |
11 | By default the header files are placed into an `ucx` directory within your | |
282
39e69d78b01d
minor formatting fix in modules.md
Mike Becker <universe@uap-core.de>
parents:
281
diff
changeset
|
12 | systems include directory. In this case you can use a module by including it |
259 | 13 | via `#include <ucx/MODULENAME.h>`. |
14 | Required modules are included automatically. | |
15 | ||
267
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
16 | <div id="modules" align="center"> |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
17 | |
340 | 18 | ----------------------- ---------------------- -------------------------------- --------------------------- |
19 | [String](#string) [Buffer](#buffer) | |
20 | [Allocator](#allocator) [Stack](#stack) [Memory Pool](#memory-pool) | |
21 | [Array](#array) [List](#list) [Map](#map) [AVL Tree](#avl-tree) | |
22 | [Logging](#logging) [Testing](#testing) [Utilities](#utilities) [Properties](#properties) | |
23 | ----------------------- ---------------------- -------------------------------- --------------------------- | |
267
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
24 | |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
25 | </div> |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
26 | |
259 | 27 | ## Allocator |
28 | ||
390
d345541018fa
starts ucx 3.0 development
Mike Becker <universe@uap-core.de>
parents:
370
diff
changeset
|
29 | *Header file:* [allocator.h](api-2.1/allocator_8h.html) |
259 | 30 | *Required modules:* None. |
31 | ||
32 | A UCX allocator consists of a pointer to the memory area / pool and four | |
33 | function pointers to memory management functions operating on this memory | |
34 | area / pool. These functions shall behave equivalent to the standard libc | |
35 | functions `malloc`, `calloc`, `realloc` and `free`. | |
36 | ||
37 | The signature of the memory management functions is based on the signature | |
38 | of the respective libc function but each of them takes the pointer to the | |
39 | memory area / pool as first argument. | |
40 | ||
41 | As the pointer to the memory area / pool can be arbitrarily chosen, any data | |
42 | can be provided to the memory management functions. One example is the | |
280
6e3c4036a80c
removes artificial anchors from modules.md
Mike Becker <universe@uap-core.de>
parents:
279
diff
changeset
|
43 | [UCX Memory Pool](#memory-pool). |
259 | 44 | |
340 | 45 | ## Array |
46 | ||
390
d345541018fa
starts ucx 3.0 development
Mike Becker <universe@uap-core.de>
parents:
370
diff
changeset
|
47 | *Header file:* [array.h](api-2.1/array_8h.html) |
340 | 48 | *Required modules:* [Allocator](#allocator) |
49 | ||
50 | The UCX Array is an implementation of a dynamic array with automatic | |
51 | reallocation. The array structure contains a capacity, the current size, | |
52 | the size of each element, the raw pointer to the memory area and an allocator. | |
359
9f86bc73f96b
adjusts the UcxArray documentation to the recent changes
Mike Becker <universe@uap-core.de>
parents:
340
diff
changeset
|
53 | Arrays are in most cases much faster than linked list. |
9f86bc73f96b
adjusts the UcxArray documentation to the recent changes
Mike Becker <universe@uap-core.de>
parents:
340
diff
changeset
|
54 | One can decide, whether to create a new array on the heap with `ucx_array_new()` |
9f86bc73f96b
adjusts the UcxArray documentation to the recent changes
Mike Becker <universe@uap-core.de>
parents:
340
diff
changeset
|
55 | or to save one indirection by initializing a `UcxArray` structure on the stack |
9f86bc73f96b
adjusts the UcxArray documentation to the recent changes
Mike Becker <universe@uap-core.de>
parents:
340
diff
changeset
|
56 | with `ucx_array_init()`. |
340 | 57 | |
58 | ### Remove duplicates from an array of strings | |
59 | ||
60 | The following example shows, how a `UcxArray` can be built with | |
61 | a standard dynamic C array (pointer+length) as basis. | |
62 | ||
63 | ```C | |
370
07ac32b385e4
updates the web doc for array
Mike Becker <universe@uap-core.de>
parents:
359
diff
changeset
|
64 | UcxArray* create_unique(sstr_t* array, size_t arrlen) { |
340 | 65 | // worst case is no duplicates, hence the capacity is set to arrlen |
370
07ac32b385e4
updates the web doc for array
Mike Becker <universe@uap-core.de>
parents:
359
diff
changeset
|
66 | UcxArray* result = ucx_array_new(arrlen, sizeof(sstr_t)); |
340 | 67 | // only append elements, if they are not already present in the array |
68 | for (size_t i = 0 ; i < arrlen ; ++i) { | |
69 | if (!ucx_array_contains(result, array+i, ucx_cmp_sstr, NULL)) { | |
370
07ac32b385e4
updates the web doc for array
Mike Becker <universe@uap-core.de>
parents:
359
diff
changeset
|
70 | ucx_array_append_from(result, array+i, 1); |
340 | 71 | } |
72 | } | |
73 | // make the array as small as possible | |
370
07ac32b385e4
updates the web doc for array
Mike Becker <universe@uap-core.de>
parents:
359
diff
changeset
|
74 | ucx_array_shrink(result); |
340 | 75 | return result; |
76 | } | |
77 | ||
78 | /* ... */ | |
79 | ||
80 | sstr_t* array = /* some standard array of strings */ | |
81 | size_t arrlen = /* the length of the array */ | |
82 | ||
370
07ac32b385e4
updates the web doc for array
Mike Becker <universe@uap-core.de>
parents:
359
diff
changeset
|
83 | UcxArray* result = create_unique(array,arrlen); |
340 | 84 | |
85 | /* Iterate over the array and print the elements */ | |
370
07ac32b385e4
updates the web doc for array
Mike Becker <universe@uap-core.de>
parents:
359
diff
changeset
|
86 | sstr_t* unique = result->data; |
07ac32b385e4
updates the web doc for array
Mike Becker <universe@uap-core.de>
parents:
359
diff
changeset
|
87 | for (size_t i = 0 ; i < result->size ; i++) { |
07ac32b385e4
updates the web doc for array
Mike Becker <universe@uap-core.de>
parents:
359
diff
changeset
|
88 | printf("%" PRIsstr "\n", SFMT(unique[i])); |
340 | 89 | } |
90 | ||
91 | /* Free the array. */ | |
370
07ac32b385e4
updates the web doc for array
Mike Becker <universe@uap-core.de>
parents:
359
diff
changeset
|
92 | ucx_array_free(result); |
07ac32b385e4
updates the web doc for array
Mike Becker <universe@uap-core.de>
parents:
359
diff
changeset
|
93 | ``` |
07ac32b385e4
updates the web doc for array
Mike Becker <universe@uap-core.de>
parents:
359
diff
changeset
|
94 | ### Preventing out of bounds writes |
07ac32b385e4
updates the web doc for array
Mike Becker <universe@uap-core.de>
parents:
359
diff
changeset
|
95 | |
07ac32b385e4
updates the web doc for array
Mike Becker <universe@uap-core.de>
parents:
359
diff
changeset
|
96 | The functions `ucx_array_reserve()`, `ucx_array_resize()`, `ucx_array_grow()`, |
07ac32b385e4
updates the web doc for array
Mike Becker <universe@uap-core.de>
parents:
359
diff
changeset
|
97 | and `ucx_array_shrink()` allow easy management of the array capacity. |
07ac32b385e4
updates the web doc for array
Mike Becker <universe@uap-core.de>
parents:
359
diff
changeset
|
98 | Imagine you want to add `n` elements to an array. If your `n` elements are |
07ac32b385e4
updates the web doc for array
Mike Becker <universe@uap-core.de>
parents:
359
diff
changeset
|
99 | already somewhere else consecutively in memory, you can use |
07ac32b385e4
updates the web doc for array
Mike Becker <universe@uap-core.de>
parents:
359
diff
changeset
|
100 | `ucx_array_append_from()` and benefit from the autogrow facility in this family |
07ac32b385e4
updates the web doc for array
Mike Becker <universe@uap-core.de>
parents:
359
diff
changeset
|
101 | of functions. Otherwise, you can ask the array to have enough capacity for |
07ac32b385e4
updates the web doc for array
Mike Becker <universe@uap-core.de>
parents:
359
diff
changeset
|
102 | holding additional `n` elements. |
07ac32b385e4
updates the web doc for array
Mike Becker <universe@uap-core.de>
parents:
359
diff
changeset
|
103 | |
07ac32b385e4
updates the web doc for array
Mike Becker <universe@uap-core.de>
parents:
359
diff
changeset
|
104 | ```C |
07ac32b385e4
updates the web doc for array
Mike Becker <universe@uap-core.de>
parents:
359
diff
changeset
|
105 | size_t n = // ... elements to add |
07ac32b385e4
updates the web doc for array
Mike Becker <universe@uap-core.de>
parents:
359
diff
changeset
|
106 | if (ucx_array_grow(array, n)) { |
07ac32b385e4
updates the web doc for array
Mike Becker <universe@uap-core.de>
parents:
359
diff
changeset
|
107 | fprintf(stderr, "Cannot add %zu elements to the array.\n", n); |
07ac32b385e4
updates the web doc for array
Mike Becker <universe@uap-core.de>
parents:
359
diff
changeset
|
108 | return 1; |
07ac32b385e4
updates the web doc for array
Mike Becker <universe@uap-core.de>
parents:
359
diff
changeset
|
109 | } |
07ac32b385e4
updates the web doc for array
Mike Becker <universe@uap-core.de>
parents:
359
diff
changeset
|
110 | for (size_t i = 0 ; i < n ; i++) { |
07ac32b385e4
updates the web doc for array
Mike Becker <universe@uap-core.de>
parents:
359
diff
changeset
|
111 | ((int*)array->data)[array->size++] = 80; |
07ac32b385e4
updates the web doc for array
Mike Becker <universe@uap-core.de>
parents:
359
diff
changeset
|
112 | } |
340 | 113 | ``` |
114 | ||
259 | 115 | ## AVL Tree |
116 | ||
390
d345541018fa
starts ucx 3.0 development
Mike Becker <universe@uap-core.de>
parents:
370
diff
changeset
|
117 | *Header file:* [avl.h](api-2.1/avl_8h.html) |
259 | 118 | *Required modules:* [Allocator](#allocator) |
119 | ||
120 | This binary search tree implementation allows average O(1) insertion and | |
121 | removal of elements (excluding binary search time). | |
122 | All common binary tree operations are implemented. Furthermore, this module | |
123 | provides search functions via lower and upper bounds. | |
124 | ||
287
98da78a1e69a
adds ucx_avl_free_content() function and documentation in modules.md
Mike Becker <universe@uap-core.de>
parents:
282
diff
changeset
|
125 | ### Filtering items with a time window |
98da78a1e69a
adds ucx_avl_free_content() function and documentation in modules.md
Mike Becker <universe@uap-core.de>
parents:
282
diff
changeset
|
126 | |
98da78a1e69a
adds ucx_avl_free_content() function and documentation in modules.md
Mike Becker <universe@uap-core.de>
parents:
282
diff
changeset
|
127 | Suppose you have a list of items which contain a `time_t` value and your task |
98da78a1e69a
adds ucx_avl_free_content() function and documentation in modules.md
Mike Becker <universe@uap-core.de>
parents:
282
diff
changeset
|
128 | is to find all items within a time window `[t_start, t_end]`. |
98da78a1e69a
adds ucx_avl_free_content() function and documentation in modules.md
Mike Becker <universe@uap-core.de>
parents:
282
diff
changeset
|
129 | With AVL Trees this is easy: |
98da78a1e69a
adds ucx_avl_free_content() function and documentation in modules.md
Mike Becker <universe@uap-core.de>
parents:
282
diff
changeset
|
130 | ```C |
98da78a1e69a
adds ucx_avl_free_content() function and documentation in modules.md
Mike Becker <universe@uap-core.de>
parents:
282
diff
changeset
|
131 | /* --------------------- |
98da78a1e69a
adds ucx_avl_free_content() function and documentation in modules.md
Mike Becker <universe@uap-core.de>
parents:
282
diff
changeset
|
132 | * Somewhere in a header |
98da78a1e69a
adds ucx_avl_free_content() function and documentation in modules.md
Mike Becker <universe@uap-core.de>
parents:
282
diff
changeset
|
133 | */ |
98da78a1e69a
adds ucx_avl_free_content() function and documentation in modules.md
Mike Becker <universe@uap-core.de>
parents:
282
diff
changeset
|
134 | typedef struct { |
98da78a1e69a
adds ucx_avl_free_content() function and documentation in modules.md
Mike Becker <universe@uap-core.de>
parents:
282
diff
changeset
|
135 | time_t ts; |
294
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
136 | /* other important data */ |
287
98da78a1e69a
adds ucx_avl_free_content() function and documentation in modules.md
Mike Becker <universe@uap-core.de>
parents:
282
diff
changeset
|
137 | } MyObject; |
98da78a1e69a
adds ucx_avl_free_content() function and documentation in modules.md
Mike Becker <universe@uap-core.de>
parents:
282
diff
changeset
|
138 | |
98da78a1e69a
adds ucx_avl_free_content() function and documentation in modules.md
Mike Becker <universe@uap-core.de>
parents:
282
diff
changeset
|
139 | /* ----------- |
98da78a1e69a
adds ucx_avl_free_content() function and documentation in modules.md
Mike Becker <universe@uap-core.de>
parents:
282
diff
changeset
|
140 | * Source code |
98da78a1e69a
adds ucx_avl_free_content() function and documentation in modules.md
Mike Becker <universe@uap-core.de>
parents:
282
diff
changeset
|
141 | */ |
98da78a1e69a
adds ucx_avl_free_content() function and documentation in modules.md
Mike Becker <universe@uap-core.de>
parents:
282
diff
changeset
|
142 | |
314
5d28dc8f0765
renames int and longint distance and compare functions according to the new scheme
Mike Becker <universe@uap-core.de>
parents:
310
diff
changeset
|
143 | UcxAVLTree* tree = ucx_avl_new(ucx_cmp_longint); |
294
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
144 | /* ... populate tree with objects, use '& MyObject.ts' as key ... */ |
287
98da78a1e69a
adds ucx_avl_free_content() function and documentation in modules.md
Mike Becker <universe@uap-core.de>
parents:
282
diff
changeset
|
145 | |
98da78a1e69a
adds ucx_avl_free_content() function and documentation in modules.md
Mike Becker <universe@uap-core.de>
parents:
282
diff
changeset
|
146 | |
294
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
147 | /* Now find every item, with 30 <= ts <= 70 */ |
287
98da78a1e69a
adds ucx_avl_free_content() function and documentation in modules.md
Mike Becker <universe@uap-core.de>
parents:
282
diff
changeset
|
148 | time_t ts_start = 30; |
98da78a1e69a
adds ucx_avl_free_content() function and documentation in modules.md
Mike Becker <universe@uap-core.de>
parents:
282
diff
changeset
|
149 | time_t ts_end = 70; |
98da78a1e69a
adds ucx_avl_free_content() function and documentation in modules.md
Mike Becker <universe@uap-core.de>
parents:
282
diff
changeset
|
150 | |
98da78a1e69a
adds ucx_avl_free_content() function and documentation in modules.md
Mike Becker <universe@uap-core.de>
parents:
282
diff
changeset
|
151 | printf("Values in range:\n"); |
98da78a1e69a
adds ucx_avl_free_content() function and documentation in modules.md
Mike Becker <universe@uap-core.de>
parents:
282
diff
changeset
|
152 | for ( |
98da78a1e69a
adds ucx_avl_free_content() function and documentation in modules.md
Mike Becker <universe@uap-core.de>
parents:
282
diff
changeset
|
153 | UcxAVLNode* node = ucx_avl_find_node( |
98da78a1e69a
adds ucx_avl_free_content() function and documentation in modules.md
Mike Becker <universe@uap-core.de>
parents:
282
diff
changeset
|
154 | tree, (intptr_t) &ts_start, |
314
5d28dc8f0765
renames int and longint distance and compare functions according to the new scheme
Mike Becker <universe@uap-core.de>
parents:
310
diff
changeset
|
155 | ucx_dist_longint, UCX_AVL_FIND_LOWER_BOUNDED); |
287
98da78a1e69a
adds ucx_avl_free_content() function and documentation in modules.md
Mike Becker <universe@uap-core.de>
parents:
282
diff
changeset
|
156 | node && (*(time_t*)node->key) <= ts_end; |
98da78a1e69a
adds ucx_avl_free_content() function and documentation in modules.md
Mike Becker <universe@uap-core.de>
parents:
282
diff
changeset
|
157 | node = ucx_avl_succ(node) |
98da78a1e69a
adds ucx_avl_free_content() function and documentation in modules.md
Mike Becker <universe@uap-core.de>
parents:
282
diff
changeset
|
158 | ) { |
98da78a1e69a
adds ucx_avl_free_content() function and documentation in modules.md
Mike Becker <universe@uap-core.de>
parents:
282
diff
changeset
|
159 | printf(" ts: %ld\n", ((MyObject*)node->value)->ts); |
98da78a1e69a
adds ucx_avl_free_content() function and documentation in modules.md
Mike Becker <universe@uap-core.de>
parents:
282
diff
changeset
|
160 | } |
98da78a1e69a
adds ucx_avl_free_content() function and documentation in modules.md
Mike Becker <universe@uap-core.de>
parents:
282
diff
changeset
|
161 | |
98da78a1e69a
adds ucx_avl_free_content() function and documentation in modules.md
Mike Becker <universe@uap-core.de>
parents:
282
diff
changeset
|
162 | ucx_avl_free_content(tree, free); |
98da78a1e69a
adds ucx_avl_free_content() function and documentation in modules.md
Mike Becker <universe@uap-core.de>
parents:
282
diff
changeset
|
163 | ucx_avl_free(tree); |
98da78a1e69a
adds ucx_avl_free_content() function and documentation in modules.md
Mike Becker <universe@uap-core.de>
parents:
282
diff
changeset
|
164 | ``` |
98da78a1e69a
adds ucx_avl_free_content() function and documentation in modules.md
Mike Becker <universe@uap-core.de>
parents:
282
diff
changeset
|
165 | |
259 | 166 | ## Buffer |
167 | ||
390
d345541018fa
starts ucx 3.0 development
Mike Becker <universe@uap-core.de>
parents:
370
diff
changeset
|
168 | *Header file:* [buffer.h](api-2.1/buffer_8h.html) |
259 | 169 | *Required modules:* None. |
170 | ||
171 | Instances of this buffer implementation can be used to read from or to write to | |
172 | memory like you would do with a stream. This allows the use of | |
282
39e69d78b01d
minor formatting fix in modules.md
Mike Becker <universe@uap-core.de>
parents:
281
diff
changeset
|
173 | `ucx_stream_copy()` from the [Utilities](#utilities) module to copy contents |
39e69d78b01d
minor formatting fix in modules.md
Mike Becker <universe@uap-core.de>
parents:
281
diff
changeset
|
174 | from one buffer to another or from file or network streams to the buffer and |
259 | 175 | vice-versa. |
176 | ||
177 | More features for convenient use of the buffer can be enabled, like automatic | |
178 | memory management and automatic resizing of the buffer space. | |
179 | See the documentation of the macro constants in the header file for more | |
180 | information. | |
181 | ||
290
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
182 | ### Add line numbers to a file |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
183 | |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
184 | When reading a file line by line, you have three options: first, you could limit |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
185 | the maximum supported line length. |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
186 | Second, you allocate a god buffer large |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
187 | enough for the most lines a text file could have. |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
188 | And third, undoubtedly the best option, you start with a small buffer, which |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
189 | adjusts on demand. |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
190 | An `UcxBuffer` can be created to do just that for you. |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
191 | Just pass the `UCX_BUFFER_AUTOEXTEND` option to the initialization function. |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
192 | Here is a full working program, which adds line numbers to a file. |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
193 | ```C |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
194 | #include <stdio.h> |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
195 | #include <ucx/buffer.h> |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
196 | #include <ucx/utils.h> |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
197 | |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
198 | int main(int argc, char** argv) { |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
199 | |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
200 | if (argc != 2) { |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
201 | fprintf(stderr, "Usage: %s <file>\n", argv[0]); |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
202 | return 1; |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
203 | } |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
204 | |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
205 | FILE* input = fopen(argv[1], "r"); |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
206 | if (!input) { |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
207 | perror("Canno read input"); |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
208 | return 1; |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
209 | } |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
210 | |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
211 | const size_t chunksize = 256; |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
212 | |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
213 | UcxBuffer* linebuf = |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
214 | ucx_buffer_new( |
294
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
215 | NULL, /* the buffer should manage the memory area for us */ |
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
216 | 2*chunksize, /* initial size should be twice the chunk size */ |
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
217 | UCX_BUFFER_AUTOEXTEND); /* the buffer will grow when necessary */ |
290
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
218 | |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
219 | size_t lineno = 1; |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
220 | do { |
294
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
221 | /* read line chunk */ |
290
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
222 | size_t read = ucx_stream_ncopy( |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
223 | input, linebuf, fread, ucx_buffer_write, chunksize); |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
224 | if (read == 0) break; |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
225 | |
294
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
226 | /* handle line endings */ |
290
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
227 | do { |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
228 | sstr_t bufstr = ucx_buffer_to_sstr(linebuf); |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
229 | sstr_t nl = sstrchr(bufstr, '\n'); |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
230 | if (nl.length == 0) break; |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
231 | |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
232 | size_t linelen = bufstr.length - nl.length; |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
233 | sstr_t linestr = sstrsubsl(bufstr, 0, linelen); |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
234 | |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
235 | printf("%zu: %" PRIsstr "\n", lineno++, SFMT(linestr)); |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
236 | |
294
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
237 | /* shift the buffer to the next line */ |
290
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
238 | ucx_buffer_shift_left(linebuf, linelen+1); |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
239 | } while(1); |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
240 | |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
241 | } while(1); |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
242 | |
294
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
243 | /* print the 'noeol' line, if any */ |
290
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
244 | sstr_t lastline = ucx_buffer_to_sstr(linebuf); |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
245 | if (lastline.length > 0) { |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
246 | printf("%zu: %" PRIsstr, lineno, SFMT(lastline)); |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
247 | } |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
248 | |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
249 | fclose(input); |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
250 | ucx_buffer_free(linebuf); |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
251 | |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
252 | return 0; |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
253 | } |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
254 | ``` |
d5d6ab809ad3
adds new shift operations for UcxBuffer (including tests and a usage example in modules.md)
Mike Becker <universe@uap-core.de>
parents:
287
diff
changeset
|
255 | |
259 | 256 | ## List |
257 | ||
390
d345541018fa
starts ucx 3.0 development
Mike Becker <universe@uap-core.de>
parents:
370
diff
changeset
|
258 | *Header file:* [list.h](api-2.1/list_8h.html) |
259 | 259 | *Required modules:* [Allocator](#allocator) |
260 | ||
261 | This module provides the data structure and several functions for a doubly | |
262 | linked list. Among the common operations like insert, remove, search and sort, | |
263 | we allow convenient iteration via a special `UCX_FOREACH` macro. | |
264 | ||
294
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
265 | ### Remove duplicates from an array of strings |
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
266 | |
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
267 | Assume you are given an array of `sstr_t` and want to create a list of these |
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
268 | strings without duplicates. |
340 | 269 | This is a similar example to the one [above](#array), but here we are |
270 | using a `UcxList`. | |
294
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
271 | ```C |
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
272 | #include <stdio.h> |
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
273 | #include <ucx/list.h> |
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
274 | #include <ucx/string.h> |
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
275 | #include <ucx/utils.h> |
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
276 | |
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
277 | UcxList* remove_duplicates(sstr_t* array, size_t arrlen) { |
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
278 | UcxList* list = NULL; |
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
279 | for (size_t i = 0 ; i < arrlen ; ++i) { |
310
b09677d72413
renames ucx_sstrcmp() to ucx_cmp_sstr()
Mike Becker <universe@uap-core.de>
parents:
304
diff
changeset
|
280 | if (ucx_list_find(list, array+i, ucx_cmp_sstr, NULL) == -1) { |
294
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
281 | sstr_t* s = malloc(sizeof(sstr_t)); |
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
282 | *s = sstrdup(array[i]); |
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
283 | list = ucx_list_append(list, s); |
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
284 | } |
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
285 | } |
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
286 | return list; |
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
287 | } |
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
288 | |
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
289 | /* we will need this function to clean up the list contents later */ |
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
290 | void free_sstr(void* ptr) { |
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
291 | sstr_t* s = ptr; |
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
292 | free(s->ptr); |
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
293 | free(s); |
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
294 | } |
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
295 | |
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
296 | /* ... */ |
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
297 | |
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
298 | sstr_t* array = /* some array of strings */ |
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
299 | size_t arrlen = /* the length of the array */ |
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
300 | |
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
301 | UcxList* list = remove_duplicates(array,arrlen); |
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
302 | |
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
303 | /* Iterate over the list and print the elements */ |
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
304 | UCX_FOREACH(elem, list) { |
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
305 | sstr_t s = *((sstr_t*)elem->data); |
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
306 | printf("%" PRIsstr "\n", SFMT(s)); |
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
307 | } |
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
308 | |
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
309 | /* Use our free function to free the duplicated strings. */ |
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
310 | ucx_list_free_content(list, free_sstr); |
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
311 | ucx_list_free(list); |
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
312 | ``` |
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
313 | |
259 | 314 | ## Logging |
315 | ||
390
d345541018fa
starts ucx 3.0 development
Mike Becker <universe@uap-core.de>
parents:
370
diff
changeset
|
316 | *Header file:* [logging.h](api-2.1/logging_8h.html) |
259 | 317 | *Required modules:* [Map](#map), [String](#string) |
318 | ||
319 | The logging module comes with some predefined log levels and allows some more | |
320 | customization. You may choose if you want to get timestamps or source file and | |
321 | line number logged automatically when outputting a message. | |
295
7fc65395188e
documents (and fixes!) the UcxLogger
Mike Becker <universe@uap-core.de>
parents:
294
diff
changeset
|
322 | The following function call initializes a debug logger with all of the above |
7fc65395188e
documents (and fixes!) the UcxLogger
Mike Becker <universe@uap-core.de>
parents:
294
diff
changeset
|
323 | information: |
7fc65395188e
documents (and fixes!) the UcxLogger
Mike Becker <universe@uap-core.de>
parents:
294
diff
changeset
|
324 | ```C |
7fc65395188e
documents (and fixes!) the UcxLogger
Mike Becker <universe@uap-core.de>
parents:
294
diff
changeset
|
325 | log = ucx_logger_new(stdout, UCX_LOGGER_DEBUG, |
7fc65395188e
documents (and fixes!) the UcxLogger
Mike Becker <universe@uap-core.de>
parents:
294
diff
changeset
|
326 | UCX_LOGGER_LEVEL | UCX_LOGGER_TIMESTAMP | UCX_LOGGER_SOURCE); |
7fc65395188e
documents (and fixes!) the UcxLogger
Mike Becker <universe@uap-core.de>
parents:
294
diff
changeset
|
327 | ``` |
7fc65395188e
documents (and fixes!) the UcxLogger
Mike Becker <universe@uap-core.de>
parents:
294
diff
changeset
|
328 | Afterwards you can use this logger with the predefined macros |
7fc65395188e
documents (and fixes!) the UcxLogger
Mike Becker <universe@uap-core.de>
parents:
294
diff
changeset
|
329 | ```C |
7fc65395188e
documents (and fixes!) the UcxLogger
Mike Becker <universe@uap-core.de>
parents:
294
diff
changeset
|
330 | ucx_logger_trace(log, "Verbose output"); |
7fc65395188e
documents (and fixes!) the UcxLogger
Mike Becker <universe@uap-core.de>
parents:
294
diff
changeset
|
331 | ucx_logger_debug(log, "Debug message"); |
7fc65395188e
documents (and fixes!) the UcxLogger
Mike Becker <universe@uap-core.de>
parents:
294
diff
changeset
|
332 | ucx_logger_info(log, "Information"); |
7fc65395188e
documents (and fixes!) the UcxLogger
Mike Becker <universe@uap-core.de>
parents:
294
diff
changeset
|
333 | ucx_logger_warn(log, "Warning"); |
7fc65395188e
documents (and fixes!) the UcxLogger
Mike Becker <universe@uap-core.de>
parents:
294
diff
changeset
|
334 | ucx_logger_error(log, "Error message"); |
7fc65395188e
documents (and fixes!) the UcxLogger
Mike Becker <universe@uap-core.de>
parents:
294
diff
changeset
|
335 | ``` |
7fc65395188e
documents (and fixes!) the UcxLogger
Mike Becker <universe@uap-core.de>
parents:
294
diff
changeset
|
336 | or you use |
7fc65395188e
documents (and fixes!) the UcxLogger
Mike Becker <universe@uap-core.de>
parents:
294
diff
changeset
|
337 | ```C |
7fc65395188e
documents (and fixes!) the UcxLogger
Mike Becker <universe@uap-core.de>
parents:
294
diff
changeset
|
338 | ucx_logger_log(log, CUSTOM_LEVEL, "Some message") |
7fc65395188e
documents (and fixes!) the UcxLogger
Mike Becker <universe@uap-core.de>
parents:
294
diff
changeset
|
339 | ``` |
7fc65395188e
documents (and fixes!) the UcxLogger
Mike Becker <universe@uap-core.de>
parents:
294
diff
changeset
|
340 | When you use your custom log level, don't forget to register it with |
7fc65395188e
documents (and fixes!) the UcxLogger
Mike Becker <universe@uap-core.de>
parents:
294
diff
changeset
|
341 | ```C |
7fc65395188e
documents (and fixes!) the UcxLogger
Mike Becker <universe@uap-core.de>
parents:
294
diff
changeset
|
342 | ucx_logger_register_level(log, CUSTOM_LEVEL, "CUSTOM") |
7fc65395188e
documents (and fixes!) the UcxLogger
Mike Becker <universe@uap-core.de>
parents:
294
diff
changeset
|
343 | ``` |
7fc65395188e
documents (and fixes!) the UcxLogger
Mike Becker <universe@uap-core.de>
parents:
294
diff
changeset
|
344 | where the last argument must be a string literal. |
259 | 345 | |
346 | ## Map | |
347 | ||
390
d345541018fa
starts ucx 3.0 development
Mike Becker <universe@uap-core.de>
parents:
370
diff
changeset
|
348 | *Header file:* [map.h](api-2.1/map_8h.html) |
259 | 349 | *Required modules:* [Allocator](#allocator), [String](#string) |
350 | ||
351 | This module provides a hash map implementation using murmur hash 2 and separate | |
352 | chaining with linked lists. Similarly to the list module, we provide a | |
353 | `UCX_MAP_FOREACH` macro to conveniently iterate through the key/value pairs. | |
354 | ||
298
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
355 | ### Parsing command line options |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
356 | |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
357 | Assume you want to parse command line options and record them within a map. |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
358 | One way to do this is shown by the following code sample: |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
359 | ```C |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
360 | UcxMap* options = ucx_map_new(16); |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
361 | const char *NOARG = ""; |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
362 | |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
363 | char *option = NULL; |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
364 | char optchar = 0; |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
365 | for(int i=1;i<argc;i++) { |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
366 | char *arg = argv[i]; |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
367 | size_t len = strlen(arg); |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
368 | if(len > 1 && arg[0] == '-') { |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
369 | for(int c=1;c<len;c++) { |
299
e7dfcf229625
adjusts code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
298
diff
changeset
|
370 | if(option) { |
e7dfcf229625
adjusts code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
298
diff
changeset
|
371 | fprintf(stderr, |
e7dfcf229625
adjusts code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
298
diff
changeset
|
372 | "Missing argument for option -%c\n", optchar); |
e7dfcf229625
adjusts code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
298
diff
changeset
|
373 | return 1; |
e7dfcf229625
adjusts code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
298
diff
changeset
|
374 | } |
298
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
375 | switch(arg[c]) { |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
376 | default: { |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
377 | fprintf(stderr, "Unknown option -%c\n\n", arg[c]); |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
378 | return 1; |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
379 | } |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
380 | case 'v': { |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
381 | ucx_map_cstr_put(options, "verbose", NOARG); |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
382 | break; |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
383 | } |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
384 | case 'o': { |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
385 | option = "output"; |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
386 | optchar = 'o'; |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
387 | break; |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
388 | } |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
389 | } |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
390 | } |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
391 | } else if(option) { |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
392 | ucx_map_cstr_put(options, option, arg); |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
393 | option = NULL; |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
394 | } else { |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
395 | /* ... handle argument that is not an option ... */ |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
396 | } |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
397 | } |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
398 | if(option) { |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
399 | fprintf(stderr, |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
400 | "Missing argument for option -%c\n", optchar); |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
401 | return 1; |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
402 | } |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
403 | ``` |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
404 | With the following loop, you can access the previously recorded options: |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
405 | ```C |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
406 | UcxMapIterator iter = ucx_map_iterator(options); |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
407 | char *arg; |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
408 | UCX_MAP_FOREACH(optkey, arg, iter) { |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
409 | char* opt = optkey.data; |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
410 | if (*arg) { |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
411 | printf("%s = %s\n", opt, arg); |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
412 | } else { |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
413 | printf("%s active\n", opt); |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
414 | } |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
415 | } |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
416 | ``` |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
417 | Don't forget to call `ucx_map_free()`, when you are done with the map. |
fffe3a16a3de
adds a code sample for UcxMap
Mike Becker <universe@uap-core.de>
parents:
297
diff
changeset
|
418 | |
259 | 419 | ## Memory Pool |
420 | ||
390
d345541018fa
starts ucx 3.0 development
Mike Becker <universe@uap-core.de>
parents:
370
diff
changeset
|
421 | *Header file:* [mempool.h](api-2.1/mempool_8h.html) |
259 | 422 | *Required modules:* [Allocator](#allocator) |
423 | ||
424 | Here we have a concrete allocator implementation in the sense of a memory pool. | |
425 | This pool allows you to register destructor functions for the allocated memory, | |
426 | which are automatically called on the destruction of the pool. | |
427 | But you may also register *independent* destructor functions within a pool in | |
302
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
428 | case some external library allocated memory for you, which should be |
259 | 429 | destroyed together with this pool. |
430 | ||
302
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
431 | Many UCX modules support the use of an allocator. |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
432 | The [String Module](#string), for instance, provides the `sstrdup_a()` function, |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
433 | which uses the specified allocator to allocate the memory for the duplicated |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
434 | string. |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
435 | This way, you can use a `UcxMempool` to keep track of the memory occupied by |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
436 | duplicated strings and cleanup everything with just a single call to |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
437 | `ucx_mempool_destroy()`. |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
438 | |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
439 | ### Read CSV data into a structure |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
440 | |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
441 | The following code example shows some of the basic memory pool functions and |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
442 | how they can be used with other UCX modules. |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
443 | ```C |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
444 | #include <stdio.h> |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
445 | #include <ucx/mempool.h> |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
446 | #include <ucx/list.h> |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
447 | #include <ucx/string.h> |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
448 | #include <ucx/buffer.h> |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
449 | #include <ucx/utils.h> |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
450 | |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
451 | typedef struct { |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
452 | sstr_t column_a; |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
453 | sstr_t column_b; |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
454 | sstr_t column_c; |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
455 | } CSVData; |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
456 | |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
457 | int main(int argc, char** argv) { |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
458 | |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
459 | UcxMempool* pool = ucx_mempool_new(128); |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
460 | |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
461 | FILE *f = fopen("test.csv", "r"); |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
462 | if (!f) { |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
463 | perror("Cannot open file"); |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
464 | return 1; |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
465 | } |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
466 | /* close the file automatically at pool destruction*/ |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
467 | ucx_mempool_reg_destr(pool, f, (ucx_destructor) fclose); |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
468 | |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
469 | /* create a buffer and register it at the memory pool for destruction */ |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
470 | UcxBuffer* content = ucx_buffer_new(NULL, 256, UCX_BUFFER_AUTOEXTEND); |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
471 | ucx_mempool_reg_destr(pool, content, (ucx_destructor) ucx_buffer_free); |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
472 | |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
473 | /* read the file and split it by lines first */ |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
474 | ucx_stream_copy(f, content, fread, ucx_buffer_write); |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
475 | sstr_t contentstr = ucx_buffer_to_sstr(content); |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
476 | ssize_t lc = 0; |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
477 | sstr_t* lines = sstrsplit_a(pool->allocator, contentstr, S("\n"), &lc); |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
478 | |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
479 | /* skip the header and parse the remaining data */ |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
480 | UcxList* datalist = NULL; |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
481 | for (size_t i = 1 ; i < lc ; i++) { |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
482 | if (lines[i].length == 0) continue; |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
483 | ssize_t fc = 3; |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
484 | sstr_t* fields = sstrsplit_a(pool->allocator, lines[i], S(";"), &fc); |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
485 | if (fc != 3) { |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
486 | fprintf(stderr, "Syntax error in line %zu.\n", i); |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
487 | ucx_mempool_destroy(pool); |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
488 | return 1; |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
489 | } |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
490 | CSVData* data = ucx_mempool_malloc(pool, sizeof(CSVData)); |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
491 | data->column_a = fields[0]; |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
492 | data->column_b = fields[1]; |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
493 | data->column_c = fields[2]; |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
494 | datalist = ucx_list_append_a(pool->allocator, datalist, data); |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
495 | } |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
496 | |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
497 | /* control output */ |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
498 | UCX_FOREACH(elem, datalist) { |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
499 | CSVData* data = elem->data; |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
500 | printf("Column A: %" PRIsstr " | " |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
501 | "Column B: %" PRIsstr " | " |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
502 | "Column C: %" PRIsstr "\n", |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
503 | SFMT(data->column_a), SFMT(data->column_b), SFMT(data->column_c) |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
504 | ); |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
505 | } |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
506 | |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
507 | /* cleanup everything, no manual free() needed */ |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
508 | ucx_mempool_destroy(pool); |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
509 | |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
510 | return 0; |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
511 | } |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
512 | ``` |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
513 | |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
514 | ### Overriding the default destructor |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
515 | |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
516 | Sometimes you need to allocate memory with `ucx_mempool_malloc()`, but the |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
517 | memory is not supposed to be freed with a simple call to `free()`. |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
518 | In this case, you can overwrite the default destructor as follows: |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
519 | ```C |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
520 | MyObject* obj = ucx_mempool_malloc(pool, sizeof(MyObject)); |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
521 | |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
522 | /* some special initialization with own resource management */ |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
523 | my_object_init(obj); |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
524 | |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
525 | /* register destructor function */ |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
526 | ucx_mempool_set_destr(obj, (ucx_destructor) my_object_destroy); |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
527 | ``` |
304
1f9237cfeb26
fixes typo in modules.md
Mike Becker <universe@uap-core.de>
parents:
302
diff
changeset
|
528 | Be aware, that your destructor function should not free any memory, that is |
302
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
529 | also managed by the pool. |
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
530 | Otherwise you might be risking a double-free. |
326
3dd7d21fb76b
being more precise on the different required behavior of a destructor function for pooled and non-pooled memory
Mike Becker <universe@uap-core.de>
parents:
325
diff
changeset
|
531 | More precisely, a destructor function set with `ucx_mempool_set_destr()` MUST |
3dd7d21fb76b
being more precise on the different required behavior of a destructor function for pooled and non-pooled memory
Mike Becker <universe@uap-core.de>
parents:
325
diff
changeset
|
532 | NOT call `free()` on the specified pointer whereas a desructor function |
3dd7d21fb76b
being more precise on the different required behavior of a destructor function for pooled and non-pooled memory
Mike Becker <universe@uap-core.de>
parents:
325
diff
changeset
|
533 | registered with `ucx_mempool_reg_destr()` MAY (and in most cases will) call |
3dd7d21fb76b
being more precise on the different required behavior of a destructor function for pooled and non-pooled memory
Mike Becker <universe@uap-core.de>
parents:
325
diff
changeset
|
534 | `free()`. |
302
8628147734d6
comprehensive code example for the memory pool
Mike Becker <universe@uap-core.de>
parents:
301
diff
changeset
|
535 | |
259 | 536 | ## Properties |
537 | ||
390
d345541018fa
starts ucx 3.0 development
Mike Becker <universe@uap-core.de>
parents:
370
diff
changeset
|
538 | *Header file:* [properties.h](api-2.1/properties_8h.html) |
259 | 539 | *Required modules:* [Map](#map) |
540 | ||
541 | This module provides load and store function for `*.properties` files. | |
542 | The key/value pairs are stored within an UCX Map. | |
543 | ||
277
f819fe5e20f5
makes destructor functions for *_free_content() optional + more documentation for UcxProperties
Mike Becker <universe@uap-core.de>
parents:
267
diff
changeset
|
544 | ### Example: Loading properties from a file |
f819fe5e20f5
makes destructor functions for *_free_content() optional + more documentation for UcxProperties
Mike Becker <universe@uap-core.de>
parents:
267
diff
changeset
|
545 | |
f819fe5e20f5
makes destructor functions for *_free_content() optional + more documentation for UcxProperties
Mike Becker <universe@uap-core.de>
parents:
267
diff
changeset
|
546 | ```C |
294
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
547 | /* Open the file as usual */ |
277
f819fe5e20f5
makes destructor functions for *_free_content() optional + more documentation for UcxProperties
Mike Becker <universe@uap-core.de>
parents:
267
diff
changeset
|
548 | FILE* file = fopen("myprops.properties", "r"); |
f819fe5e20f5
makes destructor functions for *_free_content() optional + more documentation for UcxProperties
Mike Becker <universe@uap-core.de>
parents:
267
diff
changeset
|
549 | if (!file) { |
f819fe5e20f5
makes destructor functions for *_free_content() optional + more documentation for UcxProperties
Mike Becker <universe@uap-core.de>
parents:
267
diff
changeset
|
550 | // error handling |
f819fe5e20f5
makes destructor functions for *_free_content() optional + more documentation for UcxProperties
Mike Becker <universe@uap-core.de>
parents:
267
diff
changeset
|
551 | return 1; |
f819fe5e20f5
makes destructor functions for *_free_content() optional + more documentation for UcxProperties
Mike Becker <universe@uap-core.de>
parents:
267
diff
changeset
|
552 | } |
f819fe5e20f5
makes destructor functions for *_free_content() optional + more documentation for UcxProperties
Mike Becker <universe@uap-core.de>
parents:
267
diff
changeset
|
553 | |
294
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
554 | /* Load the properties from the file */ |
277
f819fe5e20f5
makes destructor functions for *_free_content() optional + more documentation for UcxProperties
Mike Becker <universe@uap-core.de>
parents:
267
diff
changeset
|
555 | UcxMap* myprops = ucx_map_new(16); |
f819fe5e20f5
makes destructor functions for *_free_content() optional + more documentation for UcxProperties
Mike Becker <universe@uap-core.de>
parents:
267
diff
changeset
|
556 | if (ucx_properties_load(myprops, file)) { |
294
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
557 | /* ... error handling ... */ |
277
f819fe5e20f5
makes destructor functions for *_free_content() optional + more documentation for UcxProperties
Mike Becker <universe@uap-core.de>
parents:
267
diff
changeset
|
558 | fclose(file); |
f819fe5e20f5
makes destructor functions for *_free_content() optional + more documentation for UcxProperties
Mike Becker <universe@uap-core.de>
parents:
267
diff
changeset
|
559 | ucx_map_free(myprops); |
f819fe5e20f5
makes destructor functions for *_free_content() optional + more documentation for UcxProperties
Mike Becker <universe@uap-core.de>
parents:
267
diff
changeset
|
560 | return 1; |
f819fe5e20f5
makes destructor functions for *_free_content() optional + more documentation for UcxProperties
Mike Becker <universe@uap-core.de>
parents:
267
diff
changeset
|
561 | } |
f819fe5e20f5
makes destructor functions for *_free_content() optional + more documentation for UcxProperties
Mike Becker <universe@uap-core.de>
parents:
267
diff
changeset
|
562 | |
294
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
563 | /* Print out the key/value pairs */ |
277
f819fe5e20f5
makes destructor functions for *_free_content() optional + more documentation for UcxProperties
Mike Becker <universe@uap-core.de>
parents:
267
diff
changeset
|
564 | char* propval; |
f819fe5e20f5
makes destructor functions for *_free_content() optional + more documentation for UcxProperties
Mike Becker <universe@uap-core.de>
parents:
267
diff
changeset
|
565 | UcxMapIterator propiter = ucx_map_iterator(myprops); |
f819fe5e20f5
makes destructor functions for *_free_content() optional + more documentation for UcxProperties
Mike Becker <universe@uap-core.de>
parents:
267
diff
changeset
|
566 | UCX_MAP_FOREACH(key, propval, propiter) { |
f819fe5e20f5
makes destructor functions for *_free_content() optional + more documentation for UcxProperties
Mike Becker <universe@uap-core.de>
parents:
267
diff
changeset
|
567 | printf("%s = %s\n", (char*)key.data, propval); |
f819fe5e20f5
makes destructor functions for *_free_content() optional + more documentation for UcxProperties
Mike Becker <universe@uap-core.de>
parents:
267
diff
changeset
|
568 | } |
f819fe5e20f5
makes destructor functions for *_free_content() optional + more documentation for UcxProperties
Mike Becker <universe@uap-core.de>
parents:
267
diff
changeset
|
569 | |
294
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
570 | /* Don't forget to free the values before freeing the map */ |
277
f819fe5e20f5
makes destructor functions for *_free_content() optional + more documentation for UcxProperties
Mike Becker <universe@uap-core.de>
parents:
267
diff
changeset
|
571 | ucx_map_free_content(myprops, NULL); |
f819fe5e20f5
makes destructor functions for *_free_content() optional + more documentation for UcxProperties
Mike Becker <universe@uap-core.de>
parents:
267
diff
changeset
|
572 | ucx_map_free(myprops); |
f819fe5e20f5
makes destructor functions for *_free_content() optional + more documentation for UcxProperties
Mike Becker <universe@uap-core.de>
parents:
267
diff
changeset
|
573 | fclose(file); |
f819fe5e20f5
makes destructor functions for *_free_content() optional + more documentation for UcxProperties
Mike Becker <universe@uap-core.de>
parents:
267
diff
changeset
|
574 | ``` |
295
7fc65395188e
documents (and fixes!) the UcxLogger
Mike Becker <universe@uap-core.de>
parents:
294
diff
changeset
|
575 | |
259 | 576 | ## Stack |
577 | ||
390
d345541018fa
starts ucx 3.0 development
Mike Becker <universe@uap-core.de>
parents:
370
diff
changeset
|
578 | *Header file:* [stack.h](api-2.1/stack_8h.html) |
259 | 579 | *Required modules:* [Allocator](#allocator) |
580 | ||
581 | This concrete implementation of an UCX Allocator allows you to grab some amount | |
582 | of memory which is then handled as a stack. | |
583 | Please note, that the term *stack* only refers to the behavior of this | |
301
0f83916c1639
documentation for the UcxStack
Mike Becker <universe@uap-core.de>
parents:
299
diff
changeset
|
584 | allocator. You may still choose to use either stack or heap memory |
259 | 585 | for the underlying space. |
586 | A typical use case is an algorithm where you need to allocate and free large | |
587 | amounts of memory very frequently. | |
588 | ||
301
0f83916c1639
documentation for the UcxStack
Mike Becker <universe@uap-core.de>
parents:
299
diff
changeset
|
589 | The following code sample shows how to initialize a stack and push and pop |
0f83916c1639
documentation for the UcxStack
Mike Becker <universe@uap-core.de>
parents:
299
diff
changeset
|
590 | simple data. |
0f83916c1639
documentation for the UcxStack
Mike Becker <universe@uap-core.de>
parents:
299
diff
changeset
|
591 | ```C |
0f83916c1639
documentation for the UcxStack
Mike Becker <universe@uap-core.de>
parents:
299
diff
changeset
|
592 | const size_t len = 1024; |
0f83916c1639
documentation for the UcxStack
Mike Becker <universe@uap-core.de>
parents:
299
diff
changeset
|
593 | char space[len]; |
0f83916c1639
documentation for the UcxStack
Mike Becker <universe@uap-core.de>
parents:
299
diff
changeset
|
594 | UcxStack stack; |
0f83916c1639
documentation for the UcxStack
Mike Becker <universe@uap-core.de>
parents:
299
diff
changeset
|
595 | ucx_stack_init(&stack, space, len); |
0f83916c1639
documentation for the UcxStack
Mike Becker <universe@uap-core.de>
parents:
299
diff
changeset
|
596 | |
0f83916c1639
documentation for the UcxStack
Mike Becker <universe@uap-core.de>
parents:
299
diff
changeset
|
597 | int i = 42; |
0f83916c1639
documentation for the UcxStack
Mike Becker <universe@uap-core.de>
parents:
299
diff
changeset
|
598 | float f = 3.14f; |
0f83916c1639
documentation for the UcxStack
Mike Becker <universe@uap-core.de>
parents:
299
diff
changeset
|
599 | const char* str = "Hello!"; |
0f83916c1639
documentation for the UcxStack
Mike Becker <universe@uap-core.de>
parents:
299
diff
changeset
|
600 | size_t strn = 7; |
0f83916c1639
documentation for the UcxStack
Mike Becker <universe@uap-core.de>
parents:
299
diff
changeset
|
601 | |
0f83916c1639
documentation for the UcxStack
Mike Becker <universe@uap-core.de>
parents:
299
diff
changeset
|
602 | /* push the integer */ |
0f83916c1639
documentation for the UcxStack
Mike Becker <universe@uap-core.de>
parents:
299
diff
changeset
|
603 | ucx_stack_push(&stack, sizeof(int), &i); |
0f83916c1639
documentation for the UcxStack
Mike Becker <universe@uap-core.de>
parents:
299
diff
changeset
|
604 | |
0f83916c1639
documentation for the UcxStack
Mike Becker <universe@uap-core.de>
parents:
299
diff
changeset
|
605 | /* push the float and rember the address */ |
0f83916c1639
documentation for the UcxStack
Mike Becker <universe@uap-core.de>
parents:
299
diff
changeset
|
606 | float* remember = ucx_stack_push(&stack, sizeof(float), &f); |
0f83916c1639
documentation for the UcxStack
Mike Becker <universe@uap-core.de>
parents:
299
diff
changeset
|
607 | |
0f83916c1639
documentation for the UcxStack
Mike Becker <universe@uap-core.de>
parents:
299
diff
changeset
|
608 | /* push the string with zero terminator */ |
0f83916c1639
documentation for the UcxStack
Mike Becker <universe@uap-core.de>
parents:
299
diff
changeset
|
609 | ucx_stack_push(&stack, strn, str); |
0f83916c1639
documentation for the UcxStack
Mike Becker <universe@uap-core.de>
parents:
299
diff
changeset
|
610 | |
0f83916c1639
documentation for the UcxStack
Mike Becker <universe@uap-core.de>
parents:
299
diff
changeset
|
611 | /* if we forget, how big an element was, we can ask the stack */ |
0f83916c1639
documentation for the UcxStack
Mike Becker <universe@uap-core.de>
parents:
299
diff
changeset
|
612 | printf("Length of string: %zu\n", ucx_stack_topsize(&stack)-1); |
0f83916c1639
documentation for the UcxStack
Mike Becker <universe@uap-core.de>
parents:
299
diff
changeset
|
613 | |
0f83916c1639
documentation for the UcxStack
Mike Becker <universe@uap-core.de>
parents:
299
diff
changeset
|
614 | /* retrieve the string as sstr_t, without zero terminator! */ |
0f83916c1639
documentation for the UcxStack
Mike Becker <universe@uap-core.de>
parents:
299
diff
changeset
|
615 | sstr_t s; |
0f83916c1639
documentation for the UcxStack
Mike Becker <universe@uap-core.de>
parents:
299
diff
changeset
|
616 | s.length = ucx_stack_topsize(&stack)-1; |
0f83916c1639
documentation for the UcxStack
Mike Becker <universe@uap-core.de>
parents:
299
diff
changeset
|
617 | s.ptr = malloc(s.length); |
0f83916c1639
documentation for the UcxStack
Mike Becker <universe@uap-core.de>
parents:
299
diff
changeset
|
618 | ucx_stack_popn(&stack, s.ptr, s.length); |
0f83916c1639
documentation for the UcxStack
Mike Becker <universe@uap-core.de>
parents:
299
diff
changeset
|
619 | printf("%" PRIsstr "\n", SFMT(s)); |
0f83916c1639
documentation for the UcxStack
Mike Becker <universe@uap-core.de>
parents:
299
diff
changeset
|
620 | |
0f83916c1639
documentation for the UcxStack
Mike Becker <universe@uap-core.de>
parents:
299
diff
changeset
|
621 | /* print the float directly from the stack and free it */ |
0f83916c1639
documentation for the UcxStack
Mike Becker <universe@uap-core.de>
parents:
299
diff
changeset
|
622 | printf("Float: %f\n", *remember); |
0f83916c1639
documentation for the UcxStack
Mike Becker <universe@uap-core.de>
parents:
299
diff
changeset
|
623 | ucx_stack_free(&stack, remember); |
0f83916c1639
documentation for the UcxStack
Mike Becker <universe@uap-core.de>
parents:
299
diff
changeset
|
624 | |
0f83916c1639
documentation for the UcxStack
Mike Becker <universe@uap-core.de>
parents:
299
diff
changeset
|
625 | /* the last element is the integer */ |
0f83916c1639
documentation for the UcxStack
Mike Becker <universe@uap-core.de>
parents:
299
diff
changeset
|
626 | int j; |
0f83916c1639
documentation for the UcxStack
Mike Becker <universe@uap-core.de>
parents:
299
diff
changeset
|
627 | ucx_stack_pop(&stack, &j); |
0f83916c1639
documentation for the UcxStack
Mike Becker <universe@uap-core.de>
parents:
299
diff
changeset
|
628 | printf("Integer: %d\n", j); |
0f83916c1639
documentation for the UcxStack
Mike Becker <universe@uap-core.de>
parents:
299
diff
changeset
|
629 | ``` |
0f83916c1639
documentation for the UcxStack
Mike Becker <universe@uap-core.de>
parents:
299
diff
changeset
|
630 | |
0f83916c1639
documentation for the UcxStack
Mike Becker <universe@uap-core.de>
parents:
299
diff
changeset
|
631 | |
0f83916c1639
documentation for the UcxStack
Mike Becker <universe@uap-core.de>
parents:
299
diff
changeset
|
632 | |
259 | 633 | ## String |
634 | ||
390
d345541018fa
starts ucx 3.0 development
Mike Becker <universe@uap-core.de>
parents:
370
diff
changeset
|
635 | *Header file:* [string.h](api-2.1/string_8h.html) |
259 | 636 | *Required modules:* [Allocator](#allocator) |
637 | ||
638 | This module provides a safe implementation of bounded string. | |
639 | Usually C strings do not carry a length. While for zero-terminated strings you | |
640 | can easily get the length with `strlen`, this is not generally possible for | |
641 | arbitrary strings. | |
642 | The `sstr_t` type of this module always carries the string and its length to | |
643 | reduce the risk of buffer overflows dramatically. | |
644 | ||
267
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
645 | ### Initialization |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
646 | |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
647 | There are several ways to create an `sstr_t`: |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
648 | |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
649 | ```C |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
650 | /* (1) sstr() uses strlen() internally, hence cstr MUST be zero-terminated */ |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
651 | sstr_t a = sstr(cstr); |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
652 | |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
653 | /* (2) cstr does not need to be zero-terminated, if length is specified */ |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
654 | sstr_t b = sstrn(cstr, len); |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
655 | |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
656 | /* (3) S() macro creates sstr_t from a string using sizeof() and using sstrn(). |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
657 | This version is especially useful for function arguments */ |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
658 | sstr_t c = S("hello"); |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
659 | |
325
a3e63cb21e20
changes sstr shortcut macros s.t. they distinguish sstr_t and scstr_t + add macros which can completely disable the shortcuts
Mike Becker <universe@uap-core.de>
parents:
321
diff
changeset
|
660 | /* (4) SC() macro works like S(), but makes the string immutable using scstr_t. |
a3e63cb21e20
changes sstr shortcut macros s.t. they distinguish sstr_t and scstr_t + add macros which can completely disable the shortcuts
Mike Becker <universe@uap-core.de>
parents:
321
diff
changeset
|
661 | (available since UCX 2.0) */ |
a3e63cb21e20
changes sstr shortcut macros s.t. they distinguish sstr_t and scstr_t + add macros which can completely disable the shortcuts
Mike Becker <universe@uap-core.de>
parents:
321
diff
changeset
|
662 | scstr_t d = SC("hello"); |
a3e63cb21e20
changes sstr shortcut macros s.t. they distinguish sstr_t and scstr_t + add macros which can completely disable the shortcuts
Mike Becker <universe@uap-core.de>
parents:
321
diff
changeset
|
663 | |
a3e63cb21e20
changes sstr shortcut macros s.t. they distinguish sstr_t and scstr_t + add macros which can completely disable the shortcuts
Mike Becker <universe@uap-core.de>
parents:
321
diff
changeset
|
664 | /* (5) ST() macro creates sstr_t struct literal using sizeof() */ |
a3e63cb21e20
changes sstr shortcut macros s.t. they distinguish sstr_t and scstr_t + add macros which can completely disable the shortcuts
Mike Becker <universe@uap-core.de>
parents:
321
diff
changeset
|
665 | sstr_t e = ST("hello"); |
267
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
666 | ``` |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
667 | |
325
a3e63cb21e20
changes sstr shortcut macros s.t. they distinguish sstr_t and scstr_t + add macros which can completely disable the shortcuts
Mike Becker <universe@uap-core.de>
parents:
321
diff
changeset
|
668 | You should not use the `S()`, `SC()`, or `ST()` macro with string of unknown |
a3e63cb21e20
changes sstr shortcut macros s.t. they distinguish sstr_t and scstr_t + add macros which can completely disable the shortcuts
Mike Becker <universe@uap-core.de>
parents:
321
diff
changeset
|
669 | origin, since the `sizeof()` call might not coincide with the string length in |
a3e63cb21e20
changes sstr shortcut macros s.t. they distinguish sstr_t and scstr_t + add macros which can completely disable the shortcuts
Mike Becker <universe@uap-core.de>
parents:
321
diff
changeset
|
670 | those cases. If you know what you are doing, it can save you some performance, |
267
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
671 | because you do not need the `strlen()` call. |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
672 | |
321
9af21a50b516
adds scstr_t to modules.md + fixes parenthesis bug in sstrsplit_a macro
Mike Becker <universe@uap-core.de>
parents:
314
diff
changeset
|
673 | ### Handling immutable strings |
9af21a50b516
adds scstr_t to modules.md + fixes parenthesis bug in sstrsplit_a macro
Mike Becker <universe@uap-core.de>
parents:
314
diff
changeset
|
674 | |
9af21a50b516
adds scstr_t to modules.md + fixes parenthesis bug in sstrsplit_a macro
Mike Becker <universe@uap-core.de>
parents:
314
diff
changeset
|
675 | *(Since: UCX 2.0)* |
9af21a50b516
adds scstr_t to modules.md + fixes parenthesis bug in sstrsplit_a macro
Mike Becker <universe@uap-core.de>
parents:
314
diff
changeset
|
676 | |
9af21a50b516
adds scstr_t to modules.md + fixes parenthesis bug in sstrsplit_a macro
Mike Becker <universe@uap-core.de>
parents:
314
diff
changeset
|
677 | For immutable strings (i.e. `const char*` strings), UCX provides the `scstr_t` |
9af21a50b516
adds scstr_t to modules.md + fixes parenthesis bug in sstrsplit_a macro
Mike Becker <universe@uap-core.de>
parents:
314
diff
changeset
|
678 | type, which works exactly as the `sstr_t` type but with a pointer |
9af21a50b516
adds scstr_t to modules.md + fixes parenthesis bug in sstrsplit_a macro
Mike Becker <universe@uap-core.de>
parents:
314
diff
changeset
|
679 | to `const char`. All UCX string functions come in two flavors: one that enforces |
9af21a50b516
adds scstr_t to modules.md + fixes parenthesis bug in sstrsplit_a macro
Mike Becker <universe@uap-core.de>
parents:
314
diff
changeset
|
680 | the `scstr_t` type, and another that usually accepts both types and performs |
9af21a50b516
adds scstr_t to modules.md + fixes parenthesis bug in sstrsplit_a macro
Mike Becker <universe@uap-core.de>
parents:
314
diff
changeset
|
681 | a conversion automatically, if necessary. |
9af21a50b516
adds scstr_t to modules.md + fixes parenthesis bug in sstrsplit_a macro
Mike Becker <universe@uap-core.de>
parents:
314
diff
changeset
|
682 | |
9af21a50b516
adds scstr_t to modules.md + fixes parenthesis bug in sstrsplit_a macro
Mike Becker <universe@uap-core.de>
parents:
314
diff
changeset
|
683 | There are some exceptions to this rule, as the return type may depend on the |
9af21a50b516
adds scstr_t to modules.md + fixes parenthesis bug in sstrsplit_a macro
Mike Becker <universe@uap-core.de>
parents:
314
diff
changeset
|
684 | argument type. |
9af21a50b516
adds scstr_t to modules.md + fixes parenthesis bug in sstrsplit_a macro
Mike Becker <universe@uap-core.de>
parents:
314
diff
changeset
|
685 | E.g. the `sstrchr()` function returns a substring starting at |
9af21a50b516
adds scstr_t to modules.md + fixes parenthesis bug in sstrsplit_a macro
Mike Becker <universe@uap-core.de>
parents:
314
diff
changeset
|
686 | the first occurrence of the specified character. |
9af21a50b516
adds scstr_t to modules.md + fixes parenthesis bug in sstrsplit_a macro
Mike Becker <universe@uap-core.de>
parents:
314
diff
changeset
|
687 | Since this substring points to the memory of the argument string, it does not |
9af21a50b516
adds scstr_t to modules.md + fixes parenthesis bug in sstrsplit_a macro
Mike Becker <universe@uap-core.de>
parents:
314
diff
changeset
|
688 | accept `scstr_t` as input argument, because the return type would break the |
9af21a50b516
adds scstr_t to modules.md + fixes parenthesis bug in sstrsplit_a macro
Mike Becker <universe@uap-core.de>
parents:
314
diff
changeset
|
689 | constness. |
9af21a50b516
adds scstr_t to modules.md + fixes parenthesis bug in sstrsplit_a macro
Mike Becker <universe@uap-core.de>
parents:
314
diff
changeset
|
690 | |
9af21a50b516
adds scstr_t to modules.md + fixes parenthesis bug in sstrsplit_a macro
Mike Becker <universe@uap-core.de>
parents:
314
diff
changeset
|
691 | |
267
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
692 | ### Finding the position of a substring |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
693 | |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
694 | The `sstrstr()` function gives you a new `sstr_t` object starting with the |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
695 | requested substring. Thus determining the position comes down to a simple |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
696 | subtraction. |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
697 | |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
698 | ```C |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
699 | sstr_t haystack = ST("Here we go!"); |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
700 | sstr_t needle = ST("we"); |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
701 | sstr_t result = sstrstr(haystack, needle); |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
702 | if (result.ptr) |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
703 | printf("Found at position %zd.\n", haystack.length-result.length); |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
704 | else |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
705 | printf("Not found.\n"); |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
706 | ``` |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
707 | |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
708 | ### Spliting a string by a delimiter |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
709 | |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
710 | The `sstrsplit()` function (and its allocator based version `sstrsplit_a()`) is |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
711 | very powerful and might look a bit nasty at a first glance. But it is indeed |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
712 | very simple to use. It is even more convenient in combination with a memory |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
713 | pool. |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
714 | |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
715 | ```C |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
716 | sstr_t test = ST("here::are::some::strings"); |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
717 | sstr_t delim = ST("::"); |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
718 | |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
719 | ssize_t count = 0; /* no limit */ |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
720 | UcxMempool* pool = ucx_mempool_new_default(); |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
721 | |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
722 | sstr_t* result = sstrsplit_a(pool->allocator, test, delim, &count); |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
723 | for (ssize_t i = 0 ; i < count ; i++) { |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
724 | /* don't forget to specify the length via the %*s format specifier */ |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
725 | printf("%*s\n", result[i].length, result[i].ptr); |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
726 | } |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
727 | |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
728 | ucx_mempool_destroy(pool); |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
729 | ``` |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
730 | The output is: |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
731 | |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
732 | here |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
733 | are |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
734 | some |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
735 | strings |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
736 | |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
737 | The memory pool ensures, that all strings are freed. |
f4789572c9d6
restructures documentation + adds some examples for sstr_t
Mike Becker <universe@uap-core.de>
parents:
264
diff
changeset
|
738 | |
325
a3e63cb21e20
changes sstr shortcut macros s.t. they distinguish sstr_t and scstr_t + add macros which can completely disable the shortcuts
Mike Becker <universe@uap-core.de>
parents:
321
diff
changeset
|
739 | ### Disabling convenience macros |
a3e63cb21e20
changes sstr shortcut macros s.t. they distinguish sstr_t and scstr_t + add macros which can completely disable the shortcuts
Mike Becker <universe@uap-core.de>
parents:
321
diff
changeset
|
740 | |
a3e63cb21e20
changes sstr shortcut macros s.t. they distinguish sstr_t and scstr_t + add macros which can completely disable the shortcuts
Mike Becker <universe@uap-core.de>
parents:
321
diff
changeset
|
741 | If you are experiencing any troubles with the short convenience macros `S()`, |
a3e63cb21e20
changes sstr shortcut macros s.t. they distinguish sstr_t and scstr_t + add macros which can completely disable the shortcuts
Mike Becker <universe@uap-core.de>
parents:
321
diff
changeset
|
742 | `SC()`, or `ST()`, you can disable them by setting the macro |
a3e63cb21e20
changes sstr shortcut macros s.t. they distinguish sstr_t and scstr_t + add macros which can completely disable the shortcuts
Mike Becker <universe@uap-core.de>
parents:
321
diff
changeset
|
743 | `UCX_NO_SSTR_SHORTCUTS` before including the header (or via a compiler option). |
a3e63cb21e20
changes sstr shortcut macros s.t. they distinguish sstr_t and scstr_t + add macros which can completely disable the shortcuts
Mike Becker <universe@uap-core.de>
parents:
321
diff
changeset
|
744 | For the formatting macros `SFMT()` and `PRIsstr` you can use the macro |
a3e63cb21e20
changes sstr shortcut macros s.t. they distinguish sstr_t and scstr_t + add macros which can completely disable the shortcuts
Mike Becker <universe@uap-core.de>
parents:
321
diff
changeset
|
745 | `UCX_NO_SSTR_FORMAT_MACROS` to disable them. |
a3e63cb21e20
changes sstr shortcut macros s.t. they distinguish sstr_t and scstr_t + add macros which can completely disable the shortcuts
Mike Becker <universe@uap-core.de>
parents:
321
diff
changeset
|
746 | |
a3e63cb21e20
changes sstr shortcut macros s.t. they distinguish sstr_t and scstr_t + add macros which can completely disable the shortcuts
Mike Becker <universe@uap-core.de>
parents:
321
diff
changeset
|
747 | Please keep in mind, that after disabling the macros, you cannot use them in |
a3e63cb21e20
changes sstr shortcut macros s.t. they distinguish sstr_t and scstr_t + add macros which can completely disable the shortcuts
Mike Becker <universe@uap-core.de>
parents:
321
diff
changeset
|
748 | your code *and* foreign code that you might have included. |
a3e63cb21e20
changes sstr shortcut macros s.t. they distinguish sstr_t and scstr_t + add macros which can completely disable the shortcuts
Mike Becker <universe@uap-core.de>
parents:
321
diff
changeset
|
749 | You should only disable the macros, if you are experiencing a nasty name clash |
a3e63cb21e20
changes sstr shortcut macros s.t. they distinguish sstr_t and scstr_t + add macros which can completely disable the shortcuts
Mike Becker <universe@uap-core.de>
parents:
321
diff
changeset
|
750 | which cannot be otherwise resolved. |
a3e63cb21e20
changes sstr shortcut macros s.t. they distinguish sstr_t and scstr_t + add macros which can completely disable the shortcuts
Mike Becker <universe@uap-core.de>
parents:
321
diff
changeset
|
751 | |
259 | 752 | ## Testing |
753 | ||
390
d345541018fa
starts ucx 3.0 development
Mike Becker <universe@uap-core.de>
parents:
370
diff
changeset
|
754 | *Header file:* [test.h](api-2.1/test_8h.html) |
259 | 755 | *Required modules:* None. |
756 | ||
757 | This module provides a testing framework which allows you to execute test cases | |
758 | within test suites. | |
759 | To avoid code duplication within tests, we also provide the possibility to | |
760 | define test subroutines. | |
761 | ||
297
ba760f2195c3
documentation for the testing framework
Mike Becker <universe@uap-core.de>
parents:
295
diff
changeset
|
762 | You should declare test cases and subroutines in a header file per test unit |
ba760f2195c3
documentation for the testing framework
Mike Becker <universe@uap-core.de>
parents:
295
diff
changeset
|
763 | and implement them as you would implement normal functions. |
ba760f2195c3
documentation for the testing framework
Mike Becker <universe@uap-core.de>
parents:
295
diff
changeset
|
764 | ```C |
ba760f2195c3
documentation for the testing framework
Mike Becker <universe@uap-core.de>
parents:
295
diff
changeset
|
765 | /* myunit.h */ |
ba760f2195c3
documentation for the testing framework
Mike Becker <universe@uap-core.de>
parents:
295
diff
changeset
|
766 | UCX_TEST(function_name); |
ba760f2195c3
documentation for the testing framework
Mike Becker <universe@uap-core.de>
parents:
295
diff
changeset
|
767 | UCX_TEST_SUBROUTINE(subroutine_name, paramlist); /* optional */ |
ba760f2195c3
documentation for the testing framework
Mike Becker <universe@uap-core.de>
parents:
295
diff
changeset
|
768 | |
ba760f2195c3
documentation for the testing framework
Mike Becker <universe@uap-core.de>
parents:
295
diff
changeset
|
769 | |
ba760f2195c3
documentation for the testing framework
Mike Becker <universe@uap-core.de>
parents:
295
diff
changeset
|
770 | /* myunit.c */ |
ba760f2195c3
documentation for the testing framework
Mike Becker <universe@uap-core.de>
parents:
295
diff
changeset
|
771 | UCX_TEST_SUBROUTINE(subroutine_name, paramlist) { |
ba760f2195c3
documentation for the testing framework
Mike Becker <universe@uap-core.de>
parents:
295
diff
changeset
|
772 | /* ... reusable tests with UCX_TEST_ASSERT() ... */ |
ba760f2195c3
documentation for the testing framework
Mike Becker <universe@uap-core.de>
parents:
295
diff
changeset
|
773 | } |
ba760f2195c3
documentation for the testing framework
Mike Becker <universe@uap-core.de>
parents:
295
diff
changeset
|
774 | |
ba760f2195c3
documentation for the testing framework
Mike Becker <universe@uap-core.de>
parents:
295
diff
changeset
|
775 | UCX_TEST(function_name) { |
ba760f2195c3
documentation for the testing framework
Mike Becker <universe@uap-core.de>
parents:
295
diff
changeset
|
776 | /* ... resource allocation and other test preparation ... */ |
ba760f2195c3
documentation for the testing framework
Mike Becker <universe@uap-core.de>
parents:
295
diff
changeset
|
777 | |
ba760f2195c3
documentation for the testing framework
Mike Becker <universe@uap-core.de>
parents:
295
diff
changeset
|
778 | /* mandatory marker for the start of the tests */ |
ba760f2195c3
documentation for the testing framework
Mike Becker <universe@uap-core.de>
parents:
295
diff
changeset
|
779 | UCX_TEST_BEGIN |
ba760f2195c3
documentation for the testing framework
Mike Becker <universe@uap-core.de>
parents:
295
diff
changeset
|
780 | |
ba760f2195c3
documentation for the testing framework
Mike Becker <universe@uap-core.de>
parents:
295
diff
changeset
|
781 | /* ... verifications with UCX_TEST_ASSERT() ... |
ba760f2195c3
documentation for the testing framework
Mike Becker <universe@uap-core.de>
parents:
295
diff
changeset
|
782 | * (and/or calls with UCX_TEST_CALL_SUBROUTINE()) |
ba760f2195c3
documentation for the testing framework
Mike Becker <universe@uap-core.de>
parents:
295
diff
changeset
|
783 | */ |
ba760f2195c3
documentation for the testing framework
Mike Becker <universe@uap-core.de>
parents:
295
diff
changeset
|
784 | |
ba760f2195c3
documentation for the testing framework
Mike Becker <universe@uap-core.de>
parents:
295
diff
changeset
|
785 | /* mandatory marker for the end of the tests */ |
ba760f2195c3
documentation for the testing framework
Mike Becker <universe@uap-core.de>
parents:
295
diff
changeset
|
786 | UCX_TEST_END |
ba760f2195c3
documentation for the testing framework
Mike Becker <universe@uap-core.de>
parents:
295
diff
changeset
|
787 | |
ba760f2195c3
documentation for the testing framework
Mike Becker <universe@uap-core.de>
parents:
295
diff
changeset
|
788 | /* ... resource cleanup ... |
ba760f2195c3
documentation for the testing framework
Mike Becker <universe@uap-core.de>
parents:
295
diff
changeset
|
789 | * (all code after UCX_TEST_END is always executed) |
ba760f2195c3
documentation for the testing framework
Mike Becker <universe@uap-core.de>
parents:
295
diff
changeset
|
790 | */ |
ba760f2195c3
documentation for the testing framework
Mike Becker <universe@uap-core.de>
parents:
295
diff
changeset
|
791 | } |
ba760f2195c3
documentation for the testing framework
Mike Becker <universe@uap-core.de>
parents:
295
diff
changeset
|
792 | ``` |
ba760f2195c3
documentation for the testing framework
Mike Becker <universe@uap-core.de>
parents:
295
diff
changeset
|
793 | If you want to use the `UCX_TEST_ASSERT()` macro in a function, you are |
ba760f2195c3
documentation for the testing framework
Mike Becker <universe@uap-core.de>
parents:
295
diff
changeset
|
794 | *required* to use a `UCX_TEST_SUBROUTINE`. |
ba760f2195c3
documentation for the testing framework
Mike Becker <universe@uap-core.de>
parents:
295
diff
changeset
|
795 | Otherwise the testing framework does not know where to jump, when the assertion |
ba760f2195c3
documentation for the testing framework
Mike Becker <universe@uap-core.de>
parents:
295
diff
changeset
|
796 | fails. |
ba760f2195c3
documentation for the testing framework
Mike Becker <universe@uap-core.de>
parents:
295
diff
changeset
|
797 | |
ba760f2195c3
documentation for the testing framework
Mike Becker <universe@uap-core.de>
parents:
295
diff
changeset
|
798 | After implementing the tests, you can easily build a test suite and execute it: |
ba760f2195c3
documentation for the testing framework
Mike Becker <universe@uap-core.de>
parents:
295
diff
changeset
|
799 | ```C |
ba760f2195c3
documentation for the testing framework
Mike Becker <universe@uap-core.de>
parents:
295
diff
changeset
|
800 | UcxTestSuite* suite = ucx_test_suite_new(); |
ba760f2195c3
documentation for the testing framework
Mike Becker <universe@uap-core.de>
parents:
295
diff
changeset
|
801 | ucx_test_register(suite, testMyTestCase01); |
ba760f2195c3
documentation for the testing framework
Mike Becker <universe@uap-core.de>
parents:
295
diff
changeset
|
802 | ucx_test_register(suite, testMyTestCase02); |
ba760f2195c3
documentation for the testing framework
Mike Becker <universe@uap-core.de>
parents:
295
diff
changeset
|
803 | /* ... */ |
ba760f2195c3
documentation for the testing framework
Mike Becker <universe@uap-core.de>
parents:
295
diff
changeset
|
804 | ucx_test_run(suite, stdout); /* stdout, or any other FILE stream */ |
ba760f2195c3
documentation for the testing framework
Mike Becker <universe@uap-core.de>
parents:
295
diff
changeset
|
805 | ``` |
ba760f2195c3
documentation for the testing framework
Mike Becker <universe@uap-core.de>
parents:
295
diff
changeset
|
806 | |
259 | 807 | ## Utilities |
808 | ||
390
d345541018fa
starts ucx 3.0 development
Mike Becker <universe@uap-core.de>
parents:
370
diff
changeset
|
809 | *Header file:* [utils.h](api-2.1/utils_8h.html) |
259 | 810 | *Required modules:* [Allocator](#allocator), [String](#string) |
811 | ||
812 | In this module we provide very general utility function for copy and compare | |
813 | operations. | |
814 | We also provide several `printf` variants to conveniently print formatted data | |
815 | to streams or strings. | |
816 | ||
279
ee37b179e597
doc: MWE for ucx_stream_copy()
Mike Becker <universe@uap-core.de>
parents:
277
diff
changeset
|
817 | ### A simple copy program |
ee37b179e597
doc: MWE for ucx_stream_copy()
Mike Becker <universe@uap-core.de>
parents:
277
diff
changeset
|
818 | |
ee37b179e597
doc: MWE for ucx_stream_copy()
Mike Becker <universe@uap-core.de>
parents:
277
diff
changeset
|
819 | The utilities package provides several stream copy functions. |
ee37b179e597
doc: MWE for ucx_stream_copy()
Mike Becker <universe@uap-core.de>
parents:
277
diff
changeset
|
820 | One of them has a very simple interface and can, for instance, be used to copy |
ee37b179e597
doc: MWE for ucx_stream_copy()
Mike Becker <universe@uap-core.de>
parents:
277
diff
changeset
|
821 | whole files in a single call. |
ee37b179e597
doc: MWE for ucx_stream_copy()
Mike Becker <universe@uap-core.de>
parents:
277
diff
changeset
|
822 | This is a minimal working example: |
ee37b179e597
doc: MWE for ucx_stream_copy()
Mike Becker <universe@uap-core.de>
parents:
277
diff
changeset
|
823 | ```C |
ee37b179e597
doc: MWE for ucx_stream_copy()
Mike Becker <universe@uap-core.de>
parents:
277
diff
changeset
|
824 | #include <stdio.h> |
ee37b179e597
doc: MWE for ucx_stream_copy()
Mike Becker <universe@uap-core.de>
parents:
277
diff
changeset
|
825 | #include <ucx/utils.h> |
ee37b179e597
doc: MWE for ucx_stream_copy()
Mike Becker <universe@uap-core.de>
parents:
277
diff
changeset
|
826 | |
ee37b179e597
doc: MWE for ucx_stream_copy()
Mike Becker <universe@uap-core.de>
parents:
277
diff
changeset
|
827 | int main(int argc, char** argv) { |
ee37b179e597
doc: MWE for ucx_stream_copy()
Mike Becker <universe@uap-core.de>
parents:
277
diff
changeset
|
828 | |
ee37b179e597
doc: MWE for ucx_stream_copy()
Mike Becker <universe@uap-core.de>
parents:
277
diff
changeset
|
829 | if (argc != 3) { |
ee37b179e597
doc: MWE for ucx_stream_copy()
Mike Becker <universe@uap-core.de>
parents:
277
diff
changeset
|
830 | fprintf(stderr, "Use %s <src> <dest>", argv[0]); |
ee37b179e597
doc: MWE for ucx_stream_copy()
Mike Becker <universe@uap-core.de>
parents:
277
diff
changeset
|
831 | return 1; |
ee37b179e597
doc: MWE for ucx_stream_copy()
Mike Becker <universe@uap-core.de>
parents:
277
diff
changeset
|
832 | } |
ee37b179e597
doc: MWE for ucx_stream_copy()
Mike Becker <universe@uap-core.de>
parents:
277
diff
changeset
|
833 | |
294
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
834 | FILE *srcf = fopen(argv[1], "r"); /* insert error handling on your own */ |
279
ee37b179e597
doc: MWE for ucx_stream_copy()
Mike Becker <universe@uap-core.de>
parents:
277
diff
changeset
|
835 | FILE *destf = fopen(argv[2], "w"); |
ee37b179e597
doc: MWE for ucx_stream_copy()
Mike Becker <universe@uap-core.de>
parents:
277
diff
changeset
|
836 | |
ee37b179e597
doc: MWE for ucx_stream_copy()
Mike Becker <universe@uap-core.de>
parents:
277
diff
changeset
|
837 | size_t n = ucx_stream_copy(srcf, destf, fread, fwrite); |
ee37b179e597
doc: MWE for ucx_stream_copy()
Mike Becker <universe@uap-core.de>
parents:
277
diff
changeset
|
838 | printf("%zu bytes copied.\n", n); |
ee37b179e597
doc: MWE for ucx_stream_copy()
Mike Becker <universe@uap-core.de>
parents:
277
diff
changeset
|
839 | |
ee37b179e597
doc: MWE for ucx_stream_copy()
Mike Becker <universe@uap-core.de>
parents:
277
diff
changeset
|
840 | fclose(srcf); |
ee37b179e597
doc: MWE for ucx_stream_copy()
Mike Becker <universe@uap-core.de>
parents:
277
diff
changeset
|
841 | fclose(destf); |
ee37b179e597
doc: MWE for ucx_stream_copy()
Mike Becker <universe@uap-core.de>
parents:
277
diff
changeset
|
842 | |
ee37b179e597
doc: MWE for ucx_stream_copy()
Mike Becker <universe@uap-core.de>
parents:
277
diff
changeset
|
843 | |
ee37b179e597
doc: MWE for ucx_stream_copy()
Mike Becker <universe@uap-core.de>
parents:
277
diff
changeset
|
844 | return 0; |
ee37b179e597
doc: MWE for ucx_stream_copy()
Mike Becker <universe@uap-core.de>
parents:
277
diff
changeset
|
845 | } |
ee37b179e597
doc: MWE for ucx_stream_copy()
Mike Becker <universe@uap-core.de>
parents:
277
diff
changeset
|
846 | ``` |
ee37b179e597
doc: MWE for ucx_stream_copy()
Mike Becker <universe@uap-core.de>
parents:
277
diff
changeset
|
847 | |
281
e8146a561e73
doc: adds ucx_sprintf() and ucx_bprintf() samples + fixes leftmenu
Mike Becker <universe@uap-core.de>
parents:
280
diff
changeset
|
848 | ### Automatic allocation for formatted strings |
279
ee37b179e597
doc: MWE for ucx_stream_copy()
Mike Becker <universe@uap-core.de>
parents:
277
diff
changeset
|
849 | |
281
e8146a561e73
doc: adds ucx_sprintf() and ucx_bprintf() samples + fixes leftmenu
Mike Becker <universe@uap-core.de>
parents:
280
diff
changeset
|
850 | The UCX utility function `ucx_asprintf()` and it's convenient shortcut |
e8146a561e73
doc: adds ucx_sprintf() and ucx_bprintf() samples + fixes leftmenu
Mike Becker <universe@uap-core.de>
parents:
280
diff
changeset
|
851 | `ucx_sprintf` allow easy formatting of strings, without ever having to worry |
e8146a561e73
doc: adds ucx_sprintf() and ucx_bprintf() samples + fixes leftmenu
Mike Becker <universe@uap-core.de>
parents:
280
diff
changeset
|
852 | about the required space. |
e8146a561e73
doc: adds ucx_sprintf() and ucx_bprintf() samples + fixes leftmenu
Mike Becker <universe@uap-core.de>
parents:
280
diff
changeset
|
853 | ```C |
e8146a561e73
doc: adds ucx_sprintf() and ucx_bprintf() samples + fixes leftmenu
Mike Becker <universe@uap-core.de>
parents:
280
diff
changeset
|
854 | sstr_t mystring = ucx_sprintf("The answer is: %d!", 42); |
e8146a561e73
doc: adds ucx_sprintf() and ucx_bprintf() samples + fixes leftmenu
Mike Becker <universe@uap-core.de>
parents:
280
diff
changeset
|
855 | ``` |
e8146a561e73
doc: adds ucx_sprintf() and ucx_bprintf() samples + fixes leftmenu
Mike Becker <universe@uap-core.de>
parents:
280
diff
changeset
|
856 | Still, you have to pass `mystring.ptr` to `free()` (or the free function of |
e8146a561e73
doc: adds ucx_sprintf() and ucx_bprintf() samples + fixes leftmenu
Mike Becker <universe@uap-core.de>
parents:
280
diff
changeset
|
857 | your allocator, if you use `ucx_asprintf`). |
e8146a561e73
doc: adds ucx_sprintf() and ucx_bprintf() samples + fixes leftmenu
Mike Becker <universe@uap-core.de>
parents:
280
diff
changeset
|
858 | If you don't have all the information ready to build your string, you can even |
e8146a561e73
doc: adds ucx_sprintf() and ucx_bprintf() samples + fixes leftmenu
Mike Becker <universe@uap-core.de>
parents:
280
diff
changeset
|
859 | use a [UcxBuffer](#buffer) as a target with the utility function |
e8146a561e73
doc: adds ucx_sprintf() and ucx_bprintf() samples + fixes leftmenu
Mike Becker <universe@uap-core.de>
parents:
280
diff
changeset
|
860 | `ucx_bprintf()`. |
e8146a561e73
doc: adds ucx_sprintf() and ucx_bprintf() samples + fixes leftmenu
Mike Becker <universe@uap-core.de>
parents:
280
diff
changeset
|
861 | ```C |
e8146a561e73
doc: adds ucx_sprintf() and ucx_bprintf() samples + fixes leftmenu
Mike Becker <universe@uap-core.de>
parents:
280
diff
changeset
|
862 | UcxBuffer* strbuffer = ucx_buffer_new(NULL, 512, UCX_BUFFER_AUTOEXTEND); |
e8146a561e73
doc: adds ucx_sprintf() and ucx_bprintf() samples + fixes leftmenu
Mike Becker <universe@uap-core.de>
parents:
280
diff
changeset
|
863 | |
e8146a561e73
doc: adds ucx_sprintf() and ucx_bprintf() samples + fixes leftmenu
Mike Becker <universe@uap-core.de>
parents:
280
diff
changeset
|
864 | for (unsigned int i = 2 ; i < 100 ; i++) { |
e8146a561e73
doc: adds ucx_sprintf() and ucx_bprintf() samples + fixes leftmenu
Mike Becker <universe@uap-core.de>
parents:
280
diff
changeset
|
865 | ucx_bprintf(strbuffer, "Integer %d is %s\n", |
e8146a561e73
doc: adds ucx_sprintf() and ucx_bprintf() samples + fixes leftmenu
Mike Becker <universe@uap-core.de>
parents:
280
diff
changeset
|
866 | i, prime(i) ? "prime" : "not prime"); |
e8146a561e73
doc: adds ucx_sprintf() and ucx_bprintf() samples + fixes leftmenu
Mike Becker <universe@uap-core.de>
parents:
280
diff
changeset
|
867 | } |
e8146a561e73
doc: adds ucx_sprintf() and ucx_bprintf() samples + fixes leftmenu
Mike Becker <universe@uap-core.de>
parents:
280
diff
changeset
|
868 | |
294
bfa935ab7f85
example code for the usage of a UcxList
Mike Becker <universe@uap-core.de>
parents:
290
diff
changeset
|
869 | /* print the result to stdout */ |
281
e8146a561e73
doc: adds ucx_sprintf() and ucx_bprintf() samples + fixes leftmenu
Mike Becker <universe@uap-core.de>
parents:
280
diff
changeset
|
870 | printf("%s", (char*)strbuffer->space); |
e8146a561e73
doc: adds ucx_sprintf() and ucx_bprintf() samples + fixes leftmenu
Mike Becker <universe@uap-core.de>
parents:
280
diff
changeset
|
871 | |
e8146a561e73
doc: adds ucx_sprintf() and ucx_bprintf() samples + fixes leftmenu
Mike Becker <universe@uap-core.de>
parents:
280
diff
changeset
|
872 | ucx_buffer_free(strbuffer); |
e8146a561e73
doc: adds ucx_sprintf() and ucx_bprintf() samples + fixes leftmenu
Mike Becker <universe@uap-core.de>
parents:
280
diff
changeset
|
873 | ``` |