docs/Writerside/topics/mempool.h.md

branch
docs/3.1
changeset 1141
a06a2d27c043
child 1142
9437530176bc
equal deleted inserted replaced
1140:88a9ee79c102 1141:a06a2d27c043
1 # mempool.h
2
3 A memory pool is providing an allocator implementation that automatically deallocates the memory upon its destruction.
4 It also allows you to register destructor functions for the allocated memory, which are automatically called before
5 the memory is deallocated.
6 Additionally, you may also register _independent_ destructor functions within a pool in case some external library
7 allocated memory for you, which should be freed together with this pool.
8
9 Many UCX features support the use of an allocator.
10 The [strings](#string), for instance, provide several functions suffixed with `_a` that allow specifying an allocator.
11 You can use this to keep track of the memory occupied by dynamically allocated strings and cleanup everything with
12 just a single call to `cxMempoolFree()`.
13
14 The following code illustrates this on the example of reading a CSV file into memory.
15 ```C
16 #include <stdio.h>
17 #include <cx/mempool.h>
18 #include <cx/linked_list.h>
19 #include <cx/string.h>
20 #include <cx/buffer.h>
21 #include <cx/utils.h>
22
23 typedef struct {
24 cxstring column_a;
25 cxstring column_b;
26 cxstring column_c;
27 } CSVData;
28
29 int main(void) {
30 CxMempool* pool = cxBasicMempoolCreate(128);
31
32 FILE *f = fopen("test.csv", "r");
33 if (!f) {
34 perror("Cannot open file");
35 return 1;
36 }
37 // close the file automatically at pool destruction
38 cxMempoolRegister(pool, f, (cx_destructor_func) fclose);
39
40 // create a buffer using the memory pool for destruction
41 CxBuffer *content = cxBufferCreate(NULL, 256, pool->allocator, CX_BUFFER_AUTO_EXTEND);
42
43 // read the file into the buffer and turn it into a string
44 cx_stream_copy(f, content, (cx_read_func) fread, cxBufferWriteFunc);
45 fclose(f);
46 cxstring contentstr = cx_strn(content->space, content->size);
47
48 // split the string into lines - use the mempool for allocating the target array
49 cxstring* lines;
50 size_t lc = cx_strsplit_a(pool->allocator, contentstr,
51 CX_STR("\n"), SIZE_MAX, &lines);
52
53 // skip the header and parse the remaining data into a linked list
54 // the nodes of the linked list shall also be allocated by the mempool
55 CxList* datalist = cxLinkedListCreate(pool->allocator, NULL, sizeof(CSVData));
56 for (size_t i = 1 ; i < lc ; i++) {
57 if (lines[i].length == 0) continue;
58 cxstring fields[3];
59 size_t fc = cx_strsplit(lines[i], CX_STR(";"), 3, fields);
60 if (fc != 3) {
61 fprintf(stderr, "Syntax error in line %zu.\n", i);
62 cxMempoolFree(pool);
63 return 1;
64 }
65 CSVData data;
66 data.column_a = fields[0];
67 data.column_b = fields[1];
68 data.column_c = fields[2];
69 cxListAdd(datalist, &data);
70 }
71
72 // iterate through the list and output the data
73 CxIterator iter = cxListIterator(datalist);
74 cx_foreach(CSVData*, data, iter) {
75 printf("Column A: %.*s | "
76 "Column B: %.*s | "
77 "Column C: %.*s\n",
78 (int)data->column_a.length, data->column_a.ptr,
79 (int)data->column_b.length, data->column_b.ptr,
80 (int)data->column_c.length, data->column_c.ptr
81 );
82 }
83
84 // cleanup everything, no manual free() needed
85 cxMempoolFree(pool);
86
87 return 0;
88 }
89 ```
90

mercurial