Coverage Report

Created: 2024-05-20 01:00

/src/openiked-portable/compat/sys/tree.h
Line
Count
Source (jump to first uncovered line)
1
/*  $OpenBSD: tree.h,v 1.31 2023/03/08 04:43:09 guenther Exp $  */
2
/*
3
 * Copyright 2002 Niels Provos <provos@citi.umich.edu>
4
 * All rights reserved.
5
 *
6
 * Redistribution and use in source and binary forms, with or without
7
 * modification, are permitted provided that the following conditions
8
 * are met:
9
 * 1. Redistributions of source code must retain the above copyright
10
 *    notice, this list of conditions and the following disclaimer.
11
 * 2. Redistributions in binary form must reproduce the above copyright
12
 *    notice, this list of conditions and the following disclaimer in the
13
 *    documentation and/or other materials provided with the distribution.
14
 *
15
 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
16
 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
17
 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
18
 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
19
 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
20
 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
21
 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
22
 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
23
 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
24
 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
25
 */
26
27
#ifndef _SYS_TREE_H_
28
#define _SYS_TREE_H_
29
30
#include <sys/_null.h>
31
32
/*
33
 * This file defines data structures for different types of trees:
34
 * splay trees and red-black trees.
35
 *
36
 * A splay tree is a self-organizing data structure.  Every operation
37
 * on the tree causes a splay to happen.  The splay moves the requested
38
 * node to the root of the tree and partly rebalances it.
39
 *
40
 * This has the benefit that request locality causes faster lookups as
41
 * the requested nodes move to the top of the tree.  On the other hand,
42
 * every lookup causes memory writes.
43
 *
44
 * The Balance Theorem bounds the total access time for m operations
45
 * and n inserts on an initially empty tree as O((m + n)lg n).  The
46
 * amortized cost for a sequence of m accesses to a splay tree is O(lg n);
47
 *
48
 * A red-black tree is a binary search tree with the node color as an
49
 * extra attribute.  It fulfills a set of conditions:
50
 *  - every search path from the root to a leaf consists of the
51
 *    same number of black nodes,
52
 *  - each red node (except for the root) has a black parent,
53
 *  - each leaf node is black.
54
 *
55
 * Every operation on a red-black tree is bounded as O(lg n).
56
 * The maximum height of a red-black tree is 2lg (n+1).
57
 */
58
59
#define SPLAY_HEAD(name, type)            \
60
struct name {               \
61
  struct type *sph_root; /* root of the tree */     \
62
}
63
64
#define SPLAY_INITIALIZER(root)           \
65
  { NULL }
66
67
#define SPLAY_INIT(root) do {           \
68
  (root)->sph_root = NULL;          \
69
} while (0)
70
71
#define SPLAY_ENTRY(type)           \
72
struct {                \
73
  struct type *spe_left; /* left element */     \
74
  struct type *spe_right; /* right element */     \
75
}
76
77
#define SPLAY_LEFT(elm, field)    (elm)->field.spe_left
78
#define SPLAY_RIGHT(elm, field)   (elm)->field.spe_right
79
#define SPLAY_ROOT(head)    (head)->sph_root
80
#define SPLAY_EMPTY(head)   (SPLAY_ROOT(head) == NULL)
81
82
/* SPLAY_ROTATE_{LEFT,RIGHT} expect that tmp hold SPLAY_{RIGHT,LEFT} */
83
#define SPLAY_ROTATE_RIGHT(head, tmp, field) do {     \
84
  SPLAY_LEFT((head)->sph_root, field) = SPLAY_RIGHT(tmp, field);  \
85
  SPLAY_RIGHT(tmp, field) = (head)->sph_root;     \
86
  (head)->sph_root = tmp;           \
87
} while (0)
88
89
#define SPLAY_ROTATE_LEFT(head, tmp, field) do {      \
90
  SPLAY_RIGHT((head)->sph_root, field) = SPLAY_LEFT(tmp, field);  \
91
  SPLAY_LEFT(tmp, field) = (head)->sph_root;      \
92
  (head)->sph_root = tmp;           \
93
} while (0)
94
95
#define SPLAY_LINKLEFT(head, tmp, field) do {       \
96
  SPLAY_LEFT(tmp, field) = (head)->sph_root;      \
97
  tmp = (head)->sph_root;           \
98
  (head)->sph_root = SPLAY_LEFT((head)->sph_root, field);   \
99
} while (0)
100
101
#define SPLAY_LINKRIGHT(head, tmp, field) do {        \
102
  SPLAY_RIGHT(tmp, field) = (head)->sph_root;     \
103
  tmp = (head)->sph_root;           \
104
  (head)->sph_root = SPLAY_RIGHT((head)->sph_root, field);  \
105
} while (0)
106
107
#define SPLAY_ASSEMBLE(head, node, left, right, field) do {   \
108
  SPLAY_RIGHT(left, field) = SPLAY_LEFT((head)->sph_root, field); \
109
  SPLAY_LEFT(right, field) = SPLAY_RIGHT((head)->sph_root, field);\
110
  SPLAY_LEFT((head)->sph_root, field) = SPLAY_RIGHT(node, field); \
111
  SPLAY_RIGHT((head)->sph_root, field) = SPLAY_LEFT(node, field); \
112
} while (0)
113
114
/* Generates prototypes and inline functions */
115
116
#define SPLAY_PROTOTYPE(name, type, field, cmp)       \
117
void name##_SPLAY(struct name *, struct type *);      \
118
void name##_SPLAY_MINMAX(struct name *, int);       \
119
struct type *name##_SPLAY_INSERT(struct name *, struct type *);   \
120
struct type *name##_SPLAY_REMOVE(struct name *, struct type *);   \
121
                  \
122
/* Finds the node with the same key as elm */       \
123
static __unused __inline struct type *          \
124
name##_SPLAY_FIND(struct name *head, struct type *elm)      \
125
{                 \
126
  if (SPLAY_EMPTY(head))            \
127
    return(NULL);           \
128
  name##_SPLAY(head, elm);          \
129
  if ((cmp)(elm, (head)->sph_root) == 0)        \
130
    return (head->sph_root);        \
131
  return (NULL);              \
132
}                 \
133
                  \
134
static __unused __inline struct type *          \
135
name##_SPLAY_NEXT(struct name *head, struct type *elm)      \
136
{                 \
137
  name##_SPLAY(head, elm);          \
138
  if (SPLAY_RIGHT(elm, field) != NULL) {        \
139
    elm = SPLAY_RIGHT(elm, field);        \
140
    while (SPLAY_LEFT(elm, field) != NULL) {    \
141
      elm = SPLAY_LEFT(elm, field);     \
142
    }             \
143
  } else                \
144
    elm = NULL;           \
145
  return (elm);             \
146
}                 \
147
                  \
148
static __unused __inline struct type *          \
149
name##_SPLAY_MIN_MAX(struct name *head, int val)      \
150
{                 \
151
  name##_SPLAY_MINMAX(head, val);         \
152
        return (SPLAY_ROOT(head));          \
153
}
154
155
/* Main splay operation.
156
 * Moves node close to the key of elm to top
157
 */
158
#define SPLAY_GENERATE(name, type, field, cmp)        \
159
struct type *               \
160
name##_SPLAY_INSERT(struct name *head, struct type *elm)    \
161
{                 \
162
    if (SPLAY_EMPTY(head)) {            \
163
      SPLAY_LEFT(elm, field) = SPLAY_RIGHT(elm, field) = NULL;  \
164
    } else {                \
165
      int __comp;             \
166
      name##_SPLAY(head, elm);          \
167
      __comp = (cmp)(elm, (head)->sph_root);      \
168
      if(__comp < 0) {            \
169
        SPLAY_LEFT(elm, field) = SPLAY_LEFT((head)->sph_root, field);\
170
        SPLAY_RIGHT(elm, field) = (head)->sph_root;   \
171
        SPLAY_LEFT((head)->sph_root, field) = NULL;   \
172
      } else if (__comp > 0) {          \
173
        SPLAY_RIGHT(elm, field) = SPLAY_RIGHT((head)->sph_root, field);\
174
        SPLAY_LEFT(elm, field) = (head)->sph_root;    \
175
        SPLAY_RIGHT((head)->sph_root, field) = NULL;  \
176
      } else              \
177
        return ((head)->sph_root);        \
178
    }                 \
179
    (head)->sph_root = (elm);           \
180
    return (NULL);              \
181
}                 \
182
                  \
183
struct type *               \
184
name##_SPLAY_REMOVE(struct name *head, struct type *elm)    \
185
{                 \
186
  struct type *__tmp;           \
187
  if (SPLAY_EMPTY(head))            \
188
    return (NULL);            \
189
  name##_SPLAY(head, elm);          \
190
  if ((cmp)(elm, (head)->sph_root) == 0) {      \
191
    if (SPLAY_LEFT((head)->sph_root, field) == NULL) {  \
192
      (head)->sph_root = SPLAY_RIGHT((head)->sph_root, field);\
193
    } else {            \
194
      __tmp = SPLAY_RIGHT((head)->sph_root, field); \
195
      (head)->sph_root = SPLAY_LEFT((head)->sph_root, field);\
196
      name##_SPLAY(head, elm);      \
197
      SPLAY_RIGHT((head)->sph_root, field) = __tmp; \
198
    }             \
199
    return (elm);           \
200
  }               \
201
  return (NULL);              \
202
}                 \
203
                  \
204
void                  \
205
name##_SPLAY(struct name *head, struct type *elm)     \
206
{                 \
207
  struct type __node, *__left, *__right, *__tmp;      \
208
  int __comp;             \
209
\
210
  SPLAY_LEFT(&__node, field) = SPLAY_RIGHT(&__node, field) = NULL;\
211
  __left = __right = &__node;         \
212
\
213
  while ((__comp = (cmp)(elm, (head)->sph_root))) {   \
214
    if (__comp < 0) {         \
215
      __tmp = SPLAY_LEFT((head)->sph_root, field);  \
216
      if (__tmp == NULL)        \
217
        break;          \
218
      if ((cmp)(elm, __tmp) < 0){     \
219
        SPLAY_ROTATE_RIGHT(head, __tmp, field); \
220
        if (SPLAY_LEFT((head)->sph_root, field) == NULL)\
221
          break;        \
222
      }           \
223
      SPLAY_LINKLEFT(head, __right, field);   \
224
    } else if (__comp > 0) {        \
225
      __tmp = SPLAY_RIGHT((head)->sph_root, field); \
226
      if (__tmp == NULL)        \
227
        break;          \
228
      if ((cmp)(elm, __tmp) > 0){     \
229
        SPLAY_ROTATE_LEFT(head, __tmp, field);  \
230
        if (SPLAY_RIGHT((head)->sph_root, field) == NULL)\
231
          break;        \
232
      }           \
233
      SPLAY_LINKRIGHT(head, __left, field);   \
234
    }             \
235
  }               \
236
  SPLAY_ASSEMBLE(head, &__node, __left, __right, field);    \
237
}                 \
238
                  \
239
/* Splay with either the minimum or the maximum element     \
240
 * Used to find minimum or maximum element in tree.     \
241
 */                 \
242
void name##_SPLAY_MINMAX(struct name *head, int __comp) \
243
{                 \
244
  struct type __node, *__left, *__right, *__tmp;      \
245
\
246
  SPLAY_LEFT(&__node, field) = SPLAY_RIGHT(&__node, field) = NULL;\
247
  __left = __right = &__node;         \
248
\
249
  while (1) {             \
250
    if (__comp < 0) {         \
251
      __tmp = SPLAY_LEFT((head)->sph_root, field);  \
252
      if (__tmp == NULL)        \
253
        break;          \
254
      if (__comp < 0){        \
255
        SPLAY_ROTATE_RIGHT(head, __tmp, field); \
256
        if (SPLAY_LEFT((head)->sph_root, field) == NULL)\
257
          break;        \
258
      }           \
259
      SPLAY_LINKLEFT(head, __right, field);   \
260
    } else if (__comp > 0) {        \
261
      __tmp = SPLAY_RIGHT((head)->sph_root, field); \
262
      if (__tmp == NULL)        \
263
        break;          \
264
      if (__comp > 0) {       \
265
        SPLAY_ROTATE_LEFT(head, __tmp, field);  \
266
        if (SPLAY_RIGHT((head)->sph_root, field) == NULL)\
267
          break;        \
268
      }           \
269
      SPLAY_LINKRIGHT(head, __left, field);   \
270
    }             \
271
  }               \
272
  SPLAY_ASSEMBLE(head, &__node, __left, __right, field);    \
273
}
274
275
#define SPLAY_NEGINF  -1
276
#define SPLAY_INF 1
277
278
#define SPLAY_INSERT(name, x, y)  name##_SPLAY_INSERT(x, y)
279
#define SPLAY_REMOVE(name, x, y)  name##_SPLAY_REMOVE(x, y)
280
#define SPLAY_FIND(name, x, y)    name##_SPLAY_FIND(x, y)
281
#define SPLAY_NEXT(name, x, y)    name##_SPLAY_NEXT(x, y)
282
#define SPLAY_MIN(name, x)    (SPLAY_EMPTY(x) ? NULL  \
283
          : name##_SPLAY_MIN_MAX(x, SPLAY_NEGINF))
284
#define SPLAY_MAX(name, x)    (SPLAY_EMPTY(x) ? NULL  \
285
          : name##_SPLAY_MIN_MAX(x, SPLAY_INF))
286
287
#define SPLAY_FOREACH(x, name, head)          \
288
  for ((x) = SPLAY_MIN(name, head);       \
289
       (x) != NULL;           \
290
       (x) = SPLAY_NEXT(name, head, x))
291
292
/* Macros that define a red-black tree */
293
#define RB_HEAD(name, type)           \
294
struct name {               \
295
  struct type *rbh_root; /* root of the tree */     \
296
}
297
298
#define RB_INITIALIZER(root)            \
299
  { NULL }
300
301
#define RB_INIT(root) do {            \
302
  (root)->rbh_root = NULL;          \
303
} while (0)
304
305
#define RB_BLACK  0
306
#define RB_RED    1
307
#define RB_ENTRY(type)              \
308
struct {                \
309
  struct type *rbe_left;    /* left element */    \
310
  struct type *rbe_right;   /* right element */   \
311
  struct type *rbe_parent;  /* parent element */    \
312
  int rbe_color;      /* node color */    \
313
}
314
315
#define RB_LEFT(elm, field)   (elm)->field.rbe_left
316
#define RB_RIGHT(elm, field)    (elm)->field.rbe_right
317
#define RB_PARENT(elm, field)   (elm)->field.rbe_parent
318
#define RB_COLOR(elm, field)    (elm)->field.rbe_color
319
#define RB_ROOT(head)     (head)->rbh_root
320
#define RB_EMPTY(head)      (RB_ROOT(head) == NULL)
321
322
#define RB_SET(elm, parent, field) do {         \
323
  RB_PARENT(elm, field) = parent;         \
324
  RB_LEFT(elm, field) = RB_RIGHT(elm, field) = NULL;    \
325
  RB_COLOR(elm, field) = RB_RED;          \
326
} while (0)
327
328
#define RB_SET_BLACKRED(black, red, field) do {       \
329
  RB_COLOR(black, field) = RB_BLACK;        \
330
  RB_COLOR(red, field) = RB_RED;          \
331
} while (0)
332
333
#ifndef RB_AUGMENT
334
#define RB_AUGMENT(x) do {} while (0)
335
#endif
336
337
#define RB_ROTATE_LEFT(head, elm, tmp, field) do {      \
338
  (tmp) = RB_RIGHT(elm, field);         \
339
  if ((RB_RIGHT(elm, field) = RB_LEFT(tmp, field))) {   \
340
    RB_PARENT(RB_LEFT(tmp, field), field) = (elm);    \
341
  }               \
342
  RB_AUGMENT(elm);            \
343
  if ((RB_PARENT(tmp, field) = RB_PARENT(elm, field))) {    \
344
    if ((elm) == RB_LEFT(RB_PARENT(elm, field), field)) \
345
      RB_LEFT(RB_PARENT(elm, field), field) = (tmp);  \
346
    else              \
347
      RB_RIGHT(RB_PARENT(elm, field), field) = (tmp); \
348
  } else                \
349
    (head)->rbh_root = (tmp);       \
350
  RB_LEFT(tmp, field) = (elm);          \
351
  RB_PARENT(elm, field) = (tmp);          \
352
  RB_AUGMENT(tmp);            \
353
  if ((RB_PARENT(tmp, field)))          \
354
    RB_AUGMENT(RB_PARENT(tmp, field));      \
355
} while (0)
356
357
#define RB_ROTATE_RIGHT(head, elm, tmp, field) do {     \
358
  (tmp) = RB_LEFT(elm, field);          \
359
  if ((RB_LEFT(elm, field) = RB_RIGHT(tmp, field))) {   \
360
    RB_PARENT(RB_RIGHT(tmp, field), field) = (elm);   \
361
  }               \
362
  RB_AUGMENT(elm);            \
363
  if ((RB_PARENT(tmp, field) = RB_PARENT(elm, field))) {    \
364
    if ((elm) == RB_LEFT(RB_PARENT(elm, field), field)) \
365
      RB_LEFT(RB_PARENT(elm, field), field) = (tmp);  \
366
    else              \
367
      RB_RIGHT(RB_PARENT(elm, field), field) = (tmp); \
368
  } else                \
369
    (head)->rbh_root = (tmp);       \
370
  RB_RIGHT(tmp, field) = (elm);         \
371
  RB_PARENT(elm, field) = (tmp);          \
372
  RB_AUGMENT(tmp);            \
373
  if ((RB_PARENT(tmp, field)))          \
374
    RB_AUGMENT(RB_PARENT(tmp, field));      \
375
} while (0)
376
377
/* Generates prototypes and inline functions */
378
#define RB_PROTOTYPE(name, type, field, cmp)        \
379
  RB_PROTOTYPE_INTERNAL(name, type, field, cmp,)
380
#define RB_PROTOTYPE_STATIC(name, type, field, cmp)     \
381
  RB_PROTOTYPE_INTERNAL(name, type, field, cmp, __attribute__((__unused__)) static)
382
#define RB_PROTOTYPE_INTERNAL(name, type, field, cmp, attr)   \
383
attr void name##_RB_INSERT_COLOR(struct name *, struct type *);   \
384
attr void name##_RB_REMOVE_COLOR(struct name *, struct type *, struct type *);\
385
attr struct type *name##_RB_REMOVE(struct name *, struct type *); \
386
attr struct type *name##_RB_INSERT(struct name *, struct type *); \
387
attr struct type *name##_RB_FIND(struct name *, struct type *);   \
388
attr struct type *name##_RB_NFIND(struct name *, struct type *);  \
389
attr struct type *name##_RB_NEXT(struct type *);      \
390
attr struct type *name##_RB_PREV(struct type *);      \
391
attr struct type *name##_RB_MINMAX(struct name *, int);     \
392
                  \
393
394
/* Main rb operation.
395
 * Moves node close to the key of elm to top
396
 */
397
#define RB_GENERATE(name, type, field, cmp)       \
398
  RB_GENERATE_INTERNAL(name, type, field, cmp,)
399
#define RB_GENERATE_STATIC(name, type, field, cmp)      \
400
  RB_GENERATE_INTERNAL(name, type, field, cmp, __attribute__((__unused__)) static)
401
#define RB_GENERATE_INTERNAL(name, type, field, cmp, attr)    \
402
attr void               \
403
name##_RB_INSERT_COLOR(struct name *head, struct type *elm)   \
404
{                 \
405
  struct type *parent, *gparent, *tmp;        \
406
  while ((parent = RB_PARENT(elm, field)) &&      \
407
      RB_COLOR(parent, field) == RB_RED) {      \
408
    gparent = RB_PARENT(parent, field);     \
409
    if (parent == RB_LEFT(gparent, field)) {    \
410
      tmp = RB_RIGHT(gparent, field);     \
411
      if (tmp && RB_COLOR(tmp, field) == RB_RED) {  \
412
        RB_COLOR(tmp, field) = RB_BLACK;  \
413
        RB_SET_BLACKRED(parent, gparent, field);\
414
        elm = gparent;        \
415
        continue;       \
416
      }           \
417
      if (RB_RIGHT(parent, field) == elm) {   \
418
        RB_ROTATE_LEFT(head, parent, tmp, field);\
419
        tmp = parent;       \
420
        parent = elm;       \
421
        elm = tmp;        \
422
      }           \
423
      RB_SET_BLACKRED(parent, gparent, field);  \
424
      RB_ROTATE_RIGHT(head, gparent, tmp, field); \
425
    } else {            \
426
      tmp = RB_LEFT(gparent, field);      \
427
      if (tmp && RB_COLOR(tmp, field) == RB_RED) {  \
428
        RB_COLOR(tmp, field) = RB_BLACK;  \
429
        RB_SET_BLACKRED(parent, gparent, field);\
430
        elm = gparent;        \
431
        continue;       \
432
      }           \
433
      if (RB_LEFT(parent, field) == elm) {    \
434
        RB_ROTATE_RIGHT(head, parent, tmp, field);\
435
        tmp = parent;       \
436
        parent = elm;       \
437
        elm = tmp;        \
438
      }           \
439
      RB_SET_BLACKRED(parent, gparent, field);  \
440
      RB_ROTATE_LEFT(head, gparent, tmp, field);  \
441
    }             \
442
  }               \
443
  RB_COLOR(head->rbh_root, field) = RB_BLACK;     \
444
}                 \
445
                  \
446
attr void               \
447
name##_RB_REMOVE_COLOR(struct name *head, struct type *parent, struct type *elm) \
448
{                 \
449
  struct type *tmp;           \
450
  while ((elm == NULL || RB_COLOR(elm, field) == RB_BLACK) && \
451
      elm != RB_ROOT(head)) {         \
452
    if (RB_LEFT(parent, field) == elm) {      \
453
      tmp = RB_RIGHT(parent, field);      \
454
      if (RB_COLOR(tmp, field) == RB_RED) {   \
455
        RB_SET_BLACKRED(tmp, parent, field);  \
456
        RB_ROTATE_LEFT(head, parent, tmp, field);\
457
        tmp = RB_RIGHT(parent, field);    \
458
      }           \
459
      if ((RB_LEFT(tmp, field) == NULL ||   \
460
          RB_COLOR(RB_LEFT(tmp, field), field) == RB_BLACK) &&\
461
          (RB_RIGHT(tmp, field) == NULL ||    \
462
          RB_COLOR(RB_RIGHT(tmp, field), field) == RB_BLACK)) {\
463
        RB_COLOR(tmp, field) = RB_RED;    \
464
        elm = parent;       \
465
        parent = RB_PARENT(elm, field);   \
466
      } else {          \
467
        if (RB_RIGHT(tmp, field) == NULL || \
468
            RB_COLOR(RB_RIGHT(tmp, field), field) == RB_BLACK) {\
469
          struct type *oleft;   \
470
          if ((oleft = RB_LEFT(tmp, field)))\
471
            RB_COLOR(oleft, field) = RB_BLACK;\
472
          RB_COLOR(tmp, field) = RB_RED;  \
473
          RB_ROTATE_RIGHT(head, tmp, oleft, field);\
474
          tmp = RB_RIGHT(parent, field);  \
475
        }         \
476
        RB_COLOR(tmp, field) = RB_COLOR(parent, field);\
477
        RB_COLOR(parent, field) = RB_BLACK; \
478
        if (RB_RIGHT(tmp, field))   \
479
          RB_COLOR(RB_RIGHT(tmp, field), field) = RB_BLACK;\
480
        RB_ROTATE_LEFT(head, parent, tmp, field);\
481
        elm = RB_ROOT(head);      \
482
        break;          \
483
      }           \
484
    } else {            \
485
      tmp = RB_LEFT(parent, field);     \
486
      if (RB_COLOR(tmp, field) == RB_RED) {   \
487
        RB_SET_BLACKRED(tmp, parent, field);  \
488
        RB_ROTATE_RIGHT(head, parent, tmp, field);\
489
        tmp = RB_LEFT(parent, field);   \
490
      }           \
491
      if ((RB_LEFT(tmp, field) == NULL ||   \
492
          RB_COLOR(RB_LEFT(tmp, field), field) == RB_BLACK) &&\
493
          (RB_RIGHT(tmp, field) == NULL ||    \
494
          RB_COLOR(RB_RIGHT(tmp, field), field) == RB_BLACK)) {\
495
        RB_COLOR(tmp, field) = RB_RED;    \
496
        elm = parent;       \
497
        parent = RB_PARENT(elm, field);   \
498
      } else {          \
499
        if (RB_LEFT(tmp, field) == NULL ||  \
500
            RB_COLOR(RB_LEFT(tmp, field), field) == RB_BLACK) {\
501
          struct type *oright;    \
502
          if ((oright = RB_RIGHT(tmp, field)))\
503
            RB_COLOR(oright, field) = RB_BLACK;\
504
          RB_COLOR(tmp, field) = RB_RED;  \
505
          RB_ROTATE_LEFT(head, tmp, oright, field);\
506
          tmp = RB_LEFT(parent, field); \
507
        }         \
508
        RB_COLOR(tmp, field) = RB_COLOR(parent, field);\
509
        RB_COLOR(parent, field) = RB_BLACK; \
510
        if (RB_LEFT(tmp, field))    \
511
          RB_COLOR(RB_LEFT(tmp, field), field) = RB_BLACK;\
512
        RB_ROTATE_RIGHT(head, parent, tmp, field);\
513
        elm = RB_ROOT(head);      \
514
        break;          \
515
      }           \
516
    }             \
517
  }               \
518
  if (elm)              \
519
    RB_COLOR(elm, field) = RB_BLACK;      \
520
}                 \
521
                  \
522
attr struct type *              \
523
name##_RB_REMOVE(struct name *head, struct type *elm)     \
524
{                 \
525
  struct type *child, *parent, *old = elm;      \
526
  int color;              \
527
  if (RB_LEFT(elm, field) == NULL)        \
528
    child = RB_RIGHT(elm, field);       \
529
  else if (RB_RIGHT(elm, field) == NULL)        \
530
    child = RB_LEFT(elm, field);        \
531
  else {                \
532
    struct type *left;          \
533
    elm = RB_RIGHT(elm, field);       \
534
    while ((left = RB_LEFT(elm, field)))      \
535
      elm = left;         \
536
    child = RB_RIGHT(elm, field);       \
537
    parent = RB_PARENT(elm, field);       \
538
    color = RB_COLOR(elm, field);       \
539
    if (child)            \
540
      RB_PARENT(child, field) = parent;   \
541
    if (parent) {           \
542
      if (RB_LEFT(parent, field) == elm)    \
543
        RB_LEFT(parent, field) = child;   \
544
      else            \
545
        RB_RIGHT(parent, field) = child;  \
546
      RB_AUGMENT(parent);       \
547
    } else              \
548
      RB_ROOT(head) = child;        \
549
    if (RB_PARENT(elm, field) == old)     \
550
      parent = elm;         \
551
    (elm)->field = (old)->field;        \
552
    if (RB_PARENT(old, field)) {        \
553
      if (RB_LEFT(RB_PARENT(old, field), field) == old)\
554
        RB_LEFT(RB_PARENT(old, field), field) = elm;\
555
      else            \
556
        RB_RIGHT(RB_PARENT(old, field), field) = elm;\
557
      RB_AUGMENT(RB_PARENT(old, field));    \
558
    } else              \
559
      RB_ROOT(head) = elm;        \
560
    RB_PARENT(RB_LEFT(old, field), field) = elm;    \
561
    if (RB_RIGHT(old, field))       \
562
      RB_PARENT(RB_RIGHT(old, field), field) = elm; \
563
    if (parent) {           \
564
      left = parent;          \
565
      do {            \
566
        RB_AUGMENT(left);     \
567
      } while ((left = RB_PARENT(left, field)));  \
568
    }             \
569
    goto color;           \
570
  }               \
571
  parent = RB_PARENT(elm, field);         \
572
  color = RB_COLOR(elm, field);         \
573
  if (child)              \
574
    RB_PARENT(child, field) = parent;     \
575
  if (parent) {             \
576
    if (RB_LEFT(parent, field) == elm)      \
577
      RB_LEFT(parent, field) = child;     \
578
    else              \
579
      RB_RIGHT(parent, field) = child;    \
580
    RB_AUGMENT(parent);         \
581
  } else                \
582
    RB_ROOT(head) = child;          \
583
color:                  \
584
  if (color == RB_BLACK)            \
585
    name##_RB_REMOVE_COLOR(head, parent, child);    \
586
  return (old);             \
587
}                 \
588
                  \
589
/* Inserts a node into the RB tree */         \
590
attr struct type *              \
591
name##_RB_INSERT(struct name *head, struct type *elm)     \
592
{                 \
593
  struct type *tmp;           \
594
  struct type *parent = NULL;         \
595
  int comp = 0;             \
596
  tmp = RB_ROOT(head);            \
597
  while (tmp) {             \
598
    parent = tmp;           \
599
    comp = (cmp)(elm, parent);        \
600
    if (comp < 0)           \
601
      tmp = RB_LEFT(tmp, field);      \
602
    else if (comp > 0)          \
603
      tmp = RB_RIGHT(tmp, field);     \
604
    else              \
605
      return (tmp);         \
606
  }               \
607
  RB_SET(elm, parent, field);         \
608
  if (parent != NULL) {           \
609
    if (comp < 0)           \
610
      RB_LEFT(parent, field) = elm;     \
611
    else              \
612
      RB_RIGHT(parent, field) = elm;      \
613
    RB_AUGMENT(parent);         \
614
  } else                \
615
    RB_ROOT(head) = elm;          \
616
  name##_RB_INSERT_COLOR(head, elm);        \
617
  return (NULL);              \
618
}                 \
619
                  \
620
/* Finds the node with the same key as elm */       \
621
attr struct type *              \
622
name##_RB_FIND(struct name *head, struct type *elm)     \
623
{                 \
624
  struct type *tmp = RB_ROOT(head);       \
625
  int comp;             \
626
  while (tmp) {             \
627
    comp = cmp(elm, tmp);         \
628
    if (comp < 0)           \
629
      tmp = RB_LEFT(tmp, field);      \
630
    else if (comp > 0)          \
631
      tmp = RB_RIGHT(tmp, field);     \
632
    else              \
633
      return (tmp);         \
634
  }               \
635
  return (NULL);              \
636
}                 \
637
                  \
638
/* Finds the first node greater than or equal to the search key */  \
639
attr struct type *              \
640
name##_RB_NFIND(struct name *head, struct type *elm)      \
641
{                 \
642
  struct type *tmp = RB_ROOT(head);       \
643
  struct type *res = NULL;          \
644
  int comp;             \
645
  while (tmp) {             \
646
    comp = cmp(elm, tmp);         \
647
    if (comp < 0) {           \
648
      res = tmp;          \
649
      tmp = RB_LEFT(tmp, field);      \
650
    }             \
651
    else if (comp > 0)          \
652
      tmp = RB_RIGHT(tmp, field);     \
653
    else              \
654
      return (tmp);         \
655
  }               \
656
  return (res);             \
657
}                 \
658
                  \
659
attr struct type *              \
660
name##_RB_NEXT(struct type *elm)          \
661
{                 \
662
  if (RB_RIGHT(elm, field)) {         \
663
    elm = RB_RIGHT(elm, field);       \
664
    while (RB_LEFT(elm, field))       \
665
      elm = RB_LEFT(elm, field);      \
666
  } else {              \
667
    if (RB_PARENT(elm, field) &&        \
668
        (elm == RB_LEFT(RB_PARENT(elm, field), field))) \
669
      elm = RB_PARENT(elm, field);      \
670
    else {              \
671
      while (RB_PARENT(elm, field) &&     \
672
          (elm == RB_RIGHT(RB_PARENT(elm, field), field)))\
673
        elm = RB_PARENT(elm, field);    \
674
      elm = RB_PARENT(elm, field);      \
675
    }             \
676
  }               \
677
  return (elm);             \
678
}                 \
679
                  \
680
attr struct type *              \
681
name##_RB_PREV(struct type *elm)          \
682
{                 \
683
  if (RB_LEFT(elm, field)) {          \
684
    elm = RB_LEFT(elm, field);        \
685
    while (RB_RIGHT(elm, field))        \
686
      elm = RB_RIGHT(elm, field);     \
687
  } else {              \
688
    if (RB_PARENT(elm, field) &&        \
689
        (elm == RB_RIGHT(RB_PARENT(elm, field), field)))  \
690
      elm = RB_PARENT(elm, field);      \
691
    else {              \
692
      while (RB_PARENT(elm, field) &&     \
693
          (elm == RB_LEFT(RB_PARENT(elm, field), field)))\
694
        elm = RB_PARENT(elm, field);    \
695
      elm = RB_PARENT(elm, field);      \
696
    }             \
697
  }               \
698
  return (elm);             \
699
}                 \
700
                  \
701
attr struct type *              \
702
name##_RB_MINMAX(struct name *head, int val)        \
703
{                 \
704
  struct type *tmp = RB_ROOT(head);       \
705
  struct type *parent = NULL;         \
706
  while (tmp) {             \
707
    parent = tmp;           \
708
    if (val < 0)            \
709
      tmp = RB_LEFT(tmp, field);      \
710
    else              \
711
      tmp = RB_RIGHT(tmp, field);     \
712
  }               \
713
  return (parent);            \
714
}
715
716
#define RB_NEGINF -1
717
#define RB_INF  1
718
719
#define RB_INSERT(name, x, y) name##_RB_INSERT(x, y)
720
#define RB_REMOVE(name, x, y) name##_RB_REMOVE(x, y)
721
#define RB_FIND(name, x, y) name##_RB_FIND(x, y)
722
#define RB_NFIND(name, x, y)  name##_RB_NFIND(x, y)
723
#define RB_NEXT(name, x, y) name##_RB_NEXT(y)
724
#define RB_PREV(name, x, y) name##_RB_PREV(y)
725
#define RB_MIN(name, x)   name##_RB_MINMAX(x, RB_NEGINF)
726
#define RB_MAX(name, x)   name##_RB_MINMAX(x, RB_INF)
727
728
#define RB_FOREACH(x, name, head)         \
729
  for ((x) = RB_MIN(name, head);          \
730
       (x) != NULL;           \
731
       (x) = name##_RB_NEXT(x))
732
733
#define RB_FOREACH_SAFE(x, name, head, y)       \
734
  for ((x) = RB_MIN(name, head);          \
735
      ((x) != NULL) && ((y) = name##_RB_NEXT(x), 1);    \
736
       (x) = (y))
737
738
#define RB_FOREACH_REVERSE(x, name, head)       \
739
  for ((x) = RB_MAX(name, head);          \
740
       (x) != NULL;           \
741
       (x) = name##_RB_PREV(x))
742
743
#define RB_FOREACH_REVERSE_SAFE(x, name, head, y)     \
744
  for ((x) = RB_MAX(name, head);          \
745
      ((x) != NULL) && ((y) = name##_RB_PREV(x), 1);    \
746
       (x) = (y))
747
748
749
/*
750
 * Copyright (c) 2016 David Gwynne <dlg@openbsd.org>
751
 *
752
 * Permission to use, copy, modify, and distribute this software for any
753
 * purpose with or without fee is hereby granted, provided that the above
754
 * copyright notice and this permission notice appear in all copies.
755
 *
756
 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
757
 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
758
 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
759
 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
760
 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
761
 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
762
 * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
763
 */
764
765
struct rb_type {
766
  int   (*t_compare)(const void *, const void *);
767
  void    (*t_augment)(void *);
768
  unsigned int    t_offset; /* offset of rb_entry in type */
769
};
770
771
struct rb_tree {
772
  struct rb_entry *rbt_root;
773
};
774
775
struct rb_entry {
776
  struct rb_entry  *rbt_parent;
777
  struct rb_entry  *rbt_left;
778
  struct rb_entry  *rbt_right;
779
  unsigned int    rbt_color;
780
};
781
782
#define RBT_HEAD(_name, _type)            \
783
struct _name {                \
784
  struct rb_tree rbh_root;          \
785
}
786
787
#define RBT_ENTRY(_type)  struct rb_entry
788
789
static inline void
790
_rb_init(struct rb_tree *rbt)
791
0
{
792
0
  rbt->rbt_root = NULL;
793
0
}
Unexecuted instantiation: common.c:_rb_init
Unexecuted instantiation: test_parser_fuzz.c:_rb_init
Unexecuted instantiation: ikev2_pld.c:_rb_init
Unexecuted instantiation: imsg_util.c:_rb_init
Unexecuted instantiation: util.c:_rb_init
794
795
static inline int
796
_rb_empty(struct rb_tree *rbt)
797
0
{
798
0
  return (rbt->rbt_root == NULL);
799
0
}
Unexecuted instantiation: common.c:_rb_empty
Unexecuted instantiation: test_parser_fuzz.c:_rb_empty
Unexecuted instantiation: ikev2_pld.c:_rb_empty
Unexecuted instantiation: imsg_util.c:_rb_empty
Unexecuted instantiation: util.c:_rb_empty
800
801
void  *_rb_insert(const struct rb_type *, struct rb_tree *, void *);
802
void  *_rb_remove(const struct rb_type *, struct rb_tree *, void *);
803
void  *_rb_find(const struct rb_type *, struct rb_tree *, const void *);
804
void  *_rb_nfind(const struct rb_type *, struct rb_tree *, const void *);
805
void  *_rb_root(const struct rb_type *, struct rb_tree *);
806
void  *_rb_min(const struct rb_type *, struct rb_tree *);
807
void  *_rb_max(const struct rb_type *, struct rb_tree *);
808
void  *_rb_next(const struct rb_type *, void *);
809
void  *_rb_prev(const struct rb_type *, void *);
810
void  *_rb_left(const struct rb_type *, void *);
811
void  *_rb_right(const struct rb_type *, void *);
812
void  *_rb_parent(const struct rb_type *, void *);
813
void   _rb_set_left(const struct rb_type *, void *, void *);
814
void   _rb_set_right(const struct rb_type *, void *, void *);
815
void   _rb_set_parent(const struct rb_type *, void *, void *);
816
void   _rb_poison(const struct rb_type *, void *, unsigned long);
817
int  _rb_check(const struct rb_type *, void *, unsigned long);
818
819
#define RBT_INITIALIZER(_head)  { { NULL } }
820
821
#define RBT_PROTOTYPE(_name, _type, _field, _cmp)     \
822
extern const struct rb_type *const _name##_RBT_TYPE;      \
823
                  \
824
__unused static inline void           \
825
_name##_RBT_INIT(struct _name *head)          \
826
{                 \
827
  _rb_init(&head->rbh_root);          \
828
}                 \
829
                  \
830
__unused static inline struct _type *         \
831
_name##_RBT_INSERT(struct _name *head, struct _type *elm)   \
832
{                 \
833
  return _rb_insert(_name##_RBT_TYPE, &head->rbh_root, elm);  \
834
}                 \
835
                  \
836
__unused static inline struct _type *         \
837
_name##_RBT_REMOVE(struct _name *head, struct _type *elm)   \
838
{                 \
839
  return _rb_remove(_name##_RBT_TYPE, &head->rbh_root, elm);  \
840
}                 \
841
                  \
842
__unused static inline struct _type *         \
843
_name##_RBT_FIND(struct _name *head, const struct _type *key)   \
844
{                 \
845
  return _rb_find(_name##_RBT_TYPE, &head->rbh_root, key);  \
846
}                 \
847
                  \
848
__unused static inline struct _type *         \
849
_name##_RBT_NFIND(struct _name *head, const struct _type *key)    \
850
{                 \
851
  return _rb_nfind(_name##_RBT_TYPE, &head->rbh_root, key); \
852
}                 \
853
                  \
854
__unused static inline struct _type *         \
855
_name##_RBT_ROOT(struct _name *head)          \
856
{                 \
857
  return _rb_root(_name##_RBT_TYPE, &head->rbh_root);   \
858
}                 \
859
                  \
860
__unused static inline int            \
861
_name##_RBT_EMPTY(struct _name *head)         \
862
{                 \
863
  return _rb_empty(&head->rbh_root);        \
864
}                 \
865
                  \
866
__unused static inline struct _type *         \
867
_name##_RBT_MIN(struct _name *head)         \
868
{                 \
869
  return _rb_min(_name##_RBT_TYPE, &head->rbh_root);    \
870
}                 \
871
                  \
872
__unused static inline struct _type *         \
873
_name##_RBT_MAX(struct _name *head)         \
874
{                 \
875
  return _rb_max(_name##_RBT_TYPE, &head->rbh_root);    \
876
}                 \
877
                  \
878
__unused static inline struct _type *         \
879
_name##_RBT_NEXT(struct _type *elm)         \
880
{                 \
881
  return _rb_next(_name##_RBT_TYPE, elm);       \
882
}                 \
883
                  \
884
__unused static inline struct _type *         \
885
_name##_RBT_PREV(struct _type *elm)         \
886
{                 \
887
  return _rb_prev(_name##_RBT_TYPE, elm);       \
888
}                 \
889
                  \
890
__unused static inline struct _type *         \
891
_name##_RBT_LEFT(struct _type *elm)         \
892
{                 \
893
  return _rb_left(_name##_RBT_TYPE, elm);       \
894
}                 \
895
                  \
896
__unused static inline struct _type *         \
897
_name##_RBT_RIGHT(struct _type *elm)          \
898
{                 \
899
  return _rb_right(_name##_RBT_TYPE, elm);      \
900
}                 \
901
                  \
902
__unused static inline struct _type *         \
903
_name##_RBT_PARENT(struct _type *elm)         \
904
{                 \
905
  return _rb_parent(_name##_RBT_TYPE, elm);     \
906
}                 \
907
                  \
908
__unused static inline void           \
909
_name##_RBT_SET_LEFT(struct _type *elm, struct _type *left)   \
910
{                 \
911
  _rb_set_left(_name##_RBT_TYPE, elm, left);      \
912
}                 \
913
                  \
914
__unused static inline void           \
915
_name##_RBT_SET_RIGHT(struct _type *elm, struct _type *right)   \
916
{                 \
917
  _rb_set_right(_name##_RBT_TYPE, elm, right);      \
918
}                 \
919
                  \
920
__unused static inline void           \
921
_name##_RBT_SET_PARENT(struct _type *elm, struct _type *parent)   \
922
{                 \
923
  _rb_set_parent(_name##_RBT_TYPE, elm, parent);      \
924
}                 \
925
                  \
926
__unused static inline void           \
927
_name##_RBT_POISON(struct _type *elm, unsigned long poison)   \
928
{                 \
929
  _rb_poison(_name##_RBT_TYPE, elm, poison);      \
930
}                 \
931
                  \
932
__unused static inline int            \
933
_name##_RBT_CHECK(struct _type *elm, unsigned long poison)    \
934
{                 \
935
  return _rb_check(_name##_RBT_TYPE, elm, poison);    \
936
}
937
938
#define RBT_GENERATE_INTERNAL(_name, _type, _field, _cmp, _aug)   \
939
static int                \
940
_name##_RBT_COMPARE(const void *lptr, const void *rptr)     \
941
{                 \
942
  const struct _type *l = lptr, *r = rptr;      \
943
  return _cmp(l, r);            \
944
}                 \
945
static const struct rb_type _name##_RBT_INFO = {      \
946
  _name##_RBT_COMPARE,            \
947
  _aug,               \
948
  offsetof(struct _type, _field),         \
949
};                  \
950
const struct rb_type *const _name##_RBT_TYPE = &_name##_RBT_INFO
951
952
#define RBT_GENERATE_AUGMENT(_name, _type, _field, _cmp, _aug)    \
953
static void               \
954
_name##_RBT_AUGMENT(void *ptr)            \
955
{                 \
956
  struct _type *p = ptr;            \
957
  return _aug(p);             \
958
}                 \
959
RBT_GENERATE_INTERNAL(_name, _type, _field, _cmp, _name##_RBT_AUGMENT)
960
961
#define RBT_GENERATE(_name, _type, _field, _cmp)      \
962
    RBT_GENERATE_INTERNAL(_name, _type, _field, _cmp, NULL)
963
964
#define RBT_INIT(_name, _head)    _name##_RBT_INIT(_head)
965
#define RBT_INSERT(_name, _head, _elm)  _name##_RBT_INSERT(_head, _elm)
966
#define RBT_REMOVE(_name, _head, _elm)  _name##_RBT_REMOVE(_head, _elm)
967
#define RBT_FIND(_name, _head, _key)  _name##_RBT_FIND(_head, _key)
968
#define RBT_NFIND(_name, _head, _key) _name##_RBT_NFIND(_head, _key)
969
#define RBT_ROOT(_name, _head)    _name##_RBT_ROOT(_head)
970
#define RBT_EMPTY(_name, _head)   _name##_RBT_EMPTY(_head)
971
#define RBT_MIN(_name, _head)   _name##_RBT_MIN(_head)
972
#define RBT_MAX(_name, _head)   _name##_RBT_MAX(_head)
973
#define RBT_NEXT(_name, _elm)   _name##_RBT_NEXT(_elm)
974
#define RBT_PREV(_name, _elm)   _name##_RBT_PREV(_elm)
975
#define RBT_LEFT(_name, _elm)   _name##_RBT_LEFT(_elm)
976
#define RBT_RIGHT(_name, _elm)    _name##_RBT_RIGHT(_elm)
977
#define RBT_PARENT(_name, _elm)   _name##_RBT_PARENT(_elm)
978
#define RBT_SET_LEFT(_name, _elm, _l) _name##_RBT_SET_LEFT(_elm, _l)
979
#define RBT_SET_RIGHT(_name, _elm, _r)  _name##_RBT_SET_RIGHT(_elm, _r)
980
#define RBT_SET_PARENT(_name, _elm, _p) _name##_RBT_SET_PARENT(_elm, _p)
981
#define RBT_POISON(_name, _elm, _p) _name##_RBT_POISON(_elm, _p)
982
#define RBT_CHECK(_name, _elm, _p)  _name##_RBT_CHECK(_elm, _p)
983
984
#define RBT_FOREACH(_e, _name, _head)         \
985
  for ((_e) = RBT_MIN(_name, (_head));        \
986
       (_e) != NULL;            \
987
       (_e) = RBT_NEXT(_name, (_e)))
988
989
#define RBT_FOREACH_SAFE(_e, _name, _head, _n)        \
990
  for ((_e) = RBT_MIN(_name, (_head));        \
991
       (_e) != NULL && ((_n) = RBT_NEXT(_name, (_e)), 1); \
992
       (_e) = (_n))
993
994
#define RBT_FOREACH_REVERSE(_e, _name, _head)       \
995
  for ((_e) = RBT_MAX(_name, (_head));        \
996
       (_e) != NULL;            \
997
       (_e) = RBT_PREV(_name, (_e)))
998
999
#define RBT_FOREACH_REVERSE_SAFE(_e, _name, _head, _n)      \
1000
  for ((_e) = RBT_MAX(_name, (_head));        \
1001
       (_e) != NULL && ((_n) = RBT_PREV(_name, (_e)), 1); \
1002
       (_e) = (_n))
1003
1004
#endif  /* _SYS_TREE_H_ */