 0d99d37a82
			
		
	
	
		0d99d37a82
		
	
	
	
	
		
			
			Copy and simplify the Linux kernel's interval_tree_generic.h, instantiating for uint64_t. Reviewed-by: Alex Bennée <alex.bennee@linaro.org> Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
		
			
				
	
	
		
			100 lines
		
	
	
		
			2.5 KiB
		
	
	
	
		
			C
		
	
	
	
	
	
			
		
		
	
	
			100 lines
		
	
	
		
			2.5 KiB
		
	
	
	
		
			C
		
	
	
	
	
	
| /* SPDX-License-Identifier: GPL-2.0-or-later */
 | |
| /*
 | |
|  * Interval trees.
 | |
|  *
 | |
|  * Derived from include/linux/interval_tree.h and its dependencies.
 | |
|  */
 | |
| 
 | |
| #ifndef QEMU_INTERVAL_TREE_H
 | |
| #define QEMU_INTERVAL_TREE_H
 | |
| 
 | |
| /*
 | |
|  * For now, don't expose Linux Red-Black Trees separately, but retain the
 | |
|  * separate type definitions to keep the implementation sane, and allow
 | |
|  * the possibility of disentangling them later.
 | |
|  */
 | |
| typedef struct RBNode
 | |
| {
 | |
|     /* Encodes parent with color in the lsb. */
 | |
|     uintptr_t rb_parent_color;
 | |
|     struct RBNode *rb_right;
 | |
|     struct RBNode *rb_left;
 | |
| } RBNode;
 | |
| 
 | |
| typedef struct RBRoot
 | |
| {
 | |
|     RBNode *rb_node;
 | |
| } RBRoot;
 | |
| 
 | |
| typedef struct RBRootLeftCached {
 | |
|     RBRoot rb_root;
 | |
|     RBNode *rb_leftmost;
 | |
| } RBRootLeftCached;
 | |
| 
 | |
| typedef struct IntervalTreeNode
 | |
| {
 | |
|     RBNode rb;
 | |
| 
 | |
|     uint64_t start;    /* Start of interval */
 | |
|     uint64_t last;     /* Last location _in_ interval */
 | |
|     uint64_t subtree_last;
 | |
| } IntervalTreeNode;
 | |
| 
 | |
| typedef RBRootLeftCached IntervalTreeRoot;
 | |
| 
 | |
| /**
 | |
|  * interval_tree_is_empty
 | |
|  * @root: root of the tree.
 | |
|  *
 | |
|  * Returns true if the tree contains no nodes.
 | |
|  */
 | |
| static inline bool interval_tree_is_empty(const IntervalTreeRoot *root)
 | |
| {
 | |
|     return root->rb_root.rb_node == NULL;
 | |
| }
 | |
| 
 | |
| /**
 | |
|  * interval_tree_insert
 | |
|  * @node: node to insert,
 | |
|  * @root: root of the tree.
 | |
|  *
 | |
|  * Insert @node into @root, and rebalance.
 | |
|  */
 | |
| void interval_tree_insert(IntervalTreeNode *node, IntervalTreeRoot *root);
 | |
| 
 | |
| /**
 | |
|  * interval_tree_remove
 | |
|  * @node: node to remove,
 | |
|  * @root: root of the tree.
 | |
|  *
 | |
|  * Remove @node from @root, and rebalance.
 | |
|  */
 | |
| void interval_tree_remove(IntervalTreeNode *node, IntervalTreeRoot *root);
 | |
| 
 | |
| /**
 | |
|  * interval_tree_iter_first:
 | |
|  * @root: root of the tree,
 | |
|  * @start, @last: the inclusive interval [start, last].
 | |
|  *
 | |
|  * Locate the "first" of a set of nodes within the tree at @root
 | |
|  * that overlap the interval, where "first" is sorted by start.
 | |
|  * Returns NULL if no overlap found.
 | |
|  */
 | |
| IntervalTreeNode *interval_tree_iter_first(IntervalTreeRoot *root,
 | |
|                                            uint64_t start, uint64_t last);
 | |
| 
 | |
| /**
 | |
|  * interval_tree_iter_next:
 | |
|  * @node: previous search result
 | |
|  * @start, @last: the inclusive interval [start, last].
 | |
|  *
 | |
|  * Locate the "next" of a set of nodes within the tree that overlap the
 | |
|  * interval; @next is the result of a previous call to
 | |
|  * interval_tree_iter_{first,next}.  Returns NULL if @next was the last
 | |
|  * node in the set.
 | |
|  */
 | |
| IntervalTreeNode *interval_tree_iter_next(IntervalTreeNode *node,
 | |
|                                           uint64_t start, uint64_t last);
 | |
| 
 | |
| #endif /* QEMU_INTERVAL_TREE_H */
 |