- replace deprecated INCLUDES with AM_CPPFLAGS
[oweals/gnunet.git] / src / experimentation / gnunet-daemon-experimentation_experiments.c
index 300b37d2895bd24144433406e993b264f00268ae..c787c34167f718eb9a5936cc6923f03c326c5bc8 100644 (file)
 #include "gnunet-daemon-experimentation.h"
 
 
-/**
- * Struct to store information about a specific experiment
- */
-struct Experiment
-{
-       /* Header */
-       /* ----------------- */
-       char *name;
-
-       /* Experiment issuer */
-       struct GNUNET_PeerIdentity issuer;
-
-       /* Experiment version as timestamp of creation */
-       struct GNUNET_TIME_Absolute version;
-
-       /* Description */
-       char *description;
-
-       /* Required capabilities  */
-       uint32_t required_capabilities;
-
-       /* Experiment timing */
-       /* ----------------- */
-
-       /* When to start experiment */
-       struct GNUNET_TIME_Absolute start;
-
-       /* When to end experiment */
-       struct GNUNET_TIME_Absolute stop;
-
-       /* How often to run experiment */
-       struct GNUNET_TIME_Relative frequency;
-
-       /* How long to run each execution  */
-       struct GNUNET_TIME_Relative duration;
-
-
-       /* Experiment itself */
-       /* ----------------- */
-
-       /* TBD */
-};
-
 
 /**
  * Struct to store information about an experiment issuer
  */
 struct Issuer
 {
-       struct GNUNET_CRYPTO_EccPublicKeyBinaryEncoded pubkey;
+       struct GNUNET_CRYPTO_EccPublicSignKey pubkey;
 };
 
 
@@ -97,6 +54,16 @@ static struct GNUNET_CONTAINER_MultiHashMap *valid_issuers;
 static struct GNUNET_CONTAINER_MultiHashMap *experiments;
 
 
+uint32_t GSE_my_issuer_count;
+
+/**
+ * Valid experiment issuer for this daemon
+ *
+ * Array Experimentation_Issuer with GSE_my_issuer_count elements
+ */
+struct Experimentation_Issuer *GSE_my_issuer;
+
+
 /**
  * Verify experiment signature
  *
@@ -119,7 +86,7 @@ int free_experiment (void *cls,
                                                                                 void *value)
 {
        struct Experiment *e = value;
-       GNUNET_CONTAINER_multihashmap_remove (experiments, key, value);
+       GNUNET_break (0 == GNUNET_CONTAINER_multihashmap_remove (experiments, key, value));
        GNUNET_free_non_null (e->description);
        GNUNET_free_non_null (e->name);
        GNUNET_free (e);
@@ -140,11 +107,25 @@ int free_issuer (void *cls,
                                                                 void *value)
 {
        struct Issuer *i = value;
-       GNUNET_CONTAINER_multihashmap_remove (valid_issuers, key, value);
+       GNUNET_break (0 == GNUNET_CONTAINER_multihashmap_remove (valid_issuers, key, value));
        GNUNET_free (i);
        return GNUNET_OK;
 }
 
+int create_issuer (void *cls,
+                                                                const struct GNUNET_HashCode * key,
+                                                                void *value)
+{
+       static int i = 0;
+       GNUNET_assert (i < GSE_my_issuer_count);
+       GSE_my_issuer[i].issuer_id.hashPubKey = *key;
+
+       i++;
+       return GNUNET_OK;
+
+}
+
+
 
 /**
  * Is peer a valid issuer
@@ -152,7 +133,7 @@ int free_issuer (void *cls,
  * @return GNUNET_YES or GNUNET_NO
  */
 int
-GNUNET_EXPERIMENTATION_experiments_issuer_accepted (struct GNUNET_PeerIdentity *issuer_ID)
+GED_experiments_issuer_accepted (struct GNUNET_PeerIdentity *issuer_ID)
 {
        if (GNUNET_CONTAINER_multihashmap_contains (valid_issuers, &issuer_ID->hashPubKey))
                return GNUNET_YES;
@@ -160,6 +141,94 @@ GNUNET_EXPERIMENTATION_experiments_issuer_accepted (struct GNUNET_PeerIdentity *
                return GNUNET_NO;
 }
 
+struct FindCtx
+{
+       const char *name;
+       struct GNUNET_TIME_Absolute version;
+       struct Experiment *res;
+};
+
+static int
+find_it (void *cls,
+                               const struct GNUNET_HashCode * key,
+                               void *value)
+{
+       struct FindCtx *find_ctx = cls;
+       struct Experiment *e = (struct Experiment *) value;
+
+       if (0 != strcmp(e->name, find_ctx->name))
+               return GNUNET_OK;
+       if (e->version.abs_value_us != find_ctx->version.abs_value_us)
+               return GNUNET_OK;
+
+       find_ctx->res = e;
+       return GNUNET_NO;
+}
+
+
+/*
+ * Find an experiment based on issuer name and version
+ *
+ * @param issuer the issuer
+ * @param name experiment name
+ * @param version experiment version
+ * @return the experiment or NULL if not found
+ */
+struct Experiment *
+GED_experiments_find (const struct GNUNET_PeerIdentity *issuer,
+                                                                                       const char *name,
+                                                                                       const struct GNUNET_TIME_Absolute version)
+{
+       struct FindCtx find_ctx;
+
+       find_ctx.name = name;
+       find_ctx.version = version;
+       find_ctx.res = NULL;
+
+       GNUNET_CONTAINER_multihashmap_get_multiple (experiments,
+                       &issuer->hashPubKey, &find_it, &find_ctx);
+       return find_ctx.res;
+}
+
+struct GetCtx
+{
+       struct Node *n;
+       GNUNET_EXPERIMENTATION_experiments_get_cb get_cb;
+};
+
+
+static int
+get_it (void *cls,
+                               const struct GNUNET_HashCode * key,
+                               void *value)
+{
+       struct GetCtx *get_ctx = cls;
+       struct Experiment *e = value;
+
+       get_ctx->get_cb (get_ctx->n, e);
+
+       return GNUNET_OK;
+}
+
+void
+GED_experiments_get (struct Node *n,
+                                                                                struct GNUNET_PeerIdentity *issuer,
+                                                                                GNUNET_EXPERIMENTATION_experiments_get_cb get_cb)
+{
+       struct GetCtx get_ctx;
+
+       GNUNET_assert (NULL != n);
+       GNUNET_assert (NULL != experiments);
+       GNUNET_assert (NULL != get_cb);
+
+       get_ctx.n = n;
+       get_ctx.get_cb = get_cb;
+
+       GNUNET_CONTAINER_multihashmap_get_multiple (experiments,
+                       &issuer->hashPubKey, &get_it, &get_ctx);
+
+       get_cb (n, NULL);
+}
 
 /**
  * Add a new experiment
@@ -189,8 +258,6 @@ int GNUNET_EXPERIMENTATION_experiments_add (struct Issuer *i,
        e->duration = duration;
        e->stop = stop;
 
-
-
        /* verify experiment */
        if (GNUNET_SYSERR == experiment_verify (i, e))
        {
@@ -205,10 +272,10 @@ int GNUNET_EXPERIMENTATION_experiments_add (struct Issuer *i,
                        e->name,
                        GNUNET_STRINGS_absolute_time_to_string (start),
                        GNUNET_STRINGS_absolute_time_to_string (stop),
-                       (long long unsigned int) frequency.rel_value / 1000,
-                       (long long unsigned int) duration.rel_value / 1000);
+                       (long long unsigned int) frequency.rel_value_us / 1000000LL,
+                       (long long unsigned int) duration.rel_value_us / 1000000LL);
        GNUNET_CONTAINER_multihashmap_put (experiments, &e->issuer.hashPubKey, e, GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE);
-  GNUNET_STATISTICS_set (GSE_stats, "# experiments", GNUNET_CONTAINER_multihashmap_size (experiments), GNUNET_NO);
+  GNUNET_STATISTICS_set (GED_stats, "# experiments", GNUNET_CONTAINER_multihashmap_size (experiments), GNUNET_NO);
 
        return GNUNET_OK;
 }
@@ -218,7 +285,7 @@ int GNUNET_EXPERIMENTATION_experiments_add (struct Issuer *i,
  * Parse a configuration section containing experiments
  *
  * @param cls configuration handle
- * @param section section name
+ * @param name section name
  */
 void exp_file_iterator (void *cls,
                                                                                                const char *name)
@@ -239,7 +306,7 @@ void exp_file_iterator (void *cls,
        struct GNUNET_TIME_Relative frequency;
        struct GNUNET_TIME_Relative duration;
 
-       GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Parsing section `%s'\n", name);
+       //GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Parsing section `%s'\n", name);
 
        /* Mandatory fields */
 
@@ -269,7 +336,7 @@ void exp_file_iterator (void *cls,
                        GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Experiment `%s': Version missing or invalid \n"), name);
                        return;
        }
-       version.abs_value = number;
+       version.abs_value_us = number; // FIXME: what is this supposed to be? Version != TIME!???
 
        /* Required capabilities */
        if (GNUNET_SYSERR == GNUNET_CONFIGURATION_get_value_number (exp, name, "CAPABILITIES", &number))
@@ -287,18 +354,17 @@ void exp_file_iterator (void *cls,
        /* Optional fields */
 
        /* Description */
-       GNUNET_CONFIGURATION_get_value_string (exp, name, "DESCRIPTION", &description);
+       if (GNUNET_SYSERR == GNUNET_CONFIGURATION_get_value_string (exp, name, "DESCRIPTION", &description))
+               description = NULL;
 
-
-
-       if (GNUNET_SYSERR == GNUNET_CONFIGURATION_get_value_number (exp, name, "START", (long long unsigned int *) &start.abs_value))
+       if (GNUNET_SYSERR == GNUNET_CONFIGURATION_get_value_number (exp, name, "START", (long long unsigned int *) &start.abs_value_us))
                        start = GNUNET_TIME_UNIT_ZERO_ABS;
 
        if (GNUNET_SYSERR == GNUNET_CONFIGURATION_get_value_time (exp, name, "FREQUENCY", &frequency))
                        frequency = EXP_DEFAULT_EXP_FREQ;
        if (GNUNET_SYSERR == GNUNET_CONFIGURATION_get_value_time (exp, name, "DURATION", &duration))
                        duration = EXP_DEFAULT_EXP_DUR;
-       if (GNUNET_SYSERR == GNUNET_CONFIGURATION_get_value_number (exp, name, "STOP", (long long unsigned int *)&stop.abs_value))
+       if (GNUNET_SYSERR == GNUNET_CONFIGURATION_get_value_number (exp, name, "STOP", (long long unsigned int *)&stop.abs_value_us))
                        stop = GNUNET_TIME_UNIT_FOREVER_ABS;
 
        GNUNET_EXPERIMENTATION_experiments_add (i, name, issuer, version,
@@ -335,7 +401,7 @@ load_file (const char * file)
  * Start experiments management
  */
 int
-GNUNET_EXPERIMENTATION_experiments_start ()
+GED_experiments_start ()
 {
        struct Issuer *i;
        char *issuers;
@@ -343,11 +409,11 @@ GNUNET_EXPERIMENTATION_experiments_start ()
        char *pubkey;
        char *pos;
        struct GNUNET_PeerIdentity issuer_ID;
-       struct GNUNET_CRYPTO_EccPublicKeyBinaryEncoded pub;
+       struct GNUNET_CRYPTO_EccPublicSignKey pub;
        struct GNUNET_HashCode hash;
 
        /* Load valid issuer */
-       if (GNUNET_SYSERR == GNUNET_CONFIGURATION_get_value_string (GSE_cfg, "EXPERIMENTATION", "ISSUERS", &issuers))
+       if (GNUNET_SYSERR == GNUNET_CONFIGURATION_get_value_string (GED_cfg, "EXPERIMENTATION", "ISSUERS", &issuers))
        {
                        GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("No valid experiment issuers configured! Set value to peer id of issuer! Exit...\n"));
                        return GNUNET_SYSERR;
@@ -363,7 +429,7 @@ GNUNET_EXPERIMENTATION_experiments_start ()
                }
                else
                {
-                               GNUNET_log (GNUNET_ERROR_TYPE_INFO, "`%s' is a valid issuer \n", GNUNET_i2s (&issuer_ID));
+                               GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "`%s' is a valid issuer \n", GNUNET_i2s (&issuer_ID));
                                i = GNUNET_malloc (sizeof (struct Issuer));
                                GNUNET_CONTAINER_multihashmap_put (valid_issuers, &issuer_ID.hashPubKey,
                                                i, GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST);
@@ -375,14 +441,14 @@ GNUNET_EXPERIMENTATION_experiments_start ()
   if (0 == GNUNET_CONTAINER_multihashmap_size (valid_issuers))
   {
                GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("No valid experiment issuers configured! Set value to peer id of issuer! Exit...\n"));
-               GNUNET_EXPERIMENTATION_experiments_stop ();
+               GED_experiments_stop ();
                return GNUNET_SYSERR;
   }
-  GNUNET_STATISTICS_set (GSE_stats, "# issuer", GNUNET_CONTAINER_multihashmap_size (valid_issuers), GNUNET_NO);
+  GNUNET_STATISTICS_set (GED_stats, "# issuer", GNUNET_CONTAINER_multihashmap_size (valid_issuers), GNUNET_NO);
 
-       if (GNUNET_OK == GNUNET_CONFIGURATION_get_value_string (GSE_cfg, "EXPERIMENTATION", "PUBKEY", &pubkey))
+       if (GNUNET_OK == GNUNET_CONFIGURATION_get_value_string (GED_cfg, "EXPERIMENTATION", "PUBKEY", &pubkey))
        {
-                       if (GNUNET_OK != GNUNET_CRYPTO_ecc_public_key_from_string(pubkey, strlen (pubkey), &pub))
+                       if (GNUNET_OK != GNUNET_CRYPTO_ecc_public_sign_key_from_string(pubkey, strlen (pubkey), &pub))
                        GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Invalid public key `%s'\n"), pubkey);
                        else
                        {
@@ -398,9 +464,14 @@ GNUNET_EXPERIMENTATION_experiments_start ()
                        GNUNET_free (pubkey);
        }
 
+       GSE_my_issuer_count = GNUNET_CONTAINER_multihashmap_size (valid_issuers);
+       GSE_my_issuer = GNUNET_malloc (GSE_my_issuer_count * sizeof (struct Experimentation_Issuer));
+       GNUNET_CONTAINER_multihashmap_iterate (valid_issuers, &create_issuer, GSE_my_issuer);
+       GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Daemon has %u issuers\n", GSE_my_issuer_count);
+
   experiments = GNUNET_CONTAINER_multihashmap_create (10, GNUNET_NO);
   /* Load experiments from file */
-       if (GNUNET_SYSERR == GNUNET_CONFIGURATION_get_value_string (GSE_cfg, "EXPERIMENTATION", "EXPERIMENTS", &file))
+       if (GNUNET_SYSERR == GNUNET_CONFIGURATION_get_value_string (GED_cfg, "EXPERIMENTATION", "EXPERIMENTS", &file))
                return GNUNET_OK;
 
        if (GNUNET_YES != GNUNET_DISK_file_test (file))
@@ -419,8 +490,14 @@ GNUNET_EXPERIMENTATION_experiments_start ()
  * Stop experiments management
  */
 void
-GNUNET_EXPERIMENTATION_experiments_stop ()
+GED_experiments_stop ()
 {
+       if (NULL != GSE_my_issuer)
+       {
+               GNUNET_free (GSE_my_issuer);
+               GSE_my_issuer = NULL;
+               GSE_my_issuer_count = 0;
+       }
        if (NULL != valid_issuers)
        {
                GNUNET_CONTAINER_multihashmap_iterate (valid_issuers, &free_issuer, NULL);