diff options
author | Matthias Wachs <wachs@net.in.tum.de> | 2014-01-16 17:02:54 +0000 |
---|---|---|
committer | Matthias Wachs <wachs@net.in.tum.de> | 2014-01-16 17:02:54 +0000 |
commit | 2134d1a1eaa421d42e93ce0be1f718758c4a6e4b (patch) | |
tree | 5299be8050b9be0610fce0febcf65a66ca4a4d37 /src | |
parent | 5b7924338e828c773d2179a7b7cfad6ab5074c4f (diff) | |
download | gnunet-2134d1a1eaa421d42e93ce0be1f718758c4a6e4b.tar.gz gnunet-2134d1a1eaa421d42e93ce0be1f718758c4a6e4b.zip |
perform blacklist before address switch
this commit adds the blacklist check before address switch
in the next step the old blacklist check has to be removed
Diffstat (limited to 'src')
-rw-r--r-- | src/transport/gnunet-service-transport_neighbours.c | 381 |
1 files changed, 244 insertions, 137 deletions
diff --git a/src/transport/gnunet-service-transport_neighbours.c b/src/transport/gnunet-service-transport_neighbours.c index ad649ec0a..871b6c2cf 100644 --- a/src/transport/gnunet-service-transport_neighbours.c +++ b/src/transport/gnunet-service-transport_neighbours.c | |||
@@ -463,6 +463,16 @@ static struct BlackListCheckContext *bc_head; | |||
463 | static struct BlackListCheckContext *bc_tail; | 463 | static struct BlackListCheckContext *bc_tail; |
464 | 464 | ||
465 | /** | 465 | /** |
466 | * List of pending blacklist checks: head | ||
467 | */ | ||
468 | static struct BlacklistCheckSwitchContext *pending_bc_head; | ||
469 | |||
470 | /** | ||
471 | * List of pending blacklist checks: tail | ||
472 | */ | ||
473 | static struct BlacklistCheckSwitchContext *pending_bc_tail; | ||
474 | |||
475 | /** | ||
466 | * Closure for #connect_notify_cb, #disconnect_notify_cb and #neighbour_change_cb | 476 | * Closure for #connect_notify_cb, #disconnect_notify_cb and #neighbour_change_cb |
467 | */ | 477 | */ |
468 | static void *callback_cls; | 478 | static void *callback_cls; |
@@ -2240,94 +2250,75 @@ GST_neighbours_handle_connect (const struct GNUNET_MessageHeader *message, | |||
2240 | return GNUNET_OK; | 2250 | return GNUNET_OK; |
2241 | } | 2251 | } |
2242 | 2252 | ||
2253 | struct BlacklistCheckSwitchContext | ||
2254 | { | ||
2255 | struct BlacklistCheckSwitchContext *prev; | ||
2256 | struct BlacklistCheckSwitchContext *next; | ||
2243 | 2257 | ||
2244 | /** | 2258 | struct GNUNET_HELLO_Address *address; |
2245 | * For an existing neighbour record, set the active connection to | 2259 | struct Session *session; |
2246 | * use the given address. | 2260 | struct GNUNET_ATS_Information *ats; |
2247 | * | 2261 | uint32_t ats_count; |
2248 | * @param peer identity of the peer to switch the address for | 2262 | |
2249 | * @param address address of the other peer, NULL if other peer | 2263 | struct GNUNET_BANDWIDTH_Value32NBO bandwidth_in; |
2250 | * connected to us | 2264 | struct GNUNET_BANDWIDTH_Value32NBO bandwidth_out; |
2251 | * @param session session to use (or NULL) | 2265 | }; |
2252 | * @param ats performance data | 2266 | |
2253 | * @param ats_count number of entries in ats | 2267 | static void |
2254 | * @param bandwidth_in inbound quota to be used when connection is up, | 2268 | switch_address_bl_check_cont (void *cls, |
2255 | * 0 to disconnect from peer | 2269 | const struct GNUNET_PeerIdentity *peer, int result) |
2256 | * @param bandwidth_out outbound quota to be used when connection is up, | ||
2257 | * 0 to disconnect from peer | ||
2258 | */ | ||
2259 | void | ||
2260 | GST_neighbours_switch_to_address (const struct GNUNET_PeerIdentity *peer, | ||
2261 | const struct GNUNET_HELLO_Address *address, | ||
2262 | struct Session *session, | ||
2263 | const struct GNUNET_ATS_Information *ats, | ||
2264 | uint32_t ats_count, | ||
2265 | struct GNUNET_BANDWIDTH_Value32NBO bandwidth_in, | ||
2266 | struct GNUNET_BANDWIDTH_Value32NBO bandwidth_out) | ||
2267 | { | 2270 | { |
2268 | struct NeighbourMapEntry *n; | 2271 | struct BlacklistCheckSwitchContext *blc_ctx = cls; |
2269 | struct GNUNET_TRANSPORT_PluginFunctions *papi; | 2272 | struct GNUNET_TRANSPORT_PluginFunctions *papi; |
2273 | struct NeighbourMapEntry *n; | ||
2270 | 2274 | ||
2271 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
2272 | "ATS has decided on an address for peer %s\n", | ||
2273 | GNUNET_i2s (peer)); | ||
2274 | GNUNET_assert (NULL != address->transport_name); | ||
2275 | if (NULL == (n = lookup_neighbour (peer))) | ||
2276 | { | ||
2277 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
2278 | "Peer %s is unknown, suggestion ignored\n", | ||
2279 | GNUNET_i2s (peer)); | ||
2280 | return; | ||
2281 | } | ||
2282 | 2275 | ||
2283 | /* Obtain an session for this address from plugin */ | 2276 | if ( (NULL == (n = lookup_neighbour (peer))) || (result == GNUNET_NO) || |
2284 | if (NULL == (papi = GST_plugins_find (address->transport_name))) | 2277 | (NULL == (papi = GST_plugins_find (blc_ctx->address->transport_name))) ) |
2285 | { | ||
2286 | /* we don't have the plugin for this address */ | ||
2287 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
2288 | "Plugin `%s' is unknown, suggestion for peer %s ignored\n", | ||
2289 | address->transport_name, | ||
2290 | GNUNET_i2s (peer)); | ||
2291 | GNUNET_ATS_address_destroyed (GST_ats, address, NULL); | ||
2292 | return; | ||
2293 | } | ||
2294 | if ((NULL == session) && | ||
2295 | (GNUNET_HELLO_address_check_option (address, GNUNET_HELLO_ADDRESS_INFO_INBOUND))) | ||
2296 | { | 2278 | { |
2297 | /* This is a inbound address and we do not have a session to use! */ | 2279 | if (NULL == n) |
2298 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | 2280 | { |
2299 | "Inbound address without session `%s'! Destroying address...\n", | 2281 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
2300 | GST_plugins_a2s (address)); | 2282 | "Peer %s is unknown, suggestion ignored\n", |
2301 | GNUNET_ATS_address_destroyed (GST_ats, address, NULL); | 2283 | GNUNET_i2s (peer)); |
2284 | } | ||
2285 | if (result == GNUNET_NO) | ||
2286 | { | ||
2287 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
2288 | "Blacklist denied to switch to suggested address `%s' sesion %p for peer `%s'\n", | ||
2289 | GST_plugins_a2s (blc_ctx->address), | ||
2290 | blc_ctx->session, | ||
2291 | GNUNET_i2s (&blc_ctx->address->peer)); | ||
2292 | } | ||
2293 | /* Delete address (or session if existing) in ATS */ | ||
2294 | GNUNET_ATS_address_destroyed (GST_ats, blc_ctx->address, blc_ctx->session); | ||
2295 | |||
2296 | GNUNET_CONTAINER_DLL_remove (pending_bc_head, pending_bc_tail, blc_ctx); | ||
2297 | GNUNET_HELLO_address_free(blc_ctx->address); | ||
2298 | GNUNET_free_non_null (blc_ctx->ats); | ||
2299 | GNUNET_free (blc_ctx); | ||
2302 | return; | 2300 | return; |
2303 | } | 2301 | } |
2304 | 2302 | ||
2305 | GNUNET_log (GNUNET_ERROR_TYPE_INFO, | 2303 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
2306 | "ATS tells us to switch to %s address '%s' session %p for " | 2304 | "Blacklist accepted to switch to suggested address `%s' for peer `%s'\n", |
2307 | "peer `%s' in state %s/%d (quota in/out %u %u )\n", | 2305 | GST_plugins_a2s (blc_ctx->address), |
2308 | GNUNET_HELLO_address_check_option (address, | 2306 | blc_ctx->session, |
2309 | GNUNET_HELLO_ADDRESS_INFO_INBOUND) ? "inbound" : "", | 2307 | GNUNET_i2s (&blc_ctx->address->peer)); |
2310 | GST_plugins_a2s (address), | ||
2311 | session, | ||
2312 | GNUNET_i2s (peer), | ||
2313 | GNUNET_TRANSPORT_ps2s (n->state), | ||
2314 | n->send_connect_ack, | ||
2315 | ntohl (bandwidth_in.value__), | ||
2316 | ntohl (bandwidth_out.value__)); | ||
2317 | 2308 | ||
2318 | if (NULL == session) | 2309 | if (NULL == blc_ctx->session) |
2319 | { | 2310 | { |
2320 | session = papi->get_session (papi->cls, address); | 2311 | blc_ctx->session = papi->get_session (papi->cls, blc_ctx->address); |
2321 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | 2312 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
2322 | "Obtained new session for peer `%s' and address '%s': %p\n", | 2313 | "Obtained new session for peer `%s' and address '%s': %p\n", |
2323 | GNUNET_i2s (&address->peer), GST_plugins_a2s (address), session); | 2314 | GNUNET_i2s (&blc_ctx->address->peer), GST_plugins_a2s (blc_ctx->address), blc_ctx->session); |
2324 | } | 2315 | } |
2325 | if (NULL == session) | 2316 | if (NULL == blc_ctx->session) |
2326 | { | 2317 | { |
2327 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | 2318 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
2328 | "Failed to obtain new session for peer `%s' and address '%s'\n", | 2319 | "Failed to obtain new session for peer `%s' and address '%s'\n", |
2329 | GNUNET_i2s (&address->peer), GST_plugins_a2s (address)); | 2320 | GNUNET_i2s (&blc_ctx->address->peer), GST_plugins_a2s (blc_ctx->address)); |
2330 | GNUNET_ATS_address_destroyed (GST_ats, address, NULL); | 2321 | GNUNET_ATS_address_destroyed (GST_ats, blc_ctx->address, NULL); |
2331 | return; | 2322 | return; |
2332 | } | 2323 | } |
2333 | switch (n->state) | 2324 | switch (n->state) |
@@ -2337,102 +2328,101 @@ GST_neighbours_switch_to_address (const struct GNUNET_PeerIdentity *peer, | |||
2337 | free_neighbour (n, GNUNET_NO); | 2328 | free_neighbour (n, GNUNET_NO); |
2338 | return; | 2329 | return; |
2339 | case GNUNET_TRANSPORT_PS_INIT_ATS: | 2330 | case GNUNET_TRANSPORT_PS_INIT_ATS: |
2340 | set_primary_address (n, address, session, bandwidth_in, bandwidth_out, GNUNET_NO); | 2331 | set_primary_address (n, blc_ctx->address, blc_ctx->session, |
2341 | set_state_and_timeout (n, GNUNET_TRANSPORT_PS_INIT_BLACKLIST, GNUNET_TIME_relative_to_absolute (BLACKLIST_RESPONSE_TIMEOUT)); | 2332 | blc_ctx->bandwidth_in, blc_ctx->bandwidth_out, GNUNET_NO); |
2342 | check_blacklist (&n->id, | 2333 | set_state_and_timeout (n, GNUNET_TRANSPORT_PS_INIT_BLACKLIST, |
2343 | n->connect_ack_timestamp, | 2334 | GNUNET_TIME_relative_to_absolute (BLACKLIST_RESPONSE_TIMEOUT)); |
2344 | address, session); | 2335 | check_blacklist (&n->id, n->connect_ack_timestamp, |
2336 | blc_ctx->address, blc_ctx->session); | ||
2345 | break; | 2337 | break; |
2346 | case GNUNET_TRANSPORT_PS_INIT_BLACKLIST: | 2338 | case GNUNET_TRANSPORT_PS_INIT_BLACKLIST: |
2347 | /* ATS suggests a different address, switch again */ | 2339 | /* ATS suggests a different address, switch again */ |
2348 | set_primary_address (n, | 2340 | set_primary_address (n, blc_ctx->address, blc_ctx->session, |
2349 | address, session, bandwidth_in, bandwidth_out, GNUNET_NO); | 2341 | blc_ctx->bandwidth_in, blc_ctx->bandwidth_out, GNUNET_NO); |
2350 | set_timeout (n, GNUNET_TIME_relative_to_absolute (BLACKLIST_RESPONSE_TIMEOUT)); | 2342 | set_timeout (n, GNUNET_TIME_relative_to_absolute (BLACKLIST_RESPONSE_TIMEOUT)); |
2351 | check_blacklist (&n->id, | 2343 | check_blacklist (&n->id, n->connect_ack_timestamp, |
2352 | n->connect_ack_timestamp, | 2344 | blc_ctx->address, blc_ctx->session); |
2353 | address, session); | ||
2354 | break; | 2345 | break; |
2355 | case GNUNET_TRANSPORT_PS_CONNECT_SENT: | 2346 | case GNUNET_TRANSPORT_PS_CONNECT_SENT: |
2356 | /* ATS suggests a different address, switch again */ | 2347 | /* ATS suggests a different address, switch again */ |
2357 | set_primary_address (n, address, session, bandwidth_in, bandwidth_out, GNUNET_NO); | 2348 | set_primary_address (n, blc_ctx->address, blc_ctx->session, |
2358 | set_state_and_timeout (n, GNUNET_TRANSPORT_PS_INIT_BLACKLIST, GNUNET_TIME_relative_to_absolute (BLACKLIST_RESPONSE_TIMEOUT)); | 2349 | blc_ctx->bandwidth_in, blc_ctx->bandwidth_out, GNUNET_NO); |
2359 | check_blacklist (&n->id, | 2350 | set_state_and_timeout (n, GNUNET_TRANSPORT_PS_INIT_BLACKLIST, |
2360 | n->connect_ack_timestamp, | 2351 | GNUNET_TIME_relative_to_absolute (BLACKLIST_RESPONSE_TIMEOUT)); |
2361 | address, session); | 2352 | check_blacklist (&n->id, n->connect_ack_timestamp, |
2353 | blc_ctx->address, blc_ctx->session); | ||
2362 | break; | 2354 | break; |
2363 | case GNUNET_TRANSPORT_PS_CONNECT_RECV_ATS: | 2355 | case GNUNET_TRANSPORT_PS_CONNECT_RECV_ATS: |
2364 | set_primary_address (n, | 2356 | set_primary_address (n, blc_ctx->address, blc_ctx->session, |
2365 | address, session, bandwidth_in, bandwidth_out, GNUNET_NO); | 2357 | blc_ctx->bandwidth_in, blc_ctx->bandwidth_out, GNUNET_NO); |
2366 | set_state_and_timeout (n, GNUNET_TRANSPORT_PS_CONNECT_RECV_BLACKLIST, GNUNET_TIME_relative_to_absolute (BLACKLIST_RESPONSE_TIMEOUT)); | 2358 | set_state_and_timeout (n, GNUNET_TRANSPORT_PS_CONNECT_RECV_BLACKLIST, |
2367 | check_blacklist (&n->id, | 2359 | GNUNET_TIME_relative_to_absolute (BLACKLIST_RESPONSE_TIMEOUT)); |
2368 | n->connect_ack_timestamp, | 2360 | check_blacklist (&n->id, n->connect_ack_timestamp, |
2369 | address, session); | 2361 | blc_ctx->address, blc_ctx->session); |
2370 | break; | 2362 | break; |
2371 | case GNUNET_TRANSPORT_PS_CONNECT_RECV_BLACKLIST_INBOUND: | 2363 | case GNUNET_TRANSPORT_PS_CONNECT_RECV_BLACKLIST_INBOUND: |
2372 | set_timeout (n, GNUNET_TIME_relative_to_absolute (BLACKLIST_RESPONSE_TIMEOUT)); | 2364 | set_timeout (n, GNUNET_TIME_relative_to_absolute (BLACKLIST_RESPONSE_TIMEOUT)); |
2373 | check_blacklist (&n->id, | 2365 | check_blacklist (&n->id, n->connect_ack_timestamp, |
2374 | n->connect_ack_timestamp, | 2366 | blc_ctx->address, blc_ctx->session); |
2375 | address, session); | ||
2376 | break; | 2367 | break; |
2377 | case GNUNET_TRANSPORT_PS_CONNECT_RECV_BLACKLIST: | 2368 | case GNUNET_TRANSPORT_PS_CONNECT_RECV_BLACKLIST: |
2378 | case GNUNET_TRANSPORT_PS_CONNECT_RECV_ACK: | 2369 | case GNUNET_TRANSPORT_PS_CONNECT_RECV_ACK: |
2379 | /* ATS asks us to switch while we were trying to connect; switch to new | 2370 | /* ATS asks us to switch while we were trying to connect; switch to new |
2380 | address and check blacklist again */ | 2371 | address and check blacklist again */ |
2381 | set_primary_address (n, | 2372 | set_primary_address (n, blc_ctx->address, blc_ctx->session, |
2382 | address, session, bandwidth_in, bandwidth_out, GNUNET_NO); | 2373 | blc_ctx->bandwidth_in, blc_ctx->bandwidth_out, GNUNET_NO); |
2383 | set_state_and_timeout (n, GNUNET_TRANSPORT_PS_CONNECT_RECV_BLACKLIST, GNUNET_TIME_relative_to_absolute (BLACKLIST_RESPONSE_TIMEOUT)); | 2374 | set_state_and_timeout (n, GNUNET_TRANSPORT_PS_CONNECT_RECV_BLACKLIST, |
2384 | check_blacklist (&n->id, | 2375 | GNUNET_TIME_relative_to_absolute (BLACKLIST_RESPONSE_TIMEOUT)); |
2385 | n->connect_ack_timestamp, | 2376 | check_blacklist (&n->id, n->connect_ack_timestamp, |
2386 | address, session); | 2377 | blc_ctx->address, blc_ctx->session); |
2387 | break; | 2378 | break; |
2388 | case GNUNET_TRANSPORT_PS_CONNECTED: | 2379 | case GNUNET_TRANSPORT_PS_CONNECTED: |
2389 | GNUNET_assert (NULL != n->primary_address.address); | 2380 | GNUNET_assert (NULL != n->primary_address.address); |
2390 | GNUNET_assert (NULL != n->primary_address.session); | 2381 | GNUNET_assert (NULL != n->primary_address.session); |
2391 | if (n->primary_address.session == session) | 2382 | if (n->primary_address.session == blc_ctx->session) |
2392 | { | 2383 | { |
2393 | /* not an address change, just a quota change */ | 2384 | /* not an address change, just a quota change */ |
2394 | set_primary_address (n, | 2385 | set_primary_address (n, blc_ctx->address, blc_ctx->session, |
2395 | address, session, bandwidth_in, bandwidth_out, GNUNET_YES); | 2386 | blc_ctx->bandwidth_in, blc_ctx->bandwidth_out, GNUNET_YES); |
2396 | break; | 2387 | break; |
2397 | } | 2388 | } |
2398 | /* ATS asks us to switch a life connection; see if we can get | 2389 | /* ATS asks us to switch a life connection; see if we can get |
2399 | a CONNECT_ACK on it before we actually do this! */ | 2390 | a CONNECT_ACK on it before we actually do this! */ |
2400 | set_state (n, GNUNET_TRANSPORT_PS_CONNECTED_SWITCHING_BLACKLIST); | 2391 | set_state (n, GNUNET_TRANSPORT_PS_CONNECTED_SWITCHING_BLACKLIST); |
2401 | set_alternative_address (n, address, session, bandwidth_in, bandwidth_out); | 2392 | set_alternative_address (n, blc_ctx->address, blc_ctx->session, |
2402 | check_blacklist (&n->id, | 2393 | blc_ctx->bandwidth_in, blc_ctx->bandwidth_out); |
2403 | GNUNET_TIME_absolute_get (), | 2394 | check_blacklist (&n->id, GNUNET_TIME_absolute_get (), |
2404 | address, session); | 2395 | blc_ctx->address, blc_ctx->session); |
2405 | break; | 2396 | break; |
2406 | case GNUNET_TRANSPORT_PS_RECONNECT_ATS: | 2397 | case GNUNET_TRANSPORT_PS_RECONNECT_ATS: |
2407 | set_primary_address (n, | 2398 | set_primary_address (n, blc_ctx->address, blc_ctx->session, |
2408 | address, session, bandwidth_in, bandwidth_out, GNUNET_NO); | 2399 | blc_ctx->bandwidth_in, blc_ctx->bandwidth_out, GNUNET_NO); |
2409 | set_state_and_timeout (n, GNUNET_TRANSPORT_PS_RECONNECT_BLACKLIST, GNUNET_TIME_relative_to_absolute (BLACKLIST_RESPONSE_TIMEOUT)); | 2400 | set_state_and_timeout (n, GNUNET_TRANSPORT_PS_RECONNECT_BLACKLIST, |
2410 | check_blacklist (&n->id, | 2401 | GNUNET_TIME_relative_to_absolute (BLACKLIST_RESPONSE_TIMEOUT)); |
2411 | n->connect_ack_timestamp, | 2402 | check_blacklist (&n->id, n->connect_ack_timestamp, |
2412 | address, session); | 2403 | blc_ctx->address, blc_ctx->session); |
2413 | break; | 2404 | break; |
2414 | case GNUNET_TRANSPORT_PS_RECONNECT_BLACKLIST: | 2405 | case GNUNET_TRANSPORT_PS_RECONNECT_BLACKLIST: |
2415 | /* ATS asks us to switch while we were trying to reconnect; switch to new | 2406 | /* ATS asks us to switch while we were trying to reconnect; switch to new |
2416 | address and check blacklist again */ | 2407 | address and check blacklist again */ |
2417 | set_primary_address (n, | 2408 | set_primary_address (n, blc_ctx->address, blc_ctx->session, |
2418 | address, session, bandwidth_in, bandwidth_out, GNUNET_NO); | 2409 | blc_ctx->bandwidth_in, blc_ctx->bandwidth_out, GNUNET_NO); |
2419 | set_timeout (n, GNUNET_TIME_relative_to_absolute (BLACKLIST_RESPONSE_TIMEOUT)); | 2410 | set_timeout (n, GNUNET_TIME_relative_to_absolute (BLACKLIST_RESPONSE_TIMEOUT)); |
2420 | check_blacklist (&n->id, | 2411 | check_blacklist (&n->id, n->connect_ack_timestamp, |
2421 | n->connect_ack_timestamp, | 2412 | blc_ctx->address, blc_ctx->session); |
2422 | address, session); | ||
2423 | break; | 2413 | break; |
2424 | case GNUNET_TRANSPORT_PS_RECONNECT_SENT: | 2414 | case GNUNET_TRANSPORT_PS_RECONNECT_SENT: |
2425 | /* ATS asks us to switch while we were trying to reconnect; switch to new | 2415 | /* ATS asks us to switch while we were trying to reconnect; switch to new |
2426 | address and check blacklist again */ | 2416 | address and check blacklist again */ |
2427 | set_primary_address (n, | 2417 | set_primary_address (n, blc_ctx->address, blc_ctx->session, |
2428 | address, session, bandwidth_in, bandwidth_out, GNUNET_NO); | 2418 | blc_ctx->bandwidth_in, blc_ctx->bandwidth_out, GNUNET_NO); |
2429 | set_state_and_timeout (n, GNUNET_TRANSPORT_PS_RECONNECT_BLACKLIST, GNUNET_TIME_relative_to_absolute (BLACKLIST_RESPONSE_TIMEOUT)); | 2419 | set_state_and_timeout (n, GNUNET_TRANSPORT_PS_RECONNECT_BLACKLIST, |
2430 | check_blacklist (&n->id, | 2420 | GNUNET_TIME_relative_to_absolute (BLACKLIST_RESPONSE_TIMEOUT)); |
2431 | n->connect_ack_timestamp, | 2421 | check_blacklist (&n->id, n->connect_ack_timestamp, |
2432 | address, session); | 2422 | blc_ctx->address, blc_ctx->session); |
2433 | break; | 2423 | break; |
2434 | case GNUNET_TRANSPORT_PS_CONNECTED_SWITCHING_BLACKLIST: | 2424 | case GNUNET_TRANSPORT_PS_CONNECTED_SWITCHING_BLACKLIST: |
2435 | if (n->primary_address.session == session) | 2425 | if (n->primary_address.session == blc_ctx->session) |
2436 | { | 2426 | { |
2437 | /* ATS switches back to still-active session */ | 2427 | /* ATS switches back to still-active session */ |
2438 | set_state(n, GNUNET_TRANSPORT_PS_CONNECTED); | 2428 | set_state(n, GNUNET_TRANSPORT_PS_CONNECTED); |
@@ -2440,14 +2430,13 @@ GST_neighbours_switch_to_address (const struct GNUNET_PeerIdentity *peer, | |||
2440 | break; | 2430 | break; |
2441 | } | 2431 | } |
2442 | /* ATS asks us to switch a life connection, update blacklist check */ | 2432 | /* ATS asks us to switch a life connection, update blacklist check */ |
2443 | set_primary_address (n, | 2433 | set_primary_address (n, blc_ctx->address, blc_ctx->session, |
2444 | address, session, bandwidth_in, bandwidth_out, GNUNET_NO); | 2434 | blc_ctx->bandwidth_in, blc_ctx->bandwidth_out, GNUNET_NO); |
2445 | check_blacklist (&n->id, | 2435 | check_blacklist (&n->id, GNUNET_TIME_absolute_get (), |
2446 | GNUNET_TIME_absolute_get (), | 2436 | blc_ctx->address, blc_ctx->session); |
2447 | address, session); | ||
2448 | break; | 2437 | break; |
2449 | case GNUNET_TRANSPORT_PS_CONNECTED_SWITCHING_CONNECT_SENT: | 2438 | case GNUNET_TRANSPORT_PS_CONNECTED_SWITCHING_CONNECT_SENT: |
2450 | if (n->primary_address.session == session) | 2439 | if (n->primary_address.session == blc_ctx->session) |
2451 | { | 2440 | { |
2452 | /* ATS switches back to still-active session */ | 2441 | /* ATS switches back to still-active session */ |
2453 | free_address (&n->alternative_address); | 2442 | free_address (&n->alternative_address); |
@@ -2456,10 +2445,10 @@ GST_neighbours_switch_to_address (const struct GNUNET_PeerIdentity *peer, | |||
2456 | } | 2445 | } |
2457 | /* ATS asks us to switch a life connection, update blacklist check */ | 2446 | /* ATS asks us to switch a life connection, update blacklist check */ |
2458 | set_state (n, GNUNET_TRANSPORT_PS_CONNECTED_SWITCHING_BLACKLIST); | 2447 | set_state (n, GNUNET_TRANSPORT_PS_CONNECTED_SWITCHING_BLACKLIST); |
2459 | set_alternative_address (n, address, session, bandwidth_in, bandwidth_out); | 2448 | set_alternative_address (n, blc_ctx->address, blc_ctx->session, |
2460 | check_blacklist (&n->id, | 2449 | blc_ctx->bandwidth_in, blc_ctx->bandwidth_out); |
2461 | GNUNET_TIME_absolute_get (), | 2450 | check_blacklist (&n->id, GNUNET_TIME_absolute_get (), |
2462 | address, session); | 2451 | blc_ctx->address, blc_ctx->session); |
2463 | break; | 2452 | break; |
2464 | case GNUNET_TRANSPORT_PS_DISCONNECT: | 2453 | case GNUNET_TRANSPORT_PS_DISCONNECT: |
2465 | /* not going to switch addresses while disconnecting */ | 2454 | /* not going to switch addresses while disconnecting */ |
@@ -2474,6 +2463,109 @@ GST_neighbours_switch_to_address (const struct GNUNET_PeerIdentity *peer, | |||
2474 | GNUNET_break (0); | 2463 | GNUNET_break (0); |
2475 | break; | 2464 | break; |
2476 | } | 2465 | } |
2466 | |||
2467 | GNUNET_CONTAINER_DLL_remove (pending_bc_head, pending_bc_tail, blc_ctx); | ||
2468 | GNUNET_HELLO_address_free(blc_ctx->address); | ||
2469 | GNUNET_free_non_null (blc_ctx->ats); | ||
2470 | GNUNET_free (blc_ctx); | ||
2471 | return; | ||
2472 | } | ||
2473 | |||
2474 | |||
2475 | /** | ||
2476 | * For the given peer, switch to this address. | ||
2477 | * | ||
2478 | * Before accepting this addresses and actively using it, a blacklist check | ||
2479 | * is performed. If this blacklist check fails the address will be destroyed. | ||
2480 | * | ||
2481 | * @param peer identity of the peer to switch the address for | ||
2482 | * @param address address of the other peer, | ||
2483 | * @param session session to use or NULL if transport should initiate a session | ||
2484 | * @param ats performance data | ||
2485 | * @param ats_count number of entries in ats | ||
2486 | * @param bandwidth_in inbound quota to be used when connection is up, | ||
2487 | * 0 to disconnect from peer | ||
2488 | * @param bandwidth_out outbound quota to be used when connection is up, | ||
2489 | * 0 to disconnect from peer | ||
2490 | */ | ||
2491 | void | ||
2492 | GST_neighbours_switch_to_address (const struct GNUNET_PeerIdentity *peer, | ||
2493 | const struct GNUNET_HELLO_Address *address, | ||
2494 | struct Session *session, | ||
2495 | const struct GNUNET_ATS_Information *ats, | ||
2496 | uint32_t ats_count, | ||
2497 | struct GNUNET_BANDWIDTH_Value32NBO bandwidth_in, | ||
2498 | struct GNUNET_BANDWIDTH_Value32NBO bandwidth_out) | ||
2499 | { | ||
2500 | struct NeighbourMapEntry *n; | ||
2501 | struct GNUNET_TRANSPORT_PluginFunctions *papi; | ||
2502 | struct BlacklistCheckSwitchContext *blc_ctx; | ||
2503 | int c; | ||
2504 | |||
2505 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
2506 | "ATS has decided on an address for peer %s\n", | ||
2507 | GNUNET_i2s (peer)); | ||
2508 | GNUNET_assert (NULL != address->transport_name); | ||
2509 | if (NULL == (n = lookup_neighbour (peer))) | ||
2510 | { | ||
2511 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
2512 | "Peer %s is unknown, suggestion ignored\n", | ||
2513 | GNUNET_i2s (peer)); | ||
2514 | return; | ||
2515 | } | ||
2516 | |||
2517 | /* Obtain an session for this address from plugin */ | ||
2518 | if (NULL == (papi = GST_plugins_find (address->transport_name))) | ||
2519 | { | ||
2520 | /* we don't have the plugin for this address */ | ||
2521 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
2522 | "Plugin `%s' is unknown, suggestion for peer %s ignored\n", | ||
2523 | address->transport_name, | ||
2524 | GNUNET_i2s (peer)); | ||
2525 | GNUNET_ATS_address_destroyed (GST_ats, address, NULL); | ||
2526 | return; | ||
2527 | } | ||
2528 | if ((NULL == session) && | ||
2529 | (GNUNET_HELLO_address_check_option (address, GNUNET_HELLO_ADDRESS_INFO_INBOUND))) | ||
2530 | { | ||
2531 | /* This is a inbound address and we do not have a session to use! */ | ||
2532 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
2533 | "Inbound address without session `%s'! Destroying address...\n", | ||
2534 | GST_plugins_a2s (address)); | ||
2535 | GNUNET_ATS_address_destroyed (GST_ats, address, NULL); | ||
2536 | return; | ||
2537 | } | ||
2538 | |||
2539 | GNUNET_log (GNUNET_ERROR_TYPE_INFO, | ||
2540 | "ATS tells us to switch to %s address '%s' session %p for " | ||
2541 | "peer `%s' in state %s/%d (quota in/out %u %u )\n", | ||
2542 | GNUNET_HELLO_address_check_option (address, | ||
2543 | GNUNET_HELLO_ADDRESS_INFO_INBOUND) ? "inbound" : "", | ||
2544 | GST_plugins_a2s (address), session, GNUNET_i2s (peer), | ||
2545 | GNUNET_TRANSPORT_ps2s (n->state), n->send_connect_ack, | ||
2546 | ntohl (bandwidth_in.value__), ntohl (bandwidth_out.value__)); | ||
2547 | |||
2548 | /* Perform blacklist check */ | ||
2549 | blc_ctx = GNUNET_new (struct BlacklistCheckSwitchContext); | ||
2550 | blc_ctx->address = GNUNET_HELLO_address_copy (address); | ||
2551 | blc_ctx->session = session; | ||
2552 | blc_ctx->bandwidth_in = bandwidth_in; | ||
2553 | blc_ctx->bandwidth_out = bandwidth_out; | ||
2554 | blc_ctx->ats_count = ats_count; | ||
2555 | blc_ctx->ats = NULL; | ||
2556 | if (ats_count > 0) | ||
2557 | { | ||
2558 | blc_ctx->ats = GNUNET_malloc (ats_count * sizeof (struct GNUNET_ATS_Information)); | ||
2559 | for (c = 0; c < ats_count; c++) | ||
2560 | { | ||
2561 | blc_ctx->ats[c].type = ats[c].type; | ||
2562 | blc_ctx->ats[c].value = ats[c].value; | ||
2563 | } | ||
2564 | } | ||
2565 | |||
2566 | GNUNET_CONTAINER_DLL_insert (pending_bc_head, pending_bc_tail, blc_ctx); | ||
2567 | GST_blacklist_test_allowed (peer, address->transport_name, | ||
2568 | &switch_address_bl_check_cont, blc_ctx); | ||
2477 | } | 2569 | } |
2478 | 2570 | ||
2479 | 2571 | ||
@@ -3549,6 +3641,9 @@ disconnect_all_neighbours (void *cls, | |||
3549 | void | 3641 | void |
3550 | GST_neighbours_stop () | 3642 | GST_neighbours_stop () |
3551 | { | 3643 | { |
3644 | struct BlacklistCheckSwitchContext *cur; | ||
3645 | struct BlacklistCheckSwitchContext *next; | ||
3646 | |||
3552 | if (NULL == neighbours) | 3647 | if (NULL == neighbours) |
3553 | return; | 3648 | return; |
3554 | if (GNUNET_SCHEDULER_NO_TASK != util_transmission_tk) | 3649 | if (GNUNET_SCHEDULER_NO_TASK != util_transmission_tk) |
@@ -3561,6 +3656,18 @@ GST_neighbours_stop () | |||
3561 | &disconnect_all_neighbours, | 3656 | &disconnect_all_neighbours, |
3562 | NULL); | 3657 | NULL); |
3563 | GNUNET_CONTAINER_multipeermap_destroy (neighbours); | 3658 | GNUNET_CONTAINER_multipeermap_destroy (neighbours); |
3659 | |||
3660 | next = pending_bc_head; | ||
3661 | for (cur = next; NULL != cur; cur = next ) | ||
3662 | { | ||
3663 | next = cur->next; | ||
3664 | |||
3665 | GNUNET_CONTAINER_DLL_remove (pending_bc_head, pending_bc_tail, cur); | ||
3666 | GNUNET_HELLO_address_free (cur->address); | ||
3667 | GNUNET_free_non_null (cur->ats); | ||
3668 | GNUNET_free (cur); | ||
3669 | } | ||
3670 | |||
3564 | neighbours = NULL; | 3671 | neighbours = NULL; |
3565 | callback_cls = NULL; | 3672 | callback_cls = NULL; |
3566 | connect_notify_cb = NULL; | 3673 | connect_notify_cb = NULL; |