1*2b15cb3dSCy Schubert /* $OpenBSD: tree.h,v 1.7 2002/10/17 21:51:54 art Exp $ */ 2*2b15cb3dSCy Schubert /* 3*2b15cb3dSCy Schubert * Copyright 2002 Niels Provos <provos@citi.umich.edu> 4*2b15cb3dSCy Schubert * All rights reserved. 5*2b15cb3dSCy Schubert * 6*2b15cb3dSCy Schubert * Redistribution and use in source and binary forms, with or without 7*2b15cb3dSCy Schubert * modification, are permitted provided that the following conditions 8*2b15cb3dSCy Schubert * are met: 9*2b15cb3dSCy Schubert * 1. Redistributions of source code must retain the above copyright 10*2b15cb3dSCy Schubert * notice, this list of conditions and the following disclaimer. 11*2b15cb3dSCy Schubert * 2. Redistributions in binary form must reproduce the above copyright 12*2b15cb3dSCy Schubert * notice, this list of conditions and the following disclaimer in the 13*2b15cb3dSCy Schubert * documentation and/or other materials provided with the distribution. 14*2b15cb3dSCy Schubert * 15*2b15cb3dSCy Schubert * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR 16*2b15cb3dSCy Schubert * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES 17*2b15cb3dSCy Schubert * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 18*2b15cb3dSCy Schubert * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, 19*2b15cb3dSCy Schubert * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT 20*2b15cb3dSCy Schubert * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 21*2b15cb3dSCy Schubert * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 22*2b15cb3dSCy Schubert * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 23*2b15cb3dSCy Schubert * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 24*2b15cb3dSCy Schubert * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 25*2b15cb3dSCy Schubert */ 26*2b15cb3dSCy Schubert 27*2b15cb3dSCy Schubert #ifndef _SYS_TREE_H_ 28*2b15cb3dSCy Schubert #define _SYS_TREE_H_ 29*2b15cb3dSCy Schubert 30*2b15cb3dSCy Schubert /* 31*2b15cb3dSCy Schubert * This file defines data structures for different types of trees: 32*2b15cb3dSCy Schubert * splay trees and red-black trees. 33*2b15cb3dSCy Schubert * 34*2b15cb3dSCy Schubert * A splay tree is a self-organizing data structure. Every operation 35*2b15cb3dSCy Schubert * on the tree causes a splay to happen. The splay moves the requested 36*2b15cb3dSCy Schubert * node to the root of the tree and partly rebalances it. 37*2b15cb3dSCy Schubert * 38*2b15cb3dSCy Schubert * This has the benefit that request locality causes faster lookups as 39*2b15cb3dSCy Schubert * the requested nodes move to the top of the tree. On the other hand, 40*2b15cb3dSCy Schubert * every lookup causes memory writes. 41*2b15cb3dSCy Schubert * 42*2b15cb3dSCy Schubert * The Balance Theorem bounds the total access time for m operations 43*2b15cb3dSCy Schubert * and n inserts on an initially empty tree as O((m + n)lg n). The 44*2b15cb3dSCy Schubert * amortized cost for a sequence of m accesses to a splay tree is O(lg n); 45*2b15cb3dSCy Schubert * 46*2b15cb3dSCy Schubert * A red-black tree is a binary search tree with the node color as an 47*2b15cb3dSCy Schubert * extra attribute. It fulfills a set of conditions: 48*2b15cb3dSCy Schubert * - every search path from the root to a leaf consists of the 49*2b15cb3dSCy Schubert * same number of black nodes, 50*2b15cb3dSCy Schubert * - each red node (except for the root) has a black parent, 51*2b15cb3dSCy Schubert * - each leaf node is black. 52*2b15cb3dSCy Schubert * 53*2b15cb3dSCy Schubert * Every operation on a red-black tree is bounded as O(lg n). 54*2b15cb3dSCy Schubert * The maximum height of a red-black tree is 2lg (n+1). 55*2b15cb3dSCy Schubert */ 56*2b15cb3dSCy Schubert 57*2b15cb3dSCy Schubert #define SPLAY_HEAD(name, type) \ 58*2b15cb3dSCy Schubert struct name { \ 59*2b15cb3dSCy Schubert struct type *sph_root; /* root of the tree */ \ 60*2b15cb3dSCy Schubert } 61*2b15cb3dSCy Schubert 62*2b15cb3dSCy Schubert #define SPLAY_INITIALIZER(root) \ 63*2b15cb3dSCy Schubert { NULL } 64*2b15cb3dSCy Schubert 65*2b15cb3dSCy Schubert #define SPLAY_INIT(root) do { \ 66*2b15cb3dSCy Schubert (root)->sph_root = NULL; \ 67*2b15cb3dSCy Schubert } while (0) 68*2b15cb3dSCy Schubert 69*2b15cb3dSCy Schubert #define SPLAY_ENTRY(type) \ 70*2b15cb3dSCy Schubert struct { \ 71*2b15cb3dSCy Schubert struct type *spe_left; /* left element */ \ 72*2b15cb3dSCy Schubert struct type *spe_right; /* right element */ \ 73*2b15cb3dSCy Schubert } 74*2b15cb3dSCy Schubert 75*2b15cb3dSCy Schubert #define SPLAY_LEFT(elm, field) (elm)->field.spe_left 76*2b15cb3dSCy Schubert #define SPLAY_RIGHT(elm, field) (elm)->field.spe_right 77*2b15cb3dSCy Schubert #define SPLAY_ROOT(head) (head)->sph_root 78*2b15cb3dSCy Schubert #define SPLAY_EMPTY(head) (SPLAY_ROOT(head) == NULL) 79*2b15cb3dSCy Schubert 80*2b15cb3dSCy Schubert /* SPLAY_ROTATE_{LEFT,RIGHT} expect that tmp hold SPLAY_{RIGHT,LEFT} */ 81*2b15cb3dSCy Schubert #define SPLAY_ROTATE_RIGHT(head, tmp, field) do { \ 82*2b15cb3dSCy Schubert SPLAY_LEFT((head)->sph_root, field) = SPLAY_RIGHT(tmp, field); \ 83*2b15cb3dSCy Schubert SPLAY_RIGHT(tmp, field) = (head)->sph_root; \ 84*2b15cb3dSCy Schubert (head)->sph_root = tmp; \ 85*2b15cb3dSCy Schubert } while (0) 86*2b15cb3dSCy Schubert 87*2b15cb3dSCy Schubert #define SPLAY_ROTATE_LEFT(head, tmp, field) do { \ 88*2b15cb3dSCy Schubert SPLAY_RIGHT((head)->sph_root, field) = SPLAY_LEFT(tmp, field); \ 89*2b15cb3dSCy Schubert SPLAY_LEFT(tmp, field) = (head)->sph_root; \ 90*2b15cb3dSCy Schubert (head)->sph_root = tmp; \ 91*2b15cb3dSCy Schubert } while (0) 92*2b15cb3dSCy Schubert 93*2b15cb3dSCy Schubert #define SPLAY_LINKLEFT(head, tmp, field) do { \ 94*2b15cb3dSCy Schubert SPLAY_LEFT(tmp, field) = (head)->sph_root; \ 95*2b15cb3dSCy Schubert tmp = (head)->sph_root; \ 96*2b15cb3dSCy Schubert (head)->sph_root = SPLAY_LEFT((head)->sph_root, field); \ 97*2b15cb3dSCy Schubert } while (0) 98*2b15cb3dSCy Schubert 99*2b15cb3dSCy Schubert #define SPLAY_LINKRIGHT(head, tmp, field) do { \ 100*2b15cb3dSCy Schubert SPLAY_RIGHT(tmp, field) = (head)->sph_root; \ 101*2b15cb3dSCy Schubert tmp = (head)->sph_root; \ 102*2b15cb3dSCy Schubert (head)->sph_root = SPLAY_RIGHT((head)->sph_root, field); \ 103*2b15cb3dSCy Schubert } while (0) 104*2b15cb3dSCy Schubert 105*2b15cb3dSCy Schubert #define SPLAY_ASSEMBLE(head, node, left, right, field) do { \ 106*2b15cb3dSCy Schubert SPLAY_RIGHT(left, field) = SPLAY_LEFT((head)->sph_root, field); \ 107*2b15cb3dSCy Schubert SPLAY_LEFT(right, field) = SPLAY_RIGHT((head)->sph_root, field);\ 108*2b15cb3dSCy Schubert SPLAY_LEFT((head)->sph_root, field) = SPLAY_RIGHT(node, field); \ 109*2b15cb3dSCy Schubert SPLAY_RIGHT((head)->sph_root, field) = SPLAY_LEFT(node, field); \ 110*2b15cb3dSCy Schubert } while (0) 111*2b15cb3dSCy Schubert 112*2b15cb3dSCy Schubert /* Generates prototypes and inline functions */ 113*2b15cb3dSCy Schubert 114*2b15cb3dSCy Schubert #define SPLAY_PROTOTYPE(name, type, field, cmp) \ 115*2b15cb3dSCy Schubert void name##_SPLAY(struct name *, struct type *); \ 116*2b15cb3dSCy Schubert void name##_SPLAY_MINMAX(struct name *, int); \ 117*2b15cb3dSCy Schubert struct type *name##_SPLAY_INSERT(struct name *, struct type *); \ 118*2b15cb3dSCy Schubert struct type *name##_SPLAY_REMOVE(struct name *, struct type *); \ 119*2b15cb3dSCy Schubert \ 120*2b15cb3dSCy Schubert /* Finds the node with the same key as elm */ \ 121*2b15cb3dSCy Schubert static __inline struct type * \ 122*2b15cb3dSCy Schubert name##_SPLAY_FIND(struct name *head, struct type *elm) \ 123*2b15cb3dSCy Schubert { \ 124*2b15cb3dSCy Schubert if (SPLAY_EMPTY(head)) \ 125*2b15cb3dSCy Schubert return(NULL); \ 126*2b15cb3dSCy Schubert name##_SPLAY(head, elm); \ 127*2b15cb3dSCy Schubert if ((cmp)(elm, (head)->sph_root) == 0) \ 128*2b15cb3dSCy Schubert return (head->sph_root); \ 129*2b15cb3dSCy Schubert return (NULL); \ 130*2b15cb3dSCy Schubert } \ 131*2b15cb3dSCy Schubert \ 132*2b15cb3dSCy Schubert static __inline struct type * \ 133*2b15cb3dSCy Schubert name##_SPLAY_NEXT(struct name *head, struct type *elm) \ 134*2b15cb3dSCy Schubert { \ 135*2b15cb3dSCy Schubert name##_SPLAY(head, elm); \ 136*2b15cb3dSCy Schubert if (SPLAY_RIGHT(elm, field) != NULL) { \ 137*2b15cb3dSCy Schubert elm = SPLAY_RIGHT(elm, field); \ 138*2b15cb3dSCy Schubert while (SPLAY_LEFT(elm, field) != NULL) { \ 139*2b15cb3dSCy Schubert elm = SPLAY_LEFT(elm, field); \ 140*2b15cb3dSCy Schubert } \ 141*2b15cb3dSCy Schubert } else \ 142*2b15cb3dSCy Schubert elm = NULL; \ 143*2b15cb3dSCy Schubert return (elm); \ 144*2b15cb3dSCy Schubert } \ 145*2b15cb3dSCy Schubert \ 146*2b15cb3dSCy Schubert static __inline struct type * \ 147*2b15cb3dSCy Schubert name##_SPLAY_MIN_MAX(struct name *head, int val) \ 148*2b15cb3dSCy Schubert { \ 149*2b15cb3dSCy Schubert name##_SPLAY_MINMAX(head, val); \ 150*2b15cb3dSCy Schubert return (SPLAY_ROOT(head)); \ 151*2b15cb3dSCy Schubert } 152*2b15cb3dSCy Schubert 153*2b15cb3dSCy Schubert /* Main splay operation. 154*2b15cb3dSCy Schubert * Moves node close to the key of elm to top 155*2b15cb3dSCy Schubert */ 156*2b15cb3dSCy Schubert #define SPLAY_GENERATE(name, type, field, cmp) \ 157*2b15cb3dSCy Schubert struct type * \ 158*2b15cb3dSCy Schubert name##_SPLAY_INSERT(struct name *head, struct type *elm) \ 159*2b15cb3dSCy Schubert { \ 160*2b15cb3dSCy Schubert if (SPLAY_EMPTY(head)) { \ 161*2b15cb3dSCy Schubert SPLAY_LEFT(elm, field) = SPLAY_RIGHT(elm, field) = NULL; \ 162*2b15cb3dSCy Schubert } else { \ 163*2b15cb3dSCy Schubert int __comp; \ 164*2b15cb3dSCy Schubert name##_SPLAY(head, elm); \ 165*2b15cb3dSCy Schubert __comp = (cmp)(elm, (head)->sph_root); \ 166*2b15cb3dSCy Schubert if(__comp < 0) { \ 167*2b15cb3dSCy Schubert SPLAY_LEFT(elm, field) = SPLAY_LEFT((head)->sph_root, field);\ 168*2b15cb3dSCy Schubert SPLAY_RIGHT(elm, field) = (head)->sph_root; \ 169*2b15cb3dSCy Schubert SPLAY_LEFT((head)->sph_root, field) = NULL; \ 170*2b15cb3dSCy Schubert } else if (__comp > 0) { \ 171*2b15cb3dSCy Schubert SPLAY_RIGHT(elm, field) = SPLAY_RIGHT((head)->sph_root, field);\ 172*2b15cb3dSCy Schubert SPLAY_LEFT(elm, field) = (head)->sph_root; \ 173*2b15cb3dSCy Schubert SPLAY_RIGHT((head)->sph_root, field) = NULL; \ 174*2b15cb3dSCy Schubert } else \ 175*2b15cb3dSCy Schubert return ((head)->sph_root); \ 176*2b15cb3dSCy Schubert } \ 177*2b15cb3dSCy Schubert (head)->sph_root = (elm); \ 178*2b15cb3dSCy Schubert return (NULL); \ 179*2b15cb3dSCy Schubert } \ 180*2b15cb3dSCy Schubert \ 181*2b15cb3dSCy Schubert struct type * \ 182*2b15cb3dSCy Schubert name##_SPLAY_REMOVE(struct name *head, struct type *elm) \ 183*2b15cb3dSCy Schubert { \ 184*2b15cb3dSCy Schubert struct type *__tmp; \ 185*2b15cb3dSCy Schubert if (SPLAY_EMPTY(head)) \ 186*2b15cb3dSCy Schubert return (NULL); \ 187*2b15cb3dSCy Schubert name##_SPLAY(head, elm); \ 188*2b15cb3dSCy Schubert if ((cmp)(elm, (head)->sph_root) == 0) { \ 189*2b15cb3dSCy Schubert if (SPLAY_LEFT((head)->sph_root, field) == NULL) { \ 190*2b15cb3dSCy Schubert (head)->sph_root = SPLAY_RIGHT((head)->sph_root, field);\ 191*2b15cb3dSCy Schubert } else { \ 192*2b15cb3dSCy Schubert __tmp = SPLAY_RIGHT((head)->sph_root, field); \ 193*2b15cb3dSCy Schubert (head)->sph_root = SPLAY_LEFT((head)->sph_root, field);\ 194*2b15cb3dSCy Schubert name##_SPLAY(head, elm); \ 195*2b15cb3dSCy Schubert SPLAY_RIGHT((head)->sph_root, field) = __tmp; \ 196*2b15cb3dSCy Schubert } \ 197*2b15cb3dSCy Schubert return (elm); \ 198*2b15cb3dSCy Schubert } \ 199*2b15cb3dSCy Schubert return (NULL); \ 200*2b15cb3dSCy Schubert } \ 201*2b15cb3dSCy Schubert \ 202*2b15cb3dSCy Schubert void \ 203*2b15cb3dSCy Schubert name##_SPLAY(struct name *head, struct type *elm) \ 204*2b15cb3dSCy Schubert { \ 205*2b15cb3dSCy Schubert struct type __node, *__left, *__right, *__tmp; \ 206*2b15cb3dSCy Schubert int __comp; \ 207*2b15cb3dSCy Schubert \ 208*2b15cb3dSCy Schubert SPLAY_LEFT(&__node, field) = SPLAY_RIGHT(&__node, field) = NULL;\ 209*2b15cb3dSCy Schubert __left = __right = &__node; \ 210*2b15cb3dSCy Schubert \ 211*2b15cb3dSCy Schubert while ((__comp = (cmp)(elm, (head)->sph_root))) { \ 212*2b15cb3dSCy Schubert if (__comp < 0) { \ 213*2b15cb3dSCy Schubert __tmp = SPLAY_LEFT((head)->sph_root, field); \ 214*2b15cb3dSCy Schubert if (__tmp == NULL) \ 215*2b15cb3dSCy Schubert break; \ 216*2b15cb3dSCy Schubert if ((cmp)(elm, __tmp) < 0){ \ 217*2b15cb3dSCy Schubert SPLAY_ROTATE_RIGHT(head, __tmp, field); \ 218*2b15cb3dSCy Schubert if (SPLAY_LEFT((head)->sph_root, field) == NULL)\ 219*2b15cb3dSCy Schubert break; \ 220*2b15cb3dSCy Schubert } \ 221*2b15cb3dSCy Schubert SPLAY_LINKLEFT(head, __right, field); \ 222*2b15cb3dSCy Schubert } else if (__comp > 0) { \ 223*2b15cb3dSCy Schubert __tmp = SPLAY_RIGHT((head)->sph_root, field); \ 224*2b15cb3dSCy Schubert if (__tmp == NULL) \ 225*2b15cb3dSCy Schubert break; \ 226*2b15cb3dSCy Schubert if ((cmp)(elm, __tmp) > 0){ \ 227*2b15cb3dSCy Schubert SPLAY_ROTATE_LEFT(head, __tmp, field); \ 228*2b15cb3dSCy Schubert if (SPLAY_RIGHT((head)->sph_root, field) == NULL)\ 229*2b15cb3dSCy Schubert break; \ 230*2b15cb3dSCy Schubert } \ 231*2b15cb3dSCy Schubert SPLAY_LINKRIGHT(head, __left, field); \ 232*2b15cb3dSCy Schubert } \ 233*2b15cb3dSCy Schubert } \ 234*2b15cb3dSCy Schubert SPLAY_ASSEMBLE(head, &__node, __left, __right, field); \ 235*2b15cb3dSCy Schubert } \ 236*2b15cb3dSCy Schubert \ 237*2b15cb3dSCy Schubert /* Splay with either the minimum or the maximum element \ 238*2b15cb3dSCy Schubert * Used to find minimum or maximum element in tree. \ 239*2b15cb3dSCy Schubert */ \ 240*2b15cb3dSCy Schubert void name##_SPLAY_MINMAX(struct name *head, int __comp) \ 241*2b15cb3dSCy Schubert { \ 242*2b15cb3dSCy Schubert struct type __node, *__left, *__right, *__tmp; \ 243*2b15cb3dSCy Schubert \ 244*2b15cb3dSCy Schubert SPLAY_LEFT(&__node, field) = SPLAY_RIGHT(&__node, field) = NULL;\ 245*2b15cb3dSCy Schubert __left = __right = &__node; \ 246*2b15cb3dSCy Schubert \ 247*2b15cb3dSCy Schubert while (1) { \ 248*2b15cb3dSCy Schubert if (__comp < 0) { \ 249*2b15cb3dSCy Schubert __tmp = SPLAY_LEFT((head)->sph_root, field); \ 250*2b15cb3dSCy Schubert if (__tmp == NULL) \ 251*2b15cb3dSCy Schubert break; \ 252*2b15cb3dSCy Schubert if (__comp < 0){ \ 253*2b15cb3dSCy Schubert SPLAY_ROTATE_RIGHT(head, __tmp, field); \ 254*2b15cb3dSCy Schubert if (SPLAY_LEFT((head)->sph_root, field) == NULL)\ 255*2b15cb3dSCy Schubert break; \ 256*2b15cb3dSCy Schubert } \ 257*2b15cb3dSCy Schubert SPLAY_LINKLEFT(head, __right, field); \ 258*2b15cb3dSCy Schubert } else if (__comp > 0) { \ 259*2b15cb3dSCy Schubert __tmp = SPLAY_RIGHT((head)->sph_root, field); \ 260*2b15cb3dSCy Schubert if (__tmp == NULL) \ 261*2b15cb3dSCy Schubert break; \ 262*2b15cb3dSCy Schubert if (__comp > 0) { \ 263*2b15cb3dSCy Schubert SPLAY_ROTATE_LEFT(head, __tmp, field); \ 264*2b15cb3dSCy Schubert if (SPLAY_RIGHT((head)->sph_root, field) == NULL)\ 265*2b15cb3dSCy Schubert break; \ 266*2b15cb3dSCy Schubert } \ 267*2b15cb3dSCy Schubert SPLAY_LINKRIGHT(head, __left, field); \ 268*2b15cb3dSCy Schubert } \ 269*2b15cb3dSCy Schubert } \ 270*2b15cb3dSCy Schubert SPLAY_ASSEMBLE(head, &__node, __left, __right, field); \ 271*2b15cb3dSCy Schubert } 272*2b15cb3dSCy Schubert 273*2b15cb3dSCy Schubert #define SPLAY_NEGINF -1 274*2b15cb3dSCy Schubert #define SPLAY_INF 1 275*2b15cb3dSCy Schubert 276*2b15cb3dSCy Schubert #define SPLAY_INSERT(name, x, y) name##_SPLAY_INSERT(x, y) 277*2b15cb3dSCy Schubert #define SPLAY_REMOVE(name, x, y) name##_SPLAY_REMOVE(x, y) 278*2b15cb3dSCy Schubert #define SPLAY_FIND(name, x, y) name##_SPLAY_FIND(x, y) 279*2b15cb3dSCy Schubert #define SPLAY_NEXT(name, x, y) name##_SPLAY_NEXT(x, y) 280*2b15cb3dSCy Schubert #define SPLAY_MIN(name, x) (SPLAY_EMPTY(x) ? NULL \ 281*2b15cb3dSCy Schubert : name##_SPLAY_MIN_MAX(x, SPLAY_NEGINF)) 282*2b15cb3dSCy Schubert #define SPLAY_MAX(name, x) (SPLAY_EMPTY(x) ? NULL \ 283*2b15cb3dSCy Schubert : name##_SPLAY_MIN_MAX(x, SPLAY_INF)) 284*2b15cb3dSCy Schubert 285*2b15cb3dSCy Schubert #define SPLAY_FOREACH(x, name, head) \ 286*2b15cb3dSCy Schubert for ((x) = SPLAY_MIN(name, head); \ 287*2b15cb3dSCy Schubert (x) != NULL; \ 288*2b15cb3dSCy Schubert (x) = SPLAY_NEXT(name, head, x)) 289*2b15cb3dSCy Schubert 290*2b15cb3dSCy Schubert /* Macros that define a red-back tree */ 291*2b15cb3dSCy Schubert #define RB_HEAD(name, type) \ 292*2b15cb3dSCy Schubert struct name { \ 293*2b15cb3dSCy Schubert struct type *rbh_root; /* root of the tree */ \ 294*2b15cb3dSCy Schubert } 295*2b15cb3dSCy Schubert 296*2b15cb3dSCy Schubert #define RB_INITIALIZER(root) \ 297*2b15cb3dSCy Schubert { NULL } 298*2b15cb3dSCy Schubert 299*2b15cb3dSCy Schubert #define RB_INIT(root) do { \ 300*2b15cb3dSCy Schubert (root)->rbh_root = NULL; \ 301*2b15cb3dSCy Schubert } while (0) 302*2b15cb3dSCy Schubert 303*2b15cb3dSCy Schubert #define RB_BLACK 0 304*2b15cb3dSCy Schubert #define RB_RED 1 305*2b15cb3dSCy Schubert #define RB_ENTRY(type) \ 306*2b15cb3dSCy Schubert struct { \ 307*2b15cb3dSCy Schubert struct type *rbe_left; /* left element */ \ 308*2b15cb3dSCy Schubert struct type *rbe_right; /* right element */ \ 309*2b15cb3dSCy Schubert struct type *rbe_parent; /* parent element */ \ 310*2b15cb3dSCy Schubert int rbe_color; /* node color */ \ 311*2b15cb3dSCy Schubert } 312*2b15cb3dSCy Schubert 313*2b15cb3dSCy Schubert #define RB_LEFT(elm, field) (elm)->field.rbe_left 314*2b15cb3dSCy Schubert #define RB_RIGHT(elm, field) (elm)->field.rbe_right 315*2b15cb3dSCy Schubert #define RB_PARENT(elm, field) (elm)->field.rbe_parent 316*2b15cb3dSCy Schubert #define RB_COLOR(elm, field) (elm)->field.rbe_color 317*2b15cb3dSCy Schubert #define RB_ROOT(head) (head)->rbh_root 318*2b15cb3dSCy Schubert #define RB_EMPTY(head) (RB_ROOT(head) == NULL) 319*2b15cb3dSCy Schubert 320*2b15cb3dSCy Schubert #define RB_SET(elm, parent, field) do { \ 321*2b15cb3dSCy Schubert RB_PARENT(elm, field) = parent; \ 322*2b15cb3dSCy Schubert RB_LEFT(elm, field) = RB_RIGHT(elm, field) = NULL; \ 323*2b15cb3dSCy Schubert RB_COLOR(elm, field) = RB_RED; \ 324*2b15cb3dSCy Schubert } while (0) 325*2b15cb3dSCy Schubert 326*2b15cb3dSCy Schubert #define RB_SET_BLACKRED(black, red, field) do { \ 327*2b15cb3dSCy Schubert RB_COLOR(black, field) = RB_BLACK; \ 328*2b15cb3dSCy Schubert RB_COLOR(red, field) = RB_RED; \ 329*2b15cb3dSCy Schubert } while (0) 330*2b15cb3dSCy Schubert 331*2b15cb3dSCy Schubert #ifndef RB_AUGMENT 332*2b15cb3dSCy Schubert #define RB_AUGMENT(x) 333*2b15cb3dSCy Schubert #endif 334*2b15cb3dSCy Schubert 335*2b15cb3dSCy Schubert #define RB_ROTATE_LEFT(head, elm, tmp, field) do { \ 336*2b15cb3dSCy Schubert (tmp) = RB_RIGHT(elm, field); \ 337*2b15cb3dSCy Schubert if ((RB_RIGHT(elm, field) = RB_LEFT(tmp, field))) { \ 338*2b15cb3dSCy Schubert RB_PARENT(RB_LEFT(tmp, field), field) = (elm); \ 339*2b15cb3dSCy Schubert } \ 340*2b15cb3dSCy Schubert RB_AUGMENT(elm); \ 341*2b15cb3dSCy Schubert if ((RB_PARENT(tmp, field) = RB_PARENT(elm, field))) { \ 342*2b15cb3dSCy Schubert if ((elm) == RB_LEFT(RB_PARENT(elm, field), field)) \ 343*2b15cb3dSCy Schubert RB_LEFT(RB_PARENT(elm, field), field) = (tmp); \ 344*2b15cb3dSCy Schubert else \ 345*2b15cb3dSCy Schubert RB_RIGHT(RB_PARENT(elm, field), field) = (tmp); \ 346*2b15cb3dSCy Schubert } else \ 347*2b15cb3dSCy Schubert (head)->rbh_root = (tmp); \ 348*2b15cb3dSCy Schubert RB_LEFT(tmp, field) = (elm); \ 349*2b15cb3dSCy Schubert RB_PARENT(elm, field) = (tmp); \ 350*2b15cb3dSCy Schubert RB_AUGMENT(tmp); \ 351*2b15cb3dSCy Schubert if ((RB_PARENT(tmp, field))) \ 352*2b15cb3dSCy Schubert RB_AUGMENT(RB_PARENT(tmp, field)); \ 353*2b15cb3dSCy Schubert } while (0) 354*2b15cb3dSCy Schubert 355*2b15cb3dSCy Schubert #define RB_ROTATE_RIGHT(head, elm, tmp, field) do { \ 356*2b15cb3dSCy Schubert (tmp) = RB_LEFT(elm, field); \ 357*2b15cb3dSCy Schubert if ((RB_LEFT(elm, field) = RB_RIGHT(tmp, field))) { \ 358*2b15cb3dSCy Schubert RB_PARENT(RB_RIGHT(tmp, field), field) = (elm); \ 359*2b15cb3dSCy Schubert } \ 360*2b15cb3dSCy Schubert RB_AUGMENT(elm); \ 361*2b15cb3dSCy Schubert if ((RB_PARENT(tmp, field) = RB_PARENT(elm, field))) { \ 362*2b15cb3dSCy Schubert if ((elm) == RB_LEFT(RB_PARENT(elm, field), field)) \ 363*2b15cb3dSCy Schubert RB_LEFT(RB_PARENT(elm, field), field) = (tmp); \ 364*2b15cb3dSCy Schubert else \ 365*2b15cb3dSCy Schubert RB_RIGHT(RB_PARENT(elm, field), field) = (tmp); \ 366*2b15cb3dSCy Schubert } else \ 367*2b15cb3dSCy Schubert (head)->rbh_root = (tmp); \ 368*2b15cb3dSCy Schubert RB_RIGHT(tmp, field) = (elm); \ 369*2b15cb3dSCy Schubert RB_PARENT(elm, field) = (tmp); \ 370*2b15cb3dSCy Schubert RB_AUGMENT(tmp); \ 371*2b15cb3dSCy Schubert if ((RB_PARENT(tmp, field))) \ 372*2b15cb3dSCy Schubert RB_AUGMENT(RB_PARENT(tmp, field)); \ 373*2b15cb3dSCy Schubert } while (0) 374*2b15cb3dSCy Schubert 375*2b15cb3dSCy Schubert /* Generates prototypes and inline functions */ 376*2b15cb3dSCy Schubert #define RB_PROTOTYPE(name, type, field, cmp) \ 377*2b15cb3dSCy Schubert void name##_RB_INSERT_COLOR(struct name *, struct type *); \ 378*2b15cb3dSCy Schubert void name##_RB_REMOVE_COLOR(struct name *, struct type *, struct type *);\ 379*2b15cb3dSCy Schubert struct type *name##_RB_REMOVE(struct name *, struct type *); \ 380*2b15cb3dSCy Schubert struct type *name##_RB_INSERT(struct name *, struct type *); \ 381*2b15cb3dSCy Schubert struct type *name##_RB_FIND(struct name *, struct type *); \ 382*2b15cb3dSCy Schubert struct type *name##_RB_NEXT(struct type *); \ 383*2b15cb3dSCy Schubert struct type *name##_RB_MINMAX(struct name *, int); \ 384*2b15cb3dSCy Schubert \ 385*2b15cb3dSCy Schubert 386*2b15cb3dSCy Schubert /* Main rb operation. 387*2b15cb3dSCy Schubert * Moves node close to the key of elm to top 388*2b15cb3dSCy Schubert */ 389*2b15cb3dSCy Schubert #define RB_GENERATE(name, type, field, cmp) \ 390*2b15cb3dSCy Schubert void \ 391*2b15cb3dSCy Schubert name##_RB_INSERT_COLOR(struct name *head, struct type *elm) \ 392*2b15cb3dSCy Schubert { \ 393*2b15cb3dSCy Schubert struct type *parent, *gparent, *tmp; \ 394*2b15cb3dSCy Schubert while ((parent = RB_PARENT(elm, field)) && \ 395*2b15cb3dSCy Schubert RB_COLOR(parent, field) == RB_RED) { \ 396*2b15cb3dSCy Schubert gparent = RB_PARENT(parent, field); \ 397*2b15cb3dSCy Schubert if (parent == RB_LEFT(gparent, field)) { \ 398*2b15cb3dSCy Schubert tmp = RB_RIGHT(gparent, field); \ 399*2b15cb3dSCy Schubert if (tmp && RB_COLOR(tmp, field) == RB_RED) { \ 400*2b15cb3dSCy Schubert RB_COLOR(tmp, field) = RB_BLACK; \ 401*2b15cb3dSCy Schubert RB_SET_BLACKRED(parent, gparent, field);\ 402*2b15cb3dSCy Schubert elm = gparent; \ 403*2b15cb3dSCy Schubert continue; \ 404*2b15cb3dSCy Schubert } \ 405*2b15cb3dSCy Schubert if (RB_RIGHT(parent, field) == elm) { \ 406*2b15cb3dSCy Schubert RB_ROTATE_LEFT(head, parent, tmp, field);\ 407*2b15cb3dSCy Schubert tmp = parent; \ 408*2b15cb3dSCy Schubert parent = elm; \ 409*2b15cb3dSCy Schubert elm = tmp; \ 410*2b15cb3dSCy Schubert } \ 411*2b15cb3dSCy Schubert RB_SET_BLACKRED(parent, gparent, field); \ 412*2b15cb3dSCy Schubert RB_ROTATE_RIGHT(head, gparent, tmp, field); \ 413*2b15cb3dSCy Schubert } else { \ 414*2b15cb3dSCy Schubert tmp = RB_LEFT(gparent, field); \ 415*2b15cb3dSCy Schubert if (tmp && RB_COLOR(tmp, field) == RB_RED) { \ 416*2b15cb3dSCy Schubert RB_COLOR(tmp, field) = RB_BLACK; \ 417*2b15cb3dSCy Schubert RB_SET_BLACKRED(parent, gparent, field);\ 418*2b15cb3dSCy Schubert elm = gparent; \ 419*2b15cb3dSCy Schubert continue; \ 420*2b15cb3dSCy Schubert } \ 421*2b15cb3dSCy Schubert if (RB_LEFT(parent, field) == elm) { \ 422*2b15cb3dSCy Schubert RB_ROTATE_RIGHT(head, parent, tmp, field);\ 423*2b15cb3dSCy Schubert tmp = parent; \ 424*2b15cb3dSCy Schubert parent = elm; \ 425*2b15cb3dSCy Schubert elm = tmp; \ 426*2b15cb3dSCy Schubert } \ 427*2b15cb3dSCy Schubert RB_SET_BLACKRED(parent, gparent, field); \ 428*2b15cb3dSCy Schubert RB_ROTATE_LEFT(head, gparent, tmp, field); \ 429*2b15cb3dSCy Schubert } \ 430*2b15cb3dSCy Schubert } \ 431*2b15cb3dSCy Schubert RB_COLOR(head->rbh_root, field) = RB_BLACK; \ 432*2b15cb3dSCy Schubert } \ 433*2b15cb3dSCy Schubert \ 434*2b15cb3dSCy Schubert void \ 435*2b15cb3dSCy Schubert name##_RB_REMOVE_COLOR(struct name *head, struct type *parent, struct type *elm) \ 436*2b15cb3dSCy Schubert { \ 437*2b15cb3dSCy Schubert struct type *tmp; \ 438*2b15cb3dSCy Schubert while ((elm == NULL || RB_COLOR(elm, field) == RB_BLACK) && \ 439*2b15cb3dSCy Schubert elm != RB_ROOT(head)) { \ 440*2b15cb3dSCy Schubert if (RB_LEFT(parent, field) == elm) { \ 441*2b15cb3dSCy Schubert tmp = RB_RIGHT(parent, field); \ 442*2b15cb3dSCy Schubert if (RB_COLOR(tmp, field) == RB_RED) { \ 443*2b15cb3dSCy Schubert RB_SET_BLACKRED(tmp, parent, field); \ 444*2b15cb3dSCy Schubert RB_ROTATE_LEFT(head, parent, tmp, field);\ 445*2b15cb3dSCy Schubert tmp = RB_RIGHT(parent, field); \ 446*2b15cb3dSCy Schubert } \ 447*2b15cb3dSCy Schubert if ((RB_LEFT(tmp, field) == NULL || \ 448*2b15cb3dSCy Schubert RB_COLOR(RB_LEFT(tmp, field), field) == RB_BLACK) &&\ 449*2b15cb3dSCy Schubert (RB_RIGHT(tmp, field) == NULL || \ 450*2b15cb3dSCy Schubert RB_COLOR(RB_RIGHT(tmp, field), field) == RB_BLACK)) {\ 451*2b15cb3dSCy Schubert RB_COLOR(tmp, field) = RB_RED; \ 452*2b15cb3dSCy Schubert elm = parent; \ 453*2b15cb3dSCy Schubert parent = RB_PARENT(elm, field); \ 454*2b15cb3dSCy Schubert } else { \ 455*2b15cb3dSCy Schubert if (RB_RIGHT(tmp, field) == NULL || \ 456*2b15cb3dSCy Schubert RB_COLOR(RB_RIGHT(tmp, field), field) == RB_BLACK) {\ 457*2b15cb3dSCy Schubert struct type *oleft; \ 458*2b15cb3dSCy Schubert if ((oleft = RB_LEFT(tmp, field)))\ 459*2b15cb3dSCy Schubert RB_COLOR(oleft, field) = RB_BLACK;\ 460*2b15cb3dSCy Schubert RB_COLOR(tmp, field) = RB_RED; \ 461*2b15cb3dSCy Schubert RB_ROTATE_RIGHT(head, tmp, oleft, field);\ 462*2b15cb3dSCy Schubert tmp = RB_RIGHT(parent, field); \ 463*2b15cb3dSCy Schubert } \ 464*2b15cb3dSCy Schubert RB_COLOR(tmp, field) = RB_COLOR(parent, field);\ 465*2b15cb3dSCy Schubert RB_COLOR(parent, field) = RB_BLACK; \ 466*2b15cb3dSCy Schubert if (RB_RIGHT(tmp, field)) \ 467*2b15cb3dSCy Schubert RB_COLOR(RB_RIGHT(tmp, field), field) = RB_BLACK;\ 468*2b15cb3dSCy Schubert RB_ROTATE_LEFT(head, parent, tmp, field);\ 469*2b15cb3dSCy Schubert elm = RB_ROOT(head); \ 470*2b15cb3dSCy Schubert break; \ 471*2b15cb3dSCy Schubert } \ 472*2b15cb3dSCy Schubert } else { \ 473*2b15cb3dSCy Schubert tmp = RB_LEFT(parent, field); \ 474*2b15cb3dSCy Schubert if (RB_COLOR(tmp, field) == RB_RED) { \ 475*2b15cb3dSCy Schubert RB_SET_BLACKRED(tmp, parent, field); \ 476*2b15cb3dSCy Schubert RB_ROTATE_RIGHT(head, parent, tmp, field);\ 477*2b15cb3dSCy Schubert tmp = RB_LEFT(parent, field); \ 478*2b15cb3dSCy Schubert } \ 479*2b15cb3dSCy Schubert if ((RB_LEFT(tmp, field) == NULL || \ 480*2b15cb3dSCy Schubert RB_COLOR(RB_LEFT(tmp, field), field) == RB_BLACK) &&\ 481*2b15cb3dSCy Schubert (RB_RIGHT(tmp, field) == NULL || \ 482*2b15cb3dSCy Schubert RB_COLOR(RB_RIGHT(tmp, field), field) == RB_BLACK)) {\ 483*2b15cb3dSCy Schubert RB_COLOR(tmp, field) = RB_RED; \ 484*2b15cb3dSCy Schubert elm = parent; \ 485*2b15cb3dSCy Schubert parent = RB_PARENT(elm, field); \ 486*2b15cb3dSCy Schubert } else { \ 487*2b15cb3dSCy Schubert if (RB_LEFT(tmp, field) == NULL || \ 488*2b15cb3dSCy Schubert RB_COLOR(RB_LEFT(tmp, field), field) == RB_BLACK) {\ 489*2b15cb3dSCy Schubert struct type *oright; \ 490*2b15cb3dSCy Schubert if ((oright = RB_RIGHT(tmp, field)))\ 491*2b15cb3dSCy Schubert RB_COLOR(oright, field) = RB_BLACK;\ 492*2b15cb3dSCy Schubert RB_COLOR(tmp, field) = RB_RED; \ 493*2b15cb3dSCy Schubert RB_ROTATE_LEFT(head, tmp, oright, field);\ 494*2b15cb3dSCy Schubert tmp = RB_LEFT(parent, field); \ 495*2b15cb3dSCy Schubert } \ 496*2b15cb3dSCy Schubert RB_COLOR(tmp, field) = RB_COLOR(parent, field);\ 497*2b15cb3dSCy Schubert RB_COLOR(parent, field) = RB_BLACK; \ 498*2b15cb3dSCy Schubert if (RB_LEFT(tmp, field)) \ 499*2b15cb3dSCy Schubert RB_COLOR(RB_LEFT(tmp, field), field) = RB_BLACK;\ 500*2b15cb3dSCy Schubert RB_ROTATE_RIGHT(head, parent, tmp, field);\ 501*2b15cb3dSCy Schubert elm = RB_ROOT(head); \ 502*2b15cb3dSCy Schubert break; \ 503*2b15cb3dSCy Schubert } \ 504*2b15cb3dSCy Schubert } \ 505*2b15cb3dSCy Schubert } \ 506*2b15cb3dSCy Schubert if (elm) \ 507*2b15cb3dSCy Schubert RB_COLOR(elm, field) = RB_BLACK; \ 508*2b15cb3dSCy Schubert } \ 509*2b15cb3dSCy Schubert \ 510*2b15cb3dSCy Schubert struct type * \ 511*2b15cb3dSCy Schubert name##_RB_REMOVE(struct name *head, struct type *elm) \ 512*2b15cb3dSCy Schubert { \ 513*2b15cb3dSCy Schubert struct type *child, *parent, *old = elm; \ 514*2b15cb3dSCy Schubert int color; \ 515*2b15cb3dSCy Schubert if (RB_LEFT(elm, field) == NULL) \ 516*2b15cb3dSCy Schubert child = RB_RIGHT(elm, field); \ 517*2b15cb3dSCy Schubert else if (RB_RIGHT(elm, field) == NULL) \ 518*2b15cb3dSCy Schubert child = RB_LEFT(elm, field); \ 519*2b15cb3dSCy Schubert else { \ 520*2b15cb3dSCy Schubert struct type *left; \ 521*2b15cb3dSCy Schubert elm = RB_RIGHT(elm, field); \ 522*2b15cb3dSCy Schubert while ((left = RB_LEFT(elm, field))) \ 523*2b15cb3dSCy Schubert elm = left; \ 524*2b15cb3dSCy Schubert child = RB_RIGHT(elm, field); \ 525*2b15cb3dSCy Schubert parent = RB_PARENT(elm, field); \ 526*2b15cb3dSCy Schubert color = RB_COLOR(elm, field); \ 527*2b15cb3dSCy Schubert if (child) \ 528*2b15cb3dSCy Schubert RB_PARENT(child, field) = parent; \ 529*2b15cb3dSCy Schubert if (parent) { \ 530*2b15cb3dSCy Schubert if (RB_LEFT(parent, field) == elm) \ 531*2b15cb3dSCy Schubert RB_LEFT(parent, field) = child; \ 532*2b15cb3dSCy Schubert else \ 533*2b15cb3dSCy Schubert RB_RIGHT(parent, field) = child; \ 534*2b15cb3dSCy Schubert RB_AUGMENT(parent); \ 535*2b15cb3dSCy Schubert } else \ 536*2b15cb3dSCy Schubert RB_ROOT(head) = child; \ 537*2b15cb3dSCy Schubert if (RB_PARENT(elm, field) == old) \ 538*2b15cb3dSCy Schubert parent = elm; \ 539*2b15cb3dSCy Schubert (elm)->field = (old)->field; \ 540*2b15cb3dSCy Schubert if (RB_PARENT(old, field)) { \ 541*2b15cb3dSCy Schubert if (RB_LEFT(RB_PARENT(old, field), field) == old)\ 542*2b15cb3dSCy Schubert RB_LEFT(RB_PARENT(old, field), field) = elm;\ 543*2b15cb3dSCy Schubert else \ 544*2b15cb3dSCy Schubert RB_RIGHT(RB_PARENT(old, field), field) = elm;\ 545*2b15cb3dSCy Schubert RB_AUGMENT(RB_PARENT(old, field)); \ 546*2b15cb3dSCy Schubert } else \ 547*2b15cb3dSCy Schubert RB_ROOT(head) = elm; \ 548*2b15cb3dSCy Schubert RB_PARENT(RB_LEFT(old, field), field) = elm; \ 549*2b15cb3dSCy Schubert if (RB_RIGHT(old, field)) \ 550*2b15cb3dSCy Schubert RB_PARENT(RB_RIGHT(old, field), field) = elm; \ 551*2b15cb3dSCy Schubert if (parent) { \ 552*2b15cb3dSCy Schubert left = parent; \ 553*2b15cb3dSCy Schubert do { \ 554*2b15cb3dSCy Schubert RB_AUGMENT(left); \ 555*2b15cb3dSCy Schubert } while ((left = RB_PARENT(left, field))); \ 556*2b15cb3dSCy Schubert } \ 557*2b15cb3dSCy Schubert goto color; \ 558*2b15cb3dSCy Schubert } \ 559*2b15cb3dSCy Schubert parent = RB_PARENT(elm, field); \ 560*2b15cb3dSCy Schubert color = RB_COLOR(elm, field); \ 561*2b15cb3dSCy Schubert if (child) \ 562*2b15cb3dSCy Schubert RB_PARENT(child, field) = parent; \ 563*2b15cb3dSCy Schubert if (parent) { \ 564*2b15cb3dSCy Schubert if (RB_LEFT(parent, field) == elm) \ 565*2b15cb3dSCy Schubert RB_LEFT(parent, field) = child; \ 566*2b15cb3dSCy Schubert else \ 567*2b15cb3dSCy Schubert RB_RIGHT(parent, field) = child; \ 568*2b15cb3dSCy Schubert RB_AUGMENT(parent); \ 569*2b15cb3dSCy Schubert } else \ 570*2b15cb3dSCy Schubert RB_ROOT(head) = child; \ 571*2b15cb3dSCy Schubert color: \ 572*2b15cb3dSCy Schubert if (color == RB_BLACK) \ 573*2b15cb3dSCy Schubert name##_RB_REMOVE_COLOR(head, parent, child); \ 574*2b15cb3dSCy Schubert return (old); \ 575*2b15cb3dSCy Schubert } \ 576*2b15cb3dSCy Schubert \ 577*2b15cb3dSCy Schubert /* Inserts a node into the RB tree */ \ 578*2b15cb3dSCy Schubert struct type * \ 579*2b15cb3dSCy Schubert name##_RB_INSERT(struct name *head, struct type *elm) \ 580*2b15cb3dSCy Schubert { \ 581*2b15cb3dSCy Schubert struct type *tmp; \ 582*2b15cb3dSCy Schubert struct type *parent = NULL; \ 583*2b15cb3dSCy Schubert int comp = 0; \ 584*2b15cb3dSCy Schubert tmp = RB_ROOT(head); \ 585*2b15cb3dSCy Schubert while (tmp) { \ 586*2b15cb3dSCy Schubert parent = tmp; \ 587*2b15cb3dSCy Schubert comp = (cmp)(elm, parent); \ 588*2b15cb3dSCy Schubert if (comp < 0) \ 589*2b15cb3dSCy Schubert tmp = RB_LEFT(tmp, field); \ 590*2b15cb3dSCy Schubert else if (comp > 0) \ 591*2b15cb3dSCy Schubert tmp = RB_RIGHT(tmp, field); \ 592*2b15cb3dSCy Schubert else \ 593*2b15cb3dSCy Schubert return (tmp); \ 594*2b15cb3dSCy Schubert } \ 595*2b15cb3dSCy Schubert RB_SET(elm, parent, field); \ 596*2b15cb3dSCy Schubert if (parent != NULL) { \ 597*2b15cb3dSCy Schubert if (comp < 0) \ 598*2b15cb3dSCy Schubert RB_LEFT(parent, field) = elm; \ 599*2b15cb3dSCy Schubert else \ 600*2b15cb3dSCy Schubert RB_RIGHT(parent, field) = elm; \ 601*2b15cb3dSCy Schubert RB_AUGMENT(parent); \ 602*2b15cb3dSCy Schubert } else \ 603*2b15cb3dSCy Schubert RB_ROOT(head) = elm; \ 604*2b15cb3dSCy Schubert name##_RB_INSERT_COLOR(head, elm); \ 605*2b15cb3dSCy Schubert return (NULL); \ 606*2b15cb3dSCy Schubert } \ 607*2b15cb3dSCy Schubert \ 608*2b15cb3dSCy Schubert /* Finds the node with the same key as elm */ \ 609*2b15cb3dSCy Schubert struct type * \ 610*2b15cb3dSCy Schubert name##_RB_FIND(struct name *head, struct type *elm) \ 611*2b15cb3dSCy Schubert { \ 612*2b15cb3dSCy Schubert struct type *tmp = RB_ROOT(head); \ 613*2b15cb3dSCy Schubert int comp; \ 614*2b15cb3dSCy Schubert while (tmp) { \ 615*2b15cb3dSCy Schubert comp = cmp(elm, tmp); \ 616*2b15cb3dSCy Schubert if (comp < 0) \ 617*2b15cb3dSCy Schubert tmp = RB_LEFT(tmp, field); \ 618*2b15cb3dSCy Schubert else if (comp > 0) \ 619*2b15cb3dSCy Schubert tmp = RB_RIGHT(tmp, field); \ 620*2b15cb3dSCy Schubert else \ 621*2b15cb3dSCy Schubert return (tmp); \ 622*2b15cb3dSCy Schubert } \ 623*2b15cb3dSCy Schubert return (NULL); \ 624*2b15cb3dSCy Schubert } \ 625*2b15cb3dSCy Schubert \ 626*2b15cb3dSCy Schubert struct type * \ 627*2b15cb3dSCy Schubert name##_RB_NEXT(struct type *elm) \ 628*2b15cb3dSCy Schubert { \ 629*2b15cb3dSCy Schubert if (RB_RIGHT(elm, field)) { \ 630*2b15cb3dSCy Schubert elm = RB_RIGHT(elm, field); \ 631*2b15cb3dSCy Schubert while (RB_LEFT(elm, field)) \ 632*2b15cb3dSCy Schubert elm = RB_LEFT(elm, field); \ 633*2b15cb3dSCy Schubert } else { \ 634*2b15cb3dSCy Schubert if (RB_PARENT(elm, field) && \ 635*2b15cb3dSCy Schubert (elm == RB_LEFT(RB_PARENT(elm, field), field))) \ 636*2b15cb3dSCy Schubert elm = RB_PARENT(elm, field); \ 637*2b15cb3dSCy Schubert else { \ 638*2b15cb3dSCy Schubert while (RB_PARENT(elm, field) && \ 639*2b15cb3dSCy Schubert (elm == RB_RIGHT(RB_PARENT(elm, field), field)))\ 640*2b15cb3dSCy Schubert elm = RB_PARENT(elm, field); \ 641*2b15cb3dSCy Schubert elm = RB_PARENT(elm, field); \ 642*2b15cb3dSCy Schubert } \ 643*2b15cb3dSCy Schubert } \ 644*2b15cb3dSCy Schubert return (elm); \ 645*2b15cb3dSCy Schubert } \ 646*2b15cb3dSCy Schubert \ 647*2b15cb3dSCy Schubert struct type * \ 648*2b15cb3dSCy Schubert name##_RB_MINMAX(struct name *head, int val) \ 649*2b15cb3dSCy Schubert { \ 650*2b15cb3dSCy Schubert struct type *tmp = RB_ROOT(head); \ 651*2b15cb3dSCy Schubert struct type *parent = NULL; \ 652*2b15cb3dSCy Schubert while (tmp) { \ 653*2b15cb3dSCy Schubert parent = tmp; \ 654*2b15cb3dSCy Schubert if (val < 0) \ 655*2b15cb3dSCy Schubert tmp = RB_LEFT(tmp, field); \ 656*2b15cb3dSCy Schubert else \ 657*2b15cb3dSCy Schubert tmp = RB_RIGHT(tmp, field); \ 658*2b15cb3dSCy Schubert } \ 659*2b15cb3dSCy Schubert return (parent); \ 660*2b15cb3dSCy Schubert } 661*2b15cb3dSCy Schubert 662*2b15cb3dSCy Schubert #define RB_NEGINF -1 663*2b15cb3dSCy Schubert #define RB_INF 1 664*2b15cb3dSCy Schubert 665*2b15cb3dSCy Schubert #define RB_INSERT(name, x, y) name##_RB_INSERT(x, y) 666*2b15cb3dSCy Schubert #define RB_REMOVE(name, x, y) name##_RB_REMOVE(x, y) 667*2b15cb3dSCy Schubert #define RB_FIND(name, x, y) name##_RB_FIND(x, y) 668*2b15cb3dSCy Schubert #define RB_NEXT(name, x, y) name##_RB_NEXT(y) 669*2b15cb3dSCy Schubert #define RB_MIN(name, x) name##_RB_MINMAX(x, RB_NEGINF) 670*2b15cb3dSCy Schubert #define RB_MAX(name, x) name##_RB_MINMAX(x, RB_INF) 671*2b15cb3dSCy Schubert 672*2b15cb3dSCy Schubert #define RB_FOREACH(x, name, head) \ 673*2b15cb3dSCy Schubert for ((x) = RB_MIN(name, head); \ 674*2b15cb3dSCy Schubert (x) != NULL; \ 675*2b15cb3dSCy Schubert (x) = name##_RB_NEXT(x)) 676*2b15cb3dSCy Schubert 677*2b15cb3dSCy Schubert #endif /* _SYS_TREE_H_ */ 678*2b15cb3dSCy Schubert /* $OpenBSD: tree.h,v 1.7 2002/10/17 21:51:54 art Exp $ */ 679*2b15cb3dSCy Schubert /* 680*2b15cb3dSCy Schubert * Copyright 2002 Niels Provos <provos@citi.umich.edu> 681*2b15cb3dSCy Schubert * All rights reserved. 682*2b15cb3dSCy Schubert * 683*2b15cb3dSCy Schubert * Redistribution and use in source and binary forms, with or without 684*2b15cb3dSCy Schubert * modification, are permitted provided that the following conditions 685*2b15cb3dSCy Schubert * are met: 686*2b15cb3dSCy Schubert * 1. Redistributions of source code must retain the above copyright 687*2b15cb3dSCy Schubert * notice, this list of conditions and the following disclaimer. 688*2b15cb3dSCy Schubert * 2. Redistributions in binary form must reproduce the above copyright 689*2b15cb3dSCy Schubert * notice, this list of conditions and the following disclaimer in the 690*2b15cb3dSCy Schubert * documentation and/or other materials provided with the distribution. 691*2b15cb3dSCy Schubert * 692*2b15cb3dSCy Schubert * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR 693*2b15cb3dSCy Schubert * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES 694*2b15cb3dSCy Schubert * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 695*2b15cb3dSCy Schubert * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, 696*2b15cb3dSCy Schubert * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT 697*2b15cb3dSCy Schubert * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 698*2b15cb3dSCy Schubert * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 699*2b15cb3dSCy Schubert * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 700*2b15cb3dSCy Schubert * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 701*2b15cb3dSCy Schubert * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 702*2b15cb3dSCy Schubert */ 703*2b15cb3dSCy Schubert 704*2b15cb3dSCy Schubert #ifndef _SYS_TREE_H_ 705*2b15cb3dSCy Schubert #define _SYS_TREE_H_ 706*2b15cb3dSCy Schubert 707*2b15cb3dSCy Schubert /* 708*2b15cb3dSCy Schubert * This file defines data structures for different types of trees: 709*2b15cb3dSCy Schubert * splay trees and red-black trees. 710*2b15cb3dSCy Schubert * 711*2b15cb3dSCy Schubert * A splay tree is a self-organizing data structure. Every operation 712*2b15cb3dSCy Schubert * on the tree causes a splay to happen. The splay moves the requested 713*2b15cb3dSCy Schubert * node to the root of the tree and partly rebalances it. 714*2b15cb3dSCy Schubert * 715*2b15cb3dSCy Schubert * This has the benefit that request locality causes faster lookups as 716*2b15cb3dSCy Schubert * the requested nodes move to the top of the tree. On the other hand, 717*2b15cb3dSCy Schubert * every lookup causes memory writes. 718*2b15cb3dSCy Schubert * 719*2b15cb3dSCy Schubert * The Balance Theorem bounds the total access time for m operations 720*2b15cb3dSCy Schubert * and n inserts on an initially empty tree as O((m + n)lg n). The 721*2b15cb3dSCy Schubert * amortized cost for a sequence of m accesses to a splay tree is O(lg n); 722*2b15cb3dSCy Schubert * 723*2b15cb3dSCy Schubert * A red-black tree is a binary search tree with the node color as an 724*2b15cb3dSCy Schubert * extra attribute. It fulfills a set of conditions: 725*2b15cb3dSCy Schubert * - every search path from the root to a leaf consists of the 726*2b15cb3dSCy Schubert * same number of black nodes, 727*2b15cb3dSCy Schubert * - each red node (except for the root) has a black parent, 728*2b15cb3dSCy Schubert * - each leaf node is black. 729*2b15cb3dSCy Schubert * 730*2b15cb3dSCy Schubert * Every operation on a red-black tree is bounded as O(lg n). 731*2b15cb3dSCy Schubert * The maximum height of a red-black tree is 2lg (n+1). 732*2b15cb3dSCy Schubert */ 733*2b15cb3dSCy Schubert 734*2b15cb3dSCy Schubert #define SPLAY_HEAD(name, type) \ 735*2b15cb3dSCy Schubert struct name { \ 736*2b15cb3dSCy Schubert struct type *sph_root; /* root of the tree */ \ 737*2b15cb3dSCy Schubert } 738*2b15cb3dSCy Schubert 739*2b15cb3dSCy Schubert #define SPLAY_INITIALIZER(root) \ 740*2b15cb3dSCy Schubert { NULL } 741*2b15cb3dSCy Schubert 742*2b15cb3dSCy Schubert #define SPLAY_INIT(root) do { \ 743*2b15cb3dSCy Schubert (root)->sph_root = NULL; \ 744*2b15cb3dSCy Schubert } while (0) 745*2b15cb3dSCy Schubert 746*2b15cb3dSCy Schubert #define SPLAY_ENTRY(type) \ 747*2b15cb3dSCy Schubert struct { \ 748*2b15cb3dSCy Schubert struct type *spe_left; /* left element */ \ 749*2b15cb3dSCy Schubert struct type *spe_right; /* right element */ \ 750*2b15cb3dSCy Schubert } 751*2b15cb3dSCy Schubert 752*2b15cb3dSCy Schubert #define SPLAY_LEFT(elm, field) (elm)->field.spe_left 753*2b15cb3dSCy Schubert #define SPLAY_RIGHT(elm, field) (elm)->field.spe_right 754*2b15cb3dSCy Schubert #define SPLAY_ROOT(head) (head)->sph_root 755*2b15cb3dSCy Schubert #define SPLAY_EMPTY(head) (SPLAY_ROOT(head) == NULL) 756*2b15cb3dSCy Schubert 757*2b15cb3dSCy Schubert /* SPLAY_ROTATE_{LEFT,RIGHT} expect that tmp hold SPLAY_{RIGHT,LEFT} */ 758*2b15cb3dSCy Schubert #define SPLAY_ROTATE_RIGHT(head, tmp, field) do { \ 759*2b15cb3dSCy Schubert SPLAY_LEFT((head)->sph_root, field) = SPLAY_RIGHT(tmp, field); \ 760*2b15cb3dSCy Schubert SPLAY_RIGHT(tmp, field) = (head)->sph_root; \ 761*2b15cb3dSCy Schubert (head)->sph_root = tmp; \ 762*2b15cb3dSCy Schubert } while (0) 763*2b15cb3dSCy Schubert 764*2b15cb3dSCy Schubert #define SPLAY_ROTATE_LEFT(head, tmp, field) do { \ 765*2b15cb3dSCy Schubert SPLAY_RIGHT((head)->sph_root, field) = SPLAY_LEFT(tmp, field); \ 766*2b15cb3dSCy Schubert SPLAY_LEFT(tmp, field) = (head)->sph_root; \ 767*2b15cb3dSCy Schubert (head)->sph_root = tmp; \ 768*2b15cb3dSCy Schubert } while (0) 769*2b15cb3dSCy Schubert 770*2b15cb3dSCy Schubert #define SPLAY_LINKLEFT(head, tmp, field) do { \ 771*2b15cb3dSCy Schubert SPLAY_LEFT(tmp, field) = (head)->sph_root; \ 772*2b15cb3dSCy Schubert tmp = (head)->sph_root; \ 773*2b15cb3dSCy Schubert (head)->sph_root = SPLAY_LEFT((head)->sph_root, field); \ 774*2b15cb3dSCy Schubert } while (0) 775*2b15cb3dSCy Schubert 776*2b15cb3dSCy Schubert #define SPLAY_LINKRIGHT(head, tmp, field) do { \ 777*2b15cb3dSCy Schubert SPLAY_RIGHT(tmp, field) = (head)->sph_root; \ 778*2b15cb3dSCy Schubert tmp = (head)->sph_root; \ 779*2b15cb3dSCy Schubert (head)->sph_root = SPLAY_RIGHT((head)->sph_root, field); \ 780*2b15cb3dSCy Schubert } while (0) 781*2b15cb3dSCy Schubert 782*2b15cb3dSCy Schubert #define SPLAY_ASSEMBLE(head, node, left, right, field) do { \ 783*2b15cb3dSCy Schubert SPLAY_RIGHT(left, field) = SPLAY_LEFT((head)->sph_root, field); \ 784*2b15cb3dSCy Schubert SPLAY_LEFT(right, field) = SPLAY_RIGHT((head)->sph_root, field);\ 785*2b15cb3dSCy Schubert SPLAY_LEFT((head)->sph_root, field) = SPLAY_RIGHT(node, field); \ 786*2b15cb3dSCy Schubert SPLAY_RIGHT((head)->sph_root, field) = SPLAY_LEFT(node, field); \ 787*2b15cb3dSCy Schubert } while (0) 788*2b15cb3dSCy Schubert 789*2b15cb3dSCy Schubert /* Generates prototypes and inline functions */ 790*2b15cb3dSCy Schubert 791*2b15cb3dSCy Schubert #define SPLAY_PROTOTYPE(name, type, field, cmp) \ 792*2b15cb3dSCy Schubert void name##_SPLAY(struct name *, struct type *); \ 793*2b15cb3dSCy Schubert void name##_SPLAY_MINMAX(struct name *, int); \ 794*2b15cb3dSCy Schubert struct type *name##_SPLAY_INSERT(struct name *, struct type *); \ 795*2b15cb3dSCy Schubert struct type *name##_SPLAY_REMOVE(struct name *, struct type *); \ 796*2b15cb3dSCy Schubert \ 797*2b15cb3dSCy Schubert /* Finds the node with the same key as elm */ \ 798*2b15cb3dSCy Schubert static __inline struct type * \ 799*2b15cb3dSCy Schubert name##_SPLAY_FIND(struct name *head, struct type *elm) \ 800*2b15cb3dSCy Schubert { \ 801*2b15cb3dSCy Schubert if (SPLAY_EMPTY(head)) \ 802*2b15cb3dSCy Schubert return(NULL); \ 803*2b15cb3dSCy Schubert name##_SPLAY(head, elm); \ 804*2b15cb3dSCy Schubert if ((cmp)(elm, (head)->sph_root) == 0) \ 805*2b15cb3dSCy Schubert return (head->sph_root); \ 806*2b15cb3dSCy Schubert return (NULL); \ 807*2b15cb3dSCy Schubert } \ 808*2b15cb3dSCy Schubert \ 809*2b15cb3dSCy Schubert static __inline struct type * \ 810*2b15cb3dSCy Schubert name##_SPLAY_NEXT(struct name *head, struct type *elm) \ 811*2b15cb3dSCy Schubert { \ 812*2b15cb3dSCy Schubert name##_SPLAY(head, elm); \ 813*2b15cb3dSCy Schubert if (SPLAY_RIGHT(elm, field) != NULL) { \ 814*2b15cb3dSCy Schubert elm = SPLAY_RIGHT(elm, field); \ 815*2b15cb3dSCy Schubert while (SPLAY_LEFT(elm, field) != NULL) { \ 816*2b15cb3dSCy Schubert elm = SPLAY_LEFT(elm, field); \ 817*2b15cb3dSCy Schubert } \ 818*2b15cb3dSCy Schubert } else \ 819*2b15cb3dSCy Schubert elm = NULL; \ 820*2b15cb3dSCy Schubert return (elm); \ 821*2b15cb3dSCy Schubert } \ 822*2b15cb3dSCy Schubert \ 823*2b15cb3dSCy Schubert static __inline struct type * \ 824*2b15cb3dSCy Schubert name##_SPLAY_MIN_MAX(struct name *head, int val) \ 825*2b15cb3dSCy Schubert { \ 826*2b15cb3dSCy Schubert name##_SPLAY_MINMAX(head, val); \ 827*2b15cb3dSCy Schubert return (SPLAY_ROOT(head)); \ 828*2b15cb3dSCy Schubert } 829*2b15cb3dSCy Schubert 830*2b15cb3dSCy Schubert /* Main splay operation. 831*2b15cb3dSCy Schubert * Moves node close to the key of elm to top 832*2b15cb3dSCy Schubert */ 833*2b15cb3dSCy Schubert #define SPLAY_GENERATE(name, type, field, cmp) \ 834*2b15cb3dSCy Schubert struct type * \ 835*2b15cb3dSCy Schubert name##_SPLAY_INSERT(struct name *head, struct type *elm) \ 836*2b15cb3dSCy Schubert { \ 837*2b15cb3dSCy Schubert if (SPLAY_EMPTY(head)) { \ 838*2b15cb3dSCy Schubert SPLAY_LEFT(elm, field) = SPLAY_RIGHT(elm, field) = NULL; \ 839*2b15cb3dSCy Schubert } else { \ 840*2b15cb3dSCy Schubert int __comp; \ 841*2b15cb3dSCy Schubert name##_SPLAY(head, elm); \ 842*2b15cb3dSCy Schubert __comp = (cmp)(elm, (head)->sph_root); \ 843*2b15cb3dSCy Schubert if(__comp < 0) { \ 844*2b15cb3dSCy Schubert SPLAY_LEFT(elm, field) = SPLAY_LEFT((head)->sph_root, field);\ 845*2b15cb3dSCy Schubert SPLAY_RIGHT(elm, field) = (head)->sph_root; \ 846*2b15cb3dSCy Schubert SPLAY_LEFT((head)->sph_root, field) = NULL; \ 847*2b15cb3dSCy Schubert } else if (__comp > 0) { \ 848*2b15cb3dSCy Schubert SPLAY_RIGHT(elm, field) = SPLAY_RIGHT((head)->sph_root, field);\ 849*2b15cb3dSCy Schubert SPLAY_LEFT(elm, field) = (head)->sph_root; \ 850*2b15cb3dSCy Schubert SPLAY_RIGHT((head)->sph_root, field) = NULL; \ 851*2b15cb3dSCy Schubert } else \ 852*2b15cb3dSCy Schubert return ((head)->sph_root); \ 853*2b15cb3dSCy Schubert } \ 854*2b15cb3dSCy Schubert (head)->sph_root = (elm); \ 855*2b15cb3dSCy Schubert return (NULL); \ 856*2b15cb3dSCy Schubert } \ 857*2b15cb3dSCy Schubert \ 858*2b15cb3dSCy Schubert struct type * \ 859*2b15cb3dSCy Schubert name##_SPLAY_REMOVE(struct name *head, struct type *elm) \ 860*2b15cb3dSCy Schubert { \ 861*2b15cb3dSCy Schubert struct type *__tmp; \ 862*2b15cb3dSCy Schubert if (SPLAY_EMPTY(head)) \ 863*2b15cb3dSCy Schubert return (NULL); \ 864*2b15cb3dSCy Schubert name##_SPLAY(head, elm); \ 865*2b15cb3dSCy Schubert if ((cmp)(elm, (head)->sph_root) == 0) { \ 866*2b15cb3dSCy Schubert if (SPLAY_LEFT((head)->sph_root, field) == NULL) { \ 867*2b15cb3dSCy Schubert (head)->sph_root = SPLAY_RIGHT((head)->sph_root, field);\ 868*2b15cb3dSCy Schubert } else { \ 869*2b15cb3dSCy Schubert __tmp = SPLAY_RIGHT((head)->sph_root, field); \ 870*2b15cb3dSCy Schubert (head)->sph_root = SPLAY_LEFT((head)->sph_root, field);\ 871*2b15cb3dSCy Schubert name##_SPLAY(head, elm); \ 872*2b15cb3dSCy Schubert SPLAY_RIGHT((head)->sph_root, field) = __tmp; \ 873*2b15cb3dSCy Schubert } \ 874*2b15cb3dSCy Schubert return (elm); \ 875*2b15cb3dSCy Schubert } \ 876*2b15cb3dSCy Schubert return (NULL); \ 877*2b15cb3dSCy Schubert } \ 878*2b15cb3dSCy Schubert \ 879*2b15cb3dSCy Schubert void \ 880*2b15cb3dSCy Schubert name##_SPLAY(struct name *head, struct type *elm) \ 881*2b15cb3dSCy Schubert { \ 882*2b15cb3dSCy Schubert struct type __node, *__left, *__right, *__tmp; \ 883*2b15cb3dSCy Schubert int __comp; \ 884*2b15cb3dSCy Schubert \ 885*2b15cb3dSCy Schubert SPLAY_LEFT(&__node, field) = SPLAY_RIGHT(&__node, field) = NULL;\ 886*2b15cb3dSCy Schubert __left = __right = &__node; \ 887*2b15cb3dSCy Schubert \ 888*2b15cb3dSCy Schubert while ((__comp = (cmp)(elm, (head)->sph_root))) { \ 889*2b15cb3dSCy Schubert if (__comp < 0) { \ 890*2b15cb3dSCy Schubert __tmp = SPLAY_LEFT((head)->sph_root, field); \ 891*2b15cb3dSCy Schubert if (__tmp == NULL) \ 892*2b15cb3dSCy Schubert break; \ 893*2b15cb3dSCy Schubert if ((cmp)(elm, __tmp) < 0){ \ 894*2b15cb3dSCy Schubert SPLAY_ROTATE_RIGHT(head, __tmp, field); \ 895*2b15cb3dSCy Schubert if (SPLAY_LEFT((head)->sph_root, field) == NULL)\ 896*2b15cb3dSCy Schubert break; \ 897*2b15cb3dSCy Schubert } \ 898*2b15cb3dSCy Schubert SPLAY_LINKLEFT(head, __right, field); \ 899*2b15cb3dSCy Schubert } else if (__comp > 0) { \ 900*2b15cb3dSCy Schubert __tmp = SPLAY_RIGHT((head)->sph_root, field); \ 901*2b15cb3dSCy Schubert if (__tmp == NULL) \ 902*2b15cb3dSCy Schubert break; \ 903*2b15cb3dSCy Schubert if ((cmp)(elm, __tmp) > 0){ \ 904*2b15cb3dSCy Schubert SPLAY_ROTATE_LEFT(head, __tmp, field); \ 905*2b15cb3dSCy Schubert if (SPLAY_RIGHT((head)->sph_root, field) == NULL)\ 906*2b15cb3dSCy Schubert break; \ 907*2b15cb3dSCy Schubert } \ 908*2b15cb3dSCy Schubert SPLAY_LINKRIGHT(head, __left, field); \ 909*2b15cb3dSCy Schubert } \ 910*2b15cb3dSCy Schubert } \ 911*2b15cb3dSCy Schubert SPLAY_ASSEMBLE(head, &__node, __left, __right, field); \ 912*2b15cb3dSCy Schubert } \ 913*2b15cb3dSCy Schubert \ 914*2b15cb3dSCy Schubert /* Splay with either the minimum or the maximum element \ 915*2b15cb3dSCy Schubert * Used to find minimum or maximum element in tree. \ 916*2b15cb3dSCy Schubert */ \ 917*2b15cb3dSCy Schubert void name##_SPLAY_MINMAX(struct name *head, int __comp) \ 918*2b15cb3dSCy Schubert { \ 919*2b15cb3dSCy Schubert struct type __node, *__left, *__right, *__tmp; \ 920*2b15cb3dSCy Schubert \ 921*2b15cb3dSCy Schubert SPLAY_LEFT(&__node, field) = SPLAY_RIGHT(&__node, field) = NULL;\ 922*2b15cb3dSCy Schubert __left = __right = &__node; \ 923*2b15cb3dSCy Schubert \ 924*2b15cb3dSCy Schubert while (1) { \ 925*2b15cb3dSCy Schubert if (__comp < 0) { \ 926*2b15cb3dSCy Schubert __tmp = SPLAY_LEFT((head)->sph_root, field); \ 927*2b15cb3dSCy Schubert if (__tmp == NULL) \ 928*2b15cb3dSCy Schubert break; \ 929*2b15cb3dSCy Schubert if (__comp < 0){ \ 930*2b15cb3dSCy Schubert SPLAY_ROTATE_RIGHT(head, __tmp, field); \ 931*2b15cb3dSCy Schubert if (SPLAY_LEFT((head)->sph_root, field) == NULL)\ 932*2b15cb3dSCy Schubert break; \ 933*2b15cb3dSCy Schubert } \ 934*2b15cb3dSCy Schubert SPLAY_LINKLEFT(head, __right, field); \ 935*2b15cb3dSCy Schubert } else if (__comp > 0) { \ 936*2b15cb3dSCy Schubert __tmp = SPLAY_RIGHT((head)->sph_root, field); \ 937*2b15cb3dSCy Schubert if (__tmp == NULL) \ 938*2b15cb3dSCy Schubert break; \ 939*2b15cb3dSCy Schubert if (__comp > 0) { \ 940*2b15cb3dSCy Schubert SPLAY_ROTATE_LEFT(head, __tmp, field); \ 941*2b15cb3dSCy Schubert if (SPLAY_RIGHT((head)->sph_root, field) == NULL)\ 942*2b15cb3dSCy Schubert break; \ 943*2b15cb3dSCy Schubert } \ 944*2b15cb3dSCy Schubert SPLAY_LINKRIGHT(head, __left, field); \ 945*2b15cb3dSCy Schubert } \ 946*2b15cb3dSCy Schubert } \ 947*2b15cb3dSCy Schubert SPLAY_ASSEMBLE(head, &__node, __left, __right, field); \ 948*2b15cb3dSCy Schubert } 949*2b15cb3dSCy Schubert 950*2b15cb3dSCy Schubert #define SPLAY_NEGINF -1 951*2b15cb3dSCy Schubert #define SPLAY_INF 1 952*2b15cb3dSCy Schubert 953*2b15cb3dSCy Schubert #define SPLAY_INSERT(name, x, y) name##_SPLAY_INSERT(x, y) 954*2b15cb3dSCy Schubert #define SPLAY_REMOVE(name, x, y) name##_SPLAY_REMOVE(x, y) 955*2b15cb3dSCy Schubert #define SPLAY_FIND(name, x, y) name##_SPLAY_FIND(x, y) 956*2b15cb3dSCy Schubert #define SPLAY_NEXT(name, x, y) name##_SPLAY_NEXT(x, y) 957*2b15cb3dSCy Schubert #define SPLAY_MIN(name, x) (SPLAY_EMPTY(x) ? NULL \ 958*2b15cb3dSCy Schubert : name##_SPLAY_MIN_MAX(x, SPLAY_NEGINF)) 959*2b15cb3dSCy Schubert #define SPLAY_MAX(name, x) (SPLAY_EMPTY(x) ? NULL \ 960*2b15cb3dSCy Schubert : name##_SPLAY_MIN_MAX(x, SPLAY_INF)) 961*2b15cb3dSCy Schubert 962*2b15cb3dSCy Schubert #define SPLAY_FOREACH(x, name, head) \ 963*2b15cb3dSCy Schubert for ((x) = SPLAY_MIN(name, head); \ 964*2b15cb3dSCy Schubert (x) != NULL; \ 965*2b15cb3dSCy Schubert (x) = SPLAY_NEXT(name, head, x)) 966*2b15cb3dSCy Schubert 967*2b15cb3dSCy Schubert /* Macros that define a red-back tree */ 968*2b15cb3dSCy Schubert #define RB_HEAD(name, type) \ 969*2b15cb3dSCy Schubert struct name { \ 970*2b15cb3dSCy Schubert struct type *rbh_root; /* root of the tree */ \ 971*2b15cb3dSCy Schubert } 972*2b15cb3dSCy Schubert 973*2b15cb3dSCy Schubert #define RB_INITIALIZER(root) \ 974*2b15cb3dSCy Schubert { NULL } 975*2b15cb3dSCy Schubert 976*2b15cb3dSCy Schubert #define RB_INIT(root) do { \ 977*2b15cb3dSCy Schubert (root)->rbh_root = NULL; \ 978*2b15cb3dSCy Schubert } while (0) 979*2b15cb3dSCy Schubert 980*2b15cb3dSCy Schubert #define RB_BLACK 0 981*2b15cb3dSCy Schubert #define RB_RED 1 982*2b15cb3dSCy Schubert #define RB_ENTRY(type) \ 983*2b15cb3dSCy Schubert struct { \ 984*2b15cb3dSCy Schubert struct type *rbe_left; /* left element */ \ 985*2b15cb3dSCy Schubert struct type *rbe_right; /* right element */ \ 986*2b15cb3dSCy Schubert struct type *rbe_parent; /* parent element */ \ 987*2b15cb3dSCy Schubert int rbe_color; /* node color */ \ 988*2b15cb3dSCy Schubert } 989*2b15cb3dSCy Schubert 990*2b15cb3dSCy Schubert #define RB_LEFT(elm, field) (elm)->field.rbe_left 991*2b15cb3dSCy Schubert #define RB_RIGHT(elm, field) (elm)->field.rbe_right 992*2b15cb3dSCy Schubert #define RB_PARENT(elm, field) (elm)->field.rbe_parent 993*2b15cb3dSCy Schubert #define RB_COLOR(elm, field) (elm)->field.rbe_color 994*2b15cb3dSCy Schubert #define RB_ROOT(head) (head)->rbh_root 995*2b15cb3dSCy Schubert #define RB_EMPTY(head) (RB_ROOT(head) == NULL) 996*2b15cb3dSCy Schubert 997*2b15cb3dSCy Schubert #define RB_SET(elm, parent, field) do { \ 998*2b15cb3dSCy Schubert RB_PARENT(elm, field) = parent; \ 999*2b15cb3dSCy Schubert RB_LEFT(elm, field) = RB_RIGHT(elm, field) = NULL; \ 1000*2b15cb3dSCy Schubert RB_COLOR(elm, field) = RB_RED; \ 1001*2b15cb3dSCy Schubert } while (0) 1002*2b15cb3dSCy Schubert 1003*2b15cb3dSCy Schubert #define RB_SET_BLACKRED(black, red, field) do { \ 1004*2b15cb3dSCy Schubert RB_COLOR(black, field) = RB_BLACK; \ 1005*2b15cb3dSCy Schubert RB_COLOR(red, field) = RB_RED; \ 1006*2b15cb3dSCy Schubert } while (0) 1007*2b15cb3dSCy Schubert 1008*2b15cb3dSCy Schubert #ifndef RB_AUGMENT 1009*2b15cb3dSCy Schubert #define RB_AUGMENT(x) 1010*2b15cb3dSCy Schubert #endif 1011*2b15cb3dSCy Schubert 1012*2b15cb3dSCy Schubert #define RB_ROTATE_LEFT(head, elm, tmp, field) do { \ 1013*2b15cb3dSCy Schubert (tmp) = RB_RIGHT(elm, field); \ 1014*2b15cb3dSCy Schubert if ((RB_RIGHT(elm, field) = RB_LEFT(tmp, field))) { \ 1015*2b15cb3dSCy Schubert RB_PARENT(RB_LEFT(tmp, field), field) = (elm); \ 1016*2b15cb3dSCy Schubert } \ 1017*2b15cb3dSCy Schubert RB_AUGMENT(elm); \ 1018*2b15cb3dSCy Schubert if ((RB_PARENT(tmp, field) = RB_PARENT(elm, field))) { \ 1019*2b15cb3dSCy Schubert if ((elm) == RB_LEFT(RB_PARENT(elm, field), field)) \ 1020*2b15cb3dSCy Schubert RB_LEFT(RB_PARENT(elm, field), field) = (tmp); \ 1021*2b15cb3dSCy Schubert else \ 1022*2b15cb3dSCy Schubert RB_RIGHT(RB_PARENT(elm, field), field) = (tmp); \ 1023*2b15cb3dSCy Schubert } else \ 1024*2b15cb3dSCy Schubert (head)->rbh_root = (tmp); \ 1025*2b15cb3dSCy Schubert RB_LEFT(tmp, field) = (elm); \ 1026*2b15cb3dSCy Schubert RB_PARENT(elm, field) = (tmp); \ 1027*2b15cb3dSCy Schubert RB_AUGMENT(tmp); \ 1028*2b15cb3dSCy Schubert if ((RB_PARENT(tmp, field))) \ 1029*2b15cb3dSCy Schubert RB_AUGMENT(RB_PARENT(tmp, field)); \ 1030*2b15cb3dSCy Schubert } while (0) 1031*2b15cb3dSCy Schubert 1032*2b15cb3dSCy Schubert #define RB_ROTATE_RIGHT(head, elm, tmp, field) do { \ 1033*2b15cb3dSCy Schubert (tmp) = RB_LEFT(elm, field); \ 1034*2b15cb3dSCy Schubert if ((RB_LEFT(elm, field) = RB_RIGHT(tmp, field))) { \ 1035*2b15cb3dSCy Schubert RB_PARENT(RB_RIGHT(tmp, field), field) = (elm); \ 1036*2b15cb3dSCy Schubert } \ 1037*2b15cb3dSCy Schubert RB_AUGMENT(elm); \ 1038*2b15cb3dSCy Schubert if ((RB_PARENT(tmp, field) = RB_PARENT(elm, field))) { \ 1039*2b15cb3dSCy Schubert if ((elm) == RB_LEFT(RB_PARENT(elm, field), field)) \ 1040*2b15cb3dSCy Schubert RB_LEFT(RB_PARENT(elm, field), field) = (tmp); \ 1041*2b15cb3dSCy Schubert else \ 1042*2b15cb3dSCy Schubert RB_RIGHT(RB_PARENT(elm, field), field) = (tmp); \ 1043*2b15cb3dSCy Schubert } else \ 1044*2b15cb3dSCy Schubert (head)->rbh_root = (tmp); \ 1045*2b15cb3dSCy Schubert RB_RIGHT(tmp, field) = (elm); \ 1046*2b15cb3dSCy Schubert RB_PARENT(elm, field) = (tmp); \ 1047*2b15cb3dSCy Schubert RB_AUGMENT(tmp); \ 1048*2b15cb3dSCy Schubert if ((RB_PARENT(tmp, field))) \ 1049*2b15cb3dSCy Schubert RB_AUGMENT(RB_PARENT(tmp, field)); \ 1050*2b15cb3dSCy Schubert } while (0) 1051*2b15cb3dSCy Schubert 1052*2b15cb3dSCy Schubert /* Generates prototypes and inline functions */ 1053*2b15cb3dSCy Schubert #define RB_PROTOTYPE(name, type, field, cmp) \ 1054*2b15cb3dSCy Schubert void name##_RB_INSERT_COLOR(struct name *, struct type *); \ 1055*2b15cb3dSCy Schubert void name##_RB_REMOVE_COLOR(struct name *, struct type *, struct type *);\ 1056*2b15cb3dSCy Schubert struct type *name##_RB_REMOVE(struct name *, struct type *); \ 1057*2b15cb3dSCy Schubert struct type *name##_RB_INSERT(struct name *, struct type *); \ 1058*2b15cb3dSCy Schubert struct type *name##_RB_FIND(struct name *, struct type *); \ 1059*2b15cb3dSCy Schubert struct type *name##_RB_NEXT(struct type *); \ 1060*2b15cb3dSCy Schubert struct type *name##_RB_MINMAX(struct name *, int); \ 1061*2b15cb3dSCy Schubert \ 1062*2b15cb3dSCy Schubert 1063*2b15cb3dSCy Schubert /* Main rb operation. 1064*2b15cb3dSCy Schubert * Moves node close to the key of elm to top 1065*2b15cb3dSCy Schubert */ 1066*2b15cb3dSCy Schubert #define RB_GENERATE(name, type, field, cmp) \ 1067*2b15cb3dSCy Schubert void \ 1068*2b15cb3dSCy Schubert name##_RB_INSERT_COLOR(struct name *head, struct type *elm) \ 1069*2b15cb3dSCy Schubert { \ 1070*2b15cb3dSCy Schubert struct type *parent, *gparent, *tmp; \ 1071*2b15cb3dSCy Schubert while ((parent = RB_PARENT(elm, field)) && \ 1072*2b15cb3dSCy Schubert RB_COLOR(parent, field) == RB_RED) { \ 1073*2b15cb3dSCy Schubert gparent = RB_PARENT(parent, field); \ 1074*2b15cb3dSCy Schubert if (parent == RB_LEFT(gparent, field)) { \ 1075*2b15cb3dSCy Schubert tmp = RB_RIGHT(gparent, field); \ 1076*2b15cb3dSCy Schubert if (tmp && RB_COLOR(tmp, field) == RB_RED) { \ 1077*2b15cb3dSCy Schubert RB_COLOR(tmp, field) = RB_BLACK; \ 1078*2b15cb3dSCy Schubert RB_SET_BLACKRED(parent, gparent, field);\ 1079*2b15cb3dSCy Schubert elm = gparent; \ 1080*2b15cb3dSCy Schubert continue; \ 1081*2b15cb3dSCy Schubert } \ 1082*2b15cb3dSCy Schubert if (RB_RIGHT(parent, field) == elm) { \ 1083*2b15cb3dSCy Schubert RB_ROTATE_LEFT(head, parent, tmp, field);\ 1084*2b15cb3dSCy Schubert tmp = parent; \ 1085*2b15cb3dSCy Schubert parent = elm; \ 1086*2b15cb3dSCy Schubert elm = tmp; \ 1087*2b15cb3dSCy Schubert } \ 1088*2b15cb3dSCy Schubert RB_SET_BLACKRED(parent, gparent, field); \ 1089*2b15cb3dSCy Schubert RB_ROTATE_RIGHT(head, gparent, tmp, field); \ 1090*2b15cb3dSCy Schubert } else { \ 1091*2b15cb3dSCy Schubert tmp = RB_LEFT(gparent, field); \ 1092*2b15cb3dSCy Schubert if (tmp && RB_COLOR(tmp, field) == RB_RED) { \ 1093*2b15cb3dSCy Schubert RB_COLOR(tmp, field) = RB_BLACK; \ 1094*2b15cb3dSCy Schubert RB_SET_BLACKRED(parent, gparent, field);\ 1095*2b15cb3dSCy Schubert elm = gparent; \ 1096*2b15cb3dSCy Schubert continue; \ 1097*2b15cb3dSCy Schubert } \ 1098*2b15cb3dSCy Schubert if (RB_LEFT(parent, field) == elm) { \ 1099*2b15cb3dSCy Schubert RB_ROTATE_RIGHT(head, parent, tmp, field);\ 1100*2b15cb3dSCy Schubert tmp = parent; \ 1101*2b15cb3dSCy Schubert parent = elm; \ 1102*2b15cb3dSCy Schubert elm = tmp; \ 1103*2b15cb3dSCy Schubert } \ 1104*2b15cb3dSCy Schubert RB_SET_BLACKRED(parent, gparent, field); \ 1105*2b15cb3dSCy Schubert RB_ROTATE_LEFT(head, gparent, tmp, field); \ 1106*2b15cb3dSCy Schubert } \ 1107*2b15cb3dSCy Schubert } \ 1108*2b15cb3dSCy Schubert RB_COLOR(head->rbh_root, field) = RB_BLACK; \ 1109*2b15cb3dSCy Schubert } \ 1110*2b15cb3dSCy Schubert \ 1111*2b15cb3dSCy Schubert void \ 1112*2b15cb3dSCy Schubert name##_RB_REMOVE_COLOR(struct name *head, struct type *parent, struct type *elm) \ 1113*2b15cb3dSCy Schubert { \ 1114*2b15cb3dSCy Schubert struct type *tmp; \ 1115*2b15cb3dSCy Schubert while ((elm == NULL || RB_COLOR(elm, field) == RB_BLACK) && \ 1116*2b15cb3dSCy Schubert elm != RB_ROOT(head)) { \ 1117*2b15cb3dSCy Schubert if (RB_LEFT(parent, field) == elm) { \ 1118*2b15cb3dSCy Schubert tmp = RB_RIGHT(parent, field); \ 1119*2b15cb3dSCy Schubert if (RB_COLOR(tmp, field) == RB_RED) { \ 1120*2b15cb3dSCy Schubert RB_SET_BLACKRED(tmp, parent, field); \ 1121*2b15cb3dSCy Schubert RB_ROTATE_LEFT(head, parent, tmp, field);\ 1122*2b15cb3dSCy Schubert tmp = RB_RIGHT(parent, field); \ 1123*2b15cb3dSCy Schubert } \ 1124*2b15cb3dSCy Schubert if ((RB_LEFT(tmp, field) == NULL || \ 1125*2b15cb3dSCy Schubert RB_COLOR(RB_LEFT(tmp, field), field) == RB_BLACK) &&\ 1126*2b15cb3dSCy Schubert (RB_RIGHT(tmp, field) == NULL || \ 1127*2b15cb3dSCy Schubert RB_COLOR(RB_RIGHT(tmp, field), field) == RB_BLACK)) {\ 1128*2b15cb3dSCy Schubert RB_COLOR(tmp, field) = RB_RED; \ 1129*2b15cb3dSCy Schubert elm = parent; \ 1130*2b15cb3dSCy Schubert parent = RB_PARENT(elm, field); \ 1131*2b15cb3dSCy Schubert } else { \ 1132*2b15cb3dSCy Schubert if (RB_RIGHT(tmp, field) == NULL || \ 1133*2b15cb3dSCy Schubert RB_COLOR(RB_RIGHT(tmp, field), field) == RB_BLACK) {\ 1134*2b15cb3dSCy Schubert struct type *oleft; \ 1135*2b15cb3dSCy Schubert if ((oleft = RB_LEFT(tmp, field)))\ 1136*2b15cb3dSCy Schubert RB_COLOR(oleft, field) = RB_BLACK;\ 1137*2b15cb3dSCy Schubert RB_COLOR(tmp, field) = RB_RED; \ 1138*2b15cb3dSCy Schubert RB_ROTATE_RIGHT(head, tmp, oleft, field);\ 1139*2b15cb3dSCy Schubert tmp = RB_RIGHT(parent, field); \ 1140*2b15cb3dSCy Schubert } \ 1141*2b15cb3dSCy Schubert RB_COLOR(tmp, field) = RB_COLOR(parent, field);\ 1142*2b15cb3dSCy Schubert RB_COLOR(parent, field) = RB_BLACK; \ 1143*2b15cb3dSCy Schubert if (RB_RIGHT(tmp, field)) \ 1144*2b15cb3dSCy Schubert RB_COLOR(RB_RIGHT(tmp, field), field) = RB_BLACK;\ 1145*2b15cb3dSCy Schubert RB_ROTATE_LEFT(head, parent, tmp, field);\ 1146*2b15cb3dSCy Schubert elm = RB_ROOT(head); \ 1147*2b15cb3dSCy Schubert break; \ 1148*2b15cb3dSCy Schubert } \ 1149*2b15cb3dSCy Schubert } else { \ 1150*2b15cb3dSCy Schubert tmp = RB_LEFT(parent, field); \ 1151*2b15cb3dSCy Schubert if (RB_COLOR(tmp, field) == RB_RED) { \ 1152*2b15cb3dSCy Schubert RB_SET_BLACKRED(tmp, parent, field); \ 1153*2b15cb3dSCy Schubert RB_ROTATE_RIGHT(head, parent, tmp, field);\ 1154*2b15cb3dSCy Schubert tmp = RB_LEFT(parent, field); \ 1155*2b15cb3dSCy Schubert } \ 1156*2b15cb3dSCy Schubert if ((RB_LEFT(tmp, field) == NULL || \ 1157*2b15cb3dSCy Schubert RB_COLOR(RB_LEFT(tmp, field), field) == RB_BLACK) &&\ 1158*2b15cb3dSCy Schubert (RB_RIGHT(tmp, field) == NULL || \ 1159*2b15cb3dSCy Schubert RB_COLOR(RB_RIGHT(tmp, field), field) == RB_BLACK)) {\ 1160*2b15cb3dSCy Schubert RB_COLOR(tmp, field) = RB_RED; \ 1161*2b15cb3dSCy Schubert elm = parent; \ 1162*2b15cb3dSCy Schubert parent = RB_PARENT(elm, field); \ 1163*2b15cb3dSCy Schubert } else { \ 1164*2b15cb3dSCy Schubert if (RB_LEFT(tmp, field) == NULL || \ 1165*2b15cb3dSCy Schubert RB_COLOR(RB_LEFT(tmp, field), field) == RB_BLACK) {\ 1166*2b15cb3dSCy Schubert struct type *oright; \ 1167*2b15cb3dSCy Schubert if ((oright = RB_RIGHT(tmp, field)))\ 1168*2b15cb3dSCy Schubert RB_COLOR(oright, field) = RB_BLACK;\ 1169*2b15cb3dSCy Schubert RB_COLOR(tmp, field) = RB_RED; \ 1170*2b15cb3dSCy Schubert RB_ROTATE_LEFT(head, tmp, oright, field);\ 1171*2b15cb3dSCy Schubert tmp = RB_LEFT(parent, field); \ 1172*2b15cb3dSCy Schubert } \ 1173*2b15cb3dSCy Schubert RB_COLOR(tmp, field) = RB_COLOR(parent, field);\ 1174*2b15cb3dSCy Schubert RB_COLOR(parent, field) = RB_BLACK; \ 1175*2b15cb3dSCy Schubert if (RB_LEFT(tmp, field)) \ 1176*2b15cb3dSCy Schubert RB_COLOR(RB_LEFT(tmp, field), field) = RB_BLACK;\ 1177*2b15cb3dSCy Schubert RB_ROTATE_RIGHT(head, parent, tmp, field);\ 1178*2b15cb3dSCy Schubert elm = RB_ROOT(head); \ 1179*2b15cb3dSCy Schubert break; \ 1180*2b15cb3dSCy Schubert } \ 1181*2b15cb3dSCy Schubert } \ 1182*2b15cb3dSCy Schubert } \ 1183*2b15cb3dSCy Schubert if (elm) \ 1184*2b15cb3dSCy Schubert RB_COLOR(elm, field) = RB_BLACK; \ 1185*2b15cb3dSCy Schubert } \ 1186*2b15cb3dSCy Schubert \ 1187*2b15cb3dSCy Schubert struct type * \ 1188*2b15cb3dSCy Schubert name##_RB_REMOVE(struct name *head, struct type *elm) \ 1189*2b15cb3dSCy Schubert { \ 1190*2b15cb3dSCy Schubert struct type *child, *parent, *old = elm; \ 1191*2b15cb3dSCy Schubert int color; \ 1192*2b15cb3dSCy Schubert if (RB_LEFT(elm, field) == NULL) \ 1193*2b15cb3dSCy Schubert child = RB_RIGHT(elm, field); \ 1194*2b15cb3dSCy Schubert else if (RB_RIGHT(elm, field) == NULL) \ 1195*2b15cb3dSCy Schubert child = RB_LEFT(elm, field); \ 1196*2b15cb3dSCy Schubert else { \ 1197*2b15cb3dSCy Schubert struct type *left; \ 1198*2b15cb3dSCy Schubert elm = RB_RIGHT(elm, field); \ 1199*2b15cb3dSCy Schubert while ((left = RB_LEFT(elm, field))) \ 1200*2b15cb3dSCy Schubert elm = left; \ 1201*2b15cb3dSCy Schubert child = RB_RIGHT(elm, field); \ 1202*2b15cb3dSCy Schubert parent = RB_PARENT(elm, field); \ 1203*2b15cb3dSCy Schubert color = RB_COLOR(elm, field); \ 1204*2b15cb3dSCy Schubert if (child) \ 1205*2b15cb3dSCy Schubert RB_PARENT(child, field) = parent; \ 1206*2b15cb3dSCy Schubert if (parent) { \ 1207*2b15cb3dSCy Schubert if (RB_LEFT(parent, field) == elm) \ 1208*2b15cb3dSCy Schubert RB_LEFT(parent, field) = child; \ 1209*2b15cb3dSCy Schubert else \ 1210*2b15cb3dSCy Schubert RB_RIGHT(parent, field) = child; \ 1211*2b15cb3dSCy Schubert RB_AUGMENT(parent); \ 1212*2b15cb3dSCy Schubert } else \ 1213*2b15cb3dSCy Schubert RB_ROOT(head) = child; \ 1214*2b15cb3dSCy Schubert if (RB_PARENT(elm, field) == old) \ 1215*2b15cb3dSCy Schubert parent = elm; \ 1216*2b15cb3dSCy Schubert (elm)->field = (old)->field; \ 1217*2b15cb3dSCy Schubert if (RB_PARENT(old, field)) { \ 1218*2b15cb3dSCy Schubert if (RB_LEFT(RB_PARENT(old, field), field) == old)\ 1219*2b15cb3dSCy Schubert RB_LEFT(RB_PARENT(old, field), field) = elm;\ 1220*2b15cb3dSCy Schubert else \ 1221*2b15cb3dSCy Schubert RB_RIGHT(RB_PARENT(old, field), field) = elm;\ 1222*2b15cb3dSCy Schubert RB_AUGMENT(RB_PARENT(old, field)); \ 1223*2b15cb3dSCy Schubert } else \ 1224*2b15cb3dSCy Schubert RB_ROOT(head) = elm; \ 1225*2b15cb3dSCy Schubert RB_PARENT(RB_LEFT(old, field), field) = elm; \ 1226*2b15cb3dSCy Schubert if (RB_RIGHT(old, field)) \ 1227*2b15cb3dSCy Schubert RB_PARENT(RB_RIGHT(old, field), field) = elm; \ 1228*2b15cb3dSCy Schubert if (parent) { \ 1229*2b15cb3dSCy Schubert left = parent; \ 1230*2b15cb3dSCy Schubert do { \ 1231*2b15cb3dSCy Schubert RB_AUGMENT(left); \ 1232*2b15cb3dSCy Schubert } while ((left = RB_PARENT(left, field))); \ 1233*2b15cb3dSCy Schubert } \ 1234*2b15cb3dSCy Schubert goto color; \ 1235*2b15cb3dSCy Schubert } \ 1236*2b15cb3dSCy Schubert parent = RB_PARENT(elm, field); \ 1237*2b15cb3dSCy Schubert color = RB_COLOR(elm, field); \ 1238*2b15cb3dSCy Schubert if (child) \ 1239*2b15cb3dSCy Schubert RB_PARENT(child, field) = parent; \ 1240*2b15cb3dSCy Schubert if (parent) { \ 1241*2b15cb3dSCy Schubert if (RB_LEFT(parent, field) == elm) \ 1242*2b15cb3dSCy Schubert RB_LEFT(parent, field) = child; \ 1243*2b15cb3dSCy Schubert else \ 1244*2b15cb3dSCy Schubert RB_RIGHT(parent, field) = child; \ 1245*2b15cb3dSCy Schubert RB_AUGMENT(parent); \ 1246*2b15cb3dSCy Schubert } else \ 1247*2b15cb3dSCy Schubert RB_ROOT(head) = child; \ 1248*2b15cb3dSCy Schubert color: \ 1249*2b15cb3dSCy Schubert if (color == RB_BLACK) \ 1250*2b15cb3dSCy Schubert name##_RB_REMOVE_COLOR(head, parent, child); \ 1251*2b15cb3dSCy Schubert return (old); \ 1252*2b15cb3dSCy Schubert } \ 1253*2b15cb3dSCy Schubert \ 1254*2b15cb3dSCy Schubert /* Inserts a node into the RB tree */ \ 1255*2b15cb3dSCy Schubert struct type * \ 1256*2b15cb3dSCy Schubert name##_RB_INSERT(struct name *head, struct type *elm) \ 1257*2b15cb3dSCy Schubert { \ 1258*2b15cb3dSCy Schubert struct type *tmp; \ 1259*2b15cb3dSCy Schubert struct type *parent = NULL; \ 1260*2b15cb3dSCy Schubert int comp = 0; \ 1261*2b15cb3dSCy Schubert tmp = RB_ROOT(head); \ 1262*2b15cb3dSCy Schubert while (tmp) { \ 1263*2b15cb3dSCy Schubert parent = tmp; \ 1264*2b15cb3dSCy Schubert comp = (cmp)(elm, parent); \ 1265*2b15cb3dSCy Schubert if (comp < 0) \ 1266*2b15cb3dSCy Schubert tmp = RB_LEFT(tmp, field); \ 1267*2b15cb3dSCy Schubert else if (comp > 0) \ 1268*2b15cb3dSCy Schubert tmp = RB_RIGHT(tmp, field); \ 1269*2b15cb3dSCy Schubert else \ 1270*2b15cb3dSCy Schubert return (tmp); \ 1271*2b15cb3dSCy Schubert } \ 1272*2b15cb3dSCy Schubert RB_SET(elm, parent, field); \ 1273*2b15cb3dSCy Schubert if (parent != NULL) { \ 1274*2b15cb3dSCy Schubert if (comp < 0) \ 1275*2b15cb3dSCy Schubert RB_LEFT(parent, field) = elm; \ 1276*2b15cb3dSCy Schubert else \ 1277*2b15cb3dSCy Schubert RB_RIGHT(parent, field) = elm; \ 1278*2b15cb3dSCy Schubert RB_AUGMENT(parent); \ 1279*2b15cb3dSCy Schubert } else \ 1280*2b15cb3dSCy Schubert RB_ROOT(head) = elm; \ 1281*2b15cb3dSCy Schubert name##_RB_INSERT_COLOR(head, elm); \ 1282*2b15cb3dSCy Schubert return (NULL); \ 1283*2b15cb3dSCy Schubert } \ 1284*2b15cb3dSCy Schubert \ 1285*2b15cb3dSCy Schubert /* Finds the node with the same key as elm */ \ 1286*2b15cb3dSCy Schubert struct type * \ 1287*2b15cb3dSCy Schubert name##_RB_FIND(struct name *head, struct type *elm) \ 1288*2b15cb3dSCy Schubert { \ 1289*2b15cb3dSCy Schubert struct type *tmp = RB_ROOT(head); \ 1290*2b15cb3dSCy Schubert int comp; \ 1291*2b15cb3dSCy Schubert while (tmp) { \ 1292*2b15cb3dSCy Schubert comp = cmp(elm, tmp); \ 1293*2b15cb3dSCy Schubert if (comp < 0) \ 1294*2b15cb3dSCy Schubert tmp = RB_LEFT(tmp, field); \ 1295*2b15cb3dSCy Schubert else if (comp > 0) \ 1296*2b15cb3dSCy Schubert tmp = RB_RIGHT(tmp, field); \ 1297*2b15cb3dSCy Schubert else \ 1298*2b15cb3dSCy Schubert return (tmp); \ 1299*2b15cb3dSCy Schubert } \ 1300*2b15cb3dSCy Schubert return (NULL); \ 1301*2b15cb3dSCy Schubert } \ 1302*2b15cb3dSCy Schubert \ 1303*2b15cb3dSCy Schubert struct type * \ 1304*2b15cb3dSCy Schubert name##_RB_NEXT(struct type *elm) \ 1305*2b15cb3dSCy Schubert { \ 1306*2b15cb3dSCy Schubert if (RB_RIGHT(elm, field)) { \ 1307*2b15cb3dSCy Schubert elm = RB_RIGHT(elm, field); \ 1308*2b15cb3dSCy Schubert while (RB_LEFT(elm, field)) \ 1309*2b15cb3dSCy Schubert elm = RB_LEFT(elm, field); \ 1310*2b15cb3dSCy Schubert } else { \ 1311*2b15cb3dSCy Schubert if (RB_PARENT(elm, field) && \ 1312*2b15cb3dSCy Schubert (elm == RB_LEFT(RB_PARENT(elm, field), field))) \ 1313*2b15cb3dSCy Schubert elm = RB_PARENT(elm, field); \ 1314*2b15cb3dSCy Schubert else { \ 1315*2b15cb3dSCy Schubert while (RB_PARENT(elm, field) && \ 1316*2b15cb3dSCy Schubert (elm == RB_RIGHT(RB_PARENT(elm, field), field)))\ 1317*2b15cb3dSCy Schubert elm = RB_PARENT(elm, field); \ 1318*2b15cb3dSCy Schubert elm = RB_PARENT(elm, field); \ 1319*2b15cb3dSCy Schubert } \ 1320*2b15cb3dSCy Schubert } \ 1321*2b15cb3dSCy Schubert return (elm); \ 1322*2b15cb3dSCy Schubert } \ 1323*2b15cb3dSCy Schubert \ 1324*2b15cb3dSCy Schubert struct type * \ 1325*2b15cb3dSCy Schubert name##_RB_MINMAX(struct name *head, int val) \ 1326*2b15cb3dSCy Schubert { \ 1327*2b15cb3dSCy Schubert struct type *tmp = RB_ROOT(head); \ 1328*2b15cb3dSCy Schubert struct type *parent = NULL; \ 1329*2b15cb3dSCy Schubert while (tmp) { \ 1330*2b15cb3dSCy Schubert parent = tmp; \ 1331*2b15cb3dSCy Schubert if (val < 0) \ 1332*2b15cb3dSCy Schubert tmp = RB_LEFT(tmp, field); \ 1333*2b15cb3dSCy Schubert else \ 1334*2b15cb3dSCy Schubert tmp = RB_RIGHT(tmp, field); \ 1335*2b15cb3dSCy Schubert } \ 1336*2b15cb3dSCy Schubert return (parent); \ 1337*2b15cb3dSCy Schubert } 1338*2b15cb3dSCy Schubert 1339*2b15cb3dSCy Schubert #define RB_NEGINF -1 1340*2b15cb3dSCy Schubert #define RB_INF 1 1341*2b15cb3dSCy Schubert 1342*2b15cb3dSCy Schubert #define RB_INSERT(name, x, y) name##_RB_INSERT(x, y) 1343*2b15cb3dSCy Schubert #define RB_REMOVE(name, x, y) name##_RB_REMOVE(x, y) 1344*2b15cb3dSCy Schubert #define RB_FIND(name, x, y) name##_RB_FIND(x, y) 1345*2b15cb3dSCy Schubert #define RB_NEXT(name, x, y) name##_RB_NEXT(y) 1346*2b15cb3dSCy Schubert #define RB_MIN(name, x) name##_RB_MINMAX(x, RB_NEGINF) 1347*2b15cb3dSCy Schubert #define RB_MAX(name, x) name##_RB_MINMAX(x, RB_INF) 1348*2b15cb3dSCy Schubert 1349*2b15cb3dSCy Schubert #define RB_FOREACH(x, name, head) \ 1350*2b15cb3dSCy Schubert for ((x) = RB_MIN(name, head); \ 1351*2b15cb3dSCy Schubert (x) != NULL; \ 1352*2b15cb3dSCy Schubert (x) = name##_RB_NEXT(x)) 1353*2b15cb3dSCy Schubert 1354*2b15cb3dSCy Schubert #endif /* _SYS_TREE_H_ */ 1355