fix multitracker problem reported by BentMyWookie

This commit is contained in:
Charles Kerr 2008-05-05 20:11:03 +00:00
parent d561187227
commit 2cd2b35238
2 changed files with 37 additions and 45 deletions

View File

@ -298,20 +298,21 @@ tr_torrentPromoteTracker( tr_torrent * tor, int pos )
int tier;
assert( tor != NULL );
assert( 0 <= pos && pos < tor->info.trackerCount );
assert( ( 0 <= pos ) && ( pos < tor->info.trackerCount ) );
/* the tier of the tracker we're promoting */
tier = tor->info.trackers[pos].tier;
/* find the index of the first tracker in that tier */
/* find the index of that tier's first tracker */
for( i=0; i<tor->info.trackerCount; ++i )
if( tor->info.trackers[i].tier == tier )
break;
assert( i < tor->info.trackerCount );
/* swap them if they're not the same */
/* promote the tracker at `pos' to the front of the tier */
if( i != pos ) {
tr_tracker_info tmp = tor->info.trackers[i];
const tr_tracker_info tmp = tor->info.trackers[i];
tor->info.trackers[i] = tor->info.trackers[pos];
tor->info.trackers[pos] = tmp;
}
@ -326,6 +327,8 @@ struct RandomTracker
int random_value;
};
/* the tiers will be sorted from lowest to highest,
* and trackers are randomized within the tiers */
static int
compareRandomTracker( const void * va, const void * vb )
{
@ -343,8 +346,7 @@ randomizeTiers( tr_info * info )
{
int i;
const int n = info->trackerCount;
struct RandomTracker * r;
r = tr_new0( struct RandomTracker, n );
struct RandomTracker * r = tr_new0( struct RandomTracker, n );
for( i=0; i<n; ++i ) {
r[i].tracker = info->trackers[i];
r[i].random_value = tr_rand( INT_MAX );

View File

@ -224,45 +224,33 @@ publishNewPeers( tr_tracker * t, int allAreSeeds,
static void onReqDone( tr_session * session );
static void
updateAddresses( tr_tracker * t,
long response_code,
int moveToNextAddress,
int * tryAgain )
static int
updateAddresses( tr_tracker * t, int success )
{
int retry;
tr_torrent * torrent = tr_torrentFindFromHash( t->session, t->hash );
if( !response_code ) /* tracker didn't respond */
{
tr_ninf( t->name, _( "Tracker hasn't responded yet. Retrying..." ) );
moveToNextAddress = TRUE;
}
else if( response_code == HTTP_OK )
if( success )
{
/* multitracker spec: "if a connection with a tracker is
successful, it will be moved to the front of the tier." */
t->trackerIndex = tr_torrentPromoteTracker( torrent, t->trackerIndex );
retry = FALSE; /* we succeeded; no need to retry */
}
else
else if ( ++t->trackerIndex >= torrent->info.trackerCount )
{
moveToNextAddress = TRUE;
t->trackerIndex = 0;
retry = FALSE; /* we've tried them all */
}
else
{
const tr_tracker_info * n = getCurrentAddressFromTorrent( t, torrent );
tr_ninf( t->name, _( "Trying tracker \"%s\"" ), n->announce );
retry = TRUE;
}
*tryAgain = moveToNextAddress;
if( moveToNextAddress )
{
if ( ++t->trackerIndex >= torrent->info.trackerCount ) /* we've tried them all */
{
*tryAgain = FALSE;
t->trackerIndex = 0;
}
else
{
const tr_tracker_info * n = getCurrentAddressFromTorrent( t, torrent );
tr_ninf( t->name, _( "Trying tracker \"%s\"" ), n->announce );
}
}
return retry;
}
/* Convert to compact form */
@ -321,8 +309,8 @@ onTrackerResponse( tr_session * session,
size_t responseLen,
void * torrent_hash )
{
int moveToNextAddress = FALSE;
int tryAgain;
int retry;
int success = FALSE;
tr_tracker * t;
onReqDone( session );
@ -347,10 +335,12 @@ onTrackerResponse( tr_session * session,
int incomplete = -1;
const char * str;
success = TRUE;
if(( tr_bencDictFindStr( &benc, "failure reason", &str ))) {
// publishErrorMessageAndStop( t, str );
moveToNextAddress = TRUE;
publishMessage( t, str, TR_TRACKER_ERROR );
success = FALSE;
}
if(( tr_bencDictFindStr( &benc, "warning message", &str )))
@ -397,13 +387,13 @@ onTrackerResponse( tr_session * session,
tr_bencFree( &benc );
}
updateAddresses( t, responseCode, moveToNextAddress, &tryAgain );
retry = updateAddresses( t, success );
/**
***
**/
if( tryAgain )
if( retry )
responseCode = 300;
if( 200<=responseCode && responseCode<=299 )
@ -458,8 +448,8 @@ onScrapeResponse( tr_session * session,
size_t responseLen,
void * torrent_hash )
{
int moveToNextAddress = FALSE;
int tryAgain;
int success = FALSE;
int retry;
tr_tracker * t;
onReqDone( session );
@ -504,26 +494,26 @@ onScrapeResponse( tr_session * session,
if(( tr_bencDictFindInt( flags, "min_request_interval", &itmp )))
t->scrapeIntervalSec = i;
success = TRUE;
tr_ndbg( t->name, "Scrape successful. Rescraping in %d seconds.",
t->scrapeIntervalSec );
t->retryScrapeIntervalSec = 30;
}
}
else
moveToNextAddress = TRUE;
if( bencLoaded )
tr_bencFree( &benc );
}
updateAddresses( t, responseCode, moveToNextAddress, &tryAgain );
retry = updateAddresses( t, success );
/**
***
**/
if( tryAgain )
if( retry )
responseCode = 300;
if( 200<=responseCode && responseCode<=299 )