parsing
[oweals/gnunet.git] / src / experimentation / gnunet-daemon-experimentation_experiments.c
1 /*
2      This file is part of GNUnet.
3      (C) 2009 Christian Grothoff (and other contributing authors)
4
5      GNUnet is free software; you can redistribute it and/or modify
6      it under the terms of the GNU General Public License as published
7      by the Free Software Foundation; either version 3, or (at your
8      option) any later version.
9
10      GNUnet is distributed in the hope that it will be useful, but
11      WITHOUT ANY WARRANTY; without even the implied warranty of
12      MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
13      General Public License for more details.
14
15      You should have received a copy of the GNU General Public License
16      along with GNUnet; see the file COPYING.  If not, write to the
17      Free Software Foundation, Inc., 59 Temple Place - Suite 330,
18      Boston, MA 02111-1307, USA.
19 */
20
21 /**
22  * @file experimentation/gnunet-daemon-experimentation_experiments.c
23  * @brief experimentation daemon: experiment management
24  * @author Christian Grothoff
25  * @author Matthias Wachs
26  */
27 #include "platform.h"
28 #include "gnunet_getopt_lib.h"
29 #include "gnunet_util_lib.h"
30 #include "gnunet_core_service.h"
31 #include "gnunet_statistics_service.h"
32 #include "gnunet-daemon-experimentation.h"
33
34 struct Experiment
35 {
36         /* Header */
37
38         /* Experiment issuer */
39         struct GNUNET_PeerIdentity issuer;
40
41         /* Experiment version as timestamp of creation */
42         struct GNUNET_TIME_Absolute version;
43
44         /* Description */
45         char *description;
46
47         /* Required capabilities  */
48         uint32_t required_capabilities;
49
50         /* Experiment itself */
51
52         /* TBD */
53 };
54
55 /**
56  * Hashmap containing valid experiment issuer
57  */
58 static struct GNUNET_CONTAINER_MultiHashMap *valid_issuers;
59
60 void
61 GNUNET_EXPERIMENTATION_experiments_verify ()
62 {
63
64 }
65
66 /**
67  * Is peer a valid issuer
68  *
69  * @return GNUNET_YES or GNUNET_NO
70  */
71 int
72 GNUNET_EXPERIMENTATION_experiments_issuer_accepted (struct GNUNET_PeerIdentity *issuer_ID)
73 {
74         if (GNUNET_CONTAINER_multihashmap_contains (valid_issuers, &issuer_ID->hashPubKey))
75                 return GNUNET_YES;
76         else
77                 return GNUNET_NO;
78 }
79
80 void exp_file_iterator (void *cls,
81                                                                                                 const char *section)
82 {
83         struct GNUNET_CONFIGURATION_Handle *exp = cls;
84         struct Experiment *e;
85         struct Issuer *i;
86
87         char *val;
88         unsigned long long number;
89
90         GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Parsing section `%s'\n", section);
91
92         e = GNUNET_malloc (sizeof (struct Experiment));
93         /* Mandatory fields */
94
95         /* Issuer */
96         if (GNUNET_SYSERR == GNUNET_CONFIGURATION_get_value_string (exp, section, "ISSUER", &val))
97         {
98                         GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Section `%s': Issuer missing\n", section);
99                         GNUNET_free (e);
100                         return;
101         }
102         if (GNUNET_SYSERR == GNUNET_CRYPTO_hash_from_string (section, &e->issuer.hashPubKey))
103         {
104                         GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Section `%s': Issuer invalid\n", section);
105                         GNUNET_free (val);
106                         GNUNET_free (e);
107                         return;
108         }
109         if (NULL == (i = GNUNET_CONTAINER_multihashmap_get (valid_issuers, &e->issuer.hashPubKey)))
110         {
111                 GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Section `%s': Issuer not accepted!\n", section);
112                 GNUNET_free (val);
113                 GNUNET_free (e);
114                 return;
115         }
116
117         GNUNET_free (val);
118
119         /* Version */
120         if (GNUNET_SYSERR == GNUNET_CONFIGURATION_get_value_number (exp, section, "VERSION", &number))
121         {
122                         GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Section `%s': Version missing \n", section);
123                         GNUNET_free (e);
124                         return;
125         }
126         e->version.abs_value = number;
127
128         /* Required capabilities */
129         if (GNUNET_SYSERR == GNUNET_CONFIGURATION_get_value_number (exp, section, "CAPABILITIES", &number))
130         {
131                         GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Section `%s': Required capabilities missing \n", section);
132                         GNUNET_free (e);
133                         return;
134         }
135         if (number > UINT32_MAX)
136         {
137                 GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Section `%s': Required capabilities invalid \n", section);
138                 GNUNET_free (e);
139                 return;
140         }
141         e->required_capabilities = number;
142
143         /* Optional fields  */
144
145         /* Description */
146         GNUNET_CONFIGURATION_get_value_string (exp, section, "DESCRIPTION", &e->description);
147
148
149         /* verify experiment */
150
151 }
152
153 /**
154  * Load experiments from file
155  * FIXME: Not yet sure how to store that on disk ...
156  *
157  * @param file source file
158  */
159
160 static void
161 load_file (const char * file)
162 {
163         struct GNUNET_CONFIGURATION_Handle *exp = GNUNET_CONFIGURATION_create();
164         if (NULL == exp)
165                 return;
166
167         if (GNUNET_SYSERR == GNUNET_CONFIGURATION_parse (exp, file))
168         {
169                 GNUNET_CONFIGURATION_destroy (exp);
170                 GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Failed to parse file `%s'\n"), file);
171                 return;
172         }
173
174         GNUNET_CONFIGURATION_iterate_sections (exp, &exp_file_iterator, exp);
175
176         GNUNET_CONFIGURATION_destroy (exp);
177 }
178
179 /**
180  * Start experiments management
181  */
182 int
183 GNUNET_EXPERIMENTATION_experiments_start ()
184 {
185         char *issuers;
186         char *file;
187         char *pos;
188         struct GNUNET_PeerIdentity issuer_ID;
189
190         /* Load valid issuer */
191         if (GNUNET_SYSERR == GNUNET_CONFIGURATION_get_value_string (GSE_cfg, "EXPERIMENTATION", "ISSUERS", &issuers))
192         {
193                         GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("No valid experiment issuers configured! Set value to peer id of issuer! Exit...\n"));
194                         return GNUNET_SYSERR;
195         }
196
197         valid_issuers = GNUNET_CONTAINER_multihashmap_create (10, GNUNET_NO);
198
199   for (pos = strtok (issuers, " "); pos != NULL; pos = strtok (NULL, " "))
200   {
201
202                 if (GNUNET_SYSERR == GNUNET_CRYPTO_hash_from_string (pos, &issuer_ID.hashPubKey))
203                 {
204                         GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Invalid value `%s'\n"), pos);
205                 }
206                 else
207                 {
208                                 GNUNET_log (GNUNET_ERROR_TYPE_INFO, "`%s' is a valid issuer \n", GNUNET_i2s (&issuer_ID));
209                                 GNUNET_CONTAINER_multihashmap_put (valid_issuers, &issuer_ID.hashPubKey,
210                                                 NULL, GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_FAST);
211                 }
212   }
213   GNUNET_free (issuers);
214
215   if (0 == GNUNET_CONTAINER_multihashmap_size (valid_issuers))
216   {
217                 GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("No valid experiment issuers configured! Set value to peer id of issuer! Exit...\n"));
218                 GNUNET_EXPERIMENTATION_experiments_stop ();
219                 return GNUNET_SYSERR;
220   }
221   GNUNET_STATISTICS_set (GSE_stats, "# issuer", GNUNET_CONTAINER_multihashmap_size (valid_issuers), GNUNET_NO);
222
223   /* Load experiments from file */
224         if (GNUNET_SYSERR == GNUNET_CONFIGURATION_get_value_string (GSE_cfg, "EXPERIMENTATION", "EXPERIMENTS", &file))
225                 return GNUNET_OK;
226
227         if (GNUNET_YES != GNUNET_DISK_file_test (file))
228         {
229                 GNUNET_log (GNUNET_ERROR_TYPE_ERROR, _("Cannot read experiments file `%s'\n"), file);
230                         return GNUNET_OK;
231         }
232         load_file (file);
233
234         return GNUNET_OK;
235 }
236
237 /**
238  * Stop experiments management
239  */
240 void
241 GNUNET_EXPERIMENTATION_experiments_stop ()
242 {
243         if (NULL != valid_issuers)
244                 GNUNET_CONTAINER_multihashmap_destroy (valid_issuers);
245         valid_issuers = NULL;
246 }
247
248 /* end of gnunet-daemon-experimentation_experiments.c */