xref: /openbmc/u-boot/include/linux/rbtree.h (revision 9dd228b5e702edb3295fe5cfee5e46e87233dc72)
17ba890bfSKyungmin Park /*
27ba890bfSKyungmin Park   Red Black Trees
37ba890bfSKyungmin Park   (C) 1999  Andrea Arcangeli <andrea@suse.de>
47ba890bfSKyungmin Park 
51a459660SWolfgang Denk  * SPDX-License-Identifier:	GPL-2.0+
67ba890bfSKyungmin Park 
77ba890bfSKyungmin Park   linux/include/linux/rbtree.h
87ba890bfSKyungmin Park 
97ba890bfSKyungmin Park   To use rbtrees you'll have to implement your own insert and search cores.
107ba890bfSKyungmin Park   This will avoid us to use callbacks and to drop drammatically performances.
117ba890bfSKyungmin Park   I know it's not the cleaner way,  but in C (not in C++) to get
127ba890bfSKyungmin Park   performances and genericity...
137ba890bfSKyungmin Park 
14*9dd228b5SHeiko Schocher   See Documentation/rbtree.txt for documentation and samples.
157ba890bfSKyungmin Park */
167ba890bfSKyungmin Park 
177ba890bfSKyungmin Park #ifndef	_LINUX_RBTREE_H
187ba890bfSKyungmin Park #define	_LINUX_RBTREE_H
197ba890bfSKyungmin Park 
20*9dd228b5SHeiko Schocher #define __UBOOT__
21*9dd228b5SHeiko Schocher #ifndef __UBOOT__
22*9dd228b5SHeiko Schocher #include <linux/kernel.h>
23*9dd228b5SHeiko Schocher #endif
247ba890bfSKyungmin Park #include <linux/stddef.h>
257ba890bfSKyungmin Park 
26*9dd228b5SHeiko Schocher struct rb_node {
27*9dd228b5SHeiko Schocher 	unsigned long  __rb_parent_color;
287ba890bfSKyungmin Park 	struct rb_node *rb_right;
297ba890bfSKyungmin Park 	struct rb_node *rb_left;
307ba890bfSKyungmin Park } __attribute__((aligned(sizeof(long))));
317ba890bfSKyungmin Park     /* The alignment might seem pointless, but allegedly CRIS needs it */
327ba890bfSKyungmin Park 
33*9dd228b5SHeiko Schocher struct rb_root {
347ba890bfSKyungmin Park 	struct rb_node *rb_node;
357ba890bfSKyungmin Park };
367ba890bfSKyungmin Park 
377ba890bfSKyungmin Park 
38*9dd228b5SHeiko Schocher #define rb_parent(r)   ((struct rb_node *)((r)->__rb_parent_color & ~3))
397ba890bfSKyungmin Park 
407ba890bfSKyungmin Park #define RB_ROOT	(struct rb_root) { NULL, }
417ba890bfSKyungmin Park #define	rb_entry(ptr, type, member) container_of(ptr, type, member)
427ba890bfSKyungmin Park 
437ba890bfSKyungmin Park #define RB_EMPTY_ROOT(root)  ((root)->rb_node == NULL)
44*9dd228b5SHeiko Schocher 
45*9dd228b5SHeiko Schocher /* 'empty' nodes are nodes that are known not to be inserted in an rbree */
46*9dd228b5SHeiko Schocher #define RB_EMPTY_NODE(node)  \
47*9dd228b5SHeiko Schocher 	((node)->__rb_parent_color == (unsigned long)(node))
48*9dd228b5SHeiko Schocher #define RB_CLEAR_NODE(node)  \
49*9dd228b5SHeiko Schocher 	((node)->__rb_parent_color = (unsigned long)(node))
50*9dd228b5SHeiko Schocher 
517ba890bfSKyungmin Park 
527ba890bfSKyungmin Park extern void rb_insert_color(struct rb_node *, struct rb_root *);
537ba890bfSKyungmin Park extern void rb_erase(struct rb_node *, struct rb_root *);
547ba890bfSKyungmin Park 
55*9dd228b5SHeiko Schocher 
567ba890bfSKyungmin Park /* Find logical next and previous nodes in a tree */
57*9dd228b5SHeiko Schocher extern struct rb_node *rb_next(const struct rb_node *);
58*9dd228b5SHeiko Schocher extern struct rb_node *rb_prev(const struct rb_node *);
59*9dd228b5SHeiko Schocher extern struct rb_node *rb_first(const struct rb_root *);
60*9dd228b5SHeiko Schocher extern struct rb_node *rb_last(const struct rb_root *);
61*9dd228b5SHeiko Schocher 
62*9dd228b5SHeiko Schocher /* Postorder iteration - always visit the parent after its children */
63*9dd228b5SHeiko Schocher extern struct rb_node *rb_first_postorder(const struct rb_root *);
64*9dd228b5SHeiko Schocher extern struct rb_node *rb_next_postorder(const struct rb_node *);
657ba890bfSKyungmin Park 
667ba890bfSKyungmin Park /* Fast replacement of a single node without remove/rebalance/add/rebalance */
677ba890bfSKyungmin Park extern void rb_replace_node(struct rb_node *victim, struct rb_node *new,
687ba890bfSKyungmin Park 			    struct rb_root *root);
697ba890bfSKyungmin Park 
707ba890bfSKyungmin Park static inline void rb_link_node(struct rb_node * node, struct rb_node * parent,
717ba890bfSKyungmin Park 				struct rb_node ** rb_link)
727ba890bfSKyungmin Park {
73*9dd228b5SHeiko Schocher 	node->__rb_parent_color = (unsigned long)parent;
747ba890bfSKyungmin Park 	node->rb_left = node->rb_right = NULL;
757ba890bfSKyungmin Park 
767ba890bfSKyungmin Park 	*rb_link = node;
777ba890bfSKyungmin Park }
787ba890bfSKyungmin Park 
79*9dd228b5SHeiko Schocher #define rb_entry_safe(ptr, type, member) \
80*9dd228b5SHeiko Schocher 	({ typeof(ptr) ____ptr = (ptr); \
81*9dd228b5SHeiko Schocher 	   ____ptr ? rb_entry(____ptr, type, member) : NULL; \
82*9dd228b5SHeiko Schocher 	})
83*9dd228b5SHeiko Schocher 
84*9dd228b5SHeiko Schocher /**
85*9dd228b5SHeiko Schocher  * rbtree_postorder_for_each_entry_safe - iterate over rb_root in post order of
86*9dd228b5SHeiko Schocher  * given type safe against removal of rb_node entry
87*9dd228b5SHeiko Schocher  *
88*9dd228b5SHeiko Schocher  * @pos:	the 'type *' to use as a loop cursor.
89*9dd228b5SHeiko Schocher  * @n:		another 'type *' to use as temporary storage
90*9dd228b5SHeiko Schocher  * @root:	'rb_root *' of the rbtree.
91*9dd228b5SHeiko Schocher  * @field:	the name of the rb_node field within 'type'.
92*9dd228b5SHeiko Schocher  */
93*9dd228b5SHeiko Schocher #define rbtree_postorder_for_each_entry_safe(pos, n, root, field) \
94*9dd228b5SHeiko Schocher 	for (pos = rb_entry_safe(rb_first_postorder(root), typeof(*pos), field); \
95*9dd228b5SHeiko Schocher 	     pos && ({ n = rb_entry_safe(rb_next_postorder(&pos->field), \
96*9dd228b5SHeiko Schocher 			typeof(*pos), field); 1; }); \
97*9dd228b5SHeiko Schocher 	     pos = n)
98*9dd228b5SHeiko Schocher 
997ba890bfSKyungmin Park #endif	/* _LINUX_RBTREE_H */
100