RECLAIM: refactoring; cleanup
[oweals/gnunet.git] / src / statistics / gnunet-statistics.c
index 9093336e133c5836e4d6f00c91c5ea1c3a21b779..bf111ade2a88b17bac1ec2edc927b9beec406865 100644 (file)
@@ -14,6 +14,8 @@
     
      You should have received a copy of the GNU Affero General Public License
      along with this program.  If not, see <http://www.gnu.org/licenses/>.
+
+     SPDX-License-Identifier: AGPL3.0-or-later
 */
 
 /**
@@ -158,6 +160,11 @@ static struct GNUNET_CONTAINER_MultiHashMap *values;
  */
 static int num_nodes_ready;
 
+/**
+ * @brief Number of nodes that have their values ready.
+ */
+static int num_nodes_ready_shutdown;
+
 /**
  * @brief Create a new #ValueSet
  *
@@ -211,25 +218,29 @@ printer (void *cls,
     {
       now_str = GNUNET_STRINGS_absolute_time_to_string (now);
       FPRINTF (stdout,
-              "%24s%s %s%s%12s%s %50s%s ",
+              "%24s%s %s%s%12s%s %s%50s%s%s ",
                now_str,
                csv_separator,
                value_set->is_persistent ? "!" : " ",
                csv_separator,
                value_set->subsystem,
                csv_separator,
+               (0 == strlen (csv_separator) ? "": "\""), /* quotes if csv */
                     _(value_set->name),
+               (0 == strlen (csv_separator) ? "": "\""), /* quotes if csv */
                (0 == strlen (csv_separator) ? ":": csv_separator));
     }
     else
     {
       FPRINTF (stdout,
-              "%s%s%12s%s %50s%s ",
+              "%s%s%12s%s %s%50s%s%s ",
                value_set->is_persistent ? "!" : " ",
                csv_separator,
                value_set->subsystem,
                csv_separator,
+               (0 == strlen (csv_separator) ? "": "\""), /* quotes if csv */
                _(value_set->name),
+               (0 == strlen (csv_separator) ? "": "\""), /* quotes if csv */
                (0 == strlen (csv_separator) ? ":": csv_separator));
     }
   }
@@ -248,42 +259,6 @@ printer (void *cls,
   return GNUNET_YES;
 }
 
-/**
- * @brief Called once all statistic values are available.
- *
- * Implements #GNUNET_STATISTICS_Callback
- *
- * @param cls Closure - The index of the node.
- * @param succes Whether statistics were obtained successfully.
- */
-static void
-continuation_print (void *cls,
-                    int success)
-{
-  const unsigned index_node = *(unsigned *) cls;
-
-  nodes[index_node].gh = NULL;
-  if (GNUNET_OK != success)
-  {
-    if (NULL == remote_host)
-      FPRINTF (stderr,
-               "%s",
-               _("Failed to obtain statistics.\n"));
-    else
-      FPRINTF (stderr,
-               _("Failed to obtain statistics from host `%s:%llu'\n"),
-               remote_host,
-               remote_port);
-    ret = 1;
-  }
-  num_nodes_ready++;
-  if (num_nodes_ready == num_nodes)
-  {
-    GNUNET_CONTAINER_multihashmap_iterate (values, printer, NULL);
-    GNUNET_SCHEDULER_shutdown();
-  }
-}
-
 /**
  * Callback function to process statistic values.
  *
@@ -310,26 +285,30 @@ printer_watch (void *cls,
     {
       now_str = GNUNET_STRINGS_absolute_time_to_string (now);
       FPRINTF (stdout,
-               "%24s%s %s%s%12s%s %50s%s %16llu\n",
+               "%24s%s %s%s%12s%s %s%50s%s%s %16llu\n",
                now_str,
                csv_separator,
                is_persistent ? "!" : " ",
                csv_separator,
                subsystem,
                csv_separator,
+               (0 == strlen (csv_separator) ? "": "\""), /* quotes if csv */
                _(name),
+               (0 == strlen (csv_separator) ? "": "\""), /* quotes if csv */
                (0 == strlen (csv_separator) ? ":": csv_separator),
                (unsigned long long) value);
     }
     else
     {
       FPRINTF (stdout,
-               "%s%s%12s%s %50s%s %16llu\n",
+               "%s%s%12s%s %s%50s%s%s %16llu\n",
                is_persistent ? "!" : " ",
                csv_separator,
                subsystem,
                csv_separator,
+               (0 == strlen (csv_separator) ? "": "\""), /* quotes if csv */
                _(name),
+               (0 == strlen (csv_separator) ? "": "\""), /* quotes if csv */
                (0 == strlen (csv_separator) ? ":": csv_separator),
                (unsigned long long) value);
     }
@@ -342,6 +321,112 @@ printer_watch (void *cls,
   return GNUNET_OK;
 }
 
+/**
+ * @brief Clean all data structures related to given node.
+ *
+ * Also clears global structures if we are the last node to clean.
+ *
+ * @param cls the index of the node
+ */
+static void
+clean_node (void *cls)
+{
+  const unsigned index_node = *(unsigned *) cls;
+  struct GNUNET_STATISTICS_Handle *h;
+  struct GNUNET_STATISTICS_GetHandle *gh;
+
+  if ( (NULL != path_testbed) && /* were issued with -t <testbed-path> option */
+       (NULL != nodes[index_node].conf) )
+  {
+    GNUNET_CONFIGURATION_destroy (nodes[index_node].conf);
+    nodes[index_node].conf = NULL;
+  }
+
+  h = nodes[index_node].handle;
+  gh = nodes[index_node].gh;
+
+  if (NULL != gh)
+  {
+    GNUNET_STATISTICS_get_cancel (gh);
+    gh = NULL;
+  }
+  if (GNUNET_YES == watch)
+  {
+    GNUNET_assert (GNUNET_OK ==
+      GNUNET_STATISTICS_watch_cancel (h,
+                                      subsystem,
+                                      name,
+                                      &printer_watch,
+                                      &nodes[index_node].index_node));
+  }
+
+  if (NULL != h)
+  {
+    GNUNET_STATISTICS_destroy (h, GNUNET_NO);
+    h = NULL;
+  }
+
+  num_nodes_ready_shutdown++;
+  if (num_nodes == num_nodes_ready_shutdown)
+  {
+    GNUNET_array_grow (nodes, num_nodes, 0);
+    GNUNET_CONTAINER_multihashmap_destroy (values);
+  }
+}
+
+/**
+ * @brief Print and shutdown
+ *
+ * @param cls unused
+ */
+static void
+print_finish (void *cls)
+{
+  GNUNET_CONTAINER_multihashmap_iterate (values, printer, NULL);
+  GNUNET_SCHEDULER_shutdown();
+}
+
+/**
+ * @brief Called once all statistic values are available.
+ *
+ * Implements #GNUNET_STATISTICS_Callback
+ *
+ * @param cls Closure - The index of the node.
+ * @param succes Whether statistics were obtained successfully.
+ */
+static void
+continuation_print (void *cls,
+                    int success)
+{
+  const unsigned index_node = *(unsigned *) cls;
+
+  nodes[index_node].gh = NULL;
+  if (GNUNET_OK != success)
+  {
+    if (NULL == remote_host)
+      FPRINTF (stderr,
+               "%s",
+               _("Failed to obtain statistics.\n"));
+    else
+      FPRINTF (stderr,
+               _("Failed to obtain statistics from host `%s:%llu'\n"),
+               remote_host,
+               remote_port);
+    ret = 1;
+  }
+  if (NULL != nodes[index_node].shutdown_task)
+  {
+    GNUNET_SCHEDULER_cancel (nodes[index_node].shutdown_task);
+    nodes[index_node].shutdown_task = NULL;
+  }
+  GNUNET_SCHEDULER_add_now (clean_node, &nodes[index_node].index_node);
+  num_nodes_ready++;
+  if (num_nodes_ready == num_nodes)
+  {
+    GNUNET_SCHEDULER_add_now (print_finish, NULL);
+  }
+}
+
 /**
  * Function called last by the statistics code.
  *
@@ -423,65 +508,6 @@ collector (void *cls,
   return GNUNET_OK;
 }
 
-/**
- * Function run on shutdown to clean up.
- *
- * @param cls the statistics handle
- */
-static void
-shutdown_task (void *cls)
-{
-  const unsigned index_node = *(unsigned *) cls;
-  struct GNUNET_STATISTICS_Handle *h;
-  struct GNUNET_STATISTICS_GetHandle *gh;
-
-  nodes[index_node].shutdown_task = NULL;
-  if ( (NULL != path_testbed) &&
-       (NULL != nodes[index_node].conf) )
-  {
-    GNUNET_CONFIGURATION_destroy (nodes[index_node].conf);
-    nodes[index_node].conf = NULL;
-  }
-
-  h = nodes[index_node].handle;
-  gh = nodes[index_node].gh;
-  if (NULL == h)
-  {
-    num_nodes_ready--;
-    if (0 == num_nodes_ready)
-    {
-      GNUNET_array_grow (nodes, num_nodes, 0);
-      GNUNET_CONTAINER_multihashmap_destroy (values);
-    }
-    return;
-  }
-  if (NULL != gh)
-  {
-    GNUNET_STATISTICS_get_cancel (gh);
-    gh = NULL;
-  }
-  if ( (GNUNET_YES == watch) &&
-       (NULL != subsystem) &&
-       (NULL != name) )
-    GNUNET_assert (GNUNET_OK ==
-       GNUNET_STATISTICS_watch_cancel (h,
-                                                   subsystem,
-                                                   name,
-                                                   &printer_watch,
-               &nodes[index_node].index_node));
-  GNUNET_STATISTICS_destroy (h,
-                             GNUNET_NO);
-  h = NULL;
-
-  num_nodes_ready--;
-  if (0 == num_nodes_ready)
-  {
-    GNUNET_array_grow (nodes, num_nodes, 0);
-    GNUNET_CONTAINER_multihashmap_destroy (values);
-  }
-}
-
-
 /**
  * Main task that does the actual work.
  *
@@ -562,18 +588,18 @@ main_task (void *cls)
                                  subsystem,
                                  name,
                                  &printer_watch,
-                                &nodes[index_node].index_node))
+                                 &nodes[index_node].index_node))
     {
       fprintf (stderr,
                _("Failed to initialize watch routine\n"));
       nodes[index_node].shutdown_task =
-        GNUNET_SCHEDULER_add_now (&shutdown_task,
+        GNUNET_SCHEDULER_add_now (&clean_node,
                                   &nodes[index_node].index_node);
       return;
     }
   }
   nodes[index_node].shutdown_task =
-    GNUNET_SCHEDULER_add_shutdown (&shutdown_task,
+    GNUNET_SCHEDULER_add_shutdown (&clean_node,
                                    &nodes[index_node].index_node);
 }