LCOV - code coverage report
Current view: top level - lib/util - rbtree.c (source / functions) Hit Total Coverage
Test: coverage report for smb2.twrp.listdir_fix f886ca1c Lines: 201 234 85.9 %
Date: 2023-11-07 19:11:32 Functions: 10 13 76.9 %

          Line data    Source code
       1             : /*
       2             :   Red Black Trees
       3             :   (C) 1999  Andrea Arcangeli <andrea@suse.de>
       4             :   (C) 2002  David Woodhouse <dwmw2@infradead.org>
       5             :   
       6             :   This program is free software; you can redistribute it and/or modify
       7             :   it under the terms of the GNU General Public License as published by
       8             :   the Free Software Foundation; either version 2 of the License, or
       9             :   (at your option) any later version.
      10             : 
      11             :   This program is distributed in the hope that it will be useful,
      12             :   but WITHOUT ANY WARRANTY; without even the implied warranty of
      13             :   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
      14             :   GNU General Public License for more details.
      15             : 
      16             :   You should have received a copy of the GNU General Public License
      17             :   along with this program; if not, write to the Free Software
      18             :   Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
      19             : 
      20             :   linux/lib/rbtree.c
      21             : */
      22             : 
      23             : #include "replace.h"
      24             : #include "rbtree.h"
      25             : #include "fault.h"
      26             : 
      27             : #define RB_RED          0
      28             : #define RB_BLACK        1
      29             : 
      30             : #define rb_parent(r)   ((struct rb_node *)((r)->rb_parent_color & ~3))
      31             : #define rb_color(r)   ((r)->rb_parent_color & 1)
      32             : #define rb_is_red(r)   (!rb_color(r))
      33             : #define rb_is_black(r) rb_color(r)
      34             : #define rb_set_red(r)  do { (r)->rb_parent_color &= ~1; } while (0)
      35             : #define rb_set_black(r)  do { (r)->rb_parent_color |= 1; } while (0)
      36             : 
      37     5178690 : static void rb_set_parent(struct rb_node *rb, struct rb_node *p)
      38             : {
      39     5178690 :         rb->rb_parent_color = (rb->rb_parent_color & 3) | (unsigned long)p;
      40     5123915 : }
      41       28280 : static void rb_set_color(struct rb_node *rb, int color)
      42             : {
      43       28280 :         rb->rb_parent_color = (rb->rb_parent_color & ~1) | color;
      44       27960 : }
      45             : 
      46             : #define RB_EMPTY_ROOT(root)     ((root)->rb_node == NULL)
      47             : #define RB_EMPTY_NODE(node)     (rb_parent(node) == node)
      48             : #define RB_CLEAR_NODE(node)     (rb_set_parent(node, node))
      49             : 
      50     1206340 : static void __rb_rotate_left(struct rb_node *node, struct rb_root *root)
      51             : {
      52     1206340 :         struct rb_node *right = node->rb_right;
      53     1206340 :         struct rb_node *parent = rb_parent(node);
      54             : 
      55     1206340 :         if ((node->rb_right = right->rb_left))
      56      277566 :                 rb_set_parent(right->rb_left, node);
      57     1206340 :         right->rb_left = node;
      58             : 
      59     1206340 :         rb_set_parent(right, parent);
      60             : 
      61     1206340 :         if (parent)
      62             :         {
      63     1053609 :                 if (node == parent->rb_left)
      64      671357 :                         parent->rb_left = right;
      65             :                 else
      66      382252 :                         parent->rb_right = right;
      67             :         }
      68             :         else
      69      152731 :                 root->rb_node = right;
      70     1206340 :         rb_set_parent(node, right);
      71     1206340 : }
      72             : 
      73      978843 : static void __rb_rotate_right(struct rb_node *node, struct rb_root *root)
      74             : {
      75      978843 :         struct rb_node *left = node->rb_left;
      76      978843 :         struct rb_node *parent = rb_parent(node);
      77             : 
      78      978843 :         if ((node->rb_left = left->rb_right))
      79      211661 :                 rb_set_parent(left->rb_right, node);
      80      978843 :         left->rb_right = node;
      81             : 
      82      978843 :         rb_set_parent(left, parent);
      83             : 
      84      978843 :         if (parent)
      85             :         {
      86      905814 :                 if (node == parent->rb_right)
      87      637125 :                         parent->rb_right = left;
      88             :                 else
      89      268689 :                         parent->rb_left = left;
      90             :         }
      91             :         else
      92       73029 :                 root->rb_node = left;
      93      978843 :         rb_set_parent(node, left);
      94      978843 : }
      95             : 
      96     4250925 : void rb_insert_color(struct rb_node *node, struct rb_root *root)
      97             : {
      98       48656 :         struct rb_node *parent, *gparent;
      99             : 
     100     7131349 :         while ((parent = rb_parent(node)) && rb_is_red(parent))
     101             :         {
     102     2880424 :                 gparent = rb_parent(parent);
     103             : 
     104     2880424 :                 if (parent == gparent->rb_left)
     105             :                 {
     106             :                         {
     107     1295448 :                                 register struct rb_node *uncle = gparent->rb_right;
     108     1295448 :                                 if (uncle && rb_is_red(uncle))
     109             :                                 {
     110      602676 :                                         rb_set_black(uncle);
     111      602676 :                                         rb_set_black(parent);
     112      602676 :                                         rb_set_red(gparent);
     113      602676 :                                         node = gparent;
     114      602676 :                                         continue;
     115             :                                 }
     116             :                         }
     117             : 
     118      692772 :                         if (parent->rb_right == node)
     119             :                         {
     120        4082 :                                 register struct rb_node *tmp;
     121      422130 :                                 __rb_rotate_left(parent, root);
     122      422130 :                                 tmp = parent;
     123      422130 :                                 parent = node;
     124      422130 :                                 node = tmp;
     125             :                         }
     126             : 
     127      692772 :                         rb_set_black(parent);
     128      692772 :                         rb_set_red(gparent);
     129      692772 :                         __rb_rotate_right(gparent, root);
     130             :                 } else {
     131             :                         {
     132     1584976 :                                 register struct rb_node *uncle = gparent->rb_left;
     133     1584976 :                                 if (uncle && rb_is_red(uncle))
     134             :                                 {
     135      833005 :                                         rb_set_black(uncle);
     136      833005 :                                         rb_set_black(parent);
     137      833005 :                                         rb_set_red(gparent);
     138      833005 :                                         node = gparent;
     139      833005 :                                         continue;
     140             :                                 }
     141             :                         }
     142             : 
     143      751971 :                         if (parent->rb_left == node)
     144             :                         {
     145        4755 :                                 register struct rb_node *tmp;
     146      257141 :                                 __rb_rotate_right(parent, root);
     147      257141 :                                 tmp = parent;
     148      257141 :                                 parent = node;
     149      257141 :                                 node = tmp;
     150             :                         }
     151             : 
     152      751971 :                         rb_set_black(parent);
     153      751971 :                         rb_set_red(gparent);
     154      751971 :                         __rb_rotate_left(gparent, root);
     155             :                 }
     156             :         }
     157             : 
     158     4250925 :         rb_set_black(root->rb_node);
     159     4250925 : }
     160             : 
     161      202189 : static void __rb_erase_color(struct rb_node *node, struct rb_node *parent,
     162             :                              struct rb_root *root)
     163             : {
     164        2540 :         struct rb_node *other;
     165             : 
     166      268595 :         while ((!node || rb_is_black(node)) && node != root->rb_node)
     167             :         {
     168       94686 :                 if (parent->rb_left == node)
     169             :                 {
     170       49759 :                         other = parent->rb_right;
     171       49759 :                         if (other == NULL) {
     172             :                                 /* we should never get here */
     173           0 :                                 smb_panic("corrupted rb tree");
     174             :                                 /* satisfy static checkers */
     175             :                                 return;
     176             :                         }
     177       49759 :                         if (rb_is_red(other))
     178             :                         {
     179        8254 :                                 rb_set_black(other);
     180        8254 :                                 rb_set_red(parent);
     181        8254 :                                 __rb_rotate_left(parent, root);
     182        8254 :                                 other = parent->rb_right;
     183             :                         }
     184       49759 :                         if ((!other->rb_left || rb_is_black(other->rb_left)) &&
     185       39565 :                             (!other->rb_right || rb_is_black(other->rb_right)))
     186             :                         {
     187       34086 :                                 rb_set_red(other);
     188       34086 :                                 node = parent;
     189       34086 :                                 parent = rb_parent(node);
     190             :                         }
     191             :                         else
     192             :                         {
     193       15673 :                                 if (!other->rb_right || rb_is_black(other->rb_right))
     194             :                                 {
     195          52 :                                         struct rb_node *o_left;
     196        7646 :                                         if ((o_left = other->rb_left))
     197        7646 :                                                 rb_set_black(o_left);
     198        7646 :                                         rb_set_red(other);
     199        7646 :                                         __rb_rotate_right(other, root);
     200        7646 :                                         other = parent->rb_right;
     201             :                                 }
     202       15673 :                                 rb_set_color(other, rb_color(parent));
     203       15673 :                                 rb_set_black(parent);
     204       15673 :                                 if (other->rb_right)
     205       15673 :                                         rb_set_black(other->rb_right);
     206       15673 :                                 __rb_rotate_left(parent, root);
     207       15673 :                                 node = root->rb_node;
     208       15673 :                                 break;
     209             :                         }
     210             :                 }
     211             :                 else
     212             :                 {
     213       44927 :                         other = parent->rb_left;
     214       44927 :                         if (rb_is_red(other))
     215             :                         {
     216        8677 :                                 rb_set_black(other);
     217        8677 :                                 rb_set_red(parent);
     218        8677 :                                 __rb_rotate_right(parent, root);
     219        8677 :                                 other = parent->rb_left;
     220             :                         }
     221       44927 :                         if ((!other->rb_left || rb_is_black(other->rb_left)) &&
     222       40632 :                             (!other->rb_right || rb_is_black(other->rb_right)))
     223             :                         {
     224       32320 :                                 rb_set_red(other);
     225       32320 :                                 node = parent;
     226       32320 :                                 parent = rb_parent(node);
     227             :                         }
     228             :                         else
     229             :                         {
     230       12607 :                                 if (!other->rb_left || rb_is_black(other->rb_left))
     231             :                                 {
     232          74 :                                         register struct rb_node *o_right;
     233        8312 :                                         if ((o_right = other->rb_right))
     234        8312 :                                                 rb_set_black(o_right);
     235        8312 :                                         rb_set_red(other);
     236        8312 :                                         __rb_rotate_left(other, root);
     237        8312 :                                         other = parent->rb_left;
     238             :                                 }
     239       12607 :                                 rb_set_color(other, rb_color(parent));
     240       12607 :                                 rb_set_black(parent);
     241       12607 :                                 if (other->rb_left)
     242       12607 :                                         rb_set_black(other->rb_left);
     243       12607 :                                 __rb_rotate_right(parent, root);
     244       12607 :                                 node = root->rb_node;
     245       12607 :                                 break;
     246             :                         }
     247             :                 }
     248             :         }
     249      202189 :         if (node)
     250      129096 :                 rb_set_black(node);
     251             : }
     252             : 
     253      739632 : void rb_erase(struct rb_node *node, struct rb_root *root)
     254             : {
     255        4288 :         struct rb_node *child, *parent;
     256        4288 :         int color;
     257             : 
     258      739632 :         if (!node->rb_left)
     259      528955 :                 child = node->rb_right;
     260      210677 :         else if (!node->rb_right)
     261       21942 :                 child = node->rb_left;
     262             :         else
     263             :         {
     264      188109 :                 struct rb_node *old = node, *left;
     265             : 
     266      188109 :                 node = node->rb_right;
     267      308104 :                 while ((left = node->rb_left) != NULL)
     268      119236 :                         node = left;
     269      188514 :                 child = node->rb_right;
     270      188514 :                 parent = rb_parent(node);
     271      188514 :                 color = rb_color(node);
     272             : 
     273      188514 :                 if (child)
     274       13726 :                         rb_set_parent(child, parent);
     275      188514 :                 if (parent == old) {
     276      124569 :                         parent->rb_right = child;
     277      124569 :                         parent = node;
     278             :                 } else
     279       63945 :                         parent->rb_left = child;
     280             : 
     281      188514 :                 node->rb_parent_color = old->rb_parent_color;
     282      188514 :                 node->rb_right = old->rb_right;
     283      188514 :                 node->rb_left = old->rb_left;
     284             : 
     285      188514 :                 if (rb_parent(old))
     286             :                 {
     287      181979 :                         if (rb_parent(old)->rb_left == old)
     288       48804 :                                 rb_parent(old)->rb_left = node;
     289             :                         else
     290      133175 :                                 rb_parent(old)->rb_right = node;
     291             :                 } else
     292        6535 :                         root->rb_node = node;
     293             : 
     294      188514 :                 rb_set_parent(old->rb_left, node);
     295      188514 :                 if (old->rb_right)
     296       69126 :                         rb_set_parent(old->rb_right, node);
     297      188514 :                 goto color;
     298             :         }
     299             : 
     300      551118 :         parent = rb_parent(node);
     301      551118 :         color = rb_color(node);
     302             : 
     303      551118 :         if (child)
     304       47731 :                 rb_set_parent(child, parent);
     305      551118 :         if (parent)
     306             :         {
     307      476683 :                 if (parent->rb_left == node)
     308       85356 :                         parent->rb_left = child;
     309             :                 else
     310      391327 :                         parent->rb_right = child;
     311             :         }
     312             :         else
     313       74435 :                 root->rb_node = child;
     314             : 
     315      739632 :  color:
     316      739632 :         if (color == RB_BLACK)
     317      202189 :                 __rb_erase_color(child, parent, root);
     318      739632 : }
     319             : 
     320             : /*
     321             :  * This function returns the first node (in sort order) of the tree.
     322             :  */
     323           0 : struct rb_node *rb_first(struct rb_root *root)
     324             : {
     325           0 :         struct rb_node  *n;
     326             : 
     327           0 :         n = root->rb_node;
     328           0 :         if (!n)
     329           0 :                 return NULL;
     330           0 :         while (n->rb_left)
     331           0 :                 n = n->rb_left;
     332           0 :         return n;
     333             : }
     334             : 
     335           0 : struct rb_node *rb_last(struct rb_root *root)
     336             : {
     337           0 :         struct rb_node  *n;
     338             : 
     339           0 :         n = root->rb_node;
     340           0 :         if (!n)
     341           0 :                 return NULL;
     342           0 :         while (n->rb_right)
     343           0 :                 n = n->rb_right;
     344           0 :         return n;
     345             : }
     346             : 
     347       40623 : struct rb_node *rb_next(struct rb_node *node)
     348             : {
     349           1 :         struct rb_node *parent;
     350             : 
     351       40623 :         if (rb_parent(node) == node)
     352           0 :                 return NULL;
     353             : 
     354             :         /* If we have a right-hand child, go down and then left as far
     355             :            as we can. */
     356       40623 :         if (node->rb_right) {
     357       19525 :                 node = node->rb_right; 
     358       19539 :                 while (node->rb_left)
     359          14 :                         node=node->rb_left;
     360       19525 :                 return node;
     361             :         }
     362             : 
     363             :         /* No right-hand children.  Everything down and left is
     364             :            smaller than us, so any 'next' node must be in the general
     365             :            direction of our parent. Go up the tree; any time the
     366             :            ancestor is a right-hand child of its parent, keep going
     367             :            up. First time it's a left-hand child of its parent, said
     368             :            parent is our 'next' node. */
     369       42608 :         while ((parent = rb_parent(node)) && node == parent->rb_right)
     370       21510 :                 node = parent;
     371             : 
     372       21097 :         return parent;
     373             : }
     374             : 
     375       21049 : struct rb_node *rb_prev(struct rb_node *node)
     376             : {
     377           1 :         struct rb_node *parent;
     378             : 
     379       21049 :         if (rb_parent(node) == node)
     380           0 :                 return NULL;
     381             : 
     382             :         /* If we have a left-hand child, go down and then right as far
     383             :            as we can. */
     384       21049 :         if (node->rb_left) {
     385         156 :                 node = node->rb_left; 
     386         156 :                 while (node->rb_right)
     387           0 :                         node=node->rb_right;
     388         156 :                 return node;
     389             :         }
     390             : 
     391             :         /* No left-hand children. Go up till we find an ancestor which
     392             :            is a right-hand child of its parent */
     393       20944 :         while ((parent = rb_parent(node)) && node == parent->rb_left)
     394          51 :                 node = parent;
     395             : 
     396       20892 :         return parent;
     397             : }
     398             : 
     399           0 : void rb_replace_node(struct rb_node *victim, struct rb_node *new_node,
     400             :                      struct rb_root *root)
     401             : {
     402           0 :         struct rb_node *parent = rb_parent(victim);
     403             : 
     404             :         /* Set the surrounding nodes to point to the replacement */
     405           0 :         if (parent) {
     406           0 :                 if (victim == parent->rb_left)
     407           0 :                         parent->rb_left = new_node;
     408             :                 else
     409           0 :                         parent->rb_right = new_node;
     410             :         } else {
     411           0 :                 root->rb_node = new_node;
     412             :         }
     413           0 :         if (victim->rb_left)
     414           0 :                 rb_set_parent(victim->rb_left, new_node);
     415           0 :         if (victim->rb_right)
     416           0 :                 rb_set_parent(victim->rb_right, new_node);
     417             : 
     418             :         /* Copy the pointers/colour from the victim to the replacement */
     419           0 :         *new_node = *victim;
     420           0 : }
     421             : 
     422     4250925 : void rb_link_node(struct rb_node * node, struct rb_node * parent,
     423             :                   struct rb_node ** rb_link)
     424             : {
     425     4250925 :         node->rb_parent_color = (unsigned long )parent;
     426     4250925 :         node->rb_left = node->rb_right = NULL;
     427             : 
     428     4250925 :         *rb_link = node;
     429     4250925 : }

Generated by: LCOV version 1.14