mirror of
https://github.com/transmission/transmission
synced 2025-03-03 10:15:45 +00:00
(trunk libT) #4051 "Use composition for the tr_history fields in tr_peer" -- fixed.
If we use composition on these objects we can save a handful of pointers per peer. This isn't a big deal, but it's an easy/safe change to do.
This commit is contained in:
parent
2b9db3c242
commit
f2b4a59eda
6 changed files with 63 additions and 66 deletions
|
@ -32,19 +32,19 @@ static int test = 0;
|
|||
static int
|
||||
test1( void )
|
||||
{
|
||||
tr_recentHistory * h;
|
||||
tr_recentHistory h;
|
||||
|
||||
h = tr_historyNew( 60, 10 );
|
||||
tr_historyAdd( h, 10000, 1 );
|
||||
check( (int)tr_historyGet( h, 12000, 1000 ) == 0 )
|
||||
check( (int)tr_historyGet( h, 12000, 3000 ) == 1 )
|
||||
check( (int)tr_historyGet( h, 12000, 5000 ) == 1 )
|
||||
tr_historyAdd( h, 20000, 1 );
|
||||
check( (int)tr_historyGet( h, 22000, 1000 ) == 0 )
|
||||
check( (int)tr_historyGet( h, 22000, 3000 ) == 1 )
|
||||
check( (int)tr_historyGet( h, 22000, 15000 ) == 2 )
|
||||
check( (int)tr_historyGet( h, 22000, 20000 ) == 2 )
|
||||
tr_historyFree( h );
|
||||
tr_historyConstruct( &h, 60, 10 );
|
||||
tr_historyAdd( &h, 10000, 1 );
|
||||
check( (int)tr_historyGet( &h, 12000, 1000 ) == 0 )
|
||||
check( (int)tr_historyGet( &h, 12000, 3000 ) == 1 )
|
||||
check( (int)tr_historyGet( &h, 12000, 5000 ) == 1 )
|
||||
tr_historyAdd( &h, 20000, 1 );
|
||||
check( (int)tr_historyGet( &h, 22000, 1000 ) == 0 )
|
||||
check( (int)tr_historyGet( &h, 22000, 3000 ) == 1 )
|
||||
check( (int)tr_historyGet( &h, 22000, 15000 ) == 2 )
|
||||
check( (int)tr_historyGet( &h, 22000, 20000 ) == 2 )
|
||||
tr_historyDestruct( &h );
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
|
|
@ -16,20 +16,6 @@
|
|||
#include "history.h"
|
||||
#include "utils.h"
|
||||
|
||||
struct history_slice
|
||||
{
|
||||
unsigned int n;
|
||||
time_t date;
|
||||
};
|
||||
|
||||
struct tr_recentHistory
|
||||
{
|
||||
int newest;
|
||||
int sliceCount;
|
||||
unsigned int precision;
|
||||
struct history_slice * slices;
|
||||
};
|
||||
|
||||
void
|
||||
tr_historyAdd( tr_recentHistory * h, time_t now, unsigned int n )
|
||||
{
|
||||
|
@ -63,24 +49,20 @@ tr_historyGet( const tr_recentHistory * h, time_t now, unsigned int sec )
|
|||
return n;
|
||||
}
|
||||
|
||||
tr_recentHistory *
|
||||
tr_historyNew( unsigned int seconds, unsigned int precision )
|
||||
void
|
||||
tr_historyConstruct( tr_recentHistory * h, unsigned int seconds, unsigned int precision )
|
||||
{
|
||||
tr_recentHistory * h;
|
||||
memset( h, 0, sizeof( tr_recentHistory ) );
|
||||
|
||||
assert( precision <= seconds );
|
||||
|
||||
h = tr_new0( tr_recentHistory, 1 );
|
||||
h->precision = precision;
|
||||
h->sliceCount = seconds / precision;
|
||||
h->slices = tr_new0( struct history_slice, h->sliceCount );
|
||||
|
||||
return h;
|
||||
h->slices = tr_new0( struct tr_history_slice, h->sliceCount );
|
||||
}
|
||||
|
||||
void
|
||||
tr_historyFree( tr_recentHistory * h )
|
||||
tr_historyDestruct( tr_recentHistory * h )
|
||||
{
|
||||
tr_free( h->slices );
|
||||
tr_free( h );
|
||||
}
|
||||
|
|
|
@ -24,18 +24,33 @@
|
|||
* For example, it could count how many are bytes transferred
|
||||
* to estimate the speed over the last N seconds.
|
||||
*/
|
||||
typedef struct tr_recentHistory tr_recentHistory;
|
||||
|
||||
struct tr_history_slice
|
||||
{
|
||||
unsigned int n;
|
||||
time_t date;
|
||||
};
|
||||
typedef struct tr_recentHistory
|
||||
{
|
||||
/* these are PRIVATE IMPLEMENTATION details included for composition only.
|
||||
* Don't access these directly! */
|
||||
int newest;
|
||||
int sliceCount;
|
||||
unsigned int precision;
|
||||
struct tr_history_slice * slices;
|
||||
}
|
||||
tr_recentHistory;
|
||||
|
||||
/**
|
||||
* @brief create a new tr_recentHistory object.
|
||||
* @brief construct a new tr_recentHistory object
|
||||
* @param seconds how many seconds of history this object should remember
|
||||
* @param precision how precise the history should be, in seconds
|
||||
* For a precision of 10 seconds and a history of 2 minutes, makes 12 bins.
|
||||
*/
|
||||
tr_recentHistory * tr_historyNew( unsigned int seconds, unsigned int precision );
|
||||
void tr_historyConstruct( tr_recentHistory *, unsigned int seconds, unsigned int precision );
|
||||
|
||||
/** @brief destroy an existing tr_recentHistory object. */
|
||||
void tr_historyFree( tr_recentHistory * );
|
||||
/** @brief destruct an existing tr_recentHistory object. */
|
||||
void tr_historyDestruct( tr_recentHistory * );
|
||||
|
||||
/**
|
||||
* @brief add a counter to the recent history object.
|
||||
|
|
|
@ -388,10 +388,10 @@ peerConstructor( struct peer_atom * atom )
|
|||
peer->atom = atom;
|
||||
atom->peer = peer;
|
||||
|
||||
peer->blocksSentToClient = tr_historyNew( CANCEL_HISTORY_SEC, ( RECHOKE_PERIOD_MSEC / 1000 ) );
|
||||
peer->blocksSentToPeer = tr_historyNew( CANCEL_HISTORY_SEC, ( RECHOKE_PERIOD_MSEC / 1000 ) );
|
||||
peer->cancelsSentToClient = tr_historyNew( CANCEL_HISTORY_SEC, ( RECHOKE_PERIOD_MSEC / 1000 ) );
|
||||
peer->cancelsSentToPeer = tr_historyNew( CANCEL_HISTORY_SEC, ( REFILL_UPKEEP_PERIOD_MSEC / 1000 ) );
|
||||
tr_historyConstruct( &peer->blocksSentToClient, CANCEL_HISTORY_SEC, ( RECHOKE_PERIOD_MSEC / 1000 ) );
|
||||
tr_historyConstruct( &peer->blocksSentToPeer, CANCEL_HISTORY_SEC, ( RECHOKE_PERIOD_MSEC / 1000 ) );
|
||||
tr_historyConstruct( &peer->cancelsSentToClient, CANCEL_HISTORY_SEC, ( RECHOKE_PERIOD_MSEC / 1000 ) );
|
||||
tr_historyConstruct( &peer->cancelsSentToPeer, CANCEL_HISTORY_SEC, ( REFILL_UPKEEP_PERIOD_MSEC / 1000 ) );
|
||||
|
||||
return peer;
|
||||
}
|
||||
|
@ -429,10 +429,10 @@ peerDestructor( Torrent * t, tr_peer * peer )
|
|||
tr_peerIoClear( peer->io );
|
||||
tr_peerIoUnref( peer->io ); /* balanced by the ref in handshakeDoneCB() */
|
||||
|
||||
tr_historyFree( peer->blocksSentToClient );
|
||||
tr_historyFree( peer->blocksSentToPeer );
|
||||
tr_historyFree( peer->cancelsSentToClient );
|
||||
tr_historyFree( peer->cancelsSentToPeer );
|
||||
tr_historyDestruct( &peer->blocksSentToClient );
|
||||
tr_historyDestruct( &peer->blocksSentToPeer );
|
||||
tr_historyDestruct( &peer->cancelsSentToClient );
|
||||
tr_historyDestruct( &peer->cancelsSentToPeer );
|
||||
|
||||
tr_bitsetDestruct( &peer->have );
|
||||
tr_bitfieldFree( peer->blame );
|
||||
|
@ -1474,7 +1474,7 @@ refillUpkeep( int foo UNUSED, short bar UNUSED, void * vmgr )
|
|||
/* send cancel messages for all the "cancel" ones */
|
||||
for( it=cancel, end=it+cancelCount; it!=end; ++it ) {
|
||||
if( ( it->peer != NULL ) && ( it->peer->msgs != NULL ) ) {
|
||||
tr_historyAdd( it->peer->cancelsSentToPeer, now, 1 );
|
||||
tr_historyAdd( &it->peer->cancelsSentToPeer, now, 1 );
|
||||
tr_peerMsgsCancel( it->peer->msgs, it->block );
|
||||
decrementPendingReqCount( it );
|
||||
}
|
||||
|
@ -1730,7 +1730,7 @@ peerCallbackFunc( tr_peer * peer, const tr_peer_event * e, void * vt )
|
|||
tr_peer * p = peers[i];
|
||||
assert( p != peer );
|
||||
if( p->msgs ) {
|
||||
tr_historyAdd( p->cancelsSentToPeer, tr_time( ), 1 );
|
||||
tr_historyAdd( &p->cancelsSentToPeer, tr_time( ), 1 );
|
||||
tr_peerMsgsCancel( p->msgs, block );
|
||||
}
|
||||
removeRequestFromTables( t, block, p );
|
||||
|
@ -1738,8 +1738,8 @@ peerCallbackFunc( tr_peer * peer, const tr_peer_event * e, void * vt )
|
|||
|
||||
tr_ptrArrayDestruct( &peerArr, FALSE );
|
||||
|
||||
if( peer && peer->blocksSentToClient )
|
||||
tr_historyAdd( peer->blocksSentToClient, tr_time( ), 1 );
|
||||
if( peer )
|
||||
tr_historyAdd( &peer->blocksSentToClient, tr_time( ), 1 );
|
||||
|
||||
if( tr_cpBlockIsComplete( &tor->completion, block ) )
|
||||
{
|
||||
|
@ -2642,10 +2642,10 @@ tr_peerMgrPeerStats( const tr_torrent * tor, int * setmeCount )
|
|||
stat->isUploadingTo = clientIsUploadingTo( peer );
|
||||
stat->isSeed = ( atom->uploadOnly == UPLOAD_ONLY_YES ) || ( peer->progress >= 1.0 );
|
||||
|
||||
stat->blocksToPeer = tr_historyGet( peer->blocksSentToPeer, now, CANCEL_HISTORY_SEC );
|
||||
stat->blocksToClient = tr_historyGet( peer->blocksSentToClient, now, CANCEL_HISTORY_SEC );
|
||||
stat->cancelsToPeer = tr_historyGet( peer->cancelsSentToPeer, now, CANCEL_HISTORY_SEC );
|
||||
stat->cancelsToClient = tr_historyGet( peer->cancelsSentToClient, now, CANCEL_HISTORY_SEC );
|
||||
stat->blocksToPeer = tr_historyGet( &peer->blocksSentToPeer, now, CANCEL_HISTORY_SEC );
|
||||
stat->blocksToClient = tr_historyGet( &peer->blocksSentToClient, now, CANCEL_HISTORY_SEC );
|
||||
stat->cancelsToPeer = tr_historyGet( &peer->cancelsSentToPeer, now, CANCEL_HISTORY_SEC );
|
||||
stat->cancelsToClient = tr_historyGet( &peer->cancelsSentToClient, now, CANCEL_HISTORY_SEC );
|
||||
|
||||
stat->pendingReqsToPeer = peer->pendingReqsToPeer;
|
||||
stat->pendingReqsToClient = peer->pendingReqsToClient;
|
||||
|
@ -2760,8 +2760,8 @@ rechokeDownloads( Torrent * t )
|
|||
for( i=0; i<peerCount; ++i )
|
||||
{
|
||||
const tr_peer * peer = tr_ptrArrayNth( &t->peers, i );
|
||||
const int b = tr_historyGet( peer->blocksSentToClient, now, CANCEL_HISTORY_SEC );
|
||||
const int c = tr_historyGet( peer->cancelsSentToPeer, now, CANCEL_HISTORY_SEC );
|
||||
const int b = tr_historyGet( &peer->blocksSentToClient, now, CANCEL_HISTORY_SEC );
|
||||
const int c = tr_historyGet( &peer->cancelsSentToPeer, now, CANCEL_HISTORY_SEC );
|
||||
|
||||
if( b == 0 ) /* ignore unresponsive peers, as described above */
|
||||
continue;
|
||||
|
@ -2824,8 +2824,8 @@ rechokeDownloads( Torrent * t )
|
|||
}
|
||||
else
|
||||
{
|
||||
const int blocks = tr_historyGet( peer->blocksSentToClient, now, CANCEL_HISTORY_SEC );
|
||||
const int cancels = tr_historyGet( peer->cancelsSentToPeer, now, CANCEL_HISTORY_SEC );
|
||||
const int blocks = tr_historyGet( &peer->blocksSentToClient, now, CANCEL_HISTORY_SEC );
|
||||
const int cancels = tr_historyGet( &peer->cancelsSentToPeer, now, CANCEL_HISTORY_SEC );
|
||||
|
||||
if( !blocks && !cancels )
|
||||
untested[untestedCount++] = peer;
|
||||
|
|
|
@ -122,11 +122,11 @@ typedef struct tr_peer
|
|||
|
||||
time_t chokeChangedAt;
|
||||
|
||||
tr_recentHistory * blocksSentToClient;
|
||||
tr_recentHistory * blocksSentToPeer;
|
||||
tr_recentHistory blocksSentToClient;
|
||||
tr_recentHistory blocksSentToPeer;
|
||||
|
||||
tr_recentHistory * cancelsSentToClient;
|
||||
tr_recentHistory * cancelsSentToPeer;
|
||||
tr_recentHistory cancelsSentToClient;
|
||||
tr_recentHistory cancelsSentToPeer;
|
||||
|
||||
struct tr_peermsgs * msgs;
|
||||
}
|
||||
|
|
|
@ -1476,7 +1476,7 @@ readBtMessage( tr_peermsgs * msgs, struct evbuffer * inbuf, size_t inlen )
|
|||
tr_peerIoReadUint32( msgs->peer->io, inbuf, &r.index );
|
||||
tr_peerIoReadUint32( msgs->peer->io, inbuf, &r.offset );
|
||||
tr_peerIoReadUint32( msgs->peer->io, inbuf, &r.length );
|
||||
tr_historyAdd( msgs->peer->cancelsSentToClient, tr_time( ), 1 );
|
||||
tr_historyAdd( &msgs->peer->cancelsSentToClient, tr_time( ), 1 );
|
||||
dbgmsg( msgs, "got a Cancel %u:%u->%u", r.index, r.offset, r.length );
|
||||
|
||||
for( i=0; i<msgs->peer->pendingReqsToClient; ++i ) {
|
||||
|
@ -1958,7 +1958,7 @@ fillOutputBuffer( tr_peermsgs * msgs, time_t now )
|
|||
tr_peerIoWriteBuf( msgs->peer->io, out, TRUE );
|
||||
bytesWritten += n;
|
||||
msgs->clientSentAnythingAt = now;
|
||||
tr_historyAdd( msgs->peer->blocksSentToPeer, tr_time( ), 1 );
|
||||
tr_historyAdd( &msgs->peer->blocksSentToPeer, tr_time( ), 1 );
|
||||
}
|
||||
|
||||
evbuffer_free( out );
|
||||
|
|
Loading…
Reference in a new issue