paragraph for gnunet devs that don't know how to use the web
[oweals/gnunet.git] / src / testbed / test_testbed_api_barriers.c
1 /*
2       This file is part of GNUnet
3       Copyright (C) 2008--2013 GNUnet e.V.
4
5       GNUnet is free software: you can redistribute it and/or modify it
6       under the terms of the GNU Affero General Public License as published
7       by the Free Software Foundation, either version 3 of the License,
8       or (at your 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       Affero General Public License for more details.
14      
15       You should have received a copy of the GNU Affero General Public License
16       along with this program.  If not, see <http://www.gnu.org/licenses/>.
17  */
18
19 /**
20  * @file testbed/test_testbed_api_barriers.c
21  * @brief testcase binary for testing testbed barriers API
22  * @author Sree Harsha Totakura <sreeharsha@totakura.in>
23  */
24
25 #include "platform.h"
26 #include "gnunet_util_lib.h"
27 #include "gnunet_testbed_service.h"
28 #include "test_testbed_api_barriers.h"
29
30
31 /**
32  * logging short hand
33  */
34 #define LOG(type,...) \
35   GNUNET_log (type, __VA_ARGS__);
36
37 /**
38  * Number of peers we start in this test case
39  */
40 #define NUM_PEERS 3
41
42
43 /**
44  * Our barrier
45  */
46 struct GNUNET_TESTBED_Barrier *barrier;
47
48 /**
49  * Identifier for the shutdown task
50  */
51 static struct GNUNET_SCHEDULER_Task *timeout_task;
52
53 /**
54  * Result of this test case
55  */
56 static int result;
57
58
59 /**
60  * Handle SIGINT and SIGTERM
61  */
62 static void
63 shutdown_handler(void *cls)
64 {
65   if (NULL != timeout_task)
66   {
67     GNUNET_SCHEDULER_cancel(timeout_task);
68     timeout_task = NULL;
69   }
70 }
71
72
73 /**
74  * Shutdown this test case when it takes too long
75  *
76  * @param cls NULL
77  */
78 static void
79 do_timeout (void *cls)
80 {
81   timeout_task = NULL;
82   if (barrier != NULL)
83       GNUNET_TESTBED_barrier_cancel (barrier);
84   GNUNET_SCHEDULER_shutdown ();
85 }
86
87
88 /**
89  * Functions of this type are to be given as callback argument to
90  * GNUNET_TESTBED_barrier_init().  The callback will be called when status
91  * information is available for the barrier.
92  *
93  * @param cls the closure given to GNUNET_TESTBED_barrier_init()
94  * @param name the name of the barrier
95  * @param barrier the barrier handle
96  * @param status status of the barrier; #GNUNET_OK if the barrier is crossed;
97  *   #GNUNET_SYSERR upon error
98  * @param emsg if the status were to be #GNUNET_SYSERR, this parameter has the
99  *   error messsage
100  */
101 static void
102 barrier_cb (void *cls,
103             const char *name,
104             struct GNUNET_TESTBED_Barrier *_barrier,
105             enum GNUNET_TESTBED_BarrierStatus status,
106             const char *emsg)
107 {
108   static enum GNUNET_TESTBED_BarrierStatus old_status;
109
110   GNUNET_assert (NULL == cls);
111   GNUNET_assert (_barrier == barrier);
112   switch (status)
113   {
114   case GNUNET_TESTBED_BARRIERSTATUS_INITIALISED:
115     LOG (GNUNET_ERROR_TYPE_INFO,
116          "Barrier initialised\n");
117     old_status = status;
118     return;
119   case GNUNET_TESTBED_BARRIERSTATUS_ERROR:
120     LOG (GNUNET_ERROR_TYPE_ERROR,
121          "Barrier initialisation failed: %s",
122          (NULL == emsg) ? "unknown reason" : emsg);
123     break;
124   case GNUNET_TESTBED_BARRIERSTATUS_CROSSED:
125     LOG (GNUNET_ERROR_TYPE_INFO,
126          "Barrier crossed\n");
127     if (old_status == GNUNET_TESTBED_BARRIERSTATUS_INITIALISED)
128       result = GNUNET_OK;
129     break;
130   default:
131     GNUNET_assert (0);
132     return;
133   }
134   barrier = NULL;
135   GNUNET_SCHEDULER_shutdown ();
136 }
137
138
139 /**
140  * Signature of a main function for a testcase.
141  *
142  * @param cls closure
143  * @param h the run handle
144  * @param num_peers number of peers in 'peers'
145  * @param peers_ handle to peers run in the testbed
146  * @param links_succeeded the number of overlay link connection attempts that
147  *          succeeded
148  * @param links_failed the number of overlay link connection attempts that
149  *          failed
150  */
151 static void
152 test_master (void *cls,
153              struct GNUNET_TESTBED_RunHandle *h,
154              unsigned int num_peers,
155              struct GNUNET_TESTBED_Peer **peers_,
156              unsigned int links_succeeded,
157              unsigned int links_failed)
158 {
159   struct GNUNET_TESTBED_Controller *c;
160
161   GNUNET_assert (NULL == cls);
162   if (NULL == peers_)
163   {
164     GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
165                 "Failing test due to timeout\n");
166     return;
167   }
168   GNUNET_assert (NUM_PEERS == num_peers);
169   c = GNUNET_TESTBED_run_get_controller_handle (h);
170   barrier = GNUNET_TESTBED_barrier_init (c,
171                                          TEST_BARRIER_NAME,
172                                          100,
173                                          &barrier_cb,
174                                          NULL);
175   timeout_task =
176       GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply
177                                     (GNUNET_TIME_UNIT_SECONDS,
178                                      10 * (NUM_PEERS + 1)),
179                                     &do_timeout, NULL);
180   GNUNET_SCHEDULER_add_shutdown(&shutdown_handler, NULL);
181 }
182
183
184 #ifndef PATH_MAX
185 /**
186  * Assumed maximum path length (for the log file name).
187  */
188 #define PATH_MAX 4096
189 #endif
190
191
192 /**
193  * Main function
194  */
195 int
196 main (int argc, char **argv)
197 {
198   struct GNUNET_CONFIGURATION_Handle *cfg;
199   char pwd[PATH_MAX];
200   char *binary;
201   uint64_t event_mask;
202
203   result = GNUNET_SYSERR;
204   event_mask = 0;
205   cfg = GNUNET_CONFIGURATION_create ();
206   GNUNET_assert (GNUNET_YES ==
207                  GNUNET_CONFIGURATION_parse (cfg,
208                                              "test_testbed_api_barriers.conf.in"));
209   if (NULL == getcwd (pwd, PATH_MAX))
210     return 1;
211   GNUNET_assert (0 < GNUNET_asprintf (&binary, "%s/%s", pwd,
212                                       "gnunet-service-test-barriers"));
213   GNUNET_CONFIGURATION_set_value_string (cfg, "test-barriers","BINARY", binary);
214   GNUNET_assert (GNUNET_OK == GNUNET_CONFIGURATION_write
215                  (cfg, "test_testbed_api_barriers.conf"));
216   GNUNET_CONFIGURATION_destroy (cfg);
217   cfg = NULL;
218   GNUNET_free (binary);
219   binary = NULL;
220   (void) GNUNET_TESTBED_test_run ("test_testbed_api_barriers",
221                                   "test_testbed_api_barriers.conf", NUM_PEERS,
222                                   event_mask, NULL, NULL,
223                                   &test_master, NULL);
224   (void) unlink ("test_testbed_api_barriers.conf");
225   if (GNUNET_OK != result)
226     return 1;
227   return 0;
228 }