xref: /freebsd/contrib/unbound/util/storage/dnstree.h (revision 865f46b255599c4a645e84a4cbb5ea7abdc0e207)
1b7579f77SDag-Erling Smørgrav /*
2b7579f77SDag-Erling Smørgrav  * util/storage/dnstree.h - support for rbtree types suitable for DNS code.
3b7579f77SDag-Erling Smørgrav  *
4b7579f77SDag-Erling Smørgrav  * Copyright (c) 2008, NLnet Labs. All rights reserved.
5b7579f77SDag-Erling Smørgrav  *
6b7579f77SDag-Erling Smørgrav  * This software is open source.
7b7579f77SDag-Erling Smørgrav  *
8b7579f77SDag-Erling Smørgrav  * Redistribution and use in source and binary forms, with or without
9b7579f77SDag-Erling Smørgrav  * modification, are permitted provided that the following conditions
10b7579f77SDag-Erling Smørgrav  * are met:
11b7579f77SDag-Erling Smørgrav  *
12b7579f77SDag-Erling Smørgrav  * Redistributions of source code must retain the above copyright notice,
13b7579f77SDag-Erling Smørgrav  * this list of conditions and the following disclaimer.
14b7579f77SDag-Erling Smørgrav  *
15b7579f77SDag-Erling Smørgrav  * Redistributions in binary form must reproduce the above copyright notice,
16b7579f77SDag-Erling Smørgrav  * this list of conditions and the following disclaimer in the documentation
17b7579f77SDag-Erling Smørgrav  * and/or other materials provided with the distribution.
18b7579f77SDag-Erling Smørgrav  *
19b7579f77SDag-Erling Smørgrav  * Neither the name of the NLNET LABS nor the names of its contributors may
20b7579f77SDag-Erling Smørgrav  * be used to endorse or promote products derived from this software without
21b7579f77SDag-Erling Smørgrav  * specific prior written permission.
22b7579f77SDag-Erling Smørgrav  *
23b7579f77SDag-Erling Smørgrav  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
2417d15b25SDag-Erling Smørgrav  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
2517d15b25SDag-Erling Smørgrav  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
2617d15b25SDag-Erling Smørgrav  * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
2717d15b25SDag-Erling Smørgrav  * HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
2817d15b25SDag-Erling Smørgrav  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED
2917d15b25SDag-Erling Smørgrav  * TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
3017d15b25SDag-Erling Smørgrav  * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
3117d15b25SDag-Erling Smørgrav  * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
3217d15b25SDag-Erling Smørgrav  * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
3317d15b25SDag-Erling Smørgrav  * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
34b7579f77SDag-Erling Smørgrav  */
35b7579f77SDag-Erling Smørgrav 
36b7579f77SDag-Erling Smørgrav /**
37b7579f77SDag-Erling Smørgrav  * \file
38b7579f77SDag-Erling Smørgrav  *
39b7579f77SDag-Erling Smørgrav  * This file contains structures combining types and functions to
40b7579f77SDag-Erling Smørgrav  * manipulate those structures that help building DNS lookup trees.
41b7579f77SDag-Erling Smørgrav  */
42b7579f77SDag-Erling Smørgrav 
43b7579f77SDag-Erling Smørgrav #ifndef UTIL_STORAGE_DNSTREE_H
44b7579f77SDag-Erling Smørgrav #define UTIL_STORAGE_DNSTREE_H
45b7579f77SDag-Erling Smørgrav #include "util/rbtree.h"
46b7579f77SDag-Erling Smørgrav 
47b7579f77SDag-Erling Smørgrav /**
48b7579f77SDag-Erling Smørgrav  * Tree of domain names.  Sorted first by class then by name.
49b7579f77SDag-Erling Smørgrav  * This is not sorted canonically, but fast.
50b7579f77SDag-Erling Smørgrav  * This can be looked up to obtain a closest encloser parent name.
51b7579f77SDag-Erling Smørgrav  *
523005e0a3SDag-Erling Smørgrav  * The tree itself is a rbtree_type.
53b7579f77SDag-Erling Smørgrav  * This is the element node put as first entry in the client structure.
54b7579f77SDag-Erling Smørgrav  */
55b7579f77SDag-Erling Smørgrav struct name_tree_node {
56b7579f77SDag-Erling Smørgrav 	/** rbtree node, key is this struct : dclass and name */
573005e0a3SDag-Erling Smørgrav 	rbnode_type node;
58b7579f77SDag-Erling Smørgrav 	/** parent in tree */
59b7579f77SDag-Erling Smørgrav 	struct name_tree_node* parent;
60b7579f77SDag-Erling Smørgrav 	/** name in uncompressed wireformat */
61b7579f77SDag-Erling Smørgrav 	uint8_t* name;
62b7579f77SDag-Erling Smørgrav 	/** length of name */
63b7579f77SDag-Erling Smørgrav 	size_t len;
64b7579f77SDag-Erling Smørgrav 	/** labels in name */
65b7579f77SDag-Erling Smørgrav 	int labs;
66b7579f77SDag-Erling Smørgrav 	/** the class of the name (host order) */
67b7579f77SDag-Erling Smørgrav 	uint16_t dclass;
68b7579f77SDag-Erling Smørgrav };
69b7579f77SDag-Erling Smørgrav 
70b7579f77SDag-Erling Smørgrav /**
71b7579f77SDag-Erling Smørgrav  * Tree of IP addresses.  Sorted first by protocol, then by bits.
72b7579f77SDag-Erling Smørgrav  * This can be looked up to obtain the enclosing subnet.
73b7579f77SDag-Erling Smørgrav  *
743005e0a3SDag-Erling Smørgrav  * The tree itself is a rbtree_type.
75b7579f77SDag-Erling Smørgrav  * This is the element node put as first entry in the client structure.
76b7579f77SDag-Erling Smørgrav  */
77b7579f77SDag-Erling Smørgrav struct addr_tree_node {
78b7579f77SDag-Erling Smørgrav 	/** rbtree node, key is this struct : proto and subnet */
793005e0a3SDag-Erling Smørgrav 	rbnode_type node;
80b7579f77SDag-Erling Smørgrav 	/** parent in tree */
81b7579f77SDag-Erling Smørgrav 	struct addr_tree_node* parent;
82b7579f77SDag-Erling Smørgrav 	/** address */
83b7579f77SDag-Erling Smørgrav 	struct sockaddr_storage addr;
84b7579f77SDag-Erling Smørgrav 	/** length of addr */
85b7579f77SDag-Erling Smørgrav 	socklen_t addrlen;
86b7579f77SDag-Erling Smørgrav 	/** netblock size */
87b7579f77SDag-Erling Smørgrav 	int net;
88b7579f77SDag-Erling Smørgrav };
89b7579f77SDag-Erling Smørgrav 
90b7579f77SDag-Erling Smørgrav /**
91b7579f77SDag-Erling Smørgrav  * Init a name tree to be empty
92b7579f77SDag-Erling Smørgrav  * @param tree: to init.
93b7579f77SDag-Erling Smørgrav  */
943005e0a3SDag-Erling Smørgrav void name_tree_init(rbtree_type* tree);
95b7579f77SDag-Erling Smørgrav 
96b7579f77SDag-Erling Smørgrav /**
97b7579f77SDag-Erling Smørgrav  * insert element into name tree.
98b7579f77SDag-Erling Smørgrav  * @param tree: name tree
99b7579f77SDag-Erling Smørgrav  * @param node: node element (at start of a structure that caller
100b7579f77SDag-Erling Smørgrav  *	has allocated).
101b7579f77SDag-Erling Smørgrav  * @param name: name to insert (wireformat)
102b7579f77SDag-Erling Smørgrav  *	this node has been allocated by the caller and it itself inserted.
103b7579f77SDag-Erling Smørgrav  * @param len: length of name
104b7579f77SDag-Erling Smørgrav  * @param labs: labels in name
105b7579f77SDag-Erling Smørgrav  * @param dclass: class of name
106b7579f77SDag-Erling Smørgrav  * @return false on error (duplicate element).
107b7579f77SDag-Erling Smørgrav  */
1083005e0a3SDag-Erling Smørgrav int name_tree_insert(rbtree_type* tree, struct name_tree_node* node,
109b7579f77SDag-Erling Smørgrav 	uint8_t* name, size_t len, int labs, uint16_t dclass);
110b7579f77SDag-Erling Smørgrav 
111b7579f77SDag-Erling Smørgrav /**
112b7579f77SDag-Erling Smørgrav  * Initialize parent pointers in name tree.
113b7579f77SDag-Erling Smørgrav  * Should be performed after insertions are done, before lookups
114b7579f77SDag-Erling Smørgrav  * @param tree: name tree
115b7579f77SDag-Erling Smørgrav  */
1163005e0a3SDag-Erling Smørgrav void name_tree_init_parents(rbtree_type* tree);
117b7579f77SDag-Erling Smørgrav 
118b7579f77SDag-Erling Smørgrav /**
119b7579f77SDag-Erling Smørgrav  * Lookup exact match in name tree
120b7579f77SDag-Erling Smørgrav  * @param tree: name tree
121b7579f77SDag-Erling Smørgrav  * @param name: wireformat name
122b7579f77SDag-Erling Smørgrav  * @param len: length of name
123b7579f77SDag-Erling Smørgrav  * @param labs: labels in name
124b7579f77SDag-Erling Smørgrav  * @param dclass: class of name
125b7579f77SDag-Erling Smørgrav  * @return node or NULL if not found.
126b7579f77SDag-Erling Smørgrav  */
1273005e0a3SDag-Erling Smørgrav struct name_tree_node* name_tree_find(rbtree_type* tree, uint8_t* name,
128b7579f77SDag-Erling Smørgrav 	size_t len, int labs, uint16_t dclass);
129b7579f77SDag-Erling Smørgrav 
130b7579f77SDag-Erling Smørgrav /**
131b7579f77SDag-Erling Smørgrav  * Lookup closest encloser in name tree.
132b7579f77SDag-Erling Smørgrav  * @param tree: name tree
133b7579f77SDag-Erling Smørgrav  * @param name: wireformat name
134b7579f77SDag-Erling Smørgrav  * @param len: length of name
135b7579f77SDag-Erling Smørgrav  * @param labs: labels in name
136b7579f77SDag-Erling Smørgrav  * @param dclass: class of name
137b7579f77SDag-Erling Smørgrav  * @return closest enclosing node (could be equal) or NULL if not found.
138b7579f77SDag-Erling Smørgrav  */
1393005e0a3SDag-Erling Smørgrav struct name_tree_node* name_tree_lookup(rbtree_type* tree, uint8_t* name,
140b7579f77SDag-Erling Smørgrav 	size_t len, int labs, uint16_t dclass);
141b7579f77SDag-Erling Smørgrav 
142b7579f77SDag-Erling Smørgrav /**
143b7579f77SDag-Erling Smørgrav  * Find next root item in name tree.
144b7579f77SDag-Erling Smørgrav  * @param tree: the nametree.
145b7579f77SDag-Erling Smørgrav  * @param dclass: the class to look for next (or higher).
146b7579f77SDag-Erling Smørgrav  * @return false if no classes found, true means class put into c.
147b7579f77SDag-Erling Smørgrav  */
1483005e0a3SDag-Erling Smørgrav int name_tree_next_root(rbtree_type* tree, uint16_t* dclass);
149b7579f77SDag-Erling Smørgrav 
150b7579f77SDag-Erling Smørgrav /**
151b7579f77SDag-Erling Smørgrav  * Init addr tree to be empty.
152b7579f77SDag-Erling Smørgrav  * @param tree: to init.
153b7579f77SDag-Erling Smørgrav  */
1543005e0a3SDag-Erling Smørgrav void addr_tree_init(rbtree_type* tree);
155b7579f77SDag-Erling Smørgrav 
156b7579f77SDag-Erling Smørgrav /**
157*865f46b2SCy Schubert  * Init addr tree to be empty.
158*865f46b2SCy Schubert  * The comparison function to be used is addr_tree_addrport_compare.
159*865f46b2SCy Schubert  * @param tree: to init.
160*865f46b2SCy Schubert  */
161*865f46b2SCy Schubert void addr_tree_addrport_init(rbtree_type* tree);
162*865f46b2SCy Schubert 
163*865f46b2SCy Schubert /**
164b7579f77SDag-Erling Smørgrav  * insert element into addr tree.
165b7579f77SDag-Erling Smørgrav  * @param tree: addr tree
166b7579f77SDag-Erling Smørgrav  * @param node: node element (at start of a structure that caller
167b7579f77SDag-Erling Smørgrav  *	has allocated).
168b7579f77SDag-Erling Smørgrav  * @param addr: to insert (copied).
169b7579f77SDag-Erling Smørgrav  * @param addrlen: length of addr
170b7579f77SDag-Erling Smørgrav  * @param net: size of subnet.
171b7579f77SDag-Erling Smørgrav  * @return false on error (duplicate element).
172b7579f77SDag-Erling Smørgrav  */
1733005e0a3SDag-Erling Smørgrav int addr_tree_insert(rbtree_type* tree, struct addr_tree_node* node,
174b7579f77SDag-Erling Smørgrav 	struct sockaddr_storage* addr, socklen_t addrlen, int net);
175b7579f77SDag-Erling Smørgrav 
176b7579f77SDag-Erling Smørgrav /**
177b7579f77SDag-Erling Smørgrav  * Initialize parent pointers in addr tree.
178b7579f77SDag-Erling Smørgrav  * Should be performed after insertions are done, before lookups
179b7579f77SDag-Erling Smørgrav  * @param tree: addr tree
180b7579f77SDag-Erling Smørgrav  */
1813005e0a3SDag-Erling Smørgrav void addr_tree_init_parents(rbtree_type* tree);
182b7579f77SDag-Erling Smørgrav 
183b7579f77SDag-Erling Smørgrav /**
184091e9e46SCy Schubert  * Initialize parent pointers in partial addr tree.
185091e9e46SCy Schubert  * Reinitialize pointer for part of tree, used after node deletion
186091e9e46SCy Schubert  * @param node: node to start parent pointer initialization for.
187091e9e46SCy Schubert  */
188091e9e46SCy Schubert void addr_tree_init_parents_node(struct addr_tree_node* node);
189091e9e46SCy Schubert 
190091e9e46SCy Schubert /**
191b7579f77SDag-Erling Smørgrav  * Lookup closest encloser in addr tree.
192b7579f77SDag-Erling Smørgrav  * @param tree: addr tree
193b7579f77SDag-Erling Smørgrav  * @param addr: to lookup.
194b7579f77SDag-Erling Smørgrav  * @param addrlen: length of addr
195b7579f77SDag-Erling Smørgrav  * @return closest enclosing node (could be equal) or NULL if not found.
196b7579f77SDag-Erling Smørgrav  */
1973005e0a3SDag-Erling Smørgrav struct addr_tree_node* addr_tree_lookup(rbtree_type* tree,
198b7579f77SDag-Erling Smørgrav 	struct sockaddr_storage* addr, socklen_t addrlen);
199b7579f77SDag-Erling Smørgrav 
200b5663de9SDag-Erling Smørgrav /**
201b5663de9SDag-Erling Smørgrav  * Find element in addr tree.  (search a netblock, not a match for an address)
202b5663de9SDag-Erling Smørgrav  * @param tree: addr tree
203b5663de9SDag-Erling Smørgrav  * @param addr: netblock to lookup.
204b5663de9SDag-Erling Smørgrav  * @param addrlen: length of addr
205b5663de9SDag-Erling Smørgrav  * @param net: size of subnet
206b5663de9SDag-Erling Smørgrav  * @return addr tree element, or NULL if not found.
207b5663de9SDag-Erling Smørgrav  */
2083005e0a3SDag-Erling Smørgrav struct addr_tree_node* addr_tree_find(rbtree_type* tree,
209b5663de9SDag-Erling Smørgrav 	struct sockaddr_storage* addr, socklen_t addrlen, int net);
210b5663de9SDag-Erling Smørgrav 
211b7579f77SDag-Erling Smørgrav /** compare name tree nodes */
212b7579f77SDag-Erling Smørgrav int name_tree_compare(const void* k1, const void* k2);
213b7579f77SDag-Erling Smørgrav 
214b7579f77SDag-Erling Smørgrav /** compare addr tree nodes */
215b7579f77SDag-Erling Smørgrav int addr_tree_compare(const void* k1, const void* k2);
216b7579f77SDag-Erling Smørgrav 
217*865f46b2SCy Schubert /** compare addr tree nodes (address and port only) */
218*865f46b2SCy Schubert int addr_tree_addrport_compare(const void* k1, const void* k2);
219*865f46b2SCy Schubert 
220b7579f77SDag-Erling Smørgrav #endif /* UTIL_STORAGE_DNSTREE_H */
221