]> git.ozlabs.org Git - ccan/blob - ccan/intmap/test/run-order.c
intmap: add iterator-by-callback.
[ccan] / ccan / intmap / test / run-order.c
1 #include <ccan/intmap/intmap.c>
2 #include <ccan/tap/tap.h>
3 #include <stdio.h>
4
5 #define NUM 1000
6
7 typedef UINTMAP(unsigned int *) umap;
8 typedef SINTMAP(int *) smap;
9
10 static bool uint_iterate_check(intmap_index_t i, unsigned int *v, int64_t *prev)
11 {
12         if ((int64_t)i <= *prev)
13                 return false;
14         if (*v != i)
15                 return false;
16         *prev = i;
17         return true;
18 }
19
20 static bool check_umap(const umap *map)
21 {
22         /* This is a larger type than unsigned, and allows negative */
23         int64_t prev;
24         uint64_t i, last_idx;
25         unsigned int *v;
26         bool last = true;
27
28         /* Must be in order, must contain value. */
29         prev = -1;
30         for (v = uintmap_first(map, &i); v; v = uintmap_after(map, &i)) {
31                 if ((int64_t)i <= prev)
32                         return false;
33                 if (*v != i)
34                         return false;
35                 prev = i;
36                 last = (uintmap_last(map, &last_idx) == v);
37         }
38
39         if (!last)
40                 return false;
41
42         prev = -1;
43         return uintmap_iterate(map, uint_iterate_check, &prev);
44 }
45
46 static bool sint_iterate_check(sintmap_index_t i, int *v, int64_t *prev)
47 {
48         if (i <= *prev)
49                 return false;
50         if (*v != i)
51                 return false;
52         *prev = i;
53         return true;
54 }
55
56 static bool check_smap(const smap *map)
57 {
58         /* This is a larger type than int, and allows negative */
59         int64_t prev, i, last_idx;
60         int *v;
61         bool last = true;
62
63         /* Must be in order, must contain value. */
64         prev = -0x80000001ULL;
65         for (v = sintmap_first(map, &i); v; v = sintmap_after(map, &i)) {
66                 if (i <= prev)
67                         return false;
68                 if (*v != i)
69                         return false;
70                 last = (sintmap_last(map, &last_idx) == v);
71                 prev = i;
72         }
73
74         if (!last)
75                 return false;
76
77         prev = -1;
78         return sintmap_iterate(map, sint_iterate_check, &prev);
79 }
80
81 int main(void)
82 {
83         umap umap;
84         smap smap;
85         int i;
86         unsigned int urandoms[NUM];
87         int srandoms[NUM];
88
89         plan_tests(6 * NUM + 2);
90         uintmap_init(&umap);
91         sintmap_init(&smap);
92
93         for (i = 0; i < NUM; i++) {
94                 urandoms[i] = random();
95                 srandoms[i] = random();
96         }
97         for (i = 0; i < NUM; i++) {
98                 /* In case we have duplicates. */
99                 while (!uintmap_add(&umap, urandoms[i], urandoms+i))
100                         urandoms[i] = random();
101                 ok1(check_umap(&umap));
102         }
103         for (i = 0; i < NUM; i++) {
104                 ok1(uintmap_del(&umap, urandoms[i]) == urandoms+i);
105                 ok1(check_umap(&umap));
106         }
107         ok1(uintmap_empty(&umap));
108
109         for (i = 0; i < NUM; i++) {
110                 /* In case we have duplicates. */
111                 while (!sintmap_add(&smap, srandoms[i], srandoms+i))
112                         srandoms[i] = random();
113                 ok1(check_smap(&smap));
114         }
115         for (i = 0; i < NUM; i++) {
116                 ok1(sintmap_del(&smap, srandoms[i]) == srandoms+i);
117                 ok1(check_smap(&smap));
118         }
119         ok1(sintmap_empty(&smap));
120
121         /* This exits depending on whether all tests passed */
122         return exit_status();
123 }