diff --git a/include/opendht/indexation/pht.h b/include/opendht/indexation/pht.h index d60afbe1f903d7045137ececf15a4e5fab7315a8..479952a26691c1b543eb47664c80af86b93a6446 100644 --- a/include/opendht/indexation/pht.h +++ b/include/opendht/indexation/pht.h @@ -53,7 +53,7 @@ struct Prefix { * @return : true if the bit is at 1 * false otherwise */ - bool isActivBit(size_t pos) const { + bool isActiveBit(size_t pos) const { return ((this->content_[pos / 8] >> (7 - (pos % 8)) ) & 1) == 1; } @@ -121,26 +121,6 @@ struct Prefix { using Value = std::pair<InfoHash, dht::Value::Id>; -struct IndexEntry : public dht::Value::Serializable<IndexEntry> { - static const ValueType TYPE; - - virtual void unpackValue(const dht::Value& v) { - Serializable<IndexEntry>::unpackValue(v); - name = v.user_type; - } - - virtual dht::Value packValue() const { - auto pack = Serializable<IndexEntry>::packValue(); - pack.user_type = name; - return pack; - } - - Blob prefix; - Value value; - std::string name; - MSGPACK_DEFINE_MAP(prefix, value); -}; - class Pht { static constexpr const char* INVALID_KEY = "Key does not match the PHT key spec."; @@ -193,53 +173,7 @@ private: * Insert all needed node into the tree according to a prefix * @param p : Prefix that we need to insert */ - void insert(const Prefix& p) { - size_t i = 0; - auto now = clock::now(); - - std::shared_ptr<Node> curr_node; - - while ( ( leaves_.size() > 0 && leaves_.begin()->first + NODE_EXPIRE_TIME < now ) - || leaves_.size() > MAX_ELEMENT ) { - - leaves_.erase(leaves_.begin()); - } - - if ( !(curr_node = root_.lock()) ) { - - /* Root does not exist, need to create one*/ - curr_node = std::make_shared<Node>(); - root_ = curr_node; - } - - curr_node->last_reply = now; - - /* Iterate through all bit of the Blob */ - for ( i = 0; i < p.size_; i++ ) { - - /* According to the bit define which node is the next one */ - auto& next = ( p.isActivBit(i) ) ? curr_node->right_child : curr_node->left_child; - - /** - * If lock, node exists - * else create it - */ - if (auto n = next.lock()) { - curr_node = std::move(n); - } else { - /* Create the next node if doesn't exist*/ - auto tmp_curr_node = std::make_shared<Node>(); - tmp_curr_node->parent = curr_node; - next = tmp_curr_node; - curr_node = std::move(tmp_curr_node); - } - - curr_node->last_reply = now; - } - - /* Insert the leaf (curr_node) into the multimap */ - leaves_.emplace(std::move(now), std::move(curr_node) ); - } + void insert(const Prefix& p); /** * Lookup into the tree to return the maximum prefix length in the cache tree @@ -247,43 +181,7 @@ private: * @param p : Prefix that we are looking for * @return : The size of the longest prefix known in the cache between 0 and p.size_ */ - int lookup(const Prefix& p) { - int pos = 0; - auto now = clock::now(), last_node_time = now; - - /* Before lookup remove the useless one [i.e. too old] */ - while ( leaves_.size() > 0 && leaves_.begin()->first + NODE_EXPIRE_TIME < now ) { - leaves_.erase(leaves_.begin()); - } - - auto next = root_; - std::shared_ptr<Node> curr_node; - - while ( auto n = next.lock() ) { - /* Safe since pos is equal to 0 until here */ - if ( (unsigned) pos >= p.size_ ) break; - - curr_node = n; - last_node_time = curr_node->last_reply; - curr_node->last_reply = now; - - /* Get the Prefix bit by bit, starting from left */ - next = ( p.isActivBit(pos) ) ? curr_node->right_child : curr_node->left_child; - - ++pos; - } - - if ( pos > 0 ) { - auto to_erase = leaves_.find(last_node_time); - if ( to_erase != leaves_.end() ) - leaves_.erase( to_erase ); - - leaves_.emplace( std::move(now), std::move(curr_node) ); - } - - return --pos; - } - + int lookup(const Prefix& p); private: static constexpr const size_t MAX_ELEMENT {1024}; diff --git a/src/indexation/pht.cpp b/src/indexation/pht.cpp index 17d92b157a86e52e1d8d09a7c97aa6f149a2ff5f..7fa0a042935c2876b543abe1ae08070e0e139232 100644 --- a/src/indexation/pht.cpp +++ b/src/indexation/pht.cpp @@ -4,6 +4,107 @@ namespace dht { namespace indexation { +struct IndexEntry : public dht::Value::Serializable<IndexEntry> { + static const ValueType TYPE; + + virtual void unpackValue(const dht::Value& v) { + Serializable<IndexEntry>::unpackValue(v); + name = v.user_type; + } + + virtual dht::Value packValue() const { + auto pack = Serializable<IndexEntry>::packValue(); + pack.user_type = name; + return pack; + } + + Blob prefix; + Value value; + std::string name; + MSGPACK_DEFINE_MAP(prefix, value); +}; + +void Pht::Cache::insert(const Prefix& p) { + size_t i = 0; + auto now = clock::now(); + + std::shared_ptr<Node> curr_node; + + while ((leaves_.size() > 0 && leaves_.begin()->first + NODE_EXPIRE_TIME < now) || leaves_.size() > MAX_ELEMENT) + leaves_.erase(leaves_.begin()); + + if (not (curr_node = root_.lock())) { + /* Root does not exist, need to create one*/ + curr_node = std::make_shared<Node>(); + root_ = curr_node; + } + + curr_node->last_reply = now; + + /* Iterate through all bit of the Blob */ + for ( i = 0; i < p.size_; i++ ) { + + /* According to the bit define which node is the next one */ + auto& next = ( p.isActiveBit(i) ) ? curr_node->right_child : curr_node->left_child; + + /** + * If lock, node exists + * else create it + */ + if (auto n = next.lock()) { + curr_node = std::move(n); + } else { + /* Create the next node if doesn't exist*/ + auto tmp_curr_node = std::make_shared<Node>(); + tmp_curr_node->parent = curr_node; + next = tmp_curr_node; + curr_node = std::move(tmp_curr_node); + } + + curr_node->last_reply = now; + } + + /* Insert the leaf (curr_node) into the multimap */ + leaves_.emplace(std::move(now), std::move(curr_node) ); +} + +int Pht::Cache::lookup(const Prefix& p) { + int pos = 0; + auto now = clock::now(), last_node_time = now; + + /* Before lookup remove the useless one [i.e. too old] */ + while ( leaves_.size() > 0 && leaves_.begin()->first + NODE_EXPIRE_TIME < now ) { + leaves_.erase(leaves_.begin()); + } + + auto next = root_; + std::shared_ptr<Node> curr_node; + + while ( auto n = next.lock() ) { + /* Safe since pos is equal to 0 until here */ + if ( (unsigned) pos >= p.size_ ) break; + + curr_node = n; + last_node_time = curr_node->last_reply; + curr_node->last_reply = now; + + /* Get the Prefix bit by bit, starting from left */ + next = ( p.isActiveBit(pos) ) ? curr_node->right_child : curr_node->left_child; + + ++pos; + } + + if ( pos > 0 ) { + auto to_erase = leaves_.find(last_node_time); + if ( to_erase != leaves_.end() ) + leaves_.erase( to_erase ); + + leaves_.emplace( std::move(now), std::move(curr_node) ); + } + + return --pos; +} + const ValueType IndexEntry::TYPE = ValueType::USER_DATA; constexpr std::chrono::minutes Pht::Cache::NODE_EXPIRE_TIME; diff --git a/tools/dhtnode.cpp b/tools/dhtnode.cpp index f8a6613bc3d346bbbeba27c98815911b6ab3b192..31596365472bf5ac0a6eb6f28a34d418739e11f6 100644 --- a/tools/dhtnode.cpp +++ b/tools/dhtnode.cpp @@ -279,7 +279,6 @@ void cmd_loop(std::shared_ptr<DhtRunner>& dht, std::map<std::string, indexation: iss >> exact_match; try { auto key = createPhtKey(parseStringMap(keystr)); - std::cout << "Pht::lookup(key=\"" << indexes.at(index).linearize(key).toString() << "\")" << std::endl; indexes.at(index).lookup(key, [=](std::vector<std::shared_ptr<indexation::Value>>& vals, indexation::Prefix p) { if (vals.empty()) @@ -311,8 +310,6 @@ void cmd_loop(std::shared_ptr<DhtRunner>& dht, std::map<std::string, indexation: indexation::Value v {h, 0}; try { auto key = createPhtKey(parseStringMap(keystr)); - std::cout << "Pht::insert(key=\"" << indexes.at(index).linearize(key).toString() - << "\", " << h.toString() << ")" << std::endl; indexes.at(index).insert(key, v, [=](bool success) { if (not success) {