aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorMatthias Wachs <wachs@net.in.tum.de>2011-10-25 21:03:44 +0000
committerMatthias Wachs <wachs@net.in.tum.de>2011-10-25 21:03:44 +0000
commit8bca2d91acaffcbbc747b93d347e10616c40b8fc (patch)
treed786c2f702b58522ad1f5675e8973cb63cc6c7e6 /src
parent4e8e34ae6b609a86cf8c0a6943b8b6ad13ce3a5d (diff)
downloadgnunet-8bca2d91acaffcbbc747b93d347e10616c40b8fc.tar.gz
gnunet-8bca2d91acaffcbbc747b93d347e10616c40b8fc.zip
Diffstat (limited to 'src')
-rw-r--r--src/transport/gnunet-service-transport_neighbours_fsm.c93
1 files changed, 68 insertions, 25 deletions
diff --git a/src/transport/gnunet-service-transport_neighbours_fsm.c b/src/transport/gnunet-service-transport_neighbours_fsm.c
index ea92e776f..015a25062 100644
--- a/src/transport/gnunet-service-transport_neighbours_fsm.c
+++ b/src/transport/gnunet-service-transport_neighbours_fsm.c
@@ -342,8 +342,8 @@ lookup_neighbour (const struct GNUNET_PeerIdentity *pid)
342static int 342static int
343change (struct NeighbourMapEntry * n, int state, int line) 343change (struct NeighbourMapEntry * n, int state, int line)
344{ 344{
345 char * old; 345 char * old = NULL;
346 char * new; 346 char * new = NULL;
347 347
348 switch (n->state) { 348 switch (n->state) {
349 case S_CONNECTED: 349 case S_CONNECTED:
@@ -394,23 +394,46 @@ change (struct NeighbourMapEntry * n, int state, int line)
394 } 394 }
395 395
396 /* allowed transitions */ 396 /* allowed transitions */
397 int allowed = GNUNET_NO;
397 switch (n->state) { 398 switch (n->state) {
398 case S_NOT_CONNECTED: 399 case S_NOT_CONNECTED:
399 if (state == S_CONNECT_RECV) 400 if ((state == S_CONNECT_RECV) || (state == S_CONNECT_SENT))
400 break; 401 {
401 if (state == S_CONNECT_SENT) 402 allowed = GNUNET_YES;
402 break; 403 break;
404 }
405 break;
403 case S_CONNECT_RECV: 406 case S_CONNECT_RECV:
404 if (state == S_CONNECT_RECV_ACK_SENT) 407 if ((state == S_CONNECT_RECV_ACK_SENT) || (state == S_NOT_CONNECTED))
408 {
409 allowed = GNUNET_YES;
405 break; 410 break;
411 }
412 break;
406 case S_CONNECT_SENT: 413 case S_CONNECT_SENT:
407 if (state == S_NOT_CONNECTED) 414 if ((state == S_NOT_CONNECTED) || (state == S_CONNECTED))
408 break; 415 {
409 if (state == S_CONNECTED) 416 allowed = GNUNET_YES;
410 break; 417 break;
418 }
419 break;
411 case S_CONNECTED: 420 case S_CONNECTED:
421 if (state == S_NOT_CONNECTED)
422 {
423 allowed = GNUNET_YES;
424 break;
425 }
426 break;
412 case S_DISCONNECTED: 427 case S_DISCONNECTED:
428 break;
413 default: 429 default:
430 GNUNET_break (0);
431 break;
432
433 }
434
435 if (allowed == GNUNET_NO)
436 {
414 GNUNET_log (GNUNET_ERROR_TYPE_ERROR, 437 GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
415 "Illegal state transition from `%s' to `%s' in line %u \n", 438 "Illegal state transition from `%s' to `%s' in line %u \n",
416 old, new, line); 439 old, new, line);
@@ -604,9 +627,9 @@ disconnect_neighbour (struct NeighbourMapEntry *n)
604 n->is_active->n = NULL; 627 n->is_active->n = NULL;
605 n->is_active = NULL; 628 n->is_active = NULL;
606 } 629 }
607 if (GNUNET_YES == n->is_connected) 630 if (n->state == S_CONNECTED)
608 { 631 {
609 n->is_connected = GNUNET_NO; 632 change_state (n, S_NOT_CONNECTED);
610 GNUNET_assert (GNUNET_SCHEDULER_NO_TASK != n->keepalive_task); 633 GNUNET_assert (GNUNET_SCHEDULER_NO_TASK != n->keepalive_task);
611 GNUNET_SCHEDULER_cancel (n->keepalive_task); 634 GNUNET_SCHEDULER_cancel (n->keepalive_task);
612 n->keepalive_task = GNUNET_SCHEDULER_NO_TASK; 635 n->keepalive_task = GNUNET_SCHEDULER_NO_TASK;
@@ -1317,13 +1340,14 @@ GST_neighbours_force_disconnect (const struct GNUNET_PeerIdentity *target)
1317 struct NeighbourMapEntry *n; 1340 struct NeighbourMapEntry *n;
1318 struct GNUNET_TRANSPORT_PluginFunctions *papi; 1341 struct GNUNET_TRANSPORT_PluginFunctions *papi;
1319 struct SessionDisconnectMessage disconnect_msg; 1342 struct SessionDisconnectMessage disconnect_msg;
1343 int ret;
1320 1344
1321 GNUNET_assert (neighbours != NULL); 1345 GNUNET_assert (neighbours != NULL);
1322 1346
1323 n = lookup_neighbour (target); 1347 n = lookup_neighbour (target);
1324 if (NULL == n) 1348 if (NULL == n)
1325 return; /* not active */ 1349 return; /* not active */
1326 if (GNUNET_YES == n->is_connected) 1350 if (n->state == S_CONNECTED)
1327 { 1351 {
1328 /* we're actually connected, send DISCONNECT message */ 1352 /* we're actually connected, send DISCONNECT message */
1329 disconnect_msg.header.size = htons (sizeof (struct SessionDisconnectMessage)); 1353 disconnect_msg.header.size = htons (sizeof (struct SessionDisconnectMessage));
@@ -1342,14 +1366,20 @@ GST_neighbours_force_disconnect (const struct GNUNET_PeerIdentity *target)
1342 1366
1343 papi = GST_plugins_find (n->plugin_name); 1367 papi = GST_plugins_find (n->plugin_name);
1344 if (papi != NULL) 1368 if (papi != NULL)
1345 papi->send (papi->cls, target, (const void *) &disconnect_msg, 1369 {
1370 ret = papi->send (papi->cls, target, (const void *) &disconnect_msg,
1346 sizeof (disconnect_msg), 1371 sizeof (disconnect_msg),
1347 UINT32_MAX /* priority */ , 1372 UINT32_MAX /* priority */ ,
1348 GNUNET_TIME_UNIT_FOREVER_REL, n->session, n->addr, n->addrlen, 1373 GNUNET_TIME_UNIT_FOREVER_REL, n->session, n->addr, n->addrlen,
1349 GNUNET_YES, NULL, NULL); 1374 GNUNET_YES, NULL, NULL);
1350 GNUNET_STATISTICS_update (GST_stats, 1375 GNUNET_STATISTICS_update (GST_stats,
1351 gettext_noop ("# peers disconnected due to external request"), 1, 1376 gettext_noop ("# peers disconnected due to external request"), 1,
1352 GNUNET_NO); 1377 GNUNET_NO);
1378 if (ret == GNUNET_SYSERR)
1379 change_state (n, S_NOT_CONNECTED);
1380 else
1381 change_state (n, S_DISCONNECTED);
1382 }
1353 n = lookup_neighbour (target); 1383 n = lookup_neighbour (target);
1354 if (NULL == n) 1384 if (NULL == n)
1355 return; /* gone already */ 1385 return; /* gone already */
@@ -1427,21 +1457,34 @@ static void neighbour_connected (struct NeighbourMapEntry *n,
1427 const struct GNUNET_ATS_Information *ats, 1457 const struct GNUNET_ATS_Information *ats,
1428 uint32_t ats_count) 1458 uint32_t ats_count)
1429{ 1459{
1430 /* LEGACY */ 1460 struct GNUNET_TRANSPORT_PluginFunctions *papi;
1431 int was_connected; 1461 struct SessionConnectMessage scm;
1432 was_connected = n->is_connected; 1462 int ret;
1433 n->is_connected = GNUNET_YES;
1434 /* END LEGACY */
1435 1463
1436 if (GNUNET_YES != was_connected)
1437 n->keepalive_task = GNUNET_SCHEDULER_add_delayed (KEEPALIVE_FREQUENCY,
1438 &neighbour_keepalive_task,
1439 n);
1440 if (n->state == S_CONNECTED) 1464 if (n->state == S_CONNECTED)
1441 return; 1465 return;
1442 // First tell clients about connected neighbours...
1443 //change_state (n, S_CONNECTED);
1444 change_state (n, S_CONNECTED); 1466 change_state (n, S_CONNECTED);
1467
1468 n->keepalive_task = GNUNET_SCHEDULER_add_delayed (KEEPALIVE_FREQUENCY,
1469 &neighbour_keepalive_task,
1470 n);
1471
1472 /* send CONNECT_ACK (SYN_ACK)*/
1473 scm.header.size = htons (sizeof (struct SessionConnectMessage));
1474 scm.header.type =
1475 htons (GNUNET_MESSAGE_TYPE_TRANSPORT_SESSION_ACK);
1476 scm.reserved = htonl (0);
1477 scm.timestamp =
1478 GNUNET_TIME_absolute_hton (GNUNET_TIME_absolute_get ());
1479
1480 papi = GST_plugins_find (n->plugin_name);
1481 ret = papi->send (papi->cls, &n->id, (const char *) &scm, sizeof (struct SessionConnectMessage),
1482 0,
1483 GNUNET_TIME_UNIT_FOREVER_REL, NULL, n->addr, n->addrlen, GNUNET_YES,
1484 NULL, NULL);
1485 GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
1486 "neighbour_connected %i\n", ret);
1487
1445 neighbours_connected++; 1488 neighbours_connected++;
1446 GNUNET_STATISTICS_update (GST_stats, gettext_noop ("# peers connected"), 1, 1489 GNUNET_STATISTICS_update (GST_stats, gettext_noop ("# peers connected"), 1,
1447 GNUNET_NO); 1490 GNUNET_NO);