1 // SPDX-License-Identifier: GPL-2.0
2 /*
3 * (C) Copyright 2019
4 * Roman Kapl, SYSGO, rka@sysgo.com
5 */
6
7 #include <common.h>
8 #include <command.h>
9 #include <search.h>
10 #include <stdio.h>
11 #include <test/env.h>
12 #include <test/ut.h>
13
14 #define SIZE 32
15 #define ITERATIONS 10000
16
htab_fill(struct unit_test_state * uts,struct hsearch_data * htab,size_t size)17 static int htab_fill(struct unit_test_state *uts,
18 struct hsearch_data *htab, size_t size)
19 {
20 size_t i;
21 ENTRY item;
22 ENTRY *ritem;
23 char key[20];
24
25 for (i = 0; i < size; i++) {
26 sprintf(key, "%d", (int)i);
27 item.callback = NULL;
28 item.data = key;
29 item.flags = 0;
30 item.key = key;
31 ut_asserteq(1, hsearch_r(item, ENTER, &ritem, htab, 0));
32 }
33
34 return 0;
35 }
36
htab_check_fill(struct unit_test_state * uts,struct hsearch_data * htab,size_t size)37 static int htab_check_fill(struct unit_test_state *uts,
38 struct hsearch_data *htab, size_t size)
39 {
40 size_t i;
41 ENTRY item;
42 ENTRY *ritem;
43 char key[20];
44
45 for (i = 0; i < size; i++) {
46 sprintf(key, "%d", (int)i);
47 item.callback = NULL;
48 item.flags = 0;
49 item.data = key;
50 item.key = key;
51 hsearch_r(item, FIND, &ritem, htab, 0);
52 ut_assert(ritem);
53 ut_asserteq_str(key, ritem->key);
54 ut_asserteq_str(key, ritem->data);
55 }
56
57 return 0;
58 }
59
htab_create_delete(struct unit_test_state * uts,struct hsearch_data * htab,size_t iterations)60 static int htab_create_delete(struct unit_test_state *uts,
61 struct hsearch_data *htab, size_t iterations)
62 {
63 size_t i;
64 ENTRY item;
65 ENTRY *ritem;
66 char key[20];
67
68 for (i = 0; i < iterations; i++) {
69 sprintf(key, "cd-%d", (int)i);
70 item.callback = NULL;
71 item.flags = 0;
72 item.data = key;
73 item.key = key;
74 hsearch_r(item, ENTER, &ritem, htab, 0);
75 ritem = NULL;
76
77 hsearch_r(item, FIND, &ritem, htab, 0);
78 ut_assert(ritem);
79 ut_asserteq_str(key, ritem->key);
80 ut_asserteq_str(key, ritem->data);
81
82 ut_asserteq(1, hdelete_r(key, htab, 0));
83 }
84
85 return 0;
86 }
87
88 /* Completely fill up the hash table */
env_test_htab_fill(struct unit_test_state * uts)89 static int env_test_htab_fill(struct unit_test_state *uts)
90 {
91 struct hsearch_data htab;
92
93 memset(&htab, 0, sizeof(htab));
94 ut_asserteq(1, hcreate_r(SIZE, &htab));
95
96 ut_assertok(htab_fill(uts, &htab, SIZE));
97 ut_assertok(htab_check_fill(uts, &htab, SIZE));
98 ut_asserteq(SIZE, htab.filled);
99
100 hdestroy_r(&htab);
101 return 0;
102 }
103
104 ENV_TEST(env_test_htab_fill, 0);
105
106 /* Fill the hashtable up halfway an repeateadly delete/create elements
107 * and check for corruption
108 */
env_test_htab_deletes(struct unit_test_state * uts)109 static int env_test_htab_deletes(struct unit_test_state *uts)
110 {
111 struct hsearch_data htab;
112
113 memset(&htab, 0, sizeof(htab));
114 ut_asserteq(1, hcreate_r(SIZE, &htab));
115
116 ut_assertok(htab_fill(uts, &htab, SIZE / 2));
117 ut_assertok(htab_create_delete(uts, &htab, ITERATIONS));
118 ut_assertok(htab_check_fill(uts, &htab, SIZE / 2));
119 ut_asserteq(SIZE / 2, htab.filled);
120
121 hdestroy_r(&htab);
122 return 0;
123 }
124
125 ENV_TEST(env_test_htab_deletes, 0);
126