diff options
author | Christian Grothoff <christian@grothoff.org> | 2013-03-18 11:55:12 +0000 |
---|---|---|
committer | Christian Grothoff <christian@grothoff.org> | 2013-03-18 11:55:12 +0000 |
commit | 467b7a5f6893d472663d42b6b8684616cee0f7dc (patch) | |
tree | 54eee6f7a88832c13cf24d7302c3f7a02f895d68 /src/dv | |
parent | ef4bd8de47b45e808d29a8f5ee3d1c4f15c96353 (diff) | |
download | gnunet-467b7a5f6893d472663d42b6b8684616cee0f7dc.tar.gz gnunet-467b7a5f6893d472663d42b6b8684616cee0f7dc.zip |
-towards a DV test
Diffstat (limited to 'src/dv')
-rw-r--r-- | src/dv/Makefile.am | 21 | ||||
-rw-r--r-- | src/dv/dv_api.c | 14 | ||||
-rw-r--r-- | src/dv/gnunet-service-dv.c | 28 | ||||
-rw-r--r-- | src/dv/test_transport_api_dv.c | 1133 | ||||
-rw-r--r-- | src/dv/test_transport_dv_data.conf | 70 |
5 files changed, 90 insertions, 1176 deletions
diff --git a/src/dv/Makefile.am b/src/dv/Makefile.am index 919f49e69..5af2f966a 100644 --- a/src/dv/Makefile.am +++ b/src/dv/Makefile.am | |||
@@ -64,20 +64,21 @@ libgnunet_plugin_transport_dv_la_LDFLAGS = \ | |||
64 | libgnunet_plugin_transport_dv_la_DEPENDENCIES = \ | 64 | libgnunet_plugin_transport_dv_la_DEPENDENCIES = \ |
65 | libgnunetdv.la | 65 | libgnunetdv.la |
66 | 66 | ||
67 | #check_PROGRAMS = \ | 67 | check_PROGRAMS = \ |
68 | # test_transport_api_dv | 68 | test_transport_api_dv |
69 | # test_dv_topology | 69 | |
70 | 70 | ||
71 | if ENABLE_TEST_RUN | 71 | if ENABLE_TEST_RUN |
72 | TESTS = $(check_PROGRAMS) $(check_SCRIPTS) | 72 | TESTS = $(check_PROGRAMS) |
73 | endif | 73 | endif |
74 | 74 | ||
75 | #test_transport_api_dv_SOURCES = \ | 75 | test_transport_api_dv_SOURCES = \ |
76 | # test_transport_api_dv.c | 76 | test_transport_api_dv.c |
77 | #test_transport_api_dv_LDADD = \ | 77 | test_transport_api_dv_LDADD = \ |
78 | # $(top_builddir)/src/core/libgnunetcore.la \ | 78 | $(top_builddir)/src/testbed/libgnunettestbed.la \ |
79 | # $(top_builddir)/src/transport/libgnunettransport.la \ | 79 | $(top_builddir)/src/core/libgnunetcore.la \ |
80 | # $(top_builddir)/src/util/libgnunetutil.la | 80 | $(top_builddir)/src/transport/libgnunettransport.la \ |
81 | $(top_builddir)/src/util/libgnunetutil.la | ||
81 | 82 | ||
82 | EXTRA_DIST = \ | 83 | EXTRA_DIST = \ |
83 | test_transport_dv_data.conf | 84 | test_transport_dv_data.conf |
diff --git a/src/dv/dv_api.c b/src/dv/dv_api.c index ecc13941b..cd12a0a21 100644 --- a/src/dv/dv_api.c +++ b/src/dv/dv_api.c | |||
@@ -267,6 +267,9 @@ process_ack (void *cls, | |||
267 | 267 | ||
268 | if (th->uid != ntohl (ctx->ack->uid)) | 268 | if (th->uid != ntohl (ctx->ack->uid)) |
269 | return GNUNET_OK; | 269 | return GNUNET_OK; |
270 | LOG (GNUNET_ERROR_TYPE_DEBUG, | ||
271 | "Matchedk ACK for message to peer %s\n", | ||
272 | GNUNET_h2s (key)); | ||
270 | GNUNET_assert (GNUNET_YES == | 273 | GNUNET_assert (GNUNET_YES == |
271 | GNUNET_CONTAINER_multihashmap_remove (ctx->sh->send_callbacks, | 274 | GNUNET_CONTAINER_multihashmap_remove (ctx->sh->send_callbacks, |
272 | key, | 275 | key, |
@@ -306,6 +309,9 @@ handle_message_receipt (void *cls, | |||
306 | reconnect (sh); | 309 | reconnect (sh); |
307 | return; | 310 | return; |
308 | } | 311 | } |
312 | LOG (GNUNET_ERROR_TYPE_DEBUG, | ||
313 | "Received message of type %u from DV service\n", | ||
314 | (unsigned int) msg->type); | ||
309 | switch (ntohs (msg->type)) | 315 | switch (ntohs (msg->type)) |
310 | { | 316 | { |
311 | case GNUNET_MESSAGE_TYPE_DV_CONNECT: | 317 | case GNUNET_MESSAGE_TYPE_DV_CONNECT: |
@@ -472,6 +478,8 @@ reconnect (struct GNUNET_DV_ServiceHandle *sh) | |||
472 | GNUNET_CONTAINER_multihashmap_iterate (sh->send_callbacks, | 478 | GNUNET_CONTAINER_multihashmap_iterate (sh->send_callbacks, |
473 | &cleanup_send_cb, | 479 | &cleanup_send_cb, |
474 | sh); | 480 | sh); |
481 | LOG (GNUNET_ERROR_TYPE_DEBUG, | ||
482 | "Connecting to DV service\n"); | ||
475 | sh->client = GNUNET_CLIENT_connect ("dv", sh->cfg); | 483 | sh->client = GNUNET_CLIENT_connect ("dv", sh->cfg); |
476 | if (NULL == sh->client) | 484 | if (NULL == sh->client) |
477 | { | 485 | { |
@@ -583,6 +591,12 @@ GNUNET_DV_send (struct GNUNET_DV_ServiceHandle *sh, | |||
583 | GNUNET_break (0); | 591 | GNUNET_break (0); |
584 | return NULL; | 592 | return NULL; |
585 | } | 593 | } |
594 | LOG (GNUNET_ERROR_TYPE_DEBUG, | ||
595 | "Asked to send %u bytes of type %u to %s\n", | ||
596 | (unsigned int) msg->size, | ||
597 | (unsigned int) msg->type, | ||
598 | GNUNET_i2s (target)); | ||
599 | |||
586 | th = GNUNET_malloc (sizeof (struct GNUNET_DV_TransmitHandle) + | 600 | th = GNUNET_malloc (sizeof (struct GNUNET_DV_TransmitHandle) + |
587 | sizeof (struct GNUNET_DV_SendMessage) + | 601 | sizeof (struct GNUNET_DV_SendMessage) + |
588 | ntohs (msg->size)); | 602 | ntohs (msg->size)); |
diff --git a/src/dv/gnunet-service-dv.c b/src/dv/gnunet-service-dv.c index e0a47348e..44e786589 100644 --- a/src/dv/gnunet-service-dv.c +++ b/src/dv/gnunet-service-dv.c | |||
@@ -41,6 +41,7 @@ | |||
41 | #include "dv.h" | 41 | #include "dv.h" |
42 | #include <gcrypt.h> | 42 | #include <gcrypt.h> |
43 | 43 | ||
44 | |||
44 | /** | 45 | /** |
45 | * How often do we establish the consensu? | 46 | * How often do we establish the consensu? |
46 | */ | 47 | */ |
@@ -756,7 +757,6 @@ handle_core_connect (void *cls, const struct GNUNET_PeerIdentity *peer, | |||
756 | release_route (route); | 757 | release_route (route); |
757 | GNUNET_free (route); | 758 | GNUNET_free (route); |
758 | } | 759 | } |
759 | route->next_hop = neighbor; | ||
760 | neighbor->consensus_task = GNUNET_SCHEDULER_add_now (&start_consensus, | 760 | neighbor->consensus_task = GNUNET_SCHEDULER_add_now (&start_consensus, |
761 | neighbor); | 761 | neighbor); |
762 | } | 762 | } |
@@ -1070,6 +1070,25 @@ learn_route_cb (void *cls, | |||
1070 | struct DirectNeighbor *neighbor = cls; | 1070 | struct DirectNeighbor *neighbor = cls; |
1071 | struct Target *target; | 1071 | struct Target *target; |
1072 | 1072 | ||
1073 | if (NULL == element) | ||
1074 | { | ||
1075 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, | ||
1076 | "Failed to establish DV consensus, will try again later\n"); | ||
1077 | GNUNET_CONSENSUS_destroy (neighbor->consensus); | ||
1078 | if (NULL != neighbor->neighbor_table_consensus) | ||
1079 | { | ||
1080 | GNUNET_CONTAINER_multihashmap_iterate (neighbor->neighbor_table_consensus, | ||
1081 | &free_targets, | ||
1082 | NULL); | ||
1083 | GNUNET_CONTAINER_multihashmap_destroy (neighbor->neighbor_table_consensus); | ||
1084 | neighbor->neighbor_table_consensus = NULL; | ||
1085 | } | ||
1086 | neighbor->consensus = NULL; | ||
1087 | neighbor->consensus_task = GNUNET_SCHEDULER_add_delayed (GNUNET_DV_CONSENSUS_FREQUENCY, | ||
1088 | &start_consensus, | ||
1089 | neighbor); | ||
1090 | return GNUNET_SYSERR; | ||
1091 | } | ||
1073 | if (sizeof (struct Target) != element->size) | 1092 | if (sizeof (struct Target) != element->size) |
1074 | { | 1093 | { |
1075 | GNUNET_break_op (0); | 1094 | GNUNET_break_op (0); |
@@ -1449,14 +1468,14 @@ shutdown_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) | |||
1449 | { | 1468 | { |
1450 | unsigned int i; | 1469 | unsigned int i; |
1451 | 1470 | ||
1471 | GNUNET_CORE_disconnect (core_api); | ||
1472 | core_api = NULL; | ||
1452 | GNUNET_CONTAINER_multihashmap_iterate (direct_neighbors, | 1473 | GNUNET_CONTAINER_multihashmap_iterate (direct_neighbors, |
1453 | &free_direct_neighbors, NULL); | 1474 | &free_direct_neighbors, NULL); |
1454 | GNUNET_CONTAINER_multihashmap_destroy (direct_neighbors); | ||
1455 | GNUNET_CONTAINER_multihashmap_iterate (all_routes, | 1475 | GNUNET_CONTAINER_multihashmap_iterate (all_routes, |
1456 | &free_route, NULL); | 1476 | &free_route, NULL); |
1477 | GNUNET_CONTAINER_multihashmap_destroy (direct_neighbors); | ||
1457 | GNUNET_CONTAINER_multihashmap_destroy (all_routes); | 1478 | GNUNET_CONTAINER_multihashmap_destroy (all_routes); |
1458 | GNUNET_CORE_disconnect (core_api); | ||
1459 | core_api = NULL; | ||
1460 | GNUNET_STATISTICS_destroy (stats, GNUNET_NO); | 1479 | GNUNET_STATISTICS_destroy (stats, GNUNET_NO); |
1461 | stats = NULL; | 1480 | stats = NULL; |
1462 | GNUNET_SERVER_notification_context_destroy (nc); | 1481 | GNUNET_SERVER_notification_context_destroy (nc); |
@@ -1511,6 +1530,7 @@ handle_start (void *cls, struct GNUNET_SERVER_Client *client, | |||
1511 | const struct GNUNET_MessageHeader *message) | 1530 | const struct GNUNET_MessageHeader *message) |
1512 | { | 1531 | { |
1513 | GNUNET_SERVER_notification_context_add (nc, client); | 1532 | GNUNET_SERVER_notification_context_add (nc, client); |
1533 | GNUNET_SERVER_receive_done (client, GNUNET_OK); | ||
1514 | GNUNET_CONTAINER_multihashmap_iterate (all_routes, | 1534 | GNUNET_CONTAINER_multihashmap_iterate (all_routes, |
1515 | &add_route, | 1535 | &add_route, |
1516 | client); | 1536 | client); |
diff --git a/src/dv/test_transport_api_dv.c b/src/dv/test_transport_api_dv.c index e36622f2f..f56f80cbc 100644 --- a/src/dv/test_transport_api_dv.c +++ b/src/dv/test_transport_api_dv.c | |||
@@ -23,8 +23,7 @@ | |||
23 | */ | 23 | */ |
24 | #include "platform.h" | 24 | #include "platform.h" |
25 | #include "gnunet_core_service.h" | 25 | #include "gnunet_core_service.h" |
26 | 26 | #include "gnunet_testbed_service.h" | |
27 | #define TEST_ALL GNUNET_NO | ||
28 | 27 | ||
29 | /** | 28 | /** |
30 | * How long until we fail the whole testcase? | 29 | * How long until we fail the whole testcase? |
@@ -32,1134 +31,40 @@ | |||
32 | #define TEST_TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 600) | 31 | #define TEST_TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 600) |
33 | 32 | ||
34 | /** | 33 | /** |
35 | * How long until we give up on starting the peers? | 34 | * Return value from main, set to 0 on success. |
36 | */ | 35 | */ |
37 | #define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 500) | ||
38 | |||
39 | #define DEFAULT_NUM_PEERS 4 | ||
40 | |||
41 | #define DEFAULT_ADDITIONAL_MESSAGES 2 | ||
42 | |||
43 | #define MAX_OUTSTANDING_CONNECTIONS 100 | ||
44 | |||
45 | static float fail_percentage = 0.00; | ||
46 | |||
47 | static int ok; | 36 | static int ok; |
48 | 37 | ||
49 | static unsigned long long num_additional_messages; | ||
50 | |||
51 | static unsigned long long num_peers; | ||
52 | |||
53 | static unsigned int total_connections; | ||
54 | |||
55 | static unsigned int failed_connections; | ||
56 | |||
57 | static unsigned int total_server_connections; | ||
58 | |||
59 | static unsigned int total_messages_received; | ||
60 | |||
61 | static unsigned int total_other_expected_messages; | ||
62 | |||
63 | static unsigned int temp_total_other_messages; | ||
64 | |||
65 | static unsigned int total_other_messages; | ||
66 | |||
67 | static unsigned int expected_messages; | ||
68 | |||
69 | static unsigned int expected_connections; | ||
70 | |||
71 | static unsigned long long peers_left; | ||
72 | |||
73 | static struct GNUNET_TESTING_PeerGroup *pg; | ||
74 | |||
75 | const struct GNUNET_CONFIGURATION_Handle *main_cfg; | ||
76 | |||
77 | static GNUNET_SCHEDULER_TaskIdentifier die_task; | ||
78 | |||
79 | static char *dotOutFileName = "topology.dot"; | ||
80 | |||
81 | static FILE *dotOutFile; | ||
82 | |||
83 | static char *blacklist_transports; | ||
84 | |||
85 | static int transmit_ready_scheduled; | ||
86 | |||
87 | static int transmit_ready_failed; | ||
88 | |||
89 | static int transmit_ready_called; | ||
90 | |||
91 | static enum GNUNET_TESTING_Topology topology; | ||
92 | |||
93 | static enum GNUNET_TESTING_Topology blacklist_topology = GNUNET_TESTING_TOPOLOGY_NONE; /* Don't do any blacklisting */ | ||
94 | |||
95 | static enum GNUNET_TESTING_Topology connection_topology = GNUNET_TESTING_TOPOLOGY_NONE; /* NONE actually means connect all allowed peers */ | ||
96 | |||
97 | static enum GNUNET_TESTING_TopologyOption connect_topology_option = | ||
98 | GNUNET_TESTING_TOPOLOGY_OPTION_ALL; | ||
99 | |||
100 | static double connect_topology_option_modifier = 0.0; | ||
101 | |||
102 | static char *test_directory; | ||
103 | |||
104 | struct GNUNET_CONTAINER_MultiHashMap *peer_daemon_hash; | ||
105 | |||
106 | #define MTYPE 12345 | ||
107 | |||
108 | GNUNET_NETWORK_STRUCT_BEGIN | ||
109 | |||
110 | struct GNUNET_TestMessage | ||
111 | { | ||
112 | /** | ||
113 | * Header of the message | ||
114 | */ | ||
115 | struct GNUNET_MessageHeader header; | ||
116 | |||
117 | /** | ||
118 | * Unique identifier for this message. | ||
119 | */ | ||
120 | uint32_t uid; | ||
121 | }; | ||
122 | GNUNET_NETWORK_STRUCT_END | ||
123 | |||
124 | struct PeerContext | ||
125 | { | ||
126 | /* This is a linked list */ | ||
127 | struct PeerContext *next; | ||
128 | |||
129 | /** | ||
130 | * Handle to the daemon | ||
131 | */ | ||
132 | struct GNUNET_TESTING_Daemon *daemon; | ||
133 | |||
134 | /* Handle to the peer core */ | ||
135 | struct GNUNET_CORE_Handle *peer_handle; | ||
136 | }; | ||
137 | |||
138 | static struct PeerContext *all_peers; | ||
139 | |||
140 | struct TestMessageContext | ||
141 | { | ||
142 | /* This is a linked list */ | ||
143 | struct TestMessageContext *next; | ||
144 | |||
145 | /* Handle to the sending peer core */ | ||
146 | struct GNUNET_CORE_Handle *peer1handle; | ||
147 | |||
148 | /* Handle to the receiving peer core */ | ||
149 | struct GNUNET_CORE_Handle *peer2handle; | ||
150 | |||
151 | /* Handle to the sending peer daemon */ | ||
152 | struct GNUNET_TESTING_Daemon *peer1; | ||
153 | |||
154 | /* Handle to the receiving peer daemon */ | ||
155 | struct GNUNET_TESTING_Daemon *peer2; | ||
156 | |||
157 | /* Identifier for this message, so we don't disconnect other peers! */ | ||
158 | uint32_t uid; | ||
159 | |||
160 | /* Task for disconnecting cores, allow task to be cancelled on shutdown */ | ||
161 | GNUNET_SCHEDULER_TaskIdentifier disconnect_task; | ||
162 | }; | ||
163 | |||
164 | static struct TestMessageContext *test_messages; | ||
165 | |||
166 | static struct TestMessageContext *other_test_messages; | ||
167 | |||
168 | /** | ||
169 | * Check whether peers successfully shut down. | ||
170 | */ | ||
171 | void | ||
172 | shutdown_callback (void *cls, const char *emsg) | ||
173 | { | ||
174 | if (emsg != NULL) | ||
175 | { | ||
176 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Shutdown of peers failed!\n"); | ||
177 | if (ok == 0) | ||
178 | ok = 666; | ||
179 | } | ||
180 | else | ||
181 | { | ||
182 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "All peers successfully shut down!\n"); | ||
183 | } | ||
184 | } | ||
185 | 38 | ||
186 | static void | 39 | static void |
187 | finish_testing (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) | 40 | test_connection (void *cls, |
41 | unsigned int num_peers, | ||
42 | struct GNUNET_TESTBED_Peer **peers) | ||
188 | { | 43 | { |
189 | GNUNET_assert (pg != NULL); | 44 | if (4 != num_peers) |
190 | struct PeerContext *peer_pos; | ||
191 | struct PeerContext *free_peer_pos; | ||
192 | struct TestMessageContext *pos; | ||
193 | struct TestMessageContext *free_pos; | ||
194 | |||
195 | die_task = GNUNET_SCHEDULER_NO_TASK; | ||
196 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
197 | "Called finish testing, stopping daemons.\n"); | ||
198 | peer_pos = all_peers; | ||
199 | while (peer_pos != NULL) | ||
200 | { | 45 | { |
201 | if (peer_pos->peer_handle != NULL) | 46 | fprintf (stderr, "Testbed failed to connect peers\n"); |
202 | GNUNET_CORE_disconnect (peer_pos->peer_handle); | 47 | GNUNET_SCHEDULER_shutdown (); |
203 | free_peer_pos = peer_pos; | ||
204 | peer_pos = peer_pos->next; | ||
205 | GNUNET_free (free_peer_pos); | ||
206 | } | ||
207 | all_peers = NULL; | ||
208 | |||
209 | pos = test_messages; | ||
210 | while (pos != NULL) | ||
211 | { | ||
212 | if (pos->peer1handle != NULL) | ||
213 | { | ||
214 | GNUNET_CORE_disconnect (pos->peer1handle); | ||
215 | pos->peer1handle = NULL; | ||
216 | } | ||
217 | if (pos->peer2handle != NULL) | ||
218 | { | ||
219 | GNUNET_CORE_disconnect (pos->peer2handle); | ||
220 | pos->peer2handle = NULL; | ||
221 | } | ||
222 | free_pos = pos; | ||
223 | pos = pos->next; | ||
224 | if (free_pos->disconnect_task != GNUNET_SCHEDULER_NO_TASK) | ||
225 | { | ||
226 | GNUNET_SCHEDULER_cancel (free_pos->disconnect_task); | ||
227 | } | ||
228 | GNUNET_free (free_pos); | ||
229 | } | ||
230 | |||
231 | pos = other_test_messages; | ||
232 | while (pos != NULL) | ||
233 | { | ||
234 | if (pos->peer1handle != NULL) | ||
235 | { | ||
236 | GNUNET_CORE_disconnect (pos->peer1handle); | ||
237 | pos->peer1handle = NULL; | ||
238 | } | ||
239 | if (pos->peer2handle != NULL) | ||
240 | { | ||
241 | GNUNET_CORE_disconnect (pos->peer2handle); | ||
242 | pos->peer2handle = NULL; | ||
243 | } | ||
244 | free_pos = pos; | ||
245 | pos = pos->next; | ||
246 | if (free_pos->disconnect_task != GNUNET_SCHEDULER_NO_TASK) | ||
247 | { | ||
248 | GNUNET_SCHEDULER_cancel (free_pos->disconnect_task); | ||
249 | } | ||
250 | GNUNET_free (free_pos); | ||
251 | } | ||
252 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
253 | "transmit_ready's scheduled %d, failed %d, transmit_ready's called %d\n", | ||
254 | transmit_ready_scheduled, transmit_ready_failed, | ||
255 | transmit_ready_called); | ||
256 | GNUNET_TESTING_daemons_stop (pg, TIMEOUT, &shutdown_callback, NULL); | ||
257 | if (dotOutFile != NULL) | ||
258 | { | ||
259 | FPRINTF (dotOutFile, "%s", "}"); | ||
260 | FCLOSE (dotOutFile); | ||
261 | } | ||
262 | |||
263 | ok = 0; | ||
264 | } | ||
265 | |||
266 | |||
267 | static void | ||
268 | disconnect_cores (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) | ||
269 | { | ||
270 | struct TestMessageContext *pos = cls; | ||
271 | |||
272 | /* Disconnect from the respective cores */ | ||
273 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Disconnecting from peer 1 `%4s'\n", | ||
274 | GNUNET_i2s (&pos->peer1->id)); | ||
275 | if (pos->peer1handle != NULL) | ||
276 | GNUNET_CORE_disconnect (pos->peer1handle); | ||
277 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Disconnecting from peer 2 `%4s'\n", | ||
278 | GNUNET_i2s (&pos->peer2->id)); | ||
279 | if (pos->peer2handle != NULL) | ||
280 | GNUNET_CORE_disconnect (pos->peer2handle); | ||
281 | /* Set handles to NULL so test case can be ended properly */ | ||
282 | pos->peer1handle = NULL; | ||
283 | pos->peer2handle = NULL; | ||
284 | pos->disconnect_task = GNUNET_SCHEDULER_NO_TASK; | ||
285 | /* Decrement total connections so new can be established */ | ||
286 | total_server_connections -= 2; | ||
287 | } | ||
288 | |||
289 | static void | ||
290 | end_badly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) | ||
291 | { | ||
292 | char *msg = cls; | ||
293 | struct TestMessageContext *pos; | ||
294 | struct TestMessageContext *free_pos; | ||
295 | struct PeerContext *peer_pos; | ||
296 | struct PeerContext *free_peer_pos; | ||
297 | |||
298 | die_task = GNUNET_SCHEDULER_NO_TASK; | ||
299 | GNUNET_log (GNUNET_ERROR_TYPE_WARNING, | ||
300 | "End badly was called (%s)... stopping daemons.\n", msg); | ||
301 | |||
302 | peer_pos = all_peers; | ||
303 | while (peer_pos != NULL) | ||
304 | { | ||
305 | if (peer_pos->peer_handle != NULL) | ||
306 | GNUNET_CORE_disconnect (peer_pos->peer_handle); | ||
307 | free_peer_pos = peer_pos; | ||
308 | peer_pos = peer_pos->next; | ||
309 | GNUNET_free (free_peer_pos); | ||
310 | } | ||
311 | all_peers = NULL; | ||
312 | |||
313 | pos = test_messages; | ||
314 | while (pos != NULL) | ||
315 | { | ||
316 | if (pos->peer1handle != NULL) | ||
317 | { | ||
318 | GNUNET_CORE_disconnect (pos->peer1handle); | ||
319 | pos->peer1handle = NULL; | ||
320 | } | ||
321 | if (pos->peer2handle != NULL) | ||
322 | { | ||
323 | GNUNET_CORE_disconnect (pos->peer2handle); | ||
324 | pos->peer2handle = NULL; | ||
325 | } | ||
326 | free_pos = pos; | ||
327 | pos = pos->next; | ||
328 | GNUNET_free (free_pos); | ||
329 | } | ||
330 | |||
331 | pos = other_test_messages; | ||
332 | while (pos != NULL) | ||
333 | { | ||
334 | if (pos->peer1handle != NULL) | ||
335 | { | ||
336 | GNUNET_CORE_disconnect (pos->peer1handle); | ||
337 | pos->peer1handle = NULL; | ||
338 | } | ||
339 | if (pos->peer2handle != NULL) | ||
340 | { | ||
341 | GNUNET_CORE_disconnect (pos->peer2handle); | ||
342 | pos->peer2handle = NULL; | ||
343 | } | ||
344 | free_pos = pos; | ||
345 | pos = pos->next; | ||
346 | if (free_pos->disconnect_task != GNUNET_SCHEDULER_NO_TASK) | ||
347 | { | ||
348 | GNUNET_SCHEDULER_cancel (free_pos->disconnect_task); | ||
349 | } | ||
350 | GNUNET_free (free_pos); | ||
351 | } | ||
352 | |||
353 | if (pg != NULL) | ||
354 | { | ||
355 | GNUNET_TESTING_daemons_stop (pg, TIMEOUT, &shutdown_callback, NULL); | ||
356 | ok = 7331; /* Opposite of leet */ | ||
357 | } | ||
358 | else | ||
359 | ok = 401; /* Never got peers started */ | ||
360 | |||
361 | if (dotOutFile != NULL) | ||
362 | { | ||
363 | FPRINTF (dotOutFile, "%s", "}"); | ||
364 | FCLOSE (dotOutFile); | ||
365 | } | ||
366 | } | ||
367 | |||
368 | static void | ||
369 | send_other_messages (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc); | ||
370 | |||
371 | /** | ||
372 | * Get distance information from 'atsi'. | ||
373 | * | ||
374 | * @param atsi performance data | ||
375 | * @return connected transport distance | ||
376 | */ | ||
377 | static uint32_t | ||
378 | get_atsi_distance (const struct GNUNET_ATS_Information *atsi, | ||
379 | unsigned int atsi_count) | ||
380 | { | ||
381 | unsigned int i; | ||
382 | |||
383 | for (i = 0; i < atsi_count; i++) | ||
384 | { | ||
385 | if (ntohl (atsi->type) == GNUNET_ATS_QUALITY_NET_DISTANCE) | ||
386 | return ntohl (atsi->value); | ||
387 | } | ||
388 | |||
389 | GNUNET_break (0); | ||
390 | /* FIXME: we do not have distance data? Assume direct neighbor. */ | ||
391 | return 1; | ||
392 | } | ||
393 | |||
394 | |||
395 | static int | ||
396 | process_mtype (void *cls, const struct GNUNET_PeerIdentity *peer, | ||
397 | const struct GNUNET_MessageHeader *message, | ||
398 | const struct GNUNET_ATS_Information *atsi, | ||
399 | unsigned int atsi_count) | ||
400 | { | ||
401 | struct TestMessageContext *pos = cls; | ||
402 | struct GNUNET_TestMessage *msg = (struct GNUNET_TestMessage *) message; | ||
403 | uint32_t distance; | ||
404 | |||
405 | if (pos->uid != ntohl (msg->uid)) | ||
406 | return GNUNET_OK; | ||
407 | distance = get_atsi_distance (atsi, atsi_count); | ||
408 | GNUNET_assert (0 == | ||
409 | memcmp (peer, &pos->peer1->id, | ||
410 | sizeof (struct GNUNET_PeerIdentity))); | ||
411 | if (total_other_expected_messages == 0) | ||
412 | { | ||
413 | total_messages_received++; | ||
414 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
415 | "Received message from `%4s', type %d, uid %u, distance %u.\n", | ||
416 | GNUNET_i2s (peer), ntohs (message->type), ntohl (msg->uid), | ||
417 | distance); | ||
418 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
419 | "Total messages received %d, expected %d.\n", | ||
420 | total_messages_received, expected_messages); | ||
421 | } | ||
422 | else | ||
423 | { | ||
424 | total_other_messages++; | ||
425 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
426 | "Received message from `%4s', type %d, uid %u, distance %u.\n", | ||
427 | GNUNET_i2s (peer), ntohs (message->type), ntohl (msg->uid), | ||
428 | distance); | ||
429 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
430 | "Total OTHER messages received %d, expected %d.\n", | ||
431 | total_other_messages, total_other_expected_messages); | ||
432 | } | ||
433 | |||
434 | if ((total_messages_received == expected_messages) && | ||
435 | (total_other_messages == 0)) | ||
436 | { | ||
437 | GNUNET_SCHEDULER_cancel (die_task); | ||
438 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
439 | "Scheduling timeout from DV connections.\n"); | ||
440 | die_task = | ||
441 | GNUNET_SCHEDULER_add_delayed (TEST_TIMEOUT, &end_badly, | ||
442 | "waiting for DV peers to connect!"); | ||
443 | } | ||
444 | else if ((total_other_expected_messages > 0) && | ||
445 | (total_other_messages == total_other_expected_messages)) | ||
446 | { | ||
447 | GNUNET_SCHEDULER_cancel (die_task); | ||
448 | die_task = GNUNET_SCHEDULER_add_now (&finish_testing, NULL); | ||
449 | } | ||
450 | else | ||
451 | { | ||
452 | pos->disconnect_task = GNUNET_SCHEDULER_add_now (&disconnect_cores, pos); | ||
453 | } | ||
454 | |||
455 | return GNUNET_OK; | ||
456 | } | ||
457 | |||
458 | static size_t | ||
459 | transmit_ready (void *cls, size_t size, void *buf) | ||
460 | { | ||
461 | struct GNUNET_TestMessage *m; | ||
462 | struct TestMessageContext *pos = cls; | ||
463 | |||
464 | GNUNET_assert (buf != NULL); | ||
465 | m = (struct GNUNET_TestMessage *) buf; | ||
466 | m->header.type = htons (MTYPE); | ||
467 | m->header.size = htons (sizeof (struct GNUNET_TestMessage)); | ||
468 | m->uid = htonl (pos->uid); | ||
469 | transmit_ready_called++; | ||
470 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
471 | "transmit ready for peer %s\ntransmit_ready's scheduled %d, transmit_ready's called %d\n", | ||
472 | GNUNET_i2s (&pos->peer1->id), transmit_ready_scheduled, | ||
473 | transmit_ready_called); | ||
474 | return sizeof (struct GNUNET_TestMessage); | ||
475 | } | ||
476 | |||
477 | |||
478 | static struct GNUNET_CORE_MessageHandler no_handlers[] = { | ||
479 | {NULL, 0, 0} | ||
480 | }; | ||
481 | |||
482 | static struct GNUNET_CORE_MessageHandler handlers[] = { | ||
483 | {&process_mtype, MTYPE, sizeof (struct GNUNET_TestMessage)}, | ||
484 | {NULL, 0, 0} | ||
485 | }; | ||
486 | |||
487 | |||
488 | /** | ||
489 | * Notify of all peer1's peers, once peer 2 is found, schedule connect | ||
490 | * to peer two for message send. | ||
491 | * | ||
492 | * @param cls closure | ||
493 | * @param peer peer identity this notification is about | ||
494 | * @param atsi performance data for the connection | ||
495 | * @param atsi_count number of ATS information included | ||
496 | */ | ||
497 | static void | ||
498 | connect_notify_peer2 (void *cls, const struct GNUNET_PeerIdentity *peer, | ||
499 | const struct GNUNET_ATS_Information *atsi, | ||
500 | unsigned int atsi_count) | ||
501 | { | ||
502 | struct TestMessageContext *pos = cls; | ||
503 | |||
504 | if (0 == memcmp (&pos->peer1->id, peer, sizeof (struct GNUNET_PeerIdentity))) | ||
505 | { | ||
506 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
507 | "Core connection from `%s' to `%4s' verfied, sending message!\n", | ||
508 | GNUNET_i2s (&pos->peer2->id), GNUNET_h2s (&peer->hashPubKey)); | ||
509 | if (NULL == | ||
510 | GNUNET_CORE_notify_transmit_ready (pos->peer1handle, GNUNET_YES, 0, | ||
511 | TIMEOUT, &pos->peer2->id, | ||
512 | sizeof (struct GNUNET_TestMessage), | ||
513 | &transmit_ready, pos)) | ||
514 | { | ||
515 | /* This probably shouldn't happen, but it does (timing issue?) */ | ||
516 | GNUNET_log (GNUNET_ERROR_TYPE_WARNING, | ||
517 | "RECEIVED NULL when asking core (1) for transmission to peer `%4s'\n", | ||
518 | GNUNET_i2s (&pos->peer2->id)); | ||
519 | transmit_ready_failed++; | ||
520 | total_other_expected_messages--; | ||
521 | } | ||
522 | else | ||
523 | { | ||
524 | transmit_ready_scheduled++; | ||
525 | } | ||
526 | } | ||
527 | } | ||
528 | |||
529 | |||
530 | static void | ||
531 | init_notify_peer2 (void *cls, struct GNUNET_CORE_Handle *server, | ||
532 | const struct GNUNET_PeerIdentity *my_identity) | ||
533 | { | ||
534 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
535 | "Core connection to `%4s' established, awaiting connections.\n", | ||
536 | GNUNET_i2s (my_identity)); | ||
537 | total_server_connections++; | ||
538 | } | ||
539 | |||
540 | |||
541 | /** | ||
542 | * Notify of all peer1's peers, once peer 2 is found, schedule connect | ||
543 | * to peer two for message send. | ||
544 | * | ||
545 | * @param cls closure | ||
546 | * @param peer peer identity this notification is about | ||
547 | * @param atsi performance data for the connection | ||
548 | * @param atsi_count number of atsi datums | ||
549 | */ | ||
550 | static void | ||
551 | connect_notify_peer1 (void *cls, const struct GNUNET_PeerIdentity *peer, | ||
552 | const struct GNUNET_ATS_Information *atsi, | ||
553 | unsigned int atsi_count) | ||
554 | { | ||
555 | struct TestMessageContext *pos = cls; | ||
556 | |||
557 | if (0 == memcmp (&pos->peer2->id, peer, sizeof (struct GNUNET_PeerIdentity))) | ||
558 | { | ||
559 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
560 | "Core connection from `%s' to `%4s' verified.\n", | ||
561 | GNUNET_i2s (&pos->peer1->id), GNUNET_h2s (&peer->hashPubKey)); | ||
562 | /* | ||
563 | * Connect to the receiving peer | ||
564 | */ | ||
565 | pos->peer2handle = | ||
566 | GNUNET_CORE_connect (pos->peer2->cfg, pos, &init_notify_peer2, | ||
567 | &connect_notify_peer2, NULL, NULL, GNUNET_YES, | ||
568 | NULL, GNUNET_YES, handlers); | ||
569 | } | ||
570 | } | ||
571 | |||
572 | |||
573 | static void | ||
574 | init_notify_peer1 (void *cls, struct GNUNET_CORE_Handle *server, | ||
575 | const struct GNUNET_PeerIdentity *my_identity) | ||
576 | { | ||
577 | total_server_connections++; | ||
578 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
579 | "Core connection to `%4s' established, awaiting connections...\n", | ||
580 | GNUNET_i2s (my_identity)); | ||
581 | } | ||
582 | |||
583 | |||
584 | static void | ||
585 | send_test_messages (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) | ||
586 | { | ||
587 | struct TestMessageContext *pos = cls; | ||
588 | |||
589 | if (((tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN) != 0) || (cls == NULL)) | ||
590 | return; | 48 | return; |
591 | |||
592 | if (die_task == GNUNET_SCHEDULER_NO_TASK) | ||
593 | { | ||
594 | die_task = | ||
595 | GNUNET_SCHEDULER_add_delayed (TEST_TIMEOUT, &end_badly, | ||
596 | "from create topology (timeout)"); | ||
597 | } | ||
598 | |||
599 | if (total_server_connections >= MAX_OUTSTANDING_CONNECTIONS) | ||
600 | { | ||
601 | GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply | ||
602 | (GNUNET_TIME_UNIT_SECONDS, 1), | ||
603 | &send_test_messages, pos); | ||
604 | return; /* Otherwise we'll double schedule messages here! */ | ||
605 | } | ||
606 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
607 | "Attempting to send test message from %s to %s\n", | ||
608 | pos->peer1->shortname, pos->peer2->shortname); | ||
609 | /* | ||
610 | * Connect to the sending peer | ||
611 | */ | ||
612 | pos->peer1handle = | ||
613 | GNUNET_CORE_connect (pos->peer1->cfg, pos, &init_notify_peer1, | ||
614 | &connect_notify_peer1, NULL, NULL, GNUNET_NO, NULL, | ||
615 | GNUNET_NO, no_handlers); | ||
616 | |||
617 | GNUNET_assert (pos->peer1handle != NULL); | ||
618 | |||
619 | if (total_server_connections < MAX_OUTSTANDING_CONNECTIONS) | ||
620 | { | ||
621 | GNUNET_SCHEDULER_add_now (&send_test_messages, pos->next); | ||
622 | } | ||
623 | else | ||
624 | { | ||
625 | GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply | ||
626 | (GNUNET_TIME_UNIT_SECONDS, 1), | ||
627 | &send_test_messages, pos->next); | ||
628 | } | ||
629 | } | ||
630 | |||
631 | |||
632 | static void | ||
633 | send_other_messages (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) | ||
634 | { | ||
635 | struct TestMessageContext *pos; | ||
636 | struct TestMessageContext *free_pos; | ||
637 | struct PeerContext *peer_pos; | ||
638 | |||
639 | #if TEST_ALL | ||
640 | struct PeerContext *inner_peer_pos; | ||
641 | struct TestMessageContext *temp_context; | ||
642 | #endif | ||
643 | peer_pos = all_peers; | ||
644 | while (peer_pos != NULL) | ||
645 | { | ||
646 | if (peer_pos->peer_handle != NULL) | ||
647 | { | ||
648 | GNUNET_CORE_disconnect (peer_pos->peer_handle); | ||
649 | peer_pos->peer_handle = NULL; | ||
650 | } | ||
651 | #if TEST_ALL | ||
652 | inner_peer_pos = all_peers; | ||
653 | while (inner_peer_pos != NULL) | ||
654 | { | ||
655 | if (inner_peer_pos != peer_pos) | ||
656 | { | ||
657 | temp_total_other_messages++; | ||
658 | temp_context = GNUNET_malloc (sizeof (struct TestMessageContext)); | ||
659 | temp_context->peer1 = peer_pos->daemon; | ||
660 | temp_context->peer2 = inner_peer_pos->daemon; | ||
661 | temp_context->next = other_test_messages; | ||
662 | temp_context->uid = total_connections + temp_total_other_messages; | ||
663 | temp_context->disconnect_task = GNUNET_SCHEDULER_NO_TASK; | ||
664 | other_test_messages = temp_context; | ||
665 | } | ||
666 | inner_peer_pos = inner_peer_pos->next; | ||
667 | } | ||
668 | #endif | ||
669 | peer_pos = peer_pos->next; | ||
670 | } | ||
671 | all_peers = NULL; | ||
672 | |||
673 | pos = test_messages; | ||
674 | while (pos != NULL) | ||
675 | { | ||
676 | if (pos->peer1handle != NULL) | ||
677 | { | ||
678 | GNUNET_CORE_disconnect (pos->peer1handle); | ||
679 | pos->peer1handle = NULL; | ||
680 | } | ||
681 | if (pos->peer2handle != NULL) | ||
682 | { | ||
683 | GNUNET_CORE_disconnect (pos->peer2handle); | ||
684 | pos->peer2handle = NULL; | ||
685 | } | ||
686 | free_pos = pos; | ||
687 | pos = pos->next; | ||
688 | if (free_pos->disconnect_task != GNUNET_SCHEDULER_NO_TASK) | ||
689 | { | ||
690 | GNUNET_SCHEDULER_cancel (free_pos->disconnect_task); | ||
691 | } | ||
692 | GNUNET_free (free_pos); | ||
693 | } | ||
694 | test_messages = NULL; | ||
695 | |||
696 | total_other_expected_messages = temp_total_other_messages; | ||
697 | if (total_other_expected_messages == 0) | ||
698 | { | ||
699 | GNUNET_SCHEDULER_add_now (&end_badly, | ||
700 | "send_other_messages had 0 messages to send, no DV connections made!"); | ||
701 | } | ||
702 | GNUNET_log (GNUNET_ERROR_TYPE_WARNING, | ||
703 | "Preparing to send %d other test messages\n", | ||
704 | total_other_expected_messages); | ||
705 | GNUNET_SCHEDULER_add_now (&send_test_messages, other_test_messages); | ||
706 | if (GNUNET_SCHEDULER_NO_TASK != die_task) | ||
707 | GNUNET_SCHEDULER_cancel (die_task); | ||
708 | die_task = | ||
709 | GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply | ||
710 | (GNUNET_TIME_UNIT_SECONDS, 250), &end_badly, | ||
711 | "from send_other_messages"); | ||
712 | } | ||
713 | |||
714 | |||
715 | static void | ||
716 | topology_callback (void *cls, const struct GNUNET_PeerIdentity *first, | ||
717 | const struct GNUNET_PeerIdentity *second, uint32_t distance, | ||
718 | const struct GNUNET_CONFIGURATION_Handle *first_cfg, | ||
719 | const struct GNUNET_CONFIGURATION_Handle *second_cfg, | ||
720 | struct GNUNET_TESTING_Daemon *first_daemon, | ||
721 | struct GNUNET_TESTING_Daemon *second_daemon, | ||
722 | const char *emsg) | ||
723 | { | ||
724 | struct TestMessageContext *temp_context; | ||
725 | |||
726 | if (emsg == NULL) | ||
727 | { | ||
728 | total_connections++; | ||
729 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
730 | "connected peer %s to peer %s, distance %u\n", | ||
731 | first_daemon->shortname, second_daemon->shortname, distance); | ||
732 | temp_context = GNUNET_malloc (sizeof (struct TestMessageContext)); | ||
733 | temp_context->peer1 = first_daemon; | ||
734 | temp_context->peer2 = second_daemon; | ||
735 | temp_context->next = test_messages; | ||
736 | temp_context->uid = total_connections; | ||
737 | temp_context->disconnect_task = GNUNET_SCHEDULER_NO_TASK; | ||
738 | test_messages = temp_context; | ||
739 | expected_messages++; | ||
740 | } | ||
741 | else | ||
742 | { | ||
743 | failed_connections++; | ||
744 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
745 | "Failed to connect peer %s to peer %s with error :\n%s\n", | ||
746 | first_daemon->shortname, second_daemon->shortname, emsg); | ||
747 | } | ||
748 | |||
749 | if (total_connections == expected_connections) | ||
750 | { | ||
751 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
752 | "Created %u total connections, which is our target number! Calling send messages.\n", | ||
753 | total_connections); | ||
754 | if (GNUNET_SCHEDULER_NO_TASK != die_task) | ||
755 | GNUNET_SCHEDULER_cancel (die_task); | ||
756 | die_task = GNUNET_SCHEDULER_NO_TASK; | ||
757 | GNUNET_SCHEDULER_add_now (&send_test_messages, test_messages); | ||
758 | } | ||
759 | else if (total_connections + failed_connections == expected_connections) | ||
760 | { | ||
761 | if (failed_connections < | ||
762 | (unsigned int) (fail_percentage * total_connections)) | ||
763 | { | ||
764 | GNUNET_SCHEDULER_cancel (die_task); | ||
765 | die_task = GNUNET_SCHEDULER_NO_TASK; | ||
766 | /* FIXME: ret value!? */ GNUNET_SCHEDULER_add_now (&send_test_messages, | ||
767 | test_messages); | ||
768 | } | ||
769 | else | ||
770 | { | ||
771 | if (die_task != GNUNET_SCHEDULER_NO_TASK) | ||
772 | GNUNET_SCHEDULER_cancel (die_task); | ||
773 | die_task = | ||
774 | GNUNET_SCHEDULER_add_now (&end_badly, | ||
775 | "from topology_callback (too many failed connections)"); | ||
776 | } | ||
777 | } | 49 | } |
50 | ok = 0; | ||
51 | if (1) | ||
52 | GNUNET_SCHEDULER_shutdown (); | ||
778 | else | 53 | else |
779 | { | 54 | fprintf (stderr, "Test passed, press CTRL-C to shut down\n"); |
780 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
781 | "Have %d total connections, %d failed connections, Want %d (at least %d)\n", | ||
782 | total_connections, failed_connections, expected_connections, | ||
783 | expected_connections - | ||
784 | (unsigned int) (fail_percentage * expected_connections)); | ||
785 | } | ||
786 | } | ||
787 | |||
788 | |||
789 | /** | ||
790 | * Method called whenever a given peer connects. | ||
791 | * | ||
792 | * @param cls closure | ||
793 | * @param peer peer identity this notification is about | ||
794 | * @param atsi performance data about this peer's connection | ||
795 | * @param atsi_count number of atsi datums | ||
796 | * | ||
797 | */ | ||
798 | static void | ||
799 | all_connect_handler (void *cls, const struct GNUNET_PeerIdentity *peer, | ||
800 | const struct GNUNET_ATS_Information *atsi, | ||
801 | unsigned int atsi_count) | ||
802 | { | ||
803 | struct GNUNET_TESTING_Daemon *d = cls; | ||
804 | struct GNUNET_TESTING_Daemon *second_daemon; | ||
805 | char *second_shortname; | ||
806 | |||
807 | #if !TEST_ALL | ||
808 | struct TestMessageContext *temp_context; | ||
809 | #endif | ||
810 | uint32_t distance; | ||
811 | |||
812 | if (0 == memcmp (&d->id, peer, sizeof (struct GNUNET_PeerIdentity))) | ||
813 | return; | ||
814 | second_shortname = GNUNET_strdup (GNUNET_i2s (peer)); | ||
815 | distance = get_atsi_distance (atsi, atsi_count); | ||
816 | |||
817 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
818 | "connected peer %s to peer %s, distance %u\n", d->shortname, | ||
819 | second_shortname, distance); | ||
820 | second_daemon = | ||
821 | GNUNET_CONTAINER_multihashmap_get (peer_daemon_hash, &peer->hashPubKey); | ||
822 | |||
823 | if (second_daemon == NULL) | ||
824 | { | ||
825 | GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Couldn't find second peer!\n"); | ||
826 | GNUNET_free (second_shortname); | ||
827 | return; | ||
828 | } | ||
829 | #if !TEST_ALL | ||
830 | if (distance > 1) | ||
831 | { | ||
832 | temp_total_other_messages++; | ||
833 | temp_context = GNUNET_malloc (sizeof (struct TestMessageContext)); | ||
834 | temp_context->peer1 = d; | ||
835 | temp_context->peer2 = second_daemon; | ||
836 | temp_context->next = other_test_messages; | ||
837 | temp_context->uid = total_connections + temp_total_other_messages; | ||
838 | temp_context->disconnect_task = GNUNET_SCHEDULER_NO_TASK; | ||
839 | other_test_messages = temp_context; | ||
840 | } | ||
841 | #endif | ||
842 | |||
843 | if (dotOutFile != NULL) | ||
844 | { | ||
845 | if (distance == 1) | ||
846 | FPRINTF (dotOutFile, "\tn%s -- n%s;\n", d->shortname, second_shortname); | ||
847 | else if (distance == 2) | ||
848 | FPRINTF (dotOutFile, "\tn%s -- n%s [color=blue];\n", d->shortname, | ||
849 | second_shortname); | ||
850 | else if (distance == 3) | ||
851 | FPRINTF (dotOutFile, "\tn%s -- n%s [color=red];\n", d->shortname, | ||
852 | second_shortname); | ||
853 | else if (distance == 4) | ||
854 | FPRINTF (dotOutFile, "\tn%s -- n%s [color=green];\n", d->shortname, | ||
855 | second_shortname); | ||
856 | else | ||
857 | FPRINTF (dotOutFile, "\tn%s -- n%s [color=brown];\n", d->shortname, | ||
858 | second_shortname); | ||
859 | } | ||
860 | GNUNET_free (second_shortname); | ||
861 | |||
862 | if (temp_total_other_messages == num_additional_messages) | ||
863 | { | ||
864 | /* FIXME: ret value!? */ GNUNET_SCHEDULER_add_now (&send_other_messages, | ||
865 | NULL); | ||
866 | } | ||
867 | } | ||
868 | |||
869 | |||
870 | static void | ||
871 | peers_started_callback (void *cls, const struct GNUNET_PeerIdentity *id, | ||
872 | const struct GNUNET_CONFIGURATION_Handle *cfg, | ||
873 | struct GNUNET_TESTING_Daemon *d, const char *emsg) | ||
874 | { | ||
875 | struct PeerContext *new_peer; | ||
876 | |||
877 | if (emsg != NULL) | ||
878 | { | ||
879 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
880 | "Failed to start daemon with error: `%s'\n", emsg); | ||
881 | return; | ||
882 | } | ||
883 | GNUNET_assert (id != NULL); | ||
884 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Started daemon %llu out of %llu\n", | ||
885 | (num_peers - peers_left) + 1, num_peers); | ||
886 | GNUNET_assert (GNUNET_SYSERR != | ||
887 | GNUNET_CONTAINER_multihashmap_put (peer_daemon_hash, | ||
888 | &id->hashPubKey, d, | ||
889 | GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY)); | ||
890 | |||
891 | new_peer = GNUNET_malloc (sizeof (struct PeerContext)); | ||
892 | new_peer->peer_handle = | ||
893 | GNUNET_CORE_connect (cfg, d, NULL, &all_connect_handler, NULL, NULL, | ||
894 | GNUNET_NO, NULL, GNUNET_NO, no_handlers); | ||
895 | new_peer->daemon = d; | ||
896 | new_peer->next = all_peers; | ||
897 | all_peers = new_peer; | ||
898 | peers_left--; | ||
899 | |||
900 | if (peers_left == 0) | ||
901 | { | ||
902 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
903 | "All %d daemons started, now creating topology!\n", num_peers); | ||
904 | GNUNET_SCHEDULER_cancel (die_task); | ||
905 | die_task = GNUNET_SCHEDULER_NO_TASK; | ||
906 | expected_connections = -1; | ||
907 | if ((pg != NULL) && (peers_left == 0)) | ||
908 | { | ||
909 | expected_connections = | ||
910 | GNUNET_TESTING_connect_topology (pg, connection_topology, | ||
911 | connect_topology_option, | ||
912 | connect_topology_option_modifier, | ||
913 | TIMEOUT, 12, NULL, NULL); | ||
914 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Have %d expected connections\n", | ||
915 | expected_connections); | ||
916 | } | ||
917 | |||
918 | if (expected_connections == GNUNET_SYSERR) | ||
919 | { | ||
920 | die_task = | ||
921 | GNUNET_SCHEDULER_add_now (&end_badly, | ||
922 | "from connect topology (bad return)"); | ||
923 | } | ||
924 | else | ||
925 | { | ||
926 | /* Set up task in case topology creation doesn't finish | ||
927 | * within a reasonable amount of time */ | ||
928 | die_task = | ||
929 | GNUNET_SCHEDULER_add_delayed (TEST_TIMEOUT, &end_badly, | ||
930 | "from connect topology (timeout)"); | ||
931 | } | ||
932 | ok = 0; | ||
933 | } | ||
934 | } | ||
935 | |||
936 | |||
937 | /** | ||
938 | * Callback indicating that the hostkey was created for a peer. | ||
939 | * | ||
940 | * @param cls NULL | ||
941 | * @param id the peer identity | ||
942 | * @param d the daemon handle (pretty useless at this point, remove?) | ||
943 | * @param emsg non-null on failure | ||
944 | */ | ||
945 | static void | ||
946 | hostkey_callback (void *cls, const struct GNUNET_PeerIdentity *id, | ||
947 | struct GNUNET_TESTING_Daemon *d, const char *emsg) | ||
948 | { | ||
949 | if (emsg != NULL) | ||
950 | { | ||
951 | GNUNET_log (GNUNET_ERROR_TYPE_WARNING, | ||
952 | "Hostkey callback received error: %s\n", emsg); | ||
953 | } | ||
954 | |||
955 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Hostkey created for peer `%s'\n", | ||
956 | GNUNET_i2s (id)); | ||
957 | peers_left--; | ||
958 | if (peers_left == 0) | ||
959 | { | ||
960 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
961 | "All %d hostkeys created, now creating topology!\n", num_peers); | ||
962 | if (GNUNET_SCHEDULER_NO_TASK != die_task) | ||
963 | { | ||
964 | GNUNET_SCHEDULER_cancel (die_task); | ||
965 | die_task = GNUNET_SCHEDULER_NO_TASK; | ||
966 | } | ||
967 | /* create topology */ | ||
968 | peers_left = num_peers; /* Reset counter */ | ||
969 | if (GNUNET_TESTING_create_topology | ||
970 | (pg, topology, blacklist_topology, | ||
971 | blacklist_transports) != GNUNET_SYSERR) | ||
972 | { | ||
973 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
974 | "Topology set up, now starting peers!\n"); | ||
975 | GNUNET_TESTING_daemons_continue_startup (pg); | ||
976 | /* Set up task in case topology creation doesn't finish | ||
977 | * within a reasonable amount of time */ | ||
978 | die_task = | ||
979 | GNUNET_SCHEDULER_add_delayed (TEST_TIMEOUT, &end_badly, | ||
980 | "from continue startup (timeout)"); | ||
981 | } | ||
982 | else | ||
983 | { | ||
984 | die_task = | ||
985 | GNUNET_SCHEDULER_add_now (&end_badly, | ||
986 | "from create topology (bad return)"); | ||
987 | } | ||
988 | ok = 0; | ||
989 | } | ||
990 | } | ||
991 | |||
992 | |||
993 | static void | ||
994 | run (void *cls, char *const *args, const char *cfgfile, | ||
995 | const struct GNUNET_CONFIGURATION_Handle *cfg) | ||
996 | { | ||
997 | char *topology_str; | ||
998 | char *connect_topology_str; | ||
999 | char *blacklist_topology_str; | ||
1000 | char *connect_topology_option_str; | ||
1001 | char *connect_topology_option_modifier_string; | ||
1002 | |||
1003 | ok = 1; | ||
1004 | |||
1005 | dotOutFile = fopen (dotOutFileName, "w"); | ||
1006 | if (dotOutFile != NULL) | ||
1007 | { | ||
1008 | FPRINTF (dotOutFile, "%s", "strict graph G {\n"); | ||
1009 | } | ||
1010 | |||
1011 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
1012 | "Starting daemons based on config file %s\n", cfgfile); | ||
1013 | if (GNUNET_YES != | ||
1014 | GNUNET_CONFIGURATION_get_value_string (cfg, "paths", "servicehome", | ||
1015 | &test_directory)) | ||
1016 | { | ||
1017 | ok = 404; | ||
1018 | return; | ||
1019 | } | ||
1020 | |||
1021 | if ((GNUNET_YES == | ||
1022 | GNUNET_CONFIGURATION_get_value_string (cfg, "testing", "topology", | ||
1023 | &topology_str)) && | ||
1024 | (GNUNET_NO == GNUNET_TESTING_topology_get (&topology, topology_str))) | ||
1025 | { | ||
1026 | GNUNET_log (GNUNET_ERROR_TYPE_WARNING, | ||
1027 | "Invalid topology `%s' given for section %s option %s\n", | ||
1028 | topology_str, "TESTING", "TOPOLOGY"); | ||
1029 | topology = GNUNET_TESTING_TOPOLOGY_CLIQUE; /* Defaults to NONE, so set better default here */ | ||
1030 | } | ||
1031 | |||
1032 | if ((GNUNET_YES == | ||
1033 | GNUNET_CONFIGURATION_get_value_string (cfg, "testing", | ||
1034 | "connect_topology", | ||
1035 | &connect_topology_str)) && | ||
1036 | (GNUNET_NO == | ||
1037 | GNUNET_TESTING_topology_get (&connection_topology, | ||
1038 | connect_topology_str))) | ||
1039 | { | ||
1040 | GNUNET_log (GNUNET_ERROR_TYPE_WARNING, | ||
1041 | "Invalid connect topology `%s' given for section %s option %s\n", | ||
1042 | connect_topology_str, "TESTING", "CONNECT_TOPOLOGY"); | ||
1043 | } | ||
1044 | GNUNET_free_non_null (connect_topology_str); | ||
1045 | if ((GNUNET_YES == | ||
1046 | GNUNET_CONFIGURATION_get_value_string (cfg, "testing", | ||
1047 | "connect_topology_option", | ||
1048 | &connect_topology_option_str)) && | ||
1049 | (GNUNET_NO == | ||
1050 | GNUNET_TESTING_topology_option_get (&connect_topology_option, | ||
1051 | connect_topology_option_str))) | ||
1052 | { | ||
1053 | GNUNET_log (GNUNET_ERROR_TYPE_WARNING, | ||
1054 | "Invalid connect topology option `%s' given for section %s option %s\n", | ||
1055 | connect_topology_option_str, "TESTING", | ||
1056 | "CONNECT_TOPOLOGY_OPTION"); | ||
1057 | connect_topology_option = GNUNET_TESTING_TOPOLOGY_OPTION_ALL; /* Defaults to NONE, set to ALL */ | ||
1058 | } | ||
1059 | GNUNET_free_non_null (connect_topology_option_str); | ||
1060 | if (GNUNET_YES == | ||
1061 | GNUNET_CONFIGURATION_get_value_string (cfg, "testing", | ||
1062 | "connect_topology_option_modifier", | ||
1063 | &connect_topology_option_modifier_string)) | ||
1064 | { | ||
1065 | if (SSCANF | ||
1066 | (connect_topology_option_modifier_string, "%lf", | ||
1067 | &connect_topology_option_modifier) != 1) | ||
1068 | { | ||
1069 | GNUNET_log_config_invalid (GNUNET_ERROR_TYPE_WARNING, | ||
1070 | "testing", "connect_topology_option_modifier", | ||
1071 | "expected float"); | ||
1072 | } | ||
1073 | GNUNET_free (connect_topology_option_modifier_string); | ||
1074 | } | ||
1075 | |||
1076 | if (GNUNET_YES != | ||
1077 | GNUNET_CONFIGURATION_get_value_string (cfg, "testing", | ||
1078 | "blacklist_transports", | ||
1079 | &blacklist_transports)) | ||
1080 | blacklist_transports = NULL; | ||
1081 | |||
1082 | if ((GNUNET_YES == | ||
1083 | GNUNET_CONFIGURATION_get_value_string (cfg, "testing", | ||
1084 | "blacklist_topology", | ||
1085 | &blacklist_topology_str)) && | ||
1086 | (GNUNET_NO == | ||
1087 | GNUNET_TESTING_topology_get (&blacklist_topology, | ||
1088 | blacklist_topology_str))) | ||
1089 | { | ||
1090 | GNUNET_log (GNUNET_ERROR_TYPE_WARNING, | ||
1091 | "Invalid topology `%s' given for section %s option %s\n", | ||
1092 | topology_str, "TESTING", "BLACKLIST_TOPOLOGY"); | ||
1093 | } | ||
1094 | GNUNET_free_non_null (topology_str); | ||
1095 | GNUNET_free_non_null (blacklist_topology_str); | ||
1096 | if (GNUNET_SYSERR == | ||
1097 | GNUNET_CONFIGURATION_get_value_number (cfg, "testing", "num_peers", | ||
1098 | &num_peers)) | ||
1099 | num_peers = DEFAULT_NUM_PEERS; | ||
1100 | |||
1101 | if (GNUNET_SYSERR == | ||
1102 | GNUNET_CONFIGURATION_get_value_number (cfg, "testing", | ||
1103 | "additional_messages", | ||
1104 | &num_additional_messages)) | ||
1105 | num_additional_messages = DEFAULT_ADDITIONAL_MESSAGES; | ||
1106 | |||
1107 | main_cfg = cfg; | ||
1108 | |||
1109 | GNUNET_assert (num_peers > 0 && num_peers < (unsigned int) -1); | ||
1110 | peers_left = num_peers; | ||
1111 | |||
1112 | /* Set up a task to end testing if peer start fails */ | ||
1113 | die_task = | ||
1114 | GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_relative_multiply | ||
1115 | (GNUNET_TIME_UNIT_MINUTES, 5), &end_badly, | ||
1116 | "didn't start all daemons in reasonable amount of time!!!"); | ||
1117 | |||
1118 | peer_daemon_hash = GNUNET_CONTAINER_multihashmap_create (peers_left, GNUNET_NO); | ||
1119 | pg = GNUNET_TESTING_daemons_start (cfg, peers_left, /* Total number of peers */ | ||
1120 | peers_left, /* Number of outstanding connections */ | ||
1121 | peers_left, /* Number of parallel ssh connections, or peers being started at once */ | ||
1122 | TIMEOUT, &hostkey_callback, NULL, | ||
1123 | &peers_started_callback, NULL, | ||
1124 | &topology_callback, NULL, NULL); | ||
1125 | |||
1126 | } | 55 | } |
1127 | 56 | ||
1128 | 57 | ||
1129 | int | 58 | int |
1130 | main (int argc, char *argv[]) | 59 | main (int argc, char *argv[]) |
1131 | { | 60 | { |
1132 | int ret; | 61 | ok = 1; |
1133 | 62 | (void) GNUNET_TESTBED_test_run ("test-transport-api-dv", | |
1134 | char *const argv[] = { "test-transport-dv", | 63 | "test_transport_dv_data.conf", |
1135 | "-c", | 64 | 4, |
1136 | "test_transport_dv_data.conf", | 65 | 0, NULL, NULL, |
1137 | NULL | 66 | &test_connection, NULL); |
1138 | }; | 67 | return ok; |
1139 | struct GNUNET_GETOPT_CommandLineOption options[] = { | ||
1140 | GNUNET_GETOPT_OPTION_END | ||
1141 | }; | ||
1142 | GNUNET_log_setup ("test-transport-dv", | ||
1143 | "WARNING", | ||
1144 | NULL); | ||
1145 | ret = | ||
1146 | GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, argv, | ||
1147 | "test-transport-dv", "nohelp", options, &run, &ok); | ||
1148 | if (ret != GNUNET_OK) | ||
1149 | { | ||
1150 | GNUNET_log (GNUNET_ERROR_TYPE_WARNING, | ||
1151 | "`test-transport-dv': Failed with error code %d\n", ret); | ||
1152 | } | ||
1153 | /** | ||
1154 | * Need to remove base directory, subdirectories taken care | ||
1155 | * of by the testing framework. | ||
1156 | */ | ||
1157 | if (GNUNET_DISK_directory_remove (test_directory) != GNUNET_OK) | ||
1158 | { | ||
1159 | GNUNET_log (GNUNET_ERROR_TYPE_WARNING, | ||
1160 | "Failed to remove testing directory %s\n", test_directory); | ||
1161 | } | ||
1162 | return (GNUNET_OK == ret) ? 0 : 1; | ||
1163 | } | 68 | } |
1164 | 69 | ||
1165 | /* end of test_transport_api_dv.c */ | 70 | /* end of test_transport_api_dv.c */ |
diff --git a/src/dv/test_transport_dv_data.conf b/src/dv/test_transport_dv_data.conf index 8232461e5..9ff130f9c 100644 --- a/src/dv/test_transport_dv_data.conf +++ b/src/dv/test_transport_dv_data.conf | |||
@@ -1,74 +1,48 @@ | |||
1 | [PATHS] | 1 | [PATHS] |
2 | SERVICEHOME = /tmp/test-gnunet-dv-testing/ | 2 | SERVICEHOME = /tmp/test-gnunet-dv-testing/ |
3 | 3 | ||
4 | [resolver] | ||
5 | PORT = 2564 | ||
6 | |||
7 | [transport] | 4 | [transport] |
8 | PORT = 2565 | 5 | PORT = 2565 |
9 | PLUGINS = tcp dv | 6 | PLUGINS = tcp dv |
10 | BLACKLIST_FILE = $SERVICEHOME/blacklist | 7 | BLACKLIST_FILE = $SERVICEHOME/blacklist |
11 | BINARY = gnunet-service-transport | ||
12 | USE_LOCALADDR = NO | ||
13 | 8 | ||
14 | [arm] | 9 | [arm] |
15 | PORT = 2566 | 10 | DEFAULTSERVICES = core |
16 | DEFAULTSERVICES = | ||
17 | |||
18 | [statistics] | ||
19 | PORT = 2567 | ||
20 | |||
21 | [transport-tcp] | ||
22 | PORT = 2568 | ||
23 | BINDTO = 127.0.0.1 | ||
24 | |||
25 | [transport-udp] | ||
26 | PORT = 2568 | ||
27 | |||
28 | [peerinfo] | ||
29 | PORT = 2569 | ||
30 | |||
31 | [core] | ||
32 | PORT = 2570 | ||
33 | 11 | ||
34 | [dv] | 12 | [dv] |
35 | AUTOSTART = YES | 13 | AUTOSTART = YES |
36 | ACCEPT_FROM6 = ::1; | 14 | #PREFIX = valgrind |
37 | ACCEPT_FROM = 127.0.0.1; | 15 | |
38 | BINARY = gnunet-service-dv | 16 | [consensus] |
39 | HOME = $SERVICEHOME | 17 | PREFIX = valgrind |
40 | HOSTNAME = localhost | ||
41 | PORT = 2571 | ||
42 | 18 | ||
43 | [testing] | 19 | [testbed] |
44 | NUM_PEERS = 3 | 20 | OVERLAY_TOPOLOGY = CLIQUE |
45 | ADDITIONAL_MESSAGES = 10 | ||
46 | WEAKRANDOM = YES | ||
47 | TOPOLOGY = CLIQUE | ||
48 | CONNECT_TOPOLOGY = LINE | ||
49 | BLACKLIST_TOPOLOGY = LINE | ||
50 | BLACKLIST_TRANSPORTS = tcp | ||
51 | F2F = YES | ||
52 | HOSTKEYSFILE = ${DATADIR}/testing_hostkeys.dat | ||
53 | 21 | ||
54 | [fs] | 22 | [fs] |
55 | AUTOSTART = NO | 23 | AUTOSTART = NO |
56 | 24 | ||
57 | [nat] | 25 | [datastore] |
58 | DISABLEV6 = YES | 26 | AUTOSTART = NO |
59 | ENABLE_UPNP = NO | ||
60 | BEHIND_NAT = NO | ||
61 | ALLOW_NAT = NO | ||
62 | INTERNAL_ADDRESS = 127.0.0.1 | ||
63 | EXTERNAL_ADDRESS = 127.0.0.1 | ||
64 | USE_LOCALADDR = NO | ||
65 | 27 | ||
66 | [dns] | 28 | [dns] |
67 | AUTOSTART = NO | 29 | AUTOSTART = NO |
68 | 30 | ||
31 | [nse] | ||
32 | AUTOSTART = NO | ||
69 | 33 | ||
34 | [chat] | ||
35 | AUTOSTART = NO | ||
70 | 36 | ||
71 | [nse] | 37 | [gns] |
38 | AUTOSTART = NO | ||
39 | |||
40 | [vpn] | ||
41 | AUTOSTART = NO | ||
42 | |||
43 | [namestore] | ||
72 | AUTOSTART = NO | 44 | AUTOSTART = NO |
73 | 45 | ||
46 | [lockmanager] | ||
47 | AUTOSTART = NO | ||
74 | 48 | ||