blob: 6432583c5060b68274f6caf1a4c1cb608e8ccf83 [file] [log] [blame]
HYuana9b85752014-02-26 02:32:30 -06001/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
2/**
3 * Copyright (C) 2014 Named Data Networking Project
4 * See COPYING for copyright and distribution information.
5 */
6
7// Name Tree (Name Prefix Hash Table)
8
9#ifndef NFD_TABLE_NAME_TREE_HPP
10#define NFD_TABLE_NAME_TREE_HPP
11
12#include "common.hpp"
13#include "name-tree-entry.hpp"
14
15namespace nfd {
16namespace name_tree {
17
18/**
19 * @brief Compute the hash value of the given name prefix.
20 * @todo 1) have another parameter that specifies the number of components
21 * 2) optimize the hash function to return a list of have values for all
22 * the (or a certain number of, like a batch operation) prefixes. 3) move
23 * the hash-related code to a separate file in /core or ndn-cpp-dev lib.
24 */
25uint32_t
26hashName(const Name& prefix);
27
28} // namespace name_tree
29
30/**
31 * @brief Class Name Tree
32 */
33class NameTree : noncopyable
34{
35public:
36 explicit
37 NameTree(size_t nBuckets);
38
39 ~NameTree();
40
41 /**
42 * @brief Get the number of occupied entries in the Name Tree
43 */
44 size_t
45 size() const;
46
47 /**
48 * @brief Get the number of buckets in the Name Tree (NPHT)
49 * @details The number of buckets is the one that used to create the hash
50 * table, i.e., m_nBuckets.
51 */
52 size_t
53 getNBuckets() const;
54
55 /**
56 * @brief Look for the Name Tree Entry that contains this name prefix.
57 * @details Starts from the shortest name prefix, and then increase the
58 * number of name components by one each time. All non-existing Name Tree
59 * Entries will be created.
60 * @param prefix The querying name prefix.
61 * @return The pointer to the Name Tree Entry that contains this full name
62 * prefix.
63 */
64 shared_ptr<name_tree::Entry>
65 lookup(const Name& prefix);
66
67 /**
68 * @brief Exact match lookup for the given name prefix.
69 * @return a null shared_ptr if this prefix is not found;
70 * otherwise return the Name Tree Entry address
71 */
72 shared_ptr<name_tree::Entry>
73 findExactMatch(const Name& prefix) const;
74
75 /**
76 * @brief Erase a Name Tree Entry if this entry is empty.
77 * @details If a Name Tree Entry contains no Children, no FIB, no PIT, and
78 * no Measurements entries, then it can be erased. In addition, its parent entry
79 * will also be examined by following the parent pointer until all empty entries
80 * are erased.
81 * @param entry The pointer to the entry to be erased. The entry pointer should
82 * returned by the findExactMatch(), lookup(), or findLongestPrefixMatch() functions.
83 */
84 bool
85 eraseEntryIfEmpty(shared_ptr<name_tree::Entry> entry);
86
87 /**
88 * @brief Longest prefix matching for the given name
89 * @details Starts from the full name string, reduce the number of name component
90 * by one each time, until an Entry is found.
91 */
92 shared_ptr<name_tree::Entry>
93 findLongestPrefixMatch(const Name& prefix);
94
95 /**
96 * @brief Resize the hash table size when its load factor reaches a threshold.
97 * @details As we are currently using a hand-written hash table implementation
98 * for the Name Tree, the hash table resize() function should be kept in the
99 * name-tree.hpp file.
100 * @param newNBuckets The number of buckets for the new hash table.
101 */
102 void
103 resize(size_t newNBuckets);
104
105 /**
106 * @brief Enumerate all the name prefixes stored in the Name Tree.
107 */
108 shared_ptr<std::vector<shared_ptr<name_tree::Entry> > >
109 fullEnumerate();
110
111 /**
112 * @brief Enumerate all the name prefixes under a specific name prefix
113 * @todo It might be better to have functions like fullEnemerateFib() to reduce the
114 * number of entries stored in the vector.
115 */
116 shared_ptr<std::vector<shared_ptr<name_tree::Entry> > >
117 partialEnumerate(const Name& prefix);
118
119 /**
120 * @brief Dump all the information stored in the Name Tree for debugging.
121 */
122 void
123 dump(std::ostream& output);
124
125private:
126 size_t m_nItems; // Number of items being stored
127 size_t m_nBuckets; // Number of hash buckets
128 double m_loadFactor;
129 size_t m_resizeThreshold;
130 int m_resizeFactor;
131 name_tree::Node** m_buckets; // Name Tree Buckets in the NPHT
132
133 /**
134 * @brief Create a Name Tree Entry if it does not exist, or return the existing
135 * Name Tree Entry address.
136 * @details Called by lookup() only.
137 * @return The first item is the Name Tree Entry address, the second item is
138 * a bool value indicates whether this is an old entry (false) or a new
139 * entry (true).
140 */
141 std::pair<shared_ptr<name_tree::Entry>, bool>
142 insert(const Name& prefix);
143
144 /**
145 * @brief Helper function for partialEnumerate()
146 */
147 void
148 partialEnumerateAddChildren(shared_ptr<name_tree::Entry> entry,
149 shared_ptr<std::vector<shared_ptr<name_tree::Entry> > > ret);
150
151};
152
153inline size_t
154NameTree::size() const
155{
156 return m_nItems;
157}
158
159inline size_t
160NameTree::getNBuckets() const
161{
162 return m_nBuckets;
163}
164
165} // namespace nfd
166
167#endif // NFD_TABLE_NAME_TREE_HPP