gnunet-daemon-topology.c | gnunet-daemon-topology.c | |||
---|---|---|---|---|
skipping to change at line 26 | skipping to change at line 26 | |||
along with GNUnet; see the file COPYING. If not, write to the | along with GNUnet; see the file COPYING. If not, write to the | |||
Free Software Foundation, Inc., 59 Temple Place - Suite 330, | Free Software Foundation, Inc., 59 Temple Place - Suite 330, | |||
Boston, MA 02111-1307, USA. | Boston, MA 02111-1307, USA. | |||
*/ | */ | |||
/** | /** | |||
* @file topology/gnunet-daemon-topology.c | * @file topology/gnunet-daemon-topology.c | |||
* @brief code for maintaining the mesh topology | * @brief code for maintaining the mesh topology | |||
* @author Christian Grothoff | * @author Christian Grothoff | |||
*/ | */ | |||
#include <stdlib.h> | ||||
#include "platform.h" | #include "platform.h" | |||
#include "gnunet_constants.h" | #include "gnunet_constants.h" | |||
#include "gnunet_core_service.h" | #include "gnunet_core_service.h" | |||
#include "gnunet_protocols.h" | #include "gnunet_protocols.h" | |||
#include "gnunet_peerinfo_service.h" | #include "gnunet_peerinfo_service.h" | |||
#include "gnunet_statistics_service.h" | #include "gnunet_statistics_service.h" | |||
#include "gnunet_transport_service.h" | #include "gnunet_transport_service.h" | |||
#include "gnunet_util_lib.h" | #include "gnunet_util_lib.h" | |||
#define DEBUG_TOPOLOGY GNUNET_YES | /** | |||
* Minimum required delay between calls to GNUNET_TRANSPORT_try_connect. | ||||
*/ | ||||
#define MAX_CONNECT_FREQUENCY_DELAY GNUNET_TIME_relative_multiply (GNUNET_T | ||||
IME_UNIT_MILLISECONDS, 250) | ||||
/** | /** | |||
* For how long do we blacklist a peer after a failed connection | * For how long do we blacklist a peer after a failed connection | |||
* attempt? | * attempt? This is the baseline factor which is then multiplied by | |||
* two to the power of the number of failed attempts. | ||||
*/ | */ | |||
#define GREYLIST_AFTER_ATTEMPT GNUNET_TIME_relative_multiply (GNUNET_TIME_U NIT_MINUTES, 15) | #define GREYLIST_AFTER_ATTEMPT GNUNET_TIME_relative_multiply (GNUNET_TIME_U NIT_MINUTES, 1) | |||
/** | /** | |||
* For how long do we blacklist a friend after a failed connection | * For how long do we blacklist a friend after a failed connection | |||
* attempt? | * attempt? This is the baseline factor which is then multiplied by | |||
* two to the power of the number of failed attempts. | ||||
*/ | */ | |||
#define GREYLIST_AFTER_ATTEMPT_FRIEND GNUNET_TIME_relative_multiply (GNUNET _TIME_UNIT_MINUTES, 2) | #define GREYLIST_AFTER_ATTEMPT_FRIEND GNUNET_TIME_relative_multiply (GNUNET _TIME_UNIT_SECONDS, 2) | |||
/** | /** | |||
* For how long do we blacklist anyone under any cirumstances after a faile | * For how long do we blacklist anyone under any cirumstances at least afte | |||
d connection | r a failed connection | |||
* attempt? | * attempt? This is the absolute minimum, regardless of what the calculati | |||
on based on | ||||
* exponential backoff returns. | ||||
*/ | */ | |||
#define GREYLIST_AFTER_ATTEMPT_MIN GNUNET_TIME_relative_multiply (GNUNET_TI ME_UNIT_SECONDS, 15) | #define GREYLIST_AFTER_ATTEMPT_MIN GNUNET_TIME_relative_multiply (GNUNET_TI ME_UNIT_SECONDS, 5) | |||
/** | /** | |||
* For how long do we blacklist anyone under any cirumstances after a faile | * For how long do we blacklist anyone under any cirumstances at most after | |||
d connection | a failed connection | |||
* attempt? | * attempt? This is the absolute maximum, regardless of what the calculati | |||
on based on | ||||
* exponential back-off returns. | ||||
*/ | */ | |||
#define GREYLIST_AFTER_ATTEMPT_MAX GNUNET_TIME_relative_multiply (GNUNET_TI ME_UNIT_HOURS, 1) | #define GREYLIST_AFTER_ATTEMPT_MAX GNUNET_TIME_relative_multiply (GNUNET_TI ME_UNIT_HOURS, 1) | |||
/** | /** | |||
* How often do we at most advertise any HELLO to a peer? | * At what frequency do we sent HELLOs to a peer? | |||
*/ | */ | |||
#define HELLO_ADVERTISEMENT_MIN_FREQUENCY GNUNET_TIME_relative_multiply (GN UNET_TIME_UNIT_HOURS, 4) | #define HELLO_ADVERTISEMENT_MIN_FREQUENCY GNUNET_TIME_relative_multiply (GN UNET_TIME_UNIT_MINUTES, 5) | |||
/** | /** | |||
* How often do we at most advertise the same HELLO to the same peer? | * After what time period do we expire the HELLO Bloom filter? | |||
*/ | */ | |||
#define HELLO_ADVERTISEMENT_MIN_REPEAT_FREQUENCY GNUNET_TIME_relative_multi ply (GNUNET_TIME_UNIT_HOURS, 4) | #define HELLO_ADVERTISEMENT_MIN_REPEAT_FREQUENCY GNUNET_TIME_relative_multi ply (GNUNET_TIME_UNIT_HOURS, 4) | |||
/** | /** | |||
* Record for neighbours, friends and blacklisted peers. | * Record for neighbours, friends and blacklisted peers. | |||
*/ | */ | |||
struct Peer | struct Peer | |||
{ | { | |||
/** | /** | |||
* Which peer is this entry about? | * Which peer is this entry about? | |||
skipping to change at line 123 | skipping to change at line 128 | |||
*/ | */ | |||
struct GNUNET_TIME_Absolute filter_expiration; | struct GNUNET_TIME_Absolute filter_expiration; | |||
/** | /** | |||
* ID of task we use to wait for the time to send the next HELLO | * ID of task we use to wait for the time to send the next HELLO | |||
* to this peer. | * to this peer. | |||
*/ | */ | |||
GNUNET_SCHEDULER_TaskIdentifier hello_delay_task; | GNUNET_SCHEDULER_TaskIdentifier hello_delay_task; | |||
/** | /** | |||
* Task for issuing GNUNET_TRANSPORT_try_connect for this peer. | ||||
*/ | ||||
GNUNET_SCHEDULER_TaskIdentifier attempt_connect_task; | ||||
/** | ||||
* ID of task we use to clear peers from the greylist. | * ID of task we use to clear peers from the greylist. | |||
*/ | */ | |||
GNUNET_SCHEDULER_TaskIdentifier greylist_clean_task; | GNUNET_SCHEDULER_TaskIdentifier greylist_clean_task; | |||
/** | /** | |||
* How often have we tried so far? | * How often have we tried so far? | |||
*/ | */ | |||
unsigned int connect_attempts; | unsigned int connect_attempts; | |||
/** | /** | |||
skipping to change at line 188 | skipping to change at line 198 | |||
* Handle for reporting statistics. | * Handle for reporting statistics. | |||
*/ | */ | |||
static struct GNUNET_STATISTICS_Handle *stats; | static struct GNUNET_STATISTICS_Handle *stats; | |||
/** | /** | |||
* Blacklist (NULL if we have none). | * Blacklist (NULL if we have none). | |||
*/ | */ | |||
static struct GNUNET_TRANSPORT_Blacklist *blacklist; | static struct GNUNET_TRANSPORT_Blacklist *blacklist; | |||
/** | /** | |||
* When can we next ask transport to create a connection? | ||||
*/ | ||||
static struct GNUNET_TIME_Absolute next_connect_attempt; | ||||
/** | ||||
* Task scheduled to try to add peers. | * Task scheduled to try to add peers. | |||
*/ | */ | |||
static GNUNET_SCHEDULER_TaskIdentifier add_task; | static GNUNET_SCHEDULER_TaskIdentifier add_task; | |||
/** | /** | |||
* Flag to disallow non-friend connections (pure F2F mode). | * Flag to disallow non-friend connections (pure F2F mode). | |||
*/ | */ | |||
static int friends_only; | static int friends_only; | |||
/** | /** | |||
skipping to change at line 275 | skipping to change at line 290 | |||
static int | static int | |||
is_connection_allowed (struct Peer *peer) | is_connection_allowed (struct Peer *peer) | |||
{ | { | |||
if (0 == | if (0 == | |||
memcmp (&my_identity, &peer->pid, sizeof (struct GNUNET_PeerIdentity) )) | memcmp (&my_identity, &peer->pid, sizeof (struct GNUNET_PeerIdentity) )) | |||
return GNUNET_SYSERR; /* disallow connections to self */ | return GNUNET_SYSERR; /* disallow connections to self */ | |||
if (peer->is_friend) | if (peer->is_friend) | |||
return GNUNET_OK; | return GNUNET_OK; | |||
if (GNUNET_YES == friends_only) | if (GNUNET_YES == friends_only) | |||
{ | { | |||
#if DEBUG_TOPOLOGY | ||||
GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | |||
"Determined that `%s' is not allowed to connect (not a frie nd)\n", | "Determined that `%s' is not allowed to connect (not a frie nd)\n", | |||
GNUNET_i2s (&peer->pid)); | GNUNET_i2s (&peer->pid)); | |||
#endif | ||||
return GNUNET_SYSERR; | return GNUNET_SYSERR; | |||
} | } | |||
if (friend_count >= minimum_friend_count) | if (friend_count >= minimum_friend_count) | |||
return GNUNET_OK; | return GNUNET_OK; | |||
#if DEBUG_TOPOLOGY | ||||
GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | |||
"Determined that `%s' is not allowed to connect (not enough c onnected friends)\n", | "Determined that `%s' is not allowed to connect (not enough c onnected friends)\n", | |||
GNUNET_i2s (&peer->pid)); | GNUNET_i2s (&peer->pid)); | |||
#endif | ||||
return GNUNET_SYSERR; | return GNUNET_SYSERR; | |||
} | } | |||
/** | /** | |||
* Free all resources associated with the given peer. | * Free all resources associated with the given peer. | |||
* | * | |||
* @param cls closure (not used) | * @param cls closure (not used) | |||
* @param pid identity of the peer | * @param pid identity of the peer | |||
* @param value peer to free | * @param value peer to free | |||
* @return GNUNET_YES (always: continue to iterate) | * @return GNUNET_YES (always: continue to iterate) | |||
*/ | */ | |||
static int | static int | |||
free_peer (void *cls, const GNUNET_HashCode * pid, void *value) | free_peer (void *cls, const GNUNET_HashCode * pid, void *value) | |||
{ | { | |||
struct Peer *pos = value; | struct Peer *pos = value; | |||
GNUNET_break (GNUNET_NO == pos->is_connected); | ||||
GNUNET_break (GNUNET_OK == | GNUNET_break (GNUNET_OK == | |||
GNUNET_CONTAINER_multihashmap_remove (peers, pid, pos)); | GNUNET_CONTAINER_multihashmap_remove (peers, pid, pos)); | |||
if (pos->hello_req != NULL) | if (pos->hello_req != NULL) | |||
GNUNET_CORE_notify_transmit_ready_cancel (pos->hello_req); | GNUNET_CORE_notify_transmit_ready_cancel (pos->hello_req); | |||
if (pos->hello_delay_task != GNUNET_SCHEDULER_NO_TASK) | if (pos->hello_delay_task != GNUNET_SCHEDULER_NO_TASK) | |||
GNUNET_SCHEDULER_cancel (pos->hello_delay_task); | GNUNET_SCHEDULER_cancel (pos->hello_delay_task); | |||
if (pos->attempt_connect_task != GNUNET_SCHEDULER_NO_TASK) | ||||
GNUNET_SCHEDULER_cancel (pos->attempt_connect_task); | ||||
if (pos->greylist_clean_task != GNUNET_SCHEDULER_NO_TASK) | if (pos->greylist_clean_task != GNUNET_SCHEDULER_NO_TASK) | |||
GNUNET_SCHEDULER_cancel (pos->greylist_clean_task); | GNUNET_SCHEDULER_cancel (pos->greylist_clean_task); | |||
GNUNET_free_non_null (pos->hello); | GNUNET_free_non_null (pos->hello); | |||
if (pos->filter != NULL) | if (pos->filter != NULL) | |||
GNUNET_CONTAINER_bloomfilter_free (pos->filter); | GNUNET_CONTAINER_bloomfilter_free (pos->filter); | |||
GNUNET_free (pos); | GNUNET_free (pos); | |||
return GNUNET_YES; | return GNUNET_YES; | |||
} | } | |||
/** | /** | |||
skipping to change at line 365 | skipping to change at line 379 | |||
if (pos->connect_attempts > 30) | if (pos->connect_attempts > 30) | |||
pos->connect_attempts = 30; | pos->connect_attempts = 30; | |||
rem = GNUNET_TIME_relative_multiply (rem, 1 << (++pos->connect_attempts)) ; | rem = GNUNET_TIME_relative_multiply (rem, 1 << (++pos->connect_attempts)) ; | |||
rem = GNUNET_TIME_relative_max (rem, GREYLIST_AFTER_ATTEMPT_MIN); | rem = GNUNET_TIME_relative_max (rem, GREYLIST_AFTER_ATTEMPT_MIN); | |||
rem = GNUNET_TIME_relative_min (rem, GREYLIST_AFTER_ATTEMPT_MAX); | rem = GNUNET_TIME_relative_min (rem, GREYLIST_AFTER_ATTEMPT_MAX); | |||
pos->greylisted_until = GNUNET_TIME_relative_to_absolute (rem); | pos->greylisted_until = GNUNET_TIME_relative_to_absolute (rem); | |||
if (pos->greylist_clean_task != GNUNET_SCHEDULER_NO_TASK) | if (pos->greylist_clean_task != GNUNET_SCHEDULER_NO_TASK) | |||
GNUNET_SCHEDULER_cancel (pos->greylist_clean_task); | GNUNET_SCHEDULER_cancel (pos->greylist_clean_task); | |||
pos->greylist_clean_task = | pos->greylist_clean_task = | |||
GNUNET_SCHEDULER_add_delayed (rem, &remove_from_greylist, pos); | GNUNET_SCHEDULER_add_delayed (rem, &remove_from_greylist, pos); | |||
#if DEBUG_TOPOLOGY | ||||
GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Asking to connect to `%s'\n", | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Asking to connect to `%s'\n", | |||
GNUNET_i2s (&pos->pid)); | GNUNET_i2s (&pos->pid)); | |||
#endif | ||||
GNUNET_STATISTICS_update (stats, | GNUNET_STATISTICS_update (stats, | |||
gettext_noop | gettext_noop | |||
("# connect requests issued to transport"), 1, | ("# connect requests issued to transport"), 1, | |||
GNUNET_NO); | GNUNET_NO); | |||
GNUNET_TRANSPORT_try_connect (transport, &pos->pid); | GNUNET_TRANSPORT_try_connect (transport, &pos->pid); | |||
} | } | |||
/** | /** | |||
* Try to connect to the specified peer. | ||||
* | ||||
* @param cls peer to connect to | ||||
* @param tc scheduler context | ||||
*/ | ||||
static void | ||||
do_attempt_connect (void *cls, | ||||
const struct GNUNET_SCHEDULER_TaskContext *tc) | ||||
{ | ||||
struct Peer *pos = cls; | ||||
struct GNUNET_TIME_Relative delay; | ||||
pos->attempt_connect_task = GNUNET_SCHEDULER_NO_TASK; | ||||
if (GNUNET_YES == pos->is_connected) | ||||
return; | ||||
delay = GNUNET_TIME_absolute_get_remaining (next_connect_attempt); | ||||
if (delay.rel_value > 0) | ||||
{ | ||||
pos->attempt_connect_task = GNUNET_SCHEDULER_add_delayed (delay, | ||||
&do_attempt_co | ||||
nnect, | ||||
pos); | ||||
return; | ||||
} | ||||
next_connect_attempt = GNUNET_TIME_relative_to_absolute (MAX_CONNECT_FREQ | ||||
UENCY_DELAY); | ||||
attempt_connect (pos); | ||||
} | ||||
/** | ||||
* Schedule a task to try to connect to the specified peer. | ||||
* | ||||
* @param pos peer to connect to | ||||
*/ | ||||
static void | ||||
schedule_attempt_connect (struct Peer *pos) | ||||
{ | ||||
if (GNUNET_SCHEDULER_NO_TASK != pos->attempt_connect_task) | ||||
return; | ||||
pos->attempt_connect_task = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_abs | ||||
olute_get_remaining (next_connect_attempt), | ||||
&do_attempt_conn | ||||
ect, | ||||
pos); | ||||
} | ||||
/** | ||||
* Discard peer entries for greylisted peers | * Discard peer entries for greylisted peers | |||
* where the greylisting has expired. | * where the greylisting has expired. | |||
* | * | |||
* @param cls 'struct Peer' to greylist | * @param cls 'struct Peer' to greylist | |||
* @param tc scheduler context | * @param tc scheduler context | |||
*/ | */ | |||
static void | static void | |||
remove_from_greylist (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) | remove_from_greylist (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) | |||
{ | { | |||
struct Peer *pos = cls; | struct Peer *pos = cls; | |||
struct GNUNET_TIME_Relative rem; | struct GNUNET_TIME_Relative rem; | |||
pos->greylist_clean_task = GNUNET_SCHEDULER_NO_TASK; | pos->greylist_clean_task = GNUNET_SCHEDULER_NO_TASK; | |||
rem = GNUNET_TIME_absolute_get_remaining (pos->greylisted_until); | rem = GNUNET_TIME_absolute_get_remaining (pos->greylisted_until); | |||
if (rem.rel_value == 0) | if (rem.rel_value == 0) | |||
{ | { | |||
attempt_connect (pos); | schedule_attempt_connect (pos); | |||
} | } | |||
else | else | |||
{ | { | |||
pos->greylist_clean_task = | pos->greylist_clean_task = | |||
GNUNET_SCHEDULER_add_delayed (rem, &remove_from_greylist, pos); | GNUNET_SCHEDULER_add_delayed (rem, &remove_from_greylist, pos); | |||
} | } | |||
if ((GNUNET_NO == pos->is_friend) && (GNUNET_NO == pos->is_connected) && | if ((GNUNET_NO == pos->is_friend) && (GNUNET_NO == pos->is_connected) && | |||
(NULL == pos->hello)) | (NULL == pos->hello)) | |||
{ | { | |||
free_peer (NULL, &pos->pid.hashPubKey, pos); | free_peer (NULL, &pos->pid.hashPubKey, pos); | |||
skipping to change at line 627 | skipping to change at line 682 | |||
* @param atsi performance data | * @param atsi performance data | |||
* @param atsi_count number of records in 'atsi' | * @param atsi_count number of records in 'atsi' | |||
*/ | */ | |||
static void | static void | |||
connect_notify (void *cls, const struct GNUNET_PeerIdentity *peer, | connect_notify (void *cls, const struct GNUNET_PeerIdentity *peer, | |||
const struct GNUNET_ATS_Information *atsi, | const struct GNUNET_ATS_Information *atsi, | |||
unsigned int atsi_count) | unsigned int atsi_count) | |||
{ | { | |||
struct Peer *pos; | struct Peer *pos; | |||
#if DEBUG_TOPOLOGY | ||||
GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | |||
"Core told us that we are connecting to `%s'\n", | "Core told us that we are connecting to `%s'\n", | |||
GNUNET_i2s (peer)); | GNUNET_i2s (peer)); | |||
#endif | ||||
if (0 == memcmp (&my_identity, peer, sizeof (struct GNUNET_PeerIdentity)) ) | if (0 == memcmp (&my_identity, peer, sizeof (struct GNUNET_PeerIdentity)) ) | |||
return; | return; | |||
connection_count++; | connection_count++; | |||
GNUNET_STATISTICS_set (stats, gettext_noop ("# peers connected"), | GNUNET_STATISTICS_set (stats, gettext_noop ("# peers connected"), | |||
connection_count, GNUNET_NO); | connection_count, GNUNET_NO); | |||
pos = GNUNET_CONTAINER_multihashmap_get (peers, &peer->hashPubKey); | pos = GNUNET_CONTAINER_multihashmap_get (peers, &peer->hashPubKey); | |||
if (pos == NULL) | if (NULL == pos) | |||
{ | { | |||
pos = make_peer (peer, NULL, GNUNET_NO); | pos = make_peer (peer, NULL, GNUNET_NO); | |||
GNUNET_break (GNUNET_OK == is_connection_allowed (pos)); | GNUNET_break (GNUNET_OK == is_connection_allowed (pos)); | |||
} | } | |||
else | else | |||
{ | { | |||
GNUNET_assert (GNUNET_NO == pos->is_connected); | GNUNET_assert (GNUNET_NO == pos->is_connected); | |||
pos->greylisted_until.abs_value = 0; /* remove greylisting */ | pos->greylisted_until.abs_value = 0; /* remove greylisting */ | |||
} | } | |||
pos->is_connected = GNUNET_YES; | pos->is_connected = GNUNET_YES; | |||
skipping to change at line 676 | skipping to change at line 729 | |||
* @param cls closure, not used | * @param cls closure, not used | |||
* @param pid identity of a peer | * @param pid identity of a peer | |||
* @param value 'struct Peer*' for the peer | * @param value 'struct Peer*' for the peer | |||
* @return GNUNET_YES (continue to iterate) | * @return GNUNET_YES (continue to iterate) | |||
*/ | */ | |||
static int | static int | |||
try_add_peers (void *cls, const GNUNET_HashCode * pid, void *value) | try_add_peers (void *cls, const GNUNET_HashCode * pid, void *value) | |||
{ | { | |||
struct Peer *pos = value; | struct Peer *pos = value; | |||
attempt_connect (pos); | schedule_attempt_connect (pos); | |||
return GNUNET_YES; | return GNUNET_YES; | |||
} | } | |||
/** | /** | |||
* Last task run during shutdown. Disconnects us from | * Last task run during shutdown. Disconnects us from | |||
* the transport and core. | * the transport and core. | |||
* | * | |||
* @param cls unused, NULL | * @param cls unused, NULL | |||
* @param tc scheduler context | * @param tc scheduler context | |||
*/ | */ | |||
skipping to change at line 708 | skipping to change at line 761 | |||
* @param cls closure | * @param cls closure | |||
* @param peer peer identity this notification is about | * @param peer peer identity this notification is about | |||
*/ | */ | |||
static void | static void | |||
disconnect_notify (void *cls, const struct GNUNET_PeerIdentity *peer) | disconnect_notify (void *cls, const struct GNUNET_PeerIdentity *peer) | |||
{ | { | |||
struct Peer *pos; | struct Peer *pos; | |||
if (0 == memcmp (&my_identity, peer, sizeof (struct GNUNET_PeerIdentity)) ) | if (0 == memcmp (&my_identity, peer, sizeof (struct GNUNET_PeerIdentity)) ) | |||
return; | return; | |||
#if DEBUG_TOPOLOGY | ||||
GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | |||
"Core told us that we disconnected from `%s'\n", | "Core told us that we disconnected from `%s'\n", | |||
GNUNET_i2s (peer)); | GNUNET_i2s (peer)); | |||
#endif | ||||
pos = GNUNET_CONTAINER_multihashmap_get (peers, &peer->hashPubKey); | pos = GNUNET_CONTAINER_multihashmap_get (peers, &peer->hashPubKey); | |||
if (pos == NULL) | if (NULL == pos) | |||
{ | { | |||
GNUNET_break (0); | GNUNET_break (0); | |||
return; | return; | |||
} | } | |||
if (pos->is_connected != GNUNET_YES) | if (pos->is_connected != GNUNET_YES) | |||
{ | { | |||
GNUNET_break (0); | GNUNET_break (0); | |||
return; | return; | |||
} | } | |||
pos->is_connected = GNUNET_NO; | pos->is_connected = GNUNET_NO; | |||
skipping to change at line 799 | skipping to change at line 850 | |||
return; | return; | |||
} | } | |||
if (0 == memcmp (&pid, &my_identity, sizeof (struct GNUNET_PeerIdentity)) ) | if (0 == memcmp (&pid, &my_identity, sizeof (struct GNUNET_PeerIdentity)) ) | |||
return; /* that's me! */ | return; /* that's me! */ | |||
have_address = GNUNET_NO; | have_address = GNUNET_NO; | |||
GNUNET_HELLO_iterate_addresses (hello, GNUNET_NO, &address_iterator, | GNUNET_HELLO_iterate_addresses (hello, GNUNET_NO, &address_iterator, | |||
&have_address); | &have_address); | |||
if (GNUNET_NO == have_address) | if (GNUNET_NO == have_address) | |||
return; /* no point in advertising this one... */ | return; /* no point in advertising this one... */ | |||
peer = GNUNET_CONTAINER_multihashmap_get (peers, &pid.hashPubKey); | peer = GNUNET_CONTAINER_multihashmap_get (peers, &pid.hashPubKey); | |||
if (peer == NULL) | if (NULL == peer) | |||
{ | { | |||
peer = make_peer (&pid, hello, GNUNET_NO); | peer = make_peer (&pid, hello, GNUNET_NO); | |||
} | } | |||
else if (peer->hello != NULL) | else if (peer->hello != NULL) | |||
{ | { | |||
dt = GNUNET_HELLO_equals (peer->hello, hello, GNUNET_TIME_absolute_get ()); | dt = GNUNET_HELLO_equals (peer->hello, hello, GNUNET_TIME_absolute_get ()); | |||
if (dt.abs_value == GNUNET_TIME_UNIT_FOREVER_ABS.abs_value) | if (dt.abs_value == GNUNET_TIME_UNIT_FOREVER_ABS.abs_value) | |||
return; /* nothing new here */ | return; /* nothing new here */ | |||
} | } | |||
#if DEBUG_TOPOLOGY | ||||
GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | |||
"Found `%s' from peer `%s' for advertising\n", "HELLO", | "Found `%s' from peer `%s' for advertising\n", "HELLO", | |||
GNUNET_i2s (&pid)); | GNUNET_i2s (&pid)); | |||
#endif | ||||
if (peer->hello != NULL) | if (peer->hello != NULL) | |||
{ | { | |||
nh = GNUNET_HELLO_merge (peer->hello, hello); | nh = GNUNET_HELLO_merge (peer->hello, hello); | |||
GNUNET_free (peer->hello); | GNUNET_free (peer->hello); | |||
peer->hello = nh; | peer->hello = nh; | |||
} | } | |||
else | else | |||
{ | { | |||
size = GNUNET_HELLO_size (hello); | size = GNUNET_HELLO_size (hello); | |||
peer->hello = GNUNET_malloc (size); | peer->hello = GNUNET_malloc (size); | |||
skipping to change at line 874 | skipping to change at line 923 | |||
pos = GNUNET_CONTAINER_multihashmap_get (peers, &peer->hashPubKey); | pos = GNUNET_CONTAINER_multihashmap_get (peers, &peer->hashPubKey); | |||
if (NULL != pos) | if (NULL != pos) | |||
{ | { | |||
GNUNET_free_non_null (pos->hello); | GNUNET_free_non_null (pos->hello); | |||
pos->hello = NULL; | pos->hello = NULL; | |||
if (pos->filter != NULL) | if (pos->filter != NULL) | |||
{ | { | |||
GNUNET_CONTAINER_bloomfilter_free (pos->filter); | GNUNET_CONTAINER_bloomfilter_free (pos->filter); | |||
pos->filter = NULL; | pos->filter = NULL; | |||
} | } | |||
if ((!pos->is_connected) && (!pos->is_friend) && | if ((GNUNET_NO == pos->is_connected) && (GNUNET_NO == pos->is_friend) && | |||
(0 == | (0 == | |||
GNUNET_TIME_absolute_get_remaining (pos-> | GNUNET_TIME_absolute_get_remaining (pos-> | |||
greylisted_until).rel_value) ) | greylisted_until).rel_value) ) | |||
free_peer (NULL, &pos->pid.hashPubKey, pos); | free_peer (NULL, &pos->pid.hashPubKey, pos); | |||
} | } | |||
return; | return; | |||
} | } | |||
consider_for_advertising (hello); | consider_for_advertising (hello); | |||
pos = GNUNET_CONTAINER_multihashmap_get (peers, &peer->hashPubKey); | pos = GNUNET_CONTAINER_multihashmap_get (peers, &peer->hashPubKey); | |||
if (pos == NULL) | if (pos == NULL) | |||
pos = make_peer (peer, hello, GNUNET_NO); | pos = make_peer (peer, hello, GNUNET_NO); | |||
GNUNET_assert (NULL != pos); | GNUNET_assert (NULL != pos); | |||
if (GNUNET_YES == pos->is_connected) | if (GNUNET_YES == pos->is_connected) | |||
{ | { | |||
#if DEBUG_TOPOLOGY | ||||
GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Already connected to peer `%s'\n" , | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Already connected to peer `%s'\n" , | |||
GNUNET_i2s (peer)); | GNUNET_i2s (peer)); | |||
#endif | ||||
return; | return; | |||
} | } | |||
if (GNUNET_TIME_absolute_get_remaining (pos->greylisted_until).rel_value > 0) | if (GNUNET_TIME_absolute_get_remaining (pos->greylisted_until).rel_value > 0) | |||
{ | { | |||
#if DEBUG_TOPOLOGY | ||||
GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Already tried peer `%s' recently\ n", | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Already tried peer `%s' recently\ n", | |||
GNUNET_i2s (peer)); | GNUNET_i2s (peer)); | |||
#endif | ||||
return; /* peer still greylisted */ | return; /* peer still greylisted */ | |||
} | } | |||
#if DEBUG_TOPOLOGY | ||||
GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Considering connecting to peer `%s' \n", | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Considering connecting to peer `%s' \n", | |||
GNUNET_i2s (peer)); | GNUNET_i2s (peer)); | |||
#endif | schedule_attempt_connect (pos); | |||
attempt_connect (pos); | ||||
} | } | |||
/** | /** | |||
* Function called after GNUNET_CORE_connect has succeeded | * Function called after GNUNET_CORE_connect has succeeded | |||
* (or failed for good). | * (or failed for good). | |||
* | * | |||
* @param cls closure | * @param cls closure | |||
* @param server handle to the server, NULL if we failed | * @param server handle to the server, NULL if we failed | |||
* @param my_id ID of this peer, NULL if we failed | * @param my_id ID of this peer, NULL if we failed | |||
*/ | */ | |||
skipping to change at line 932 | skipping to change at line 975 | |||
if (server == NULL) | if (server == NULL) | |||
{ | { | |||
GNUNET_log (GNUNET_ERROR_TYPE_ERROR, | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, | |||
_ | _ | |||
("Failed to connect to core service, can not manage topolog y!\n")); | ("Failed to connect to core service, can not manage topolog y!\n")); | |||
GNUNET_SCHEDULER_shutdown (); | GNUNET_SCHEDULER_shutdown (); | |||
return; | return; | |||
} | } | |||
handle = server; | handle = server; | |||
my_identity = *my_id; | my_identity = *my_id; | |||
#if DEBUG_TOPOLOGY | ||||
GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "I am peer `%s'\n", GNUNET_i2s (my_i d)); | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "I am peer `%s'\n", GNUNET_i2s (my_i d)); | |||
#endif | ||||
peerinfo_notify = GNUNET_PEERINFO_notify (cfg, &process_peer, NULL); | peerinfo_notify = GNUNET_PEERINFO_notify (cfg, &process_peer, NULL); | |||
} | } | |||
/** | /** | |||
* Read the friends file. | * Read the friends file. | |||
*/ | */ | |||
static void | static void | |||
read_friends_file (const struct GNUNET_CONFIGURATION_Handle *cfg) | read_friends_file (const struct GNUNET_CONFIGURATION_Handle *cfg) | |||
{ | { | |||
char *fn; | char *fn; | |||
char *data; | char *data; | |||
size_t pos; | size_t pos; | |||
struct GNUNET_PeerIdentity pid; | struct GNUNET_PeerIdentity pid; | |||
struct stat frstat; | uint64_t fsize; | |||
struct GNUNET_CRYPTO_HashAsciiEncoded enc; | struct GNUNET_CRYPTO_HashAsciiEncoded enc; | |||
unsigned int entries_found; | unsigned int entries_found; | |||
struct Peer *fl; | struct Peer *fl; | |||
if (GNUNET_OK != | if (GNUNET_OK != | |||
GNUNET_CONFIGURATION_get_value_filename (cfg, "TOPOLOGY", "FRIENDS", &fn)) | GNUNET_CONFIGURATION_get_value_filename (cfg, "TOPOLOGY", "FRIENDS", &fn)) | |||
{ | { | |||
GNUNET_log (GNUNET_ERROR_TYPE_WARNING, | GNUNET_log (GNUNET_ERROR_TYPE_WARNING, | |||
_("Option `%s' in section `%s' not specified!\n"), "FRIENDS ", | _("Option `%s' in section `%s' not specified!\n"), "FRIENDS ", | |||
"TOPOLOGY"); | "TOPOLOGY"); | |||
return; | return; | |||
} | } | |||
if (GNUNET_OK != GNUNET_DISK_file_test (fn)) | if (GNUNET_OK != GNUNET_DISK_file_test (fn)) | |||
GNUNET_DISK_fn_write (fn, NULL, 0, | GNUNET_DISK_fn_write (fn, NULL, 0, | |||
GNUNET_DISK_PERM_USER_READ | | GNUNET_DISK_PERM_USER_READ | | |||
GNUNET_DISK_PERM_USER_WRITE); | GNUNET_DISK_PERM_USER_WRITE); | |||
if (0 != STAT (fn, &frstat)) | if (GNUNET_OK != GNUNET_DISK_file_size (fn, | |||
&fsize, GNUNET_NO, GNUNET_YES)) | ||||
{ | { | |||
if ((friends_only) || (minimum_friend_count > 0)) | if ((friends_only) || (minimum_friend_count > 0)) | |||
GNUNET_log (GNUNET_ERROR_TYPE_ERROR, | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, | |||
_("Could not read friends list `%s'\n"), fn); | _("Could not read friends list `%s'\n"), fn); | |||
GNUNET_free (fn); | GNUNET_free (fn); | |||
return; | return; | |||
} | } | |||
if (frstat.st_size == 0) | if (fsize == 0) | |||
{ | { | |||
GNUNET_log (GNUNET_ERROR_TYPE_WARNING, _("Friends file `%s' is empty.\n "), | GNUNET_log (GNUNET_ERROR_TYPE_WARNING, _("Friends file `%s' is empty.\n "), | |||
fn); | fn); | |||
GNUNET_free (fn); | GNUNET_free (fn); | |||
return; | return; | |||
} | } | |||
data = GNUNET_malloc_large (frstat.st_size); | data = GNUNET_malloc_large (fsize); | |||
if (data == NULL) | if (data == NULL) | |||
{ | { | |||
GNUNET_log (GNUNET_ERROR_TYPE_ERROR, | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, | |||
_("Failed to read friends list from `%s': out of memory\n") , | _("Failed to read friends list from `%s': out of memory\n") , | |||
fn); | fn); | |||
GNUNET_free (fn); | GNUNET_free (fn); | |||
return; | return; | |||
} | } | |||
if (frstat.st_size != GNUNET_DISK_fn_read (fn, data, frstat.st_size)) | if (fsize != GNUNET_DISK_fn_read (fn, data, fsize)) | |||
{ | { | |||
GNUNET_log (GNUNET_ERROR_TYPE_ERROR, | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, | |||
_("Failed to read friends list from `%s'\n"), fn); | _("Failed to read friends list from `%s'\n"), fn); | |||
GNUNET_free (fn); | GNUNET_free (fn); | |||
GNUNET_free (data); | GNUNET_free (data); | |||
return; | return; | |||
} | } | |||
entries_found = 0; | entries_found = 0; | |||
pos = 0; | pos = 0; | |||
while ((pos < frstat.st_size) && isspace ((unsigned char) data[pos])) | while ((pos < fsize) && isspace ((unsigned char) data[pos])) | |||
pos++; | pos++; | |||
while ((frstat.st_size >= sizeof (struct GNUNET_CRYPTO_HashAsciiEncoded)) && | while ((fsize >= sizeof (struct GNUNET_CRYPTO_HashAsciiEncoded)) && | |||
(pos <= | (pos <= | |||
frstat.st_size - sizeof (struct GNUNET_CRYPTO_HashAsciiEncoded))) | fsize - sizeof (struct GNUNET_CRYPTO_HashAsciiEncoded))) | |||
{ | { | |||
memcpy (&enc, &data[pos], sizeof (struct GNUNET_CRYPTO_HashAsciiEncoded )); | memcpy (&enc, &data[pos], sizeof (struct GNUNET_CRYPTO_HashAsciiEncoded )); | |||
if (!isspace | if (!isspace | |||
((unsigned char) | ((unsigned char) | |||
enc.encoding[sizeof (struct GNUNET_CRYPTO_HashAsciiEncoded) - 1])) | enc.encoding[sizeof (struct GNUNET_CRYPTO_HashAsciiEncoded) - 1])) | |||
{ | { | |||
GNUNET_log (GNUNET_ERROR_TYPE_WARNING, | GNUNET_log (GNUNET_ERROR_TYPE_WARNING, | |||
_ | _ | |||
("Syntax error in topology specification at offset %llu, skipping bytes.\n"), | ("Syntax error in topology specification at offset %llu, skipping bytes.\n"), | |||
(unsigned long long) pos); | (unsigned long long) pos); | |||
pos++; | pos++; | |||
while ((pos < frstat.st_size) && (!isspace ((unsigned char) data[pos] ))) | while ((pos < fsize) && (!isspace ((unsigned char) data[pos]))) | |||
pos++; | pos++; | |||
continue; | continue; | |||
} | } | |||
enc.encoding[sizeof (struct GNUNET_CRYPTO_HashAsciiEncoded) - 1] = '\0' ; | enc.encoding[sizeof (struct GNUNET_CRYPTO_HashAsciiEncoded) - 1] = '\0' ; | |||
if (GNUNET_OK != | if (GNUNET_OK != | |||
GNUNET_CRYPTO_hash_from_string ((char *) &enc, &pid.hashPubKey)) | GNUNET_CRYPTO_hash_from_string ((char *) &enc, &pid.hashPubKey)) | |||
{ | { | |||
GNUNET_log (GNUNET_ERROR_TYPE_WARNING, | GNUNET_log (GNUNET_ERROR_TYPE_WARNING, | |||
_ | _ | |||
("Syntax error in topology specification at offset %llu, skipping bytes `%s'.\n"), | ("Syntax error in topology specification at offset %llu, skipping bytes `%s'.\n"), | |||
skipping to change at line 1046 | skipping to change at line 1088 | |||
GNUNET_i2s (&fl->pid)); | GNUNET_i2s (&fl->pid)); | |||
} | } | |||
else | else | |||
{ | { | |||
GNUNET_log (GNUNET_ERROR_TYPE_WARNING, | GNUNET_log (GNUNET_ERROR_TYPE_WARNING, | |||
_("Found myself `%s' in friend list (useless, ignored)\ n"), | _("Found myself `%s' in friend list (useless, ignored)\ n"), | |||
GNUNET_i2s (&pid)); | GNUNET_i2s (&pid)); | |||
} | } | |||
} | } | |||
pos = pos + sizeof (struct GNUNET_CRYPTO_HashAsciiEncoded); | pos = pos + sizeof (struct GNUNET_CRYPTO_HashAsciiEncoded); | |||
while ((pos < frstat.st_size) && isspace ((unsigned char) data[pos])) | while ((pos < fsize) && isspace ((unsigned char) data[pos])) | |||
pos++; | pos++; | |||
} | } | |||
GNUNET_free (data); | GNUNET_free (data); | |||
GNUNET_free (fn); | GNUNET_free (fn); | |||
GNUNET_STATISTICS_update (stats, gettext_noop ("# friends in configuratio n"), | GNUNET_STATISTICS_update (stats, gettext_noop ("# friends in configuratio n"), | |||
entries_found, GNUNET_NO); | entries_found, GNUNET_NO); | |||
if ((minimum_friend_count > entries_found) && (friends_only == GNUNET_NO) ) | if ((minimum_friend_count > entries_found) && (friends_only == GNUNET_NO) ) | |||
{ | { | |||
GNUNET_log (GNUNET_ERROR_TYPE_WARNING, | GNUNET_log (GNUNET_ERROR_TYPE_WARNING, | |||
_ | _ | |||
skipping to change at line 1090 | skipping to change at line 1132 | |||
*/ | */ | |||
static int | static int | |||
handle_encrypted_hello (void *cls, const struct GNUNET_PeerIdentity *other, | handle_encrypted_hello (void *cls, const struct GNUNET_PeerIdentity *other, | |||
const struct GNUNET_MessageHeader *message, | const struct GNUNET_MessageHeader *message, | |||
const struct GNUNET_ATS_Information *atsi, | const struct GNUNET_ATS_Information *atsi, | |||
unsigned int atsi_count) | unsigned int atsi_count) | |||
{ | { | |||
struct Peer *peer; | struct Peer *peer; | |||
struct GNUNET_PeerIdentity pid; | struct GNUNET_PeerIdentity pid; | |||
#if DEBUG_TOPOLOGY | ||||
GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received encrypted `%s' from peer ` %s'", | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received encrypted `%s' from peer ` %s'", | |||
"HELLO", GNUNET_i2s (other)); | "HELLO", GNUNET_i2s (other)); | |||
#endif | ||||
if (GNUNET_OK != | if (GNUNET_OK != | |||
GNUNET_HELLO_get_id ((const struct GNUNET_HELLO_Message *) message, & pid)) | GNUNET_HELLO_get_id ((const struct GNUNET_HELLO_Message *) message, & pid)) | |||
{ | { | |||
GNUNET_break_op (0); | GNUNET_break_op (0); | |||
return GNUNET_SYSERR; | return GNUNET_SYSERR; | |||
} | } | |||
GNUNET_STATISTICS_update (stats, gettext_noop ("# HELLO messages received "), | GNUNET_STATISTICS_update (stats, gettext_noop ("# HELLO messages received "), | |||
1, GNUNET_NO); | 1, GNUNET_NO); | |||
peer = GNUNET_CONTAINER_multihashmap_get (peers, &pid.hashPubKey); | peer = GNUNET_CONTAINER_multihashmap_get (peers, &pid.hashPubKey); | |||
if (peer == NULL) | if (NULL == peer) | |||
{ | { | |||
if ((GNUNET_YES == friends_only) || (friend_count < minimum_friend_coun t)) | if ((GNUNET_YES == friends_only) || (friend_count < minimum_friend_coun t)) | |||
return GNUNET_OK; | return GNUNET_OK; | |||
} | } | |||
else | else | |||
{ | { | |||
if ((GNUNET_YES != peer->is_friend) && (GNUNET_YES == friends_only)) | if ((GNUNET_YES != peer->is_friend) && (GNUNET_YES == friends_only)) | |||
return GNUNET_OK; | return GNUNET_OK; | |||
if ((GNUNET_YES != peer->is_friend) && | if ((GNUNET_YES != peer->is_friend) && | |||
(friend_count < minimum_friend_count)) | (friend_count < minimum_friend_count)) | |||
skipping to change at line 1151 | skipping to change at line 1191 | |||
fah.max_size = size; | fah.max_size = size; | |||
fah.next_adv = GNUNET_TIME_UNIT_FOREVER_REL; | fah.next_adv = GNUNET_TIME_UNIT_FOREVER_REL; | |||
GNUNET_CONTAINER_multihashmap_iterate (peers, &find_advertisable_hello, & fah); | GNUNET_CONTAINER_multihashmap_iterate (peers, &find_advertisable_hello, & fah); | |||
want = 0; | want = 0; | |||
if (fah.result != NULL) | if (fah.result != NULL) | |||
{ | { | |||
want = GNUNET_HELLO_size (fah.result->hello); | want = GNUNET_HELLO_size (fah.result->hello); | |||
GNUNET_assert (want <= size); | GNUNET_assert (want <= size); | |||
memcpy (buf, fah.result->hello, want); | memcpy (buf, fah.result->hello, want); | |||
GNUNET_CONTAINER_bloomfilter_add (fah.result->filter, &pl->pid.hashPubK ey); | GNUNET_CONTAINER_bloomfilter_add (fah.result->filter, &pl->pid.hashPubK ey); | |||
#if DEBUG_TOPOLOGY | ||||
GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending `%s' with %u bytes", "HEL LO", | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending `%s' with %u bytes", "HEL LO", | |||
(unsigned int) want); | (unsigned int) want); | |||
#endif | ||||
GNUNET_STATISTICS_update (stats, | GNUNET_STATISTICS_update (stats, | |||
gettext_noop ("# HELLO messages gossipped"), 1, | gettext_noop ("# HELLO messages gossipped"), 1, | |||
GNUNET_NO); | GNUNET_NO); | |||
} | } | |||
if (pl->hello_delay_task != GNUNET_SCHEDULER_NO_TASK) | if (pl->hello_delay_task != GNUNET_SCHEDULER_NO_TASK) | |||
GNUNET_SCHEDULER_cancel (pl->hello_delay_task); | GNUNET_SCHEDULER_cancel (pl->hello_delay_task); | |||
pl->next_hello_allowed = | pl->next_hello_allowed = | |||
GNUNET_TIME_relative_to_absolute (HELLO_ADVERTISEMENT_MIN_FREQUENCY); | GNUNET_TIME_relative_to_absolute (HELLO_ADVERTISEMENT_MIN_FREQUENCY); | |||
pl->hello_delay_task = GNUNET_SCHEDULER_add_now (&schedule_next_hello, pl ); | pl->hello_delay_task = GNUNET_SCHEDULER_add_now (&schedule_next_hello, pl ); | |||
skipping to change at line 1183 | skipping to change at line 1221 | |||
* @param tc scheduler context | * @param tc scheduler context | |||
*/ | */ | |||
static void | static void | |||
cleaning_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) | cleaning_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) | |||
{ | { | |||
if (NULL != peerinfo_notify) | if (NULL != peerinfo_notify) | |||
{ | { | |||
GNUNET_PEERINFO_notify_cancel (peerinfo_notify); | GNUNET_PEERINFO_notify_cancel (peerinfo_notify); | |||
peerinfo_notify = NULL; | peerinfo_notify = NULL; | |||
} | } | |||
if (GNUNET_SCHEDULER_NO_TASK != add_task) | ||||
{ | ||||
GNUNET_SCHEDULER_cancel (add_task); | ||||
add_task = GNUNET_SCHEDULER_NO_TASK; | ||||
} | ||||
GNUNET_TRANSPORT_disconnect (transport); | GNUNET_TRANSPORT_disconnect (transport); | |||
transport = NULL; | transport = NULL; | |||
GNUNET_CONTAINER_multihashmap_iterate (peers, &free_peer, NULL); | ||||
GNUNET_CONTAINER_multihashmap_destroy (peers); | ||||
if (handle != NULL) | if (handle != NULL) | |||
{ | { | |||
GNUNET_CORE_disconnect (handle); | GNUNET_CORE_disconnect (handle); | |||
handle = NULL; | handle = NULL; | |||
} | } | |||
whitelist_peers (); | whitelist_peers (); | |||
if (GNUNET_SCHEDULER_NO_TASK != add_task) | ||||
{ | ||||
GNUNET_SCHEDULER_cancel (add_task); | ||||
add_task = GNUNET_SCHEDULER_NO_TASK; | ||||
} | ||||
GNUNET_CONTAINER_multihashmap_iterate (peers, &free_peer, NULL); | ||||
GNUNET_CONTAINER_multihashmap_destroy (peers); | ||||
peers = NULL; | ||||
if (stats != NULL) | if (stats != NULL) | |||
{ | { | |||
GNUNET_STATISTICS_destroy (stats, GNUNET_NO); | GNUNET_STATISTICS_destroy (stats, GNUNET_NO); | |||
stats = NULL; | stats = NULL; | |||
} | } | |||
} | } | |||
/** | /** | |||
* Main function that will be run. | * Main function that will be run. | |||
* | * | |||
skipping to change at line 1243 | skipping to change at line 1282 | |||
minimum_friend_count = (unsigned int) opt; | minimum_friend_count = (unsigned int) opt; | |||
if (GNUNET_OK != | if (GNUNET_OK != | |||
GNUNET_CONFIGURATION_get_value_number (cfg, "TOPOLOGY", | GNUNET_CONFIGURATION_get_value_number (cfg, "TOPOLOGY", | |||
"TARGET-CONNECTION-COUNT", &op t)) | "TARGET-CONNECTION-COUNT", &op t)) | |||
opt = 16; | opt = 16; | |||
target_connection_count = (unsigned int) opt; | target_connection_count = (unsigned int) opt; | |||
peers = GNUNET_CONTAINER_multihashmap_create (target_connection_count * 2 ); | peers = GNUNET_CONTAINER_multihashmap_create (target_connection_count * 2 ); | |||
if ((friends_only == GNUNET_YES) || (minimum_friend_count > 0)) | if ((friends_only == GNUNET_YES) || (minimum_friend_count > 0)) | |||
read_friends_file (cfg); | read_friends_file (cfg); | |||
#if DEBUG_TOPOLOGY | ||||
GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | |||
"Topology would like %u connections with at least %u friends (%s)\n", | "Topology would like %u connections with at least %u friends (%s)\n", | |||
target_connection_count, minimum_friend_count, | target_connection_count, minimum_friend_count, | |||
autoconnect ? "autoconnect enabled" : "autoconnect disabled") ; | autoconnect ? "autoconnect enabled" : "autoconnect disabled") ; | |||
#endif | ||||
if ((friend_count < minimum_friend_count) && (blacklist == NULL)) | if ((friend_count < minimum_friend_count) && (blacklist == NULL)) | |||
blacklist = GNUNET_TRANSPORT_blacklist (cfg, &blacklist_check, NULL); | blacklist = GNUNET_TRANSPORT_blacklist (cfg, &blacklist_check, NULL); | |||
transport = GNUNET_TRANSPORT_connect (cfg, NULL, NULL, NULL, NULL, NULL); | transport = GNUNET_TRANSPORT_connect (cfg, NULL, NULL, NULL, NULL, NULL); | |||
handle = | handle = | |||
GNUNET_CORE_connect (cfg, 1, NULL, &core_init, &connect_notify, | GNUNET_CORE_connect (cfg, 1, NULL, &core_init, &connect_notify, | |||
&disconnect_notify, NULL, GNUNET_NO, NULL, GNUNE T_NO, | &disconnect_notify, NULL, GNUNET_NO, NULL, GNUNE T_NO, | |||
handlers); | handlers); | |||
GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, &cleaning_tas k, | GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, &cleaning_tas k, | |||
NULL); | NULL); | |||
if (NULL == transport) | if (NULL == transport) | |||
End of changes. 63 change blocks. | ||||
68 lines changed or deleted | 112 lines changed or added | |||
This html diff was produced by rfcdiff 1.41. The latest version is available from http://tools.ietf.org/tools/rfcdiff/ |