tree.h - dedup - deduplicating backup program
 (HTM) git clone git://bitreich.org/dedup/ git://enlrupgkhuxnvlhsf6lc3fziv5h2hhfrinws65d7roiv6bfj7d652fid.onion/dedup/
 (DIR) Log
 (DIR) Files
 (DIR) Refs
 (DIR) Tags
 (DIR) README
 (DIR) LICENSE
       ---
       tree.h (33874B)
       ---
            1 /*        $OpenBSD: tree.h,v 1.29 2017/07/30 19:27:20 deraadt 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 /*
           31  * This file defines data structures for different types of trees:
           32  * splay trees and red-black trees.
           33  *
           34  * A splay tree is a self-organizing data structure.  Every operation
           35  * on the tree causes a splay to happen.  The splay moves the requested
           36  * node to the root of the tree and partly rebalances it.
           37  *
           38  * This has the benefit that request locality causes faster lookups as
           39  * the requested nodes move to the top of the tree.  On the other hand,
           40  * every lookup causes memory writes.
           41  *
           42  * The Balance Theorem bounds the total access time for m operations
           43  * and n inserts on an initially empty tree as O((m + n)lg n).  The
           44  * amortized cost for a sequence of m accesses to a splay tree is O(lg n);
           45  *
           46  * A red-black tree is a binary search tree with the node color as an
           47  * extra attribute.  It fulfills a set of conditions:
           48  *        - every search path from the root to a leaf consists of the
           49  *          same number of black nodes,
           50  *        - each red node (except for the root) has a black parent,
           51  *        - each leaf node is black.
           52  *
           53  * Every operation on a red-black tree is bounded as O(lg n).
           54  * The maximum height of a red-black tree is 2lg (n+1).
           55  */
           56 
           57 #define SPLAY_HEAD(name, type)                                                \
           58 struct name {                                                                \
           59         struct type *sph_root; /* root of the tree */                        \
           60 }
           61 
           62 #define SPLAY_INITIALIZER(root)                                                \
           63         { NULL }
           64 
           65 #define SPLAY_INIT(root) do {                                                \
           66         (root)->sph_root = NULL;                                        \
           67 } while (0)
           68 
           69 #define SPLAY_ENTRY(type)                                                \
           70 struct {                                                                \
           71         struct type *spe_left; /* left element */                        \
           72         struct type *spe_right; /* right element */                        \
           73 }
           74 
           75 #define SPLAY_LEFT(elm, field)                (elm)->field.spe_left
           76 #define SPLAY_RIGHT(elm, field)                (elm)->field.spe_right
           77 #define SPLAY_ROOT(head)                (head)->sph_root
           78 #define SPLAY_EMPTY(head)                (SPLAY_ROOT(head) == NULL)
           79 
           80 /* SPLAY_ROTATE_{LEFT,RIGHT} expect that tmp hold SPLAY_{RIGHT,LEFT} */
           81 #define SPLAY_ROTATE_RIGHT(head, tmp, field) do {                        \
           82         SPLAY_LEFT((head)->sph_root, field) = SPLAY_RIGHT(tmp, field);        \
           83         SPLAY_RIGHT(tmp, field) = (head)->sph_root;                        \
           84         (head)->sph_root = tmp;                                                \
           85 } while (0)
           86 
           87 #define SPLAY_ROTATE_LEFT(head, tmp, field) do {                        \
           88         SPLAY_RIGHT((head)->sph_root, field) = SPLAY_LEFT(tmp, field);        \
           89         SPLAY_LEFT(tmp, field) = (head)->sph_root;                        \
           90         (head)->sph_root = tmp;                                                \
           91 } while (0)
           92 
           93 #define SPLAY_LINKLEFT(head, tmp, field) do {                                \
           94         SPLAY_LEFT(tmp, field) = (head)->sph_root;                        \
           95         tmp = (head)->sph_root;                                                \
           96         (head)->sph_root = SPLAY_LEFT((head)->sph_root, field);                \
           97 } while (0)
           98 
           99 #define SPLAY_LINKRIGHT(head, tmp, field) do {                                \
          100         SPLAY_RIGHT(tmp, field) = (head)->sph_root;                        \
          101         tmp = (head)->sph_root;                                                \
          102         (head)->sph_root = SPLAY_RIGHT((head)->sph_root, field);        \
          103 } while (0)
          104 
          105 #define SPLAY_ASSEMBLE(head, node, left, right, field) do {                \
          106         SPLAY_RIGHT(left, field) = SPLAY_LEFT((head)->sph_root, field);        \
          107         SPLAY_LEFT(right, field) = SPLAY_RIGHT((head)->sph_root, field);\
          108         SPLAY_LEFT((head)->sph_root, field) = SPLAY_RIGHT(node, field);        \
          109         SPLAY_RIGHT((head)->sph_root, field) = SPLAY_LEFT(node, field);        \
          110 } while (0)
          111 
          112 /* Generates prototypes and inline functions */
          113 
          114 #define SPLAY_PROTOTYPE(name, type, field, cmp)                                \
          115 void name##_SPLAY(struct name *, struct type *);                        \
          116 void name##_SPLAY_MINMAX(struct name *, int);                                \
          117 struct type *name##_SPLAY_INSERT(struct name *, struct type *);                \
          118 struct type *name##_SPLAY_REMOVE(struct name *, struct type *);                \
          119                                                                         \
          120 /* Finds the node with the same key as elm */                                \
          121 static __unused __inline struct type *                                        \
          122 name##_SPLAY_FIND(struct name *head, struct type *elm)                        \
          123 {                                                                        \
          124         if (SPLAY_EMPTY(head))                                                \
          125                 return(NULL);                                                \
          126         name##_SPLAY(head, elm);                                        \
          127         if ((cmp)(elm, (head)->sph_root) == 0)                                \
          128                 return (head->sph_root);                                \
          129         return (NULL);                                                        \
          130 }                                                                        \
          131                                                                         \
          132 static __unused __inline struct type *                                        \
          133 name##_SPLAY_NEXT(struct name *head, struct type *elm)                        \
          134 {                                                                        \
          135         name##_SPLAY(head, elm);                                        \
          136         if (SPLAY_RIGHT(elm, field) != NULL) {                                \
          137                 elm = SPLAY_RIGHT(elm, field);                                \
          138                 while (SPLAY_LEFT(elm, field) != NULL) {                \
          139                         elm = SPLAY_LEFT(elm, field);                        \
          140                 }                                                        \
          141         } else                                                                \
          142                 elm = NULL;                                                \
          143         return (elm);                                                        \
          144 }                                                                        \
          145                                                                         \
          146 static __unused __inline struct type *                                        \
          147 name##_SPLAY_MIN_MAX(struct name *head, int val)                        \
          148 {                                                                        \
          149         name##_SPLAY_MINMAX(head, val);                                        \
          150         return (SPLAY_ROOT(head));                                        \
          151 }
          152 
          153 /* Main splay operation.
          154  * Moves node close to the key of elm to top
          155  */
          156 #define SPLAY_GENERATE(name, type, field, cmp)                                \
          157 struct type *                                                                \
          158 name##_SPLAY_INSERT(struct name *head, struct type *elm)                \
          159 {                                                                        \
          160     if (SPLAY_EMPTY(head)) {                                                \
          161             SPLAY_LEFT(elm, field) = SPLAY_RIGHT(elm, field) = NULL;        \
          162     } else {                                                                \
          163             int __comp;                                                        \
          164             name##_SPLAY(head, elm);                                        \
          165             __comp = (cmp)(elm, (head)->sph_root);                        \
          166             if(__comp < 0) {                                                \
          167                     SPLAY_LEFT(elm, field) = SPLAY_LEFT((head)->sph_root, field);\
          168                     SPLAY_RIGHT(elm, field) = (head)->sph_root;                \
          169                     SPLAY_LEFT((head)->sph_root, field) = NULL;                \
          170             } else if (__comp > 0) {                                        \
          171                     SPLAY_RIGHT(elm, field) = SPLAY_RIGHT((head)->sph_root, field);\
          172                     SPLAY_LEFT(elm, field) = (head)->sph_root;                \
          173                     SPLAY_RIGHT((head)->sph_root, field) = NULL;        \
          174             } else                                                        \
          175                     return ((head)->sph_root);                                \
          176     }                                                                        \
          177     (head)->sph_root = (elm);                                                \
          178     return (NULL);                                                        \
          179 }                                                                        \
          180                                                                         \
          181 struct type *                                                                \
          182 name##_SPLAY_REMOVE(struct name *head, struct type *elm)                \
          183 {                                                                        \
          184         struct type *__tmp;                                                \
          185         if (SPLAY_EMPTY(head))                                                \
          186                 return (NULL);                                                \
          187         name##_SPLAY(head, elm);                                        \
          188         if ((cmp)(elm, (head)->sph_root) == 0) {                        \
          189                 if (SPLAY_LEFT((head)->sph_root, field) == NULL) {        \
          190                         (head)->sph_root = SPLAY_RIGHT((head)->sph_root, field);\
          191                 } else {                                                \
          192                         __tmp = SPLAY_RIGHT((head)->sph_root, field);        \
          193                         (head)->sph_root = SPLAY_LEFT((head)->sph_root, field);\
          194                         name##_SPLAY(head, elm);                        \
          195                         SPLAY_RIGHT((head)->sph_root, field) = __tmp;        \
          196                 }                                                        \
          197                 return (elm);                                                \
          198         }                                                                \
          199         return (NULL);                                                        \
          200 }                                                                        \
          201                                                                         \
          202 void                                                                        \
          203 name##_SPLAY(struct name *head, struct type *elm)                        \
          204 {                                                                        \
          205         struct type __node, *__left, *__right, *__tmp;                        \
          206         int __comp;                                                        \
          207 \
          208         SPLAY_LEFT(&__node, field) = SPLAY_RIGHT(&__node, field) = NULL;\
          209         __left = __right = &__node;                                        \
          210 \
          211         while ((__comp = (cmp)(elm, (head)->sph_root))) {                \
          212                 if (__comp < 0) {                                        \
          213                         __tmp = SPLAY_LEFT((head)->sph_root, field);        \
          214                         if (__tmp == NULL)                                \
          215                                 break;                                        \
          216                         if ((cmp)(elm, __tmp) < 0){                        \
          217                                 SPLAY_ROTATE_RIGHT(head, __tmp, field);        \
          218                                 if (SPLAY_LEFT((head)->sph_root, field) == NULL)\
          219                                         break;                                \
          220                         }                                                \
          221                         SPLAY_LINKLEFT(head, __right, field);                \
          222                 } else if (__comp > 0) {                                \
          223                         __tmp = SPLAY_RIGHT((head)->sph_root, field);        \
          224                         if (__tmp == NULL)                                \
          225                                 break;                                        \
          226                         if ((cmp)(elm, __tmp) > 0){                        \
          227                                 SPLAY_ROTATE_LEFT(head, __tmp, field);        \
          228                                 if (SPLAY_RIGHT((head)->sph_root, field) == NULL)\
          229                                         break;                                \
          230                         }                                                \
          231                         SPLAY_LINKRIGHT(head, __left, field);                \
          232                 }                                                        \
          233         }                                                                \
          234         SPLAY_ASSEMBLE(head, &__node, __left, __right, field);                \
          235 }                                                                        \
          236                                                                         \
          237 /* Splay with either the minimum or the maximum element                        \
          238  * Used to find minimum or maximum element in tree.                        \
          239  */                                                                        \
          240 void name##_SPLAY_MINMAX(struct name *head, int __comp) \
          241 {                                                                        \
          242         struct type __node, *__left, *__right, *__tmp;                        \
          243 \
          244         SPLAY_LEFT(&__node, field) = SPLAY_RIGHT(&__node, field) = NULL;\
          245         __left = __right = &__node;                                        \
          246 \
          247         while (1) {                                                        \
          248                 if (__comp < 0) {                                        \
          249                         __tmp = SPLAY_LEFT((head)->sph_root, field);        \
          250                         if (__tmp == NULL)                                \
          251                                 break;                                        \
          252                         if (__comp < 0){                                \
          253                                 SPLAY_ROTATE_RIGHT(head, __tmp, field);        \
          254                                 if (SPLAY_LEFT((head)->sph_root, field) == NULL)\
          255                                         break;                                \
          256                         }                                                \
          257                         SPLAY_LINKLEFT(head, __right, field);                \
          258                 } else if (__comp > 0) {                                \
          259                         __tmp = SPLAY_RIGHT((head)->sph_root, field);        \
          260                         if (__tmp == NULL)                                \
          261                                 break;                                        \
          262                         if (__comp > 0) {                                \
          263                                 SPLAY_ROTATE_LEFT(head, __tmp, field);        \
          264                                 if (SPLAY_RIGHT((head)->sph_root, field) == NULL)\
          265                                         break;                                \
          266                         }                                                \
          267                         SPLAY_LINKRIGHT(head, __left, field);                \
          268                 }                                                        \
          269         }                                                                \
          270         SPLAY_ASSEMBLE(head, &__node, __left, __right, field);                \
          271 }
          272 
          273 #define SPLAY_NEGINF        -1
          274 #define SPLAY_INF        1
          275 
          276 #define SPLAY_INSERT(name, x, y)        name##_SPLAY_INSERT(x, y)
          277 #define SPLAY_REMOVE(name, x, y)        name##_SPLAY_REMOVE(x, y)
          278 #define SPLAY_FIND(name, x, y)                name##_SPLAY_FIND(x, y)
          279 #define SPLAY_NEXT(name, x, y)                name##_SPLAY_NEXT(x, y)
          280 #define SPLAY_MIN(name, x)                (SPLAY_EMPTY(x) ? NULL        \
          281                                         : name##_SPLAY_MIN_MAX(x, SPLAY_NEGINF))
          282 #define SPLAY_MAX(name, x)                (SPLAY_EMPTY(x) ? NULL        \
          283                                         : name##_SPLAY_MIN_MAX(x, SPLAY_INF))
          284 
          285 #define SPLAY_FOREACH(x, name, head)                                        \
          286         for ((x) = SPLAY_MIN(name, head);                                \
          287              (x) != NULL;                                                \
          288              (x) = SPLAY_NEXT(name, head, x))
          289 
          290 /* Macros that define a red-black tree */
          291 #define RB_HEAD(name, type)                                                \
          292 struct name {                                                                \
          293         struct type *rbh_root; /* root of the tree */                        \
          294 }
          295 
          296 #define RB_INITIALIZER(root)                                                \
          297         { NULL }
          298 
          299 #define RB_INIT(root) do {                                                \
          300         (root)->rbh_root = NULL;                                        \
          301 } while (0)
          302 
          303 #define RB_BLACK        0
          304 #define RB_RED                1
          305 #define RB_ENTRY(type)                                                        \
          306 struct {                                                                \
          307         struct type *rbe_left;                /* left element */                \
          308         struct type *rbe_right;                /* right element */                \
          309         struct type *rbe_parent;        /* parent element */                \
          310         int rbe_color;                        /* node color */                \
          311 }
          312 
          313 #define RB_LEFT(elm, field)                (elm)->field.rbe_left
          314 #define RB_RIGHT(elm, field)                (elm)->field.rbe_right
          315 #define RB_PARENT(elm, field)                (elm)->field.rbe_parent
          316 #define RB_COLOR(elm, field)                (elm)->field.rbe_color
          317 #define RB_ROOT(head)                        (head)->rbh_root
          318 #define RB_EMPTY(head)                        (RB_ROOT(head) == NULL)
          319 
          320 #define RB_SET(elm, parent, field) do {                                        \
          321         RB_PARENT(elm, field) = parent;                                        \
          322         RB_LEFT(elm, field) = RB_RIGHT(elm, field) = NULL;                \
          323         RB_COLOR(elm, field) = RB_RED;                                        \
          324 } while (0)
          325 
          326 #define RB_SET_BLACKRED(black, red, field) do {                                \
          327         RB_COLOR(black, field) = RB_BLACK;                                \
          328         RB_COLOR(red, field) = RB_RED;                                        \
          329 } while (0)
          330 
          331 #ifndef RB_AUGMENT
          332 #define RB_AUGMENT(x)        do {} while (0)
          333 #endif
          334 
          335 #define RB_ROTATE_LEFT(head, elm, tmp, field) do {                        \
          336         (tmp) = RB_RIGHT(elm, field);                                        \
          337         if ((RB_RIGHT(elm, field) = RB_LEFT(tmp, field))) {                \
          338                 RB_PARENT(RB_LEFT(tmp, field), field) = (elm);                \
          339         }                                                                \
          340         RB_AUGMENT(elm);                                                \
          341         if ((RB_PARENT(tmp, field) = RB_PARENT(elm, field))) {                \
          342                 if ((elm) == RB_LEFT(RB_PARENT(elm, field), field))        \
          343                         RB_LEFT(RB_PARENT(elm, field), field) = (tmp);        \
          344                 else                                                        \
          345                         RB_RIGHT(RB_PARENT(elm, field), field) = (tmp);        \
          346         } else                                                                \
          347                 (head)->rbh_root = (tmp);                                \
          348         RB_LEFT(tmp, field) = (elm);                                        \
          349         RB_PARENT(elm, field) = (tmp);                                        \
          350         RB_AUGMENT(tmp);                                                \
          351         if ((RB_PARENT(tmp, field)))                                        \
          352                 RB_AUGMENT(RB_PARENT(tmp, field));                        \
          353 } while (0)
          354 
          355 #define RB_ROTATE_RIGHT(head, elm, tmp, field) do {                        \
          356         (tmp) = RB_LEFT(elm, field);                                        \
          357         if ((RB_LEFT(elm, field) = RB_RIGHT(tmp, field))) {                \
          358                 RB_PARENT(RB_RIGHT(tmp, field), field) = (elm);                \
          359         }                                                                \
          360         RB_AUGMENT(elm);                                                \
          361         if ((RB_PARENT(tmp, field) = RB_PARENT(elm, field))) {                \
          362                 if ((elm) == RB_LEFT(RB_PARENT(elm, field), field))        \
          363                         RB_LEFT(RB_PARENT(elm, field), field) = (tmp);        \
          364                 else                                                        \
          365                         RB_RIGHT(RB_PARENT(elm, field), field) = (tmp);        \
          366         } else                                                                \
          367                 (head)->rbh_root = (tmp);                                \
          368         RB_RIGHT(tmp, field) = (elm);                                        \
          369         RB_PARENT(elm, field) = (tmp);                                        \
          370         RB_AUGMENT(tmp);                                                \
          371         if ((RB_PARENT(tmp, field)))                                        \
          372                 RB_AUGMENT(RB_PARENT(tmp, field));                        \
          373 } while (0)
          374 
          375 /* Generates prototypes and inline functions */
          376 #define        RB_PROTOTYPE(name, type, field, cmp)                                \
          377         RB_PROTOTYPE_INTERNAL(name, type, field, cmp,)
          378 #define        RB_PROTOTYPE_STATIC(name, type, field, cmp)                        \
          379         RB_PROTOTYPE_INTERNAL(name, type, field, cmp, __attribute__((__unused__)) static)
          380 #define RB_PROTOTYPE_INTERNAL(name, type, field, cmp, attr)                \
          381 attr void name##_RB_INSERT_COLOR(struct name *, struct type *);                \
          382 attr void name##_RB_REMOVE_COLOR(struct name *, struct type *, struct type *);\
          383 attr struct type *name##_RB_REMOVE(struct name *, struct type *);        \
          384 attr struct type *name##_RB_INSERT(struct name *, struct type *);        \
          385 attr struct type *name##_RB_FIND(struct name *, struct type *);                \
          386 attr struct type *name##_RB_NFIND(struct name *, struct type *);        \
          387 attr struct type *name##_RB_NEXT(struct type *);                        \
          388 attr struct type *name##_RB_PREV(struct type *);                        \
          389 attr struct type *name##_RB_MINMAX(struct name *, int);                        \
          390                                                                         \
          391 
          392 /* Main rb operation.
          393  * Moves node close to the key of elm to top
          394  */
          395 #define        RB_GENERATE(name, type, field, cmp)                                \
          396         RB_GENERATE_INTERNAL(name, type, field, cmp,)
          397 #define        RB_GENERATE_STATIC(name, type, field, cmp)                        \
          398         RB_GENERATE_INTERNAL(name, type, field, cmp, __attribute__((__unused__)) static)
          399 #define RB_GENERATE_INTERNAL(name, type, field, cmp, attr)                \
          400 attr void                                                                \
          401 name##_RB_INSERT_COLOR(struct name *head, struct type *elm)                \
          402 {                                                                        \
          403         struct type *parent, *gparent, *tmp;                                \
          404         while ((parent = RB_PARENT(elm, field)) &&                        \
          405             RB_COLOR(parent, field) == RB_RED) {                        \
          406                 gparent = RB_PARENT(parent, field);                        \
          407                 if (parent == RB_LEFT(gparent, field)) {                \
          408                         tmp = RB_RIGHT(gparent, field);                        \
          409                         if (tmp && RB_COLOR(tmp, field) == RB_RED) {        \
          410                                 RB_COLOR(tmp, field) = RB_BLACK;        \
          411                                 RB_SET_BLACKRED(parent, gparent, field);\
          412                                 elm = gparent;                                \
          413                                 continue;                                \
          414                         }                                                \
          415                         if (RB_RIGHT(parent, field) == elm) {                \
          416                                 RB_ROTATE_LEFT(head, parent, tmp, field);\
          417                                 tmp = parent;                                \
          418                                 parent = elm;                                \
          419                                 elm = tmp;                                \
          420                         }                                                \
          421                         RB_SET_BLACKRED(parent, gparent, field);        \
          422                         RB_ROTATE_RIGHT(head, gparent, tmp, field);        \
          423                 } else {                                                \
          424                         tmp = RB_LEFT(gparent, field);                        \
          425                         if (tmp && RB_COLOR(tmp, field) == RB_RED) {        \
          426                                 RB_COLOR(tmp, field) = RB_BLACK;        \
          427                                 RB_SET_BLACKRED(parent, gparent, field);\
          428                                 elm = gparent;                                \
          429                                 continue;                                \
          430                         }                                                \
          431                         if (RB_LEFT(parent, field) == elm) {                \
          432                                 RB_ROTATE_RIGHT(head, parent, tmp, field);\
          433                                 tmp = parent;                                \
          434                                 parent = elm;                                \
          435                                 elm = tmp;                                \
          436                         }                                                \
          437                         RB_SET_BLACKRED(parent, gparent, field);        \
          438                         RB_ROTATE_LEFT(head, gparent, tmp, field);        \
          439                 }                                                        \
          440         }                                                                \
          441         RB_COLOR(head->rbh_root, field) = RB_BLACK;                        \
          442 }                                                                        \
          443                                                                         \
          444 attr void                                                                \
          445 name##_RB_REMOVE_COLOR(struct name *head, struct type *parent, struct type *elm) \
          446 {                                                                        \
          447         struct type *tmp;                                                \
          448         while ((elm == NULL || RB_COLOR(elm, field) == RB_BLACK) &&        \
          449             elm != RB_ROOT(head)) {                                        \
          450                 if (RB_LEFT(parent, field) == elm) {                        \
          451                         tmp = RB_RIGHT(parent, field);                        \
          452                         if (RB_COLOR(tmp, field) == RB_RED) {                \
          453                                 RB_SET_BLACKRED(tmp, parent, field);        \
          454                                 RB_ROTATE_LEFT(head, parent, tmp, field);\
          455                                 tmp = RB_RIGHT(parent, field);                \
          456                         }                                                \
          457                         if ((RB_LEFT(tmp, field) == NULL ||                \
          458                             RB_COLOR(RB_LEFT(tmp, field), field) == RB_BLACK) &&\
          459                             (RB_RIGHT(tmp, field) == NULL ||                \
          460                             RB_COLOR(RB_RIGHT(tmp, field), field) == RB_BLACK)) {\
          461                                 RB_COLOR(tmp, field) = RB_RED;                \
          462                                 elm = parent;                                \
          463                                 parent = RB_PARENT(elm, field);                \
          464                         } else {                                        \
          465                                 if (RB_RIGHT(tmp, field) == NULL ||        \
          466                                     RB_COLOR(RB_RIGHT(tmp, field), field) == RB_BLACK) {\
          467                                         struct type *oleft;                \
          468                                         if ((oleft = RB_LEFT(tmp, field)))\
          469                                                 RB_COLOR(oleft, field) = RB_BLACK;\
          470                                         RB_COLOR(tmp, field) = RB_RED;        \
          471                                         RB_ROTATE_RIGHT(head, tmp, oleft, field);\
          472                                         tmp = RB_RIGHT(parent, field);        \
          473                                 }                                        \
          474                                 RB_COLOR(tmp, field) = RB_COLOR(parent, field);\
          475                                 RB_COLOR(parent, field) = RB_BLACK;        \
          476                                 if (RB_RIGHT(tmp, field))                \
          477                                         RB_COLOR(RB_RIGHT(tmp, field), field) = RB_BLACK;\
          478                                 RB_ROTATE_LEFT(head, parent, tmp, field);\
          479                                 elm = RB_ROOT(head);                        \
          480                                 break;                                        \
          481                         }                                                \
          482                 } else {                                                \
          483                         tmp = RB_LEFT(parent, field);                        \
          484                         if (RB_COLOR(tmp, field) == RB_RED) {                \
          485                                 RB_SET_BLACKRED(tmp, parent, field);        \
          486                                 RB_ROTATE_RIGHT(head, parent, tmp, field);\
          487                                 tmp = RB_LEFT(parent, field);                \
          488                         }                                                \
          489                         if ((RB_LEFT(tmp, field) == NULL ||                \
          490                             RB_COLOR(RB_LEFT(tmp, field), field) == RB_BLACK) &&\
          491                             (RB_RIGHT(tmp, field) == NULL ||                \
          492                             RB_COLOR(RB_RIGHT(tmp, field), field) == RB_BLACK)) {\
          493                                 RB_COLOR(tmp, field) = RB_RED;                \
          494                                 elm = parent;                                \
          495                                 parent = RB_PARENT(elm, field);                \
          496                         } else {                                        \
          497                                 if (RB_LEFT(tmp, field) == NULL ||        \
          498                                     RB_COLOR(RB_LEFT(tmp, field), field) == RB_BLACK) {\
          499                                         struct type *oright;                \
          500                                         if ((oright = RB_RIGHT(tmp, field)))\
          501                                                 RB_COLOR(oright, field) = RB_BLACK;\
          502                                         RB_COLOR(tmp, field) = RB_RED;        \
          503                                         RB_ROTATE_LEFT(head, tmp, oright, field);\
          504                                         tmp = RB_LEFT(parent, field);        \
          505                                 }                                        \
          506                                 RB_COLOR(tmp, field) = RB_COLOR(parent, field);\
          507                                 RB_COLOR(parent, field) = RB_BLACK;        \
          508                                 if (RB_LEFT(tmp, field))                \
          509                                         RB_COLOR(RB_LEFT(tmp, field), field) = RB_BLACK;\
          510                                 RB_ROTATE_RIGHT(head, parent, tmp, field);\
          511                                 elm = RB_ROOT(head);                        \
          512                                 break;                                        \
          513                         }                                                \
          514                 }                                                        \
          515         }                                                                \
          516         if (elm)                                                        \
          517                 RB_COLOR(elm, field) = RB_BLACK;                        \
          518 }                                                                        \
          519                                                                         \
          520 attr struct type *                                                        \
          521 name##_RB_REMOVE(struct name *head, struct type *elm)                        \
          522 {                                                                        \
          523         struct type *child, *parent, *old = elm;                        \
          524         int color;                                                        \
          525         if (RB_LEFT(elm, field) == NULL)                                \
          526                 child = RB_RIGHT(elm, field);                                \
          527         else if (RB_RIGHT(elm, field) == NULL)                                \
          528                 child = RB_LEFT(elm, field);                                \
          529         else {                                                                \
          530                 struct type *left;                                        \
          531                 elm = RB_RIGHT(elm, field);                                \
          532                 while ((left = RB_LEFT(elm, field)))                        \
          533                         elm = left;                                        \
          534                 child = RB_RIGHT(elm, field);                                \
          535                 parent = RB_PARENT(elm, field);                                \
          536                 color = RB_COLOR(elm, field);                                \
          537                 if (child)                                                \
          538                         RB_PARENT(child, field) = parent;                \
          539                 if (parent) {                                                \
          540                         if (RB_LEFT(parent, field) == elm)                \
          541                                 RB_LEFT(parent, field) = child;                \
          542                         else                                                \
          543                                 RB_RIGHT(parent, field) = child;        \
          544                         RB_AUGMENT(parent);                                \
          545                 } else                                                        \
          546                         RB_ROOT(head) = child;                                \
          547                 if (RB_PARENT(elm, field) == old)                        \
          548                         parent = elm;                                        \
          549                 (elm)->field = (old)->field;                                \
          550                 if (RB_PARENT(old, field)) {                                \
          551                         if (RB_LEFT(RB_PARENT(old, field), field) == old)\
          552                                 RB_LEFT(RB_PARENT(old, field), field) = elm;\
          553                         else                                                \
          554                                 RB_RIGHT(RB_PARENT(old, field), field) = elm;\
          555                         RB_AUGMENT(RB_PARENT(old, field));                \
          556                 } else                                                        \
          557                         RB_ROOT(head) = elm;                                \
          558                 RB_PARENT(RB_LEFT(old, field), field) = elm;                \
          559                 if (RB_RIGHT(old, field))                                \
          560                         RB_PARENT(RB_RIGHT(old, field), field) = elm;        \
          561                 if (parent) {                                                \
          562                         left = parent;                                        \
          563                         do {                                                \
          564                                 RB_AUGMENT(left);                        \
          565                         } while ((left = RB_PARENT(left, field)));        \
          566                 }                                                        \
          567                 goto color;                                                \
          568         }                                                                \
          569         parent = RB_PARENT(elm, field);                                        \
          570         color = RB_COLOR(elm, field);                                        \
          571         if (child)                                                        \
          572                 RB_PARENT(child, field) = parent;                        \
          573         if (parent) {                                                        \
          574                 if (RB_LEFT(parent, field) == elm)                        \
          575                         RB_LEFT(parent, field) = child;                        \
          576                 else                                                        \
          577                         RB_RIGHT(parent, field) = child;                \
          578                 RB_AUGMENT(parent);                                        \
          579         } else                                                                \
          580                 RB_ROOT(head) = child;                                        \
          581 color:                                                                        \
          582         if (color == RB_BLACK)                                                \
          583                 name##_RB_REMOVE_COLOR(head, parent, child);                \
          584         return (old);                                                        \
          585 }                                                                        \
          586                                                                         \
          587 /* Inserts a node into the RB tree */                                        \
          588 attr struct type *                                                        \
          589 name##_RB_INSERT(struct name *head, struct type *elm)                        \
          590 {                                                                        \
          591         struct type *tmp;                                                \
          592         struct type *parent = NULL;                                        \
          593         int comp = 0;                                                        \
          594         tmp = RB_ROOT(head);                                                \
          595         while (tmp) {                                                        \
          596                 parent = tmp;                                                \
          597                 comp = (cmp)(elm, parent);                                \
          598                 if (comp < 0)                                                \
          599                         tmp = RB_LEFT(tmp, field);                        \
          600                 else if (comp > 0)                                        \
          601                         tmp = RB_RIGHT(tmp, field);                        \
          602                 else                                                        \
          603                         return (tmp);                                        \
          604         }                                                                \
          605         RB_SET(elm, parent, field);                                        \
          606         if (parent != NULL) {                                                \
          607                 if (comp < 0)                                                \
          608                         RB_LEFT(parent, field) = elm;                        \
          609                 else                                                        \
          610                         RB_RIGHT(parent, field) = elm;                        \
          611                 RB_AUGMENT(parent);                                        \
          612         } else                                                                \
          613                 RB_ROOT(head) = elm;                                        \
          614         name##_RB_INSERT_COLOR(head, elm);                                \
          615         return (NULL);                                                        \
          616 }                                                                        \
          617                                                                         \
          618 /* Finds the node with the same key as elm */                                \
          619 attr struct type *                                                        \
          620 name##_RB_FIND(struct name *head, struct type *elm)                        \
          621 {                                                                        \
          622         struct type *tmp = RB_ROOT(head);                                \
          623         int comp;                                                        \
          624         while (tmp) {                                                        \
          625                 comp = cmp(elm, tmp);                                        \
          626                 if (comp < 0)                                                \
          627                         tmp = RB_LEFT(tmp, field);                        \
          628                 else if (comp > 0)                                        \
          629                         tmp = RB_RIGHT(tmp, field);                        \
          630                 else                                                        \
          631                         return (tmp);                                        \
          632         }                                                                \
          633         return (NULL);                                                        \
          634 }                                                                        \
          635                                                                         \
          636 /* Finds the first node greater than or equal to the search key */        \
          637 attr struct type *                                                        \
          638 name##_RB_NFIND(struct name *head, struct type *elm)                        \
          639 {                                                                        \
          640         struct type *tmp = RB_ROOT(head);                                \
          641         struct type *res = NULL;                                        \
          642         int comp;                                                        \
          643         while (tmp) {                                                        \
          644                 comp = cmp(elm, tmp);                                        \
          645                 if (comp < 0) {                                                \
          646                         res = tmp;                                        \
          647                         tmp = RB_LEFT(tmp, field);                        \
          648                 }                                                        \
          649                 else if (comp > 0)                                        \
          650                         tmp = RB_RIGHT(tmp, field);                        \
          651                 else                                                        \
          652                         return (tmp);                                        \
          653         }                                                                \
          654         return (res);                                                        \
          655 }                                                                        \
          656                                                                         \
          657 /* ARGSUSED */                                                                \
          658 attr struct type *                                                        \
          659 name##_RB_NEXT(struct type *elm)                                        \
          660 {                                                                        \
          661         if (RB_RIGHT(elm, field)) {                                        \
          662                 elm = RB_RIGHT(elm, field);                                \
          663                 while (RB_LEFT(elm, field))                                \
          664                         elm = RB_LEFT(elm, field);                        \
          665         } else {                                                        \
          666                 if (RB_PARENT(elm, field) &&                                \
          667                     (elm == RB_LEFT(RB_PARENT(elm, field), field)))        \
          668                         elm = RB_PARENT(elm, field);                        \
          669                 else {                                                        \
          670                         while (RB_PARENT(elm, field) &&                        \
          671                             (elm == RB_RIGHT(RB_PARENT(elm, field), field)))\
          672                                 elm = RB_PARENT(elm, field);                \
          673                         elm = RB_PARENT(elm, field);                        \
          674                 }                                                        \
          675         }                                                                \
          676         return (elm);                                                        \
          677 }                                                                        \
          678                                                                         \
          679 /* ARGSUSED */                                                                \
          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 {
          792         rbt->rbt_root = NULL;
          793 }
          794 
          795 static inline int
          796 _rb_empty(struct rb_tree *rbt)
          797 {
          798         return (rbt->rbt_root == NULL);
          799 }
          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         return _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         return _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         return _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         return _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_ */