blob: 5913e62d5322225ce8de128f88fb91fcbfebb9e0 [file] [log] [blame]
Radek Krejcie84f12f2018-09-18 14:11:50 +02001/*
aPiecek023f83a2021-05-11 07:37:03 +02002 * @file test_set.c
Radek Krejcie84f12f2018-09-18 14:11:50 +02003 * @author: Radek Krejci <rkrejci@cesnet.cz>
4 * @brief unit tests for functions from set.c
5 *
6 * Copyright (c) 2018 CESNET, z.s.p.o.
7 *
8 * This source code is licensed under BSD 3-Clause License (the "License").
9 * You may not use this file except in compliance with the License.
10 * You may obtain a copy of the License at
11 *
12 * https://opensource.org/licenses/BSD-3-Clause
13 */
Radek Krejcif8dc59a2020-11-25 13:47:44 +010014#define _POSIX_C_SOURCE 200809L /* strdup */
Radek Iša56ca9e42020-09-08 18:42:00 +020015#define _UTEST_MAIN_
16#include "utests.h"
Radek Krejcie84f12f2018-09-18 14:11:50 +020017
Radek Krejci535ea9f2020-05-29 16:01:05 +020018#include <stdlib.h>
Radek Krejcie84f12f2018-09-18 14:11:50 +020019#include <string.h>
20
Radek Krejci70593c12020-06-13 20:48:09 +020021#include "set.h"
Radek Krejcie84f12f2018-09-18 14:11:50 +020022
Radek Krejcie84f12f2018-09-18 14:11:50 +020023static void
Radek Iša56ca9e42020-09-08 18:42:00 +020024test_basics(void **UNUSED(state))
Radek Krejcie84f12f2018-09-18 14:11:50 +020025{
Radek Krejcie84f12f2018-09-18 14:11:50 +020026 struct ly_set *set;
27 char *str;
28 unsigned int u;
29 void *ptr;
Radek Krejciba03a5a2020-08-27 14:40:41 +020030 uint32_t index;
Radek Krejcie84f12f2018-09-18 14:11:50 +020031
32 /* creation - everything is empty */
Radek Krejciba03a5a2020-08-27 14:40:41 +020033 assert_int_equal(LY_SUCCESS, ly_set_new(&set));
Radek Krejcie84f12f2018-09-18 14:11:50 +020034 assert_non_null(set);
35 assert_int_equal(0, set->count);
36 assert_int_equal(0, set->size);
37 assert_null(set->objs);
38
39 /* add a testing object */
40 str = strdup("test string");
41 assert_non_null(str);
42
Radek Krejciba03a5a2020-08-27 14:40:41 +020043 assert_int_equal(LY_SUCCESS, ly_set_add(set, str, 0, NULL));
Radek Krejcie84f12f2018-09-18 14:11:50 +020044 assert_int_not_equal(0, set->size);
45 assert_int_equal(1, set->count);
46 assert_non_null(set->objs);
47 assert_non_null(set->objs[0]);
48
49 /* check the presence of the testing data */
Michal Vaskof9c0a672022-02-17 10:48:14 +010050 assert_int_equal(1, ly_set_contains(set, str, &index));
Radek Krejciba03a5a2020-08-27 14:40:41 +020051 assert_int_equal(0, index);
52 assert_int_equal(0, ly_set_contains(set, str - 1, NULL));
Radek Krejcie84f12f2018-09-18 14:11:50 +020053
54 /* remove data, but keep the set */
55 u = set->size;
56 ptr = set->objs;
57 ly_set_clean(set, free);
58 assert_int_equal(0, set->count);
59 assert_int_equal(u, set->size);
60 assert_ptr_equal(ptr, set->objs);
61
62 /* remove buffer, but keep the set object */
63 ly_set_erase(set, NULL);
64 assert_int_equal(0, set->count);
65 assert_int_equal(0, set->size);
66 assert_ptr_equal(NULL, set->objs);
67
68 /* final cleanup */
69 ly_set_free(set, NULL);
70}
71
72static void
73test_inval(void **state)
74{
75 struct ly_set set;
Radek Krejcib4ac5a92020-11-23 17:54:33 +010076
Radek Krejcie84f12f2018-09-18 14:11:50 +020077 memset(&set, 0, sizeof set);
78
79 ly_set_clean(NULL, NULL);
Radek Iša56ca9e42020-09-08 18:42:00 +020080 CHECK_LOG(NULL, NULL);
Radek Krejcie84f12f2018-09-18 14:11:50 +020081
82 ly_set_erase(NULL, NULL);
Radek Iša56ca9e42020-09-08 18:42:00 +020083 CHECK_LOG(NULL, NULL);
Radek Krejcie84f12f2018-09-18 14:11:50 +020084
85 ly_set_free(NULL, NULL);
Radek Iša56ca9e42020-09-08 18:42:00 +020086 CHECK_LOG(NULL, NULL);
Radek Krejcie84f12f2018-09-18 14:11:50 +020087
Radek Krejciba03a5a2020-08-27 14:40:41 +020088 assert_int_equal(LY_EINVAL, ly_set_dup(NULL, NULL, NULL));
Radek Iša56ca9e42020-09-08 18:42:00 +020089 CHECK_LOG("Invalid argument set (ly_set_dup()).", NULL);
Radek Krejcie84f12f2018-09-18 14:11:50 +020090
Radek Krejciba03a5a2020-08-27 14:40:41 +020091 assert_int_equal(LY_EINVAL, ly_set_add(NULL, NULL, 0, NULL));
Radek Iša56ca9e42020-09-08 18:42:00 +020092 CHECK_LOG("Invalid argument set (ly_set_add()).", NULL);
Radek Krejcie84f12f2018-09-18 14:11:50 +020093
Radek Krejciba03a5a2020-08-27 14:40:41 +020094 assert_int_equal(LY_EINVAL, ly_set_merge(NULL, NULL, 0, NULL));
Radek Iša56ca9e42020-09-08 18:42:00 +020095 CHECK_LOG("Invalid argument trg (ly_set_merge()).", NULL);
Radek Krejciba03a5a2020-08-27 14:40:41 +020096 assert_int_equal(LY_SUCCESS, ly_set_merge(&set, NULL, 0, NULL));
Radek Krejcie84f12f2018-09-18 14:11:50 +020097
Radek Krejci820d2262018-09-20 12:15:31 +020098 assert_int_equal(LY_EINVAL, ly_set_rm_index(NULL, 0, NULL));
Radek Iša56ca9e42020-09-08 18:42:00 +020099 CHECK_LOG("Invalid argument set (ly_set_rm_index()).", NULL);
Radek Krejci820d2262018-09-20 12:15:31 +0200100 assert_int_equal(LY_EINVAL, ly_set_rm_index(&set, 1, NULL));
Radek Iša56ca9e42020-09-08 18:42:00 +0200101 CHECK_LOG("Invalid argument index (ly_set_rm_index()).", NULL);
Radek Krejcie84f12f2018-09-18 14:11:50 +0200102
Radek Krejci820d2262018-09-20 12:15:31 +0200103 assert_int_equal(LY_EINVAL, ly_set_rm(NULL, NULL, NULL));
Radek Iša56ca9e42020-09-08 18:42:00 +0200104 CHECK_LOG("Invalid argument set (ly_set_rm()).", NULL);
Radek Krejci820d2262018-09-20 12:15:31 +0200105 assert_int_equal(LY_EINVAL, ly_set_rm(&set, NULL, NULL));
Radek Iša56ca9e42020-09-08 18:42:00 +0200106 CHECK_LOG("Invalid argument object (ly_set_rm()).", NULL);
107 assert_int_equal(LY_EINVAL, ly_set_rm(&set, &set, NULL));
108 CHECK_LOG("Invalid argument object (ly_set_rm()).", NULL);
Radek Krejcie84f12f2018-09-18 14:11:50 +0200109}
110
Radek Krejci519b0432018-09-18 17:04:57 +0200111static void
Radek Iša56ca9e42020-09-08 18:42:00 +0200112test_duplication(void **UNUSED(state))
Radek Krejci519b0432018-09-18 17:04:57 +0200113{
Radek Krejci519b0432018-09-18 17:04:57 +0200114 struct ly_set *orig, *new;
115 char *str;
Radek Krejciba03a5a2020-08-27 14:40:41 +0200116 uint32_t index;
Radek Krejci519b0432018-09-18 17:04:57 +0200117
Radek Krejciba03a5a2020-08-27 14:40:41 +0200118 assert_int_equal(LY_SUCCESS, ly_set_new(&orig));
Radek Krejci519b0432018-09-18 17:04:57 +0200119 assert_non_null(orig);
120
121 /* add a testing object */
122 str = strdup("test string");
123 assert_non_null(str);
Radek Krejciba03a5a2020-08-27 14:40:41 +0200124 assert_int_equal(LY_SUCCESS, ly_set_add(orig, str, 0, &index));
125 assert_int_equal(0, index);
Radek Krejci519b0432018-09-18 17:04:57 +0200126
127 /* duplicate the set - without duplicator, so the new set will point to the same string */
Radek Krejciba03a5a2020-08-27 14:40:41 +0200128 assert_int_equal(LY_SUCCESS, ly_set_dup(orig, NULL, &new));
Radek Krejci519b0432018-09-18 17:04:57 +0200129 assert_non_null(new);
130 assert_ptr_not_equal(orig, new);
131 assert_int_equal(orig->count, new->count);
132 assert_ptr_equal(orig->objs[0], new->objs[0]);
133
134 ly_set_free(new, NULL);
135
136 /* duplicate the set - with duplicator, so the new set will point to a different buffer with the same content */
Radek Krejcib4ac5a92020-11-23 17:54:33 +0100137 assert_int_equal(LY_SUCCESS, ly_set_dup(orig, (void *(*)(void *))strdup, &new));
Radek Krejci519b0432018-09-18 17:04:57 +0200138 assert_non_null(new);
139 assert_ptr_not_equal(orig, new);
140 assert_int_equal(orig->count, new->count);
141 assert_ptr_not_equal(orig->objs[0], new->objs[0]);
142 assert_string_equal(orig->objs[0], new->objs[0]);
143
144 /* cleanup */
145 ly_set_free(new, free);
146 ly_set_free(orig, free);
147}
148
149static void
Radek Iša56ca9e42020-09-08 18:42:00 +0200150test_add(void **UNUSED(state))
Radek Krejci519b0432018-09-18 17:04:57 +0200151{
Radek Krejciba03a5a2020-08-27 14:40:41 +0200152 uint32_t u, index;
Radek Krejci519b0432018-09-18 17:04:57 +0200153 char *str = "test string";
154 struct ly_set set;
Radek Krejcib4ac5a92020-11-23 17:54:33 +0100155
Radek Krejci519b0432018-09-18 17:04:57 +0200156 memset(&set, 0, sizeof set);
157
158 /* add a testing object */
Radek Krejciba03a5a2020-08-27 14:40:41 +0200159 assert_int_equal(LY_SUCCESS, ly_set_add(&set, str, 0, &index));
160 assert_int_equal(0, index);
Radek Krejci519b0432018-09-18 17:04:57 +0200161
162 /* test avoiding data duplicities */
Radek Krejciba03a5a2020-08-27 14:40:41 +0200163 assert_int_equal(LY_SUCCESS, ly_set_add(&set, str, 0, &index));
164 assert_int_equal(0, index);
Radek Krejci519b0432018-09-18 17:04:57 +0200165 assert_int_equal(1, set.count);
Radek Krejci3d92e442020-10-12 12:48:13 +0200166 assert_int_equal(LY_SUCCESS, ly_set_add(&set, str, 1, &index));
Radek Krejciba03a5a2020-08-27 14:40:41 +0200167 assert_int_equal(1, index);
Radek Krejci519b0432018-09-18 17:04:57 +0200168 assert_int_equal(2, set.count);
169
170 /* test array resizing */
171 u = set.size;
Radek Krejciba03a5a2020-08-27 14:40:41 +0200172 for (uint32_t expected_index = 2; expected_index <= u; ++expected_index) {
Radek Krejci3d92e442020-10-12 12:48:13 +0200173 assert_int_equal(LY_SUCCESS, ly_set_add(&set, str, 1, &index));
Radek Krejciba03a5a2020-08-27 14:40:41 +0200174 assert_int_equal(expected_index, index);
Radek Krejci519b0432018-09-18 17:04:57 +0200175 }
176 assert_true(u != set.size);
177
178 /* cleanup */
179 ly_set_erase(&set, NULL);
180}
181
182static void
Radek Iša56ca9e42020-09-08 18:42:00 +0200183test_merge(void **UNUSED(state))
Radek Krejci519b0432018-09-18 17:04:57 +0200184{
Radek Krejci519b0432018-09-18 17:04:57 +0200185 char *str1, *str2;
186 struct ly_set one, two;
Radek Krejcib4ac5a92020-11-23 17:54:33 +0100187
Radek Krejci519b0432018-09-18 17:04:57 +0200188 memset(&one, 0, sizeof one);
189 memset(&two, 0, sizeof two);
190
191 str1 = strdup("string1");
192 str2 = strdup("string2");
193
194 /* fill first set
195 * - str1 is the same as in two, so it must not be freed! */
Radek Krejciba03a5a2020-08-27 14:40:41 +0200196 assert_int_equal(LY_SUCCESS, ly_set_add(&one, str1, 0, NULL));
Radek Krejci519b0432018-09-18 17:04:57 +0200197
198 /* fill second set */
Radek Krejciba03a5a2020-08-27 14:40:41 +0200199 assert_int_equal(LY_SUCCESS, ly_set_add(&two, str1, 0, NULL));
200 assert_int_equal(LY_SUCCESS, ly_set_add(&two, str2, 0, NULL));
Radek Krejci519b0432018-09-18 17:04:57 +0200201
202 /* merge with checking duplicities - only one item is added into one;
203 * also without duplicating data, so it must not be freed at the end */
Radek Krejciba03a5a2020-08-27 14:40:41 +0200204 assert_int_equal(LY_SUCCESS, ly_set_merge(&one, &two, 0, NULL));
205 assert_int_equal(2, one.count);
Radek Krejci519b0432018-09-18 17:04:57 +0200206 assert_ptr_equal(one.objs[1], two.objs[1]);
207
208 /* clean and re-fill one (now duplicating str1, to allow testing duplicator) */
209 ly_set_clean(&one, NULL);
Radek Krejciba03a5a2020-08-27 14:40:41 +0200210 assert_int_equal(LY_SUCCESS, ly_set_add(&one, strdup(str1), 0, NULL));
Radek Krejci519b0432018-09-18 17:04:57 +0200211
212 /* merge without checking duplicities - two items are added into one;
213 * here also with duplicator */
Radek Krejcib4ac5a92020-11-23 17:54:33 +0100214 assert_int_equal(LY_SUCCESS, ly_set_merge(&one, &two, 1, (void *(*)(void *))strdup));
Radek Krejciba03a5a2020-08-27 14:40:41 +0200215 assert_int_equal(3, one.count);
Radek Krejci519b0432018-09-18 17:04:57 +0200216 assert_ptr_not_equal(one.objs[1], two.objs[0]);
217 assert_string_equal(one.objs[1], two.objs[0]);
218
219 /* cleanup */
220 ly_set_erase(&one, free);
221 ly_set_erase(&two, free);
222}
223
224static void
Radek Iša56ca9e42020-09-08 18:42:00 +0200225test_rm(void **UNUSED(state))
Radek Krejci519b0432018-09-18 17:04:57 +0200226{
Radek Krejci519b0432018-09-18 17:04:57 +0200227 char *str1, *str2, *str3;
228 struct ly_set set;
Radek Krejcib4ac5a92020-11-23 17:54:33 +0100229
Radek Krejci519b0432018-09-18 17:04:57 +0200230 memset(&set, 0, sizeof set);
231
232 /* fill the set */
Radek Krejciba03a5a2020-08-27 14:40:41 +0200233 assert_int_equal(LY_SUCCESS, ly_set_add(&set, "string1", 0, NULL));
234 assert_int_equal(LY_SUCCESS, ly_set_add(&set, strdup("string2"), 0, NULL));
235 assert_int_equal(LY_SUCCESS, ly_set_add(&set, "string3", 0, NULL));
Radek Krejci519b0432018-09-18 17:04:57 +0200236
237 /* remove by index ... */
238 /* ... in the middle ... */
Radek Krejci820d2262018-09-20 12:15:31 +0200239 assert_int_equal(LY_SUCCESS, ly_set_rm_index(&set, 1, free));
Radek Krejci519b0432018-09-18 17:04:57 +0200240 assert_int_equal(2, set.count);
241 assert_string_not_equal("string2", set.objs[0]);
242 assert_string_not_equal("string2", set.objs[1]);
243 /* ... last .. */
Radek Krejci820d2262018-09-20 12:15:31 +0200244 assert_int_equal(LY_SUCCESS, ly_set_rm_index(&set, 1, NULL));
Radek Krejci519b0432018-09-18 17:04:57 +0200245 assert_int_equal(1, set.count);
246 assert_string_not_equal("string3", set.objs[0]);
247 /* ... first .. */
Radek Krejci820d2262018-09-20 12:15:31 +0200248 assert_int_equal(LY_SUCCESS, ly_set_rm_index(&set, 0, NULL));
Radek Krejci519b0432018-09-18 17:04:57 +0200249 assert_int_equal(0, set.count);
250
251 /* fill the set */
Radek Krejciba03a5a2020-08-27 14:40:41 +0200252 assert_int_equal(LY_SUCCESS, ly_set_add(&set, str1 = "string1", 0, NULL));
253 assert_int_equal(LY_SUCCESS, ly_set_add(&set, str2 = "string2", 0, NULL));
254 assert_int_equal(LY_SUCCESS, ly_set_add(&set, str3 = strdup("string3"), 0, NULL));
Radek Krejci519b0432018-09-18 17:04:57 +0200255
256 /* remove by pointer ... */
257 /* ... in the middle ... */
Radek Krejci820d2262018-09-20 12:15:31 +0200258 assert_int_equal(LY_SUCCESS, ly_set_rm(&set, str2, NULL));
Radek Krejci519b0432018-09-18 17:04:57 +0200259 assert_int_equal(2, set.count);
260 assert_string_not_equal("string2", set.objs[0]);
261 assert_string_not_equal("string2", set.objs[1]);
Radek Krejci820d2262018-09-20 12:15:31 +0200262 /* ... last (with destructor) .. */
263 assert_int_equal(LY_SUCCESS, ly_set_rm(&set, str3, free));
Radek Krejci519b0432018-09-18 17:04:57 +0200264 assert_int_equal(1, set.count);
265 assert_string_not_equal("string3", set.objs[0]);
266 /* ... first .. */
Radek Krejci820d2262018-09-20 12:15:31 +0200267 assert_int_equal(LY_SUCCESS, ly_set_rm(&set, str1, NULL));
Radek Krejci519b0432018-09-18 17:04:57 +0200268 assert_int_equal(0, set.count);
269
270 /* cleanup */
271 ly_set_erase(&set, NULL);
272}
273
Radek Krejcib4ac5a92020-11-23 17:54:33 +0100274int
275main(void)
Radek Krejcie84f12f2018-09-18 14:11:50 +0200276{
277 const struct CMUnitTest tests[] = {
Radek Iša56ca9e42020-09-08 18:42:00 +0200278 UTEST(test_basics),
279 UTEST(test_duplication),
280 UTEST(test_add),
281 UTEST(test_merge),
282 UTEST(test_rm),
283 UTEST(test_inval),
Radek Krejcie84f12f2018-09-18 14:11:50 +0200284 };
285
286 return cmocka_run_group_tests(tests, NULL, NULL);
287}