aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMatthias Wachs <wachs@net.in.tum.de>2013-12-03 14:23:55 +0000
committerMatthias Wachs <wachs@net.in.tum.de>2013-12-03 14:23:55 +0000
commite6360ebfcf61eaa143fe24004f5939ba133f4c2f (patch)
tree1557d88c9f01a79774098d2e3a3a89a49ffe92cc
parentac4d73e842785498e0e0a6fc53834e071a8a02d0 (diff)
downloadgnunet-e6360ebfcf61eaa143fe24004f5939ba133f4c2f.tar.gz
gnunet-e6360ebfcf61eaa143fe24004f5939ba133f4c2f.zip
- fixing crash during shutdown
- adding network functionality
-rw-r--r--src/dv/dv_api.c2
-rw-r--r--src/dv/gnunet-dv.c2
-rw-r--r--src/dv/gnunet-service-dv.c67
-rw-r--r--src/dv/plugin_transport_dv.c34
-rw-r--r--src/include/gnunet_dv_service.h3
5 files changed, 89 insertions, 19 deletions
diff --git a/src/dv/dv_api.c b/src/dv/dv_api.c
index 412ab47ad..2c2953de2 100644
--- a/src/dv/dv_api.c
+++ b/src/dv/dv_api.c
@@ -324,7 +324,7 @@ handle_message_receipt (void *cls,
324 cm = (const struct GNUNET_DV_ConnectMessage *) msg; 324 cm = (const struct GNUNET_DV_ConnectMessage *) msg;
325 sh->connect_cb (sh->cls, 325 sh->connect_cb (sh->cls,
326 &cm->peer, 326 &cm->peer,
327 ntohl (cm->distance)); 327 ntohl (cm->distance), ntohl (cm->network));
328 break; 328 break;
329 case GNUNET_MESSAGE_TYPE_DV_DISTANCE_CHANGED: 329 case GNUNET_MESSAGE_TYPE_DV_DISTANCE_CHANGED:
330 if (ntohs (msg->size) != sizeof (struct GNUNET_DV_DistanceUpdateMessage)) 330 if (ntohs (msg->size) != sizeof (struct GNUNET_DV_DistanceUpdateMessage))
diff --git a/src/dv/gnunet-dv.c b/src/dv/gnunet-dv.c
index 43af3458e..901739cc2 100644
--- a/src/dv/gnunet-dv.c
+++ b/src/dv/gnunet-dv.c
@@ -47,7 +47,7 @@ static int verbose;
47static void 47static void
48connect_cb (void *cls, 48connect_cb (void *cls,
49 const struct GNUNET_PeerIdentity *peer, 49 const struct GNUNET_PeerIdentity *peer,
50 uint32_t distance) 50 uint32_t distance, uint32_t network)
51{ 51{
52 fprintf (stderr, "Connect: %s at %u\n", 52 fprintf (stderr, "Connect: %s at %u\n",
53 GNUNET_i2s (peer), 53 GNUNET_i2s (peer),
diff --git a/src/dv/gnunet-service-dv.c b/src/dv/gnunet-service-dv.c
index f93f101d1..3946619b1 100644
--- a/src/dv/gnunet-service-dv.c
+++ b/src/dv/gnunet-service-dv.c
@@ -270,6 +270,11 @@ struct DirectNeighbor
270 uint32_t distance; 270 uint32_t distance;
271 271
272 /** 272 /**
273 * The network this peer is in
274 */
275 uint32_t network;
276
277 /**
273 * Is this neighbor connected at the core level? 278 * Is this neighbor connected at the core level?
274 */ 279 */
275 int connected; 280 int connected;
@@ -378,6 +383,7 @@ static struct GNUNET_STATISTICS_Handle *stats;
378 */ 383 */
379static struct GNUNET_ATS_PerformanceHandle *ats; 384static struct GNUNET_ATS_PerformanceHandle *ats;
380 385
386static int in_shutdown;
381 387
382/** 388/**
383 * Start creating a new DV set union by initiating the connection. 389 * Start creating a new DV set union by initiating the connection.
@@ -521,21 +527,23 @@ send_distance_change_to_plugin (const struct GNUNET_PeerIdentity *peer,
521 * 527 *
522 * @param target peer that connected 528 * @param target peer that connected
523 * @param distance distance to the target 529 * @param distance distance to the target
530 * @param the network the peer is in
524 */ 531 */
525static void 532static void
526send_connect_to_plugin (const struct GNUNET_PeerIdentity *target, 533send_connect_to_plugin (const struct GNUNET_PeerIdentity *target,
527 uint32_t distance) 534 uint32_t distance, uint32_t network)
528{ 535{
529 struct GNUNET_DV_ConnectMessage cm; 536 struct GNUNET_DV_ConnectMessage cm;
530 537
531 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, 538 GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
532 "Delivering CONNECT about peer `%s'\n", 539 "Delivering CONNECT about peer `%s' with distance %u\n",
533 GNUNET_i2s (target)); 540 GNUNET_i2s (target), distance);
534 cm.header.size = htons (sizeof (cm)); 541 cm.header.size = htons (sizeof (cm));
535 cm.header.type = htons (GNUNET_MESSAGE_TYPE_DV_CONNECT); 542 cm.header.type = htons (GNUNET_MESSAGE_TYPE_DV_CONNECT);
536 cm.distance = htonl (distance); 543 cm.distance = htonl (distance);
544 cm.network = htonl (network);
537 cm.peer = *target; 545 cm.peer = *target;
538 send_control_to_plugin (&cm.header); 546 //send_control_to_plugin (&cm.header);
539} 547}
540 548
541 549
@@ -602,6 +610,7 @@ core_transmit_notify (void *cls, size_t size, void *buf)
602 GNUNET_free (pending); 610 GNUNET_free (pending);
603 off += msize; 611 off += msize;
604 } 612 }
613 GNUNET_assert (NULL != core_api);
605 if (NULL != dn->pm_head) 614 if (NULL != dn->pm_head)
606 dn->cth = 615 dn->cth =
607 GNUNET_CORE_notify_transmit_ready (core_api, 616 GNUNET_CORE_notify_transmit_ready (core_api,
@@ -666,6 +675,7 @@ forward_payload (struct DirectNeighbor *target,
666 target->pm_tail, 675 target->pm_tail,
667 pm); 676 pm);
668 target->pm_queue_size++; 677 target->pm_queue_size++;
678 GNUNET_assert (NULL != core_api);
669 if (NULL == target->cth) 679 if (NULL == target->cth)
670 target->cth = GNUNET_CORE_notify_transmit_ready (core_api, 680 target->cth = GNUNET_CORE_notify_transmit_ready (core_api,
671 GNUNET_YES /* cork */, 681 GNUNET_YES /* cork */,
@@ -959,6 +969,7 @@ handle_core_connect (void *cls,
959 GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY)); 969 GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY));
960 neighbor->connected = GNUNET_YES; 970 neighbor->connected = GNUNET_YES;
961 neighbor->distance = 0; /* unknown */ 971 neighbor->distance = 0; /* unknown */
972 neighbor->network = GNUNET_ATS_NET_UNSPECIFIED;
962} 973}
963 974
964 975
@@ -1022,7 +1033,8 @@ check_possible_route (void *cls,
1022 &route->target.peer, 1033 &route->target.peer,
1023 route, 1034 route,
1024 GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY)); 1035 GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY));
1025 send_connect_to_plugin (&route->target.peer, ntohl (target->distance)); 1036 send_connect_to_plugin (&route->target.peer, ntohl (target->distance),
1037 neighbor->network);
1026 return GNUNET_YES; 1038 return GNUNET_YES;
1027} 1039}
1028 1040
@@ -1069,13 +1081,32 @@ get_atsi_distance (const struct GNUNET_ATS_Information *atsi,
1069 1081
1070 for (i = 0; i < atsi_count; i++) 1082 for (i = 0; i < atsi_count; i++)
1071 if (ntohl (atsi[i].type) == GNUNET_ATS_QUALITY_NET_DISTANCE) 1083 if (ntohl (atsi[i].type) == GNUNET_ATS_QUALITY_NET_DISTANCE)
1072 return (0 == ntohl (atsi->value)) ? DIRECT_NEIGHBOR_COST : ntohl (atsi->value); // FIXME: 0 check should not be required once ATS is fixed! 1084 return (0 == ntohl (atsi[i].value)) ? DIRECT_NEIGHBOR_COST : ntohl (atsi[i].value); // FIXME: 0 check should not be required once ATS is fixed!
1073 /* If we do not have explicit distance data, assume direct neighbor. */ 1085 /* If we do not have explicit distance data, assume direct neighbor. */
1074 return DIRECT_NEIGHBOR_COST; 1086 return DIRECT_NEIGHBOR_COST;
1075} 1087}
1076 1088
1077 1089
1078/** 1090/**
1091 * Get network information from 'atsi'.
1092 *
1093 * @param atsi performance data
1094 * @param atsi_count number of entries in atsi
1095 * @return connected transport network
1096 */
1097static uint32_t
1098get_atsi_network (const struct GNUNET_ATS_Information *atsi,
1099 uint32_t atsi_count)
1100{
1101 uint32_t i;
1102
1103 for (i = 0; i < atsi_count; i++)
1104 if (ntohl (atsi[i].type) == GNUNET_ATS_NETWORK_TYPE)
1105 return ntohl (atsi[i].value);
1106 return GNUNET_ATS_NET_UNSPECIFIED;
1107}
1108
1109/**
1079 * Multipeermap iterator for freeing routes that go via a particular 1110 * Multipeermap iterator for freeing routes that go via a particular
1080 * neighbor that disconnected and is thus no longer available. 1111 * neighbor that disconnected and is thus no longer available.
1081 * 1112 *
@@ -1193,10 +1224,13 @@ handle_ats_update (void *cls,
1193{ 1224{
1194 struct DirectNeighbor *neighbor; 1225 struct DirectNeighbor *neighbor;
1195 uint32_t distance; 1226 uint32_t distance;
1227 uint32_t network = GNUNET_ATS_NET_UNSPECIFIED;
1196 1228
1197 if (GNUNET_NO == active) 1229 if (GNUNET_NO == active)
1198 return; 1230 return;
1199 distance = get_atsi_distance (ats, ats_count); 1231 distance = get_atsi_distance (ats, ats_count);
1232 network = get_atsi_network (ats, ats_count);
1233
1200 /* 1234 /*
1201 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, 1235 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
1202 "ATS says distance to %s is %u\n", 1236 "ATS says distance to %s is %u\n",
@@ -1207,6 +1241,9 @@ handle_ats_update (void *cls,
1207 &address->peer); 1241 &address->peer);
1208 if (NULL != neighbor) 1242 if (NULL != neighbor)
1209 { 1243 {
1244 if (GNUNET_ATS_NET_UNSPECIFIED != network)
1245 neighbor->network = network;
1246
1210 if ( (DIRECT_NEIGHBOR_COST == neighbor->distance) && 1247 if ( (DIRECT_NEIGHBOR_COST == neighbor->distance) &&
1211 (DIRECT_NEIGHBOR_COST == distance) ) 1248 (DIRECT_NEIGHBOR_COST == distance) )
1212 return; /* no change */ 1249 return; /* no change */
@@ -1239,6 +1276,7 @@ handle_ats_update (void *cls,
1239 GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY)); 1276 GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY));
1240 neighbor->connected = GNUNET_NO; /* not yet */ 1277 neighbor->connected = GNUNET_NO; /* not yet */
1241 neighbor->distance = distance; 1278 neighbor->distance = distance;
1279 neighbor->network = network;
1242} 1280}
1243 1281
1244 1282
@@ -1350,8 +1388,10 @@ check_target_added (void *cls,
1350 &current_route->target.peer, 1388 &current_route->target.peer,
1351 current_route, 1389 current_route,
1352 GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY)); 1390 GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY));
1391
1353 send_connect_to_plugin (&current_route->target.peer, 1392 send_connect_to_plugin (&current_route->target.peer,
1354 ntohl (current_route->target.distance)); 1393 ntohl (current_route->target.distance),
1394 neighbor->network);
1355 return GNUNET_OK; 1395 return GNUNET_OK;
1356} 1396}
1357 1397
@@ -1782,6 +1822,10 @@ handle_core_disconnect (void *cls, const struct GNUNET_PeerIdentity *peer)
1782 -1, GNUNET_NO); 1822 -1, GNUNET_NO);
1783 } 1823 }
1784 cleanup_neighbor (neighbor); 1824 cleanup_neighbor (neighbor);
1825
1826 if (GNUNET_YES == in_shutdown)
1827 return;
1828
1785 GNUNET_CONTAINER_multipeermap_iterate (direct_neighbors, 1829 GNUNET_CONTAINER_multipeermap_iterate (direct_neighbors,
1786 &refresh_routes, 1830 &refresh_routes,
1787 NULL); 1831 NULL);
@@ -1842,7 +1886,9 @@ static void
1842shutdown_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) 1886shutdown_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc)
1843{ 1887{
1844 unsigned int i; 1888 unsigned int i;
1889 in_shutdown = GNUNET_YES;
1845 1890
1891 GNUNET_assert (NULL != core_api);
1846 GNUNET_CORE_disconnect (core_api); 1892 GNUNET_CORE_disconnect (core_api);
1847 core_api = NULL; 1893 core_api = NULL;
1848 GNUNET_ATS_performance_done (ats); 1894 GNUNET_ATS_performance_done (ats);
@@ -1858,9 +1904,11 @@ shutdown_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc)
1858 GNUNET_SERVER_notification_context_destroy (nc); 1904 GNUNET_SERVER_notification_context_destroy (nc);
1859 nc = NULL; 1905 nc = NULL;
1860 for (i=0;i<DEFAULT_FISHEYE_DEPTH - 1;i++) 1906 for (i=0;i<DEFAULT_FISHEYE_DEPTH - 1;i++)
1907 {
1861 GNUNET_array_grow (consensi[i].targets, 1908 GNUNET_array_grow (consensi[i].targets,
1862 consensi[i].array_length, 1909 consensi[i].array_length,
1863 0); 1910 0);
1911 }
1864} 1912}
1865 1913
1866 1914
@@ -1955,7 +2003,7 @@ run (void *cls, struct GNUNET_SERVER_Handle *server,
1955 0}, 2003 0},
1956 {NULL, NULL, 0, 0} 2004 {NULL, NULL, 0, 0}
1957 }; 2005 };
1958 2006 in_shutdown = GNUNET_NO;
1959 cfg = c; 2007 cfg = c;
1960 direct_neighbors = GNUNET_CONTAINER_multipeermap_create (128, GNUNET_NO); 2008 direct_neighbors = GNUNET_CONTAINER_multipeermap_create (128, GNUNET_NO);
1961 all_routes = GNUNET_CONTAINER_multipeermap_create (65536, GNUNET_NO); 2009 all_routes = GNUNET_CONTAINER_multipeermap_create (65536, GNUNET_NO);
@@ -1973,6 +2021,7 @@ run (void *cls, struct GNUNET_SERVER_Handle *server,
1973 if (NULL == ats) 2021 if (NULL == ats)
1974 { 2022 {
1975 GNUNET_CORE_disconnect (core_api); 2023 GNUNET_CORE_disconnect (core_api);
2024 core_api = NULL;
1976 return; 2025 return;
1977 } 2026 }
1978 nc = GNUNET_SERVER_notification_context_create (server, 2027 nc = GNUNET_SERVER_notification_context_create (server,
diff --git a/src/dv/plugin_transport_dv.c b/src/dv/plugin_transport_dv.c
index 30d33c2d7..ba625d257 100644
--- a/src/dv/plugin_transport_dv.c
+++ b/src/dv/plugin_transport_dv.c
@@ -38,6 +38,7 @@
38 38
39#define LOG(kind,...) GNUNET_log_from (kind, "transport-dv",__VA_ARGS__) 39#define LOG(kind,...) GNUNET_log_from (kind, "transport-dv",__VA_ARGS__)
40 40
41#define PLUGIN_NAME "dv"
41 42
42/** 43/**
43 * Encapsulation of all of the state of the plugin. 44 * Encapsulation of all of the state of the plugin.
@@ -123,6 +124,11 @@ struct Session
123 uint32_t distance; 124 uint32_t distance;
124 125
125 /** 126 /**
127 * Current network the next hop peer is located in
128 */
129 uint32_t network;
130
131 /**
126 * Does the transport service know about this session (and we thus 132 * Does the transport service know about this session (and we thus
127 * need to call 'session_end' when it is released?) 133 * need to call 'session_end' when it is released?)
128 */ 134 */
@@ -180,7 +186,7 @@ notify_distance_change (struct Session *session)
180 ats.value = htonl (session->distance); 186 ats.value = htonl (session->distance);
181 plugin->env->update_address_metrics (plugin->env->cls, 187 plugin->env->update_address_metrics (plugin->env->cls,
182 &session->sender, 188 &session->sender,
183 "", 0, 189 NULL, 0,
184 session, 190 session,
185 &ats, 1); 191 &ats, 1);
186} 192}
@@ -211,7 +217,7 @@ unbox_cb (void *cls,
211 message, 217 message,
212 session, "", 0); 218 session, "", 0);
213 plugin->env->update_address_metrics (plugin->env->cls, 219 plugin->env->update_address_metrics (plugin->env->cls,
214 &session->sender, "", 0, session, &ats, 1); 220 &session->sender, NULL, 0, session, &ats, 1);
215 return GNUNET_OK; 221 return GNUNET_OK;
216} 222}
217 223
@@ -278,14 +284,17 @@ handle_dv_message_received (void *cls,
278static void 284static void
279handle_dv_connect (void *cls, 285handle_dv_connect (void *cls,
280 const struct GNUNET_PeerIdentity *peer, 286 const struct GNUNET_PeerIdentity *peer,
281 uint32_t distance) 287 uint32_t distance, uint32_t network)
282{ 288{
283 struct Plugin *plugin = cls; 289 struct Plugin *plugin = cls;
284 struct Session *session; 290 struct Session *session;
291 struct GNUNET_ATS_Information ats[2];
285 292
286 LOG (GNUNET_ERROR_TYPE_DEBUG, "Received `%s' message for peer `%s'\n", 293 LOG (GNUNET_ERROR_TYPE_DEBUG,
294 "Received `%s' message for peer `%s' with next hop in network %s \n",
287 "DV_CONNECT", 295 "DV_CONNECT",
288 GNUNET_i2s (peer)); 296 GNUNET_i2s (peer),
297 GNUNET_ATS_print_network_type (network));
289 298
290 session = GNUNET_CONTAINER_multipeermap_get (plugin->sessions, 299 session = GNUNET_CONTAINER_multipeermap_get (plugin->sessions,
291 peer); 300 peer);
@@ -300,11 +309,20 @@ handle_dv_connect (void *cls,
300 session = GNUNET_new (struct Session); 309 session = GNUNET_new (struct Session);
301 session->sender = *peer; 310 session->sender = *peer;
302 session->distance = distance; 311 session->distance = distance;
312 session->network = network;
303 GNUNET_assert (GNUNET_YES == 313 GNUNET_assert (GNUNET_YES ==
304 GNUNET_CONTAINER_multipeermap_put (plugin->sessions, 314 GNUNET_CONTAINER_multipeermap_put (plugin->sessions,
305 &session->sender, 315 &session->sender,
306 session, 316 session,
307 GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY)); 317 GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY));
318
319 /* Notify transport and ats about new connection */
320 ats[0].type = htonl (GNUNET_ATS_QUALITY_NET_DISTANCE);
321 ats[0].value = htonl (distance);
322 ats[0].type = htonl (GNUNET_ATS_NETWORK_TYPE);
323 ats[0].value = htonl (network);
324 plugin->env->session_start (plugin->env->cls, peer, PLUGIN_NAME, NULL, 0,
325 session, ats, 2);
308} 326}
309 327
310 328
@@ -332,7 +350,8 @@ handle_dv_distance_changed (void *cls,
332 if (NULL == session) 350 if (NULL == session)
333 { 351 {
334 GNUNET_break (0); 352 GNUNET_break (0);
335 handle_dv_connect (plugin, peer, distance); 353 /* FIXME */
354 handle_dv_connect (plugin, peer, distance, 0);
336 return; 355 return;
337 } 356 }
338 session->distance = distance; 357 session->distance = distance;
@@ -398,6 +417,7 @@ handle_dv_disconnect (void *cls,
398 peer); 417 peer);
399 if (NULL == session) 418 if (NULL == session)
400 return; /* nothing to do */ 419 return; /* nothing to do */
420
401 free_session (session); 421 free_session (session);
402} 422}
403 423
@@ -668,7 +688,7 @@ dv_get_network (void *cls,
668 struct Session *session) 688 struct Session *session)
669{ 689{
670 GNUNET_assert (NULL != session); 690 GNUNET_assert (NULL != session);
671 return GNUNET_ATS_NET_UNSPECIFIED; 691 return session->network;
672} 692}
673 693
674 694
diff --git a/src/include/gnunet_dv_service.h b/src/include/gnunet_dv_service.h
index 967184130..9e49baf57 100644
--- a/src/include/gnunet_dv_service.h
+++ b/src/include/gnunet_dv_service.h
@@ -36,10 +36,11 @@
36 * @param cls closure 36 * @param cls closure
37 * @param peer newly connected peer 37 * @param peer newly connected peer
38 * @param distance distance to the peer 38 * @param distance distance to the peer
39 * @param network the peer is located in
39 */ 40 */
40typedef void (*GNUNET_DV_ConnectCallback)(void *cls, 41typedef void (*GNUNET_DV_ConnectCallback)(void *cls,
41 const struct GNUNET_PeerIdentity *peer, 42 const struct GNUNET_PeerIdentity *peer,
42 uint32_t distance); 43 uint32_t distance, uint32_t network);
43 44
44 45
45/** 46/**