/* Clean a single torrent return 1 if torrent timed out */ int clean_single_torrent( ot_torrent *torrent ) { ot_peerlist *peer_list = torrent->peer_list; ot_vector *bucket_list = &peer_list->peers; time_t timedout = (time_t)( g_now_minutes - peer_list->base ); int num_buckets = 1, removed_seeders = 0; /* No need to clean empty torrent */ if( !timedout ) return 0; /* Torrent has idled out */ if( timedout > OT_TORRENT_TIMEOUT ) return 1; /* Nothing to be cleaned here? Test if torrent is worth keeping */ if( timedout > OT_PEER_TIMEOUT ) { if( !peer_list->peer_count ) return peer_list->down_count ? 0 : 1; timedout = OT_PEER_TIMEOUT; } if( OT_PEERLIST_HASBUCKETS( peer_list ) ) { num_buckets = bucket_list->size; bucket_list = (ot_vector *)bucket_list->data; } while( num_buckets-- ) { size_t removed_peers = clean_single_bucket( bucket_list->data, bucket_list->size, timedout, &removed_seeders ); peer_list->peer_count -= removed_peers; bucket_list->size -= removed_peers; if( bucket_list->size < removed_peers ) vector_fixup_peers( bucket_list ); ++bucket_list; } peer_list->seed_count -= removed_seeders; /* See, if we need to convert a torrent from simple vector to bucket list */ if( ( peer_list->peer_count > OT_PEER_BUCKET_MINCOUNT ) || OT_PEERLIST_HASBUCKETS(peer_list) ) vector_redistribute_buckets( peer_list ); if( peer_list->peer_count ) peer_list->base = g_now_minutes; else { /* When we got here, the last time that torrent has been touched is OT_PEER_TIMEOUT Minutes before */ peer_list->base = g_now_minutes - OT_PEER_TIMEOUT; } return 0; }
/* This is the non-generic delete from vector-operation specialized for peers in pools. It returns 0 if no peer was found (and thus not removed) 1 if a non-seeding peer was removed 2 if a seeding peer was removed */ int vector_remove_peer( ot_vector *vector, ot_peer *peer ) { int exactmatch; ot_peer *match, *end; if( !vector->size ) return 0; /* If space is zero but size is set, we're dealing with a list of vector->size buckets */ if( vector->space < vector->size ) vector = ((ot_vector*)vector->data) + vector_hash_peer(peer, vector->size ); end = ((ot_peer*)vector->data) + vector->size; match = (ot_peer*)binary_search( peer, vector->data, vector->size, sizeof(ot_peer), OT_PEER_COMPARE_SIZE, &exactmatch ); if( !exactmatch ) return 0; exactmatch = ( OT_PEERFLAG( match ) & PEER_FLAG_SEEDING ) ? 2 : 1; memmove( match, match + 1, sizeof(ot_peer) * ( end - match - 1 ) ); vector->size--; vector_fixup_peers( vector ); return exactmatch; }
/* Clean a single torrent return 1 if torrent timed out */ int clean_single_torrent( ot_torrent *torrent ) { #ifdef _DEBUG ts_log_debug("ot_clean::clean_single_torrent: start"); #endif ot_peerlist *peer_list = torrent->peer_list; ot_vector *bucket_list = &peer_list->peers; time_t timedout = (time_t)( g_now_minutes - peer_list->base ); int num_buckets = 1, removed_seeders = 0; /* terasaur -- begin mod */ int update_stats = 0; /* terasaur -- end mod */ /* No need to clean empty torrent */ if( !timedout ) return 0; /* Torrent has idled out */ if( timedout > OT_TORRENT_TIMEOUT ) return 1; /* Nothing to be cleaned here? Test if torrent is worth keeping */ if( timedout > OT_PEER_TIMEOUT ) { if( !peer_list->peer_count ) return peer_list->down_count ? 0 : 1; timedout = OT_PEER_TIMEOUT; } if( OT_PEERLIST_HASBUCKETS( peer_list ) ) { num_buckets = bucket_list->size; bucket_list = (ot_vector *)bucket_list->data; } while( num_buckets-- ) { size_t removed_peers = clean_single_bucket( bucket_list->data, bucket_list->size, timedout, &removed_seeders ); peer_list->peer_count -= removed_peers; bucket_list->size -= removed_peers; if( bucket_list->size < removed_peers ) vector_fixup_peers( bucket_list ); ++bucket_list; /* terasaur -- begin mod */ if ((removed_peers) > 0 || (removed_seeders > 0)) { update_stats = 1; } /* terasaur -- end mod */ } peer_list->seed_count -= removed_seeders; /* See, if we need to convert a torrent from simple vector to bucket list */ if( ( peer_list->peer_count > OT_PEER_BUCKET_MINCOUNT ) || OT_PEERLIST_HASBUCKETS(peer_list) ) vector_redistribute_buckets( peer_list ); if( peer_list->peer_count ) peer_list->base = g_now_minutes; else { /* When we got here, the last time that torrent has been touched is OT_PEER_TIMEOUT Minutes before */ peer_list->base = g_now_minutes - OT_PEER_TIMEOUT; } /* terasaur -- begin mod */ if (update_stats == 1) { #ifdef _DEBUG ts_log_debug("ot_clean::clean_single_torrent: calling ts_update_torrent_stats"); #endif ts_update_torrent_stats(torrent, 0); #ifdef _DEBUG ts_log_debug("ot_clean::clean_single_torrent: after ts_update_torrent_stats"); #endif } /* terasaur -- end mod */ #ifdef _DEBUG ts_log_debug("ot_clean::clean_single_torrent: returning"); #endif return 0; }