From 2ab756906d75ee94a87513ff5c5f2b1d6cd803da Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Adrien=20B=C3=A9raud?= <adrien.beraud@savoirfairelinux.com>
Date: Thu, 27 Oct 2016 16:51:21 -0400
Subject: [PATCH] dht: getSearchLog for a specific search

---
 include/opendht/dht.h       |  1 +
 include/opendht/dhtrunner.h |  7 +++---
 src/dht.cpp                 | 45 ++++++++++++++++++++++++++++---------
 src/dhtrunner.cpp           |  6 +++++
 tools/dhtnode.cpp           | 14 ++++++++----
 5 files changed, 55 insertions(+), 18 deletions(-)

diff --git a/include/opendht/dht.h b/include/opendht/dht.h
index 80289281..beb7c51b 100644
--- a/include/opendht/dht.h
+++ b/include/opendht/dht.h
@@ -275,6 +275,7 @@ public:
 
     std::string getRoutingTablesLog(sa_family_t) const;
     std::string getSearchesLog(sa_family_t) const;
+    std::string getSearchLog(const InfoHash&, sa_family_t af = AF_UNSPEC) const;
 
     void dumpTables() const;
     std::vector<unsigned> getNodeMessageStats(bool in = false) {
diff --git a/include/opendht/dhtrunner.h b/include/opendht/dhtrunner.h
index c05a3c0a..c03056d9 100644
--- a/include/opendht/dhtrunner.h
+++ b/include/opendht/dhtrunner.h
@@ -281,9 +281,10 @@ public:
     std::string getStorageLog() const;
     std::string getStorageLog(const InfoHash&) const;
     std::string getRoutingTablesLog(sa_family_t af) const;
-    std::string getSearchesLog(sa_family_t af = 0) const;
-    std::vector<SockAddr> getPublicAddress(sa_family_t af = 0);
-    std::vector<std::string> getPublicAddressStr(sa_family_t af = 0);
+    std::string getSearchesLog(sa_family_t af = AF_UNSPEC) const;
+    std::string getSearchLog(const InfoHash&, sa_family_t af = AF_UNSPEC) const;    
+    std::vector<SockAddr> getPublicAddress(sa_family_t af = AF_UNSPEC);
+    std::vector<std::string> getPublicAddressStr(sa_family_t af = AF_UNSPEC);
 
     // securedht methods
 
diff --git a/src/dht.cpp b/src/dht.cpp
index fb23baa5..ad26fe55 100644
--- a/src/dht.cpp
+++ b/src/dht.cpp
@@ -2650,13 +2650,39 @@ std::string
 Dht::getSearchesLog(sa_family_t af) const
 {
     std::stringstream out;
-    out << "s:synched, u:updated, a:announced, c:candidate, f:cur req, x:expired, *:known" << std::endl;
-    if (not af or af == AF_INET)
-        for (const auto& sr : searches4)
-            dumpSearch(*sr.second, out);
-    if (not af or af == AF_INET6)
-        for (const auto& sr : searches6)
-            dumpSearch(*sr.second, out);
+    auto num_searches = searches4.size() + searches6.size();
+    if (num_searches > 8) {
+        if (not af or af == AF_INET)
+            for (const auto& sr : searches4)
+                out << "[search " << sr.first << " IPv4]" << std::endl;
+        if (not af or af == AF_INET6)
+            for (const auto& sr : searches6)
+                out << "[search " << sr.first << " IPv6]" << std::endl;
+    } else {
+        out << "s:synched, u:updated, a:announced, c:candidate, f:cur req, x:expired, *:known" << std::endl;
+        if (not af or af == AF_INET)
+            for (const auto& sr : searches4)
+                dumpSearch(*sr.second, out);
+        if (not af or af == AF_INET6)
+            for (const auto& sr : searches6)
+                dumpSearch(*sr.second, out);
+    }
+    out << "Total: " << num_searches << " searches (" << searches4.size() << " IPv4, " << searches6.size() << " IPv6)." << std::endl;
+    return out.str();
+}
+
+std::string
+Dht::getSearchLog(const InfoHash& id, sa_family_t af) const
+{
+    std::stringstream out;
+    if (af == AF_UNSPEC) {
+        out << getSearchLog(id, AF_INET) << getSearchLog(id, AF_INET);
+    } else {
+        auto& searches = (af == AF_INET) ? searches4 : searches6;
+        auto sr = searches.find(id);
+        if (sr != searches.end())
+            dumpSearch(*sr->second, out);
+    }
     return out.str();
 }
 
@@ -2952,10 +2978,7 @@ Dht::confirmNodes()
         : uniform_duration_distribution<> {seconds(60), seconds(180)};
     auto confirm_nodes_time = now + time_dis(rd);
 
-    if (nextNodesConfirmation)
-        scheduler.edit(nextNodesConfirmation, confirm_nodes_time);
-    else
-        nextNodesConfirmation = scheduler.add(confirm_nodes_time, std::bind(&Dht::confirmNodes, this));
+    scheduler.edit(nextNodesConfirmation, confirm_nodes_time);
 }
 
 std::vector<ValuesExport>
diff --git a/src/dhtrunner.cpp b/src/dhtrunner.cpp
index a7d41cf0..39557839 100644
--- a/src/dhtrunner.cpp
+++ b/src/dhtrunner.cpp
@@ -271,6 +271,12 @@ DhtRunner::getSearchesLog(sa_family_t af) const
     std::lock_guard<std::mutex> lck(dht_mtx);
     return dht_->getSearchesLog(af);
 }
+std::string
+DhtRunner::getSearchLog(const InfoHash& f, sa_family_t af) const
+{
+    std::lock_guard<std::mutex> lck(dht_mtx);
+    return dht_->getSearchLog(f, af);
+}
 std::vector<SockAddr>
 DhtRunner::getPublicAddress(sa_family_t af)
 {
diff --git a/tools/dhtnode.cpp b/tools/dhtnode.cpp
index a8393b71..4d61b126 100644
--- a/tools/dhtnode.cpp
+++ b/tools/dhtnode.cpp
@@ -53,8 +53,8 @@ void print_help() {
 
     std::cout << std::endl << "Node information:" << std::endl
               << "  ll         Print basic information and stats about the current node." << std::endl
-              << "  ls         Print basic information about current searches." << std::endl
-              << "  ld         Print basic information about currenty stored values on this node." << std::endl
+              << "  ls [key]   Print basic information about current search(es)." << std::endl
+              << "  ld [key]   Print basic information about currenty stored values on this node (or key)." << std::endl
               << "  lr         Print the full current routing table of this node" << std::endl;
 
     std::cout << std::endl << "Operations on the DHT:" << std::endl
@@ -123,8 +123,14 @@ void cmd_loop(std::shared_ptr<DhtRunner>& dht, dht_params& params)
                 std::cout << dht->getStorageLog(filter) << std::endl;
             continue;
         } else if (op == "ls") {
-            std::cout << "Searches:" << std::endl;
-            std::cout << dht->getSearchesLog() << std::endl;
+            iss >> idstr;
+            InfoHash filter(idstr);
+            if (filter == InfoHash{}) {
+                std::cout << "Searches:" << std::endl;
+                std::cout << dht->getSearchesLog() << std::endl;
+            } else {
+                std::cout << dht->getSearchLog(filter) << std::endl;
+            }
             continue;
         } else if (op == "la")  {
             std::cout << "Reported public addresses:" << std::endl;
-- 
GitLab