diff options
Diffstat (limited to 'trackerlogic.c')
-rw-r--r-- | trackerlogic.c | 77 |
1 files changed, 52 insertions, 25 deletions
diff --git a/trackerlogic.c b/trackerlogic.c index 4de5038..38de8ca 100644 --- a/trackerlogic.c +++ b/trackerlogic.c | |||
@@ -64,7 +64,7 @@ static void *binary_search( const void * const key, const void * base, const siz | |||
64 | */ | 64 | */ |
65 | char ths[2+2*20]="-";char*to_hex(ot_byte*s){char*m="0123456789ABCDEF";char*e=ths+41;char*t=ths+1;while(t<e){*t++=m[*s>>4];*t++=m[*s++&15];}*t=0;return ths+1;} | 65 | char ths[2+2*20]="-";char*to_hex(ot_byte*s){char*m="0123456789ABCDEF";char*e=ths+41;char*t=ths+1;while(t<e){*t++=m[*s>>4];*t++=m[*s++&15];}*t=0;return ths+1;} |
66 | 66 | ||
67 | static void *vector_find_or_insert( ot_vector *vector, void *key, size_t member_size, int compare_size, int *exactmatch ) { | 67 | static void *vector_find_or_insert( ot_vector *vector, void *key, size_t member_size, size_t compare_size, int *exactmatch ) { |
68 | ot_byte *match = binary_search( key, vector->data, vector->size, member_size, compare_size, exactmatch ); | 68 | ot_byte *match = binary_search( key, vector->data, vector->size, member_size, compare_size, exactmatch ); |
69 | 69 | ||
70 | if( *exactmatch ) return match; | 70 | if( *exactmatch ) return match; |
@@ -104,7 +104,7 @@ static int vector_remove_peer( ot_vector *vector, ot_peer *peer ) { | |||
104 | } | 104 | } |
105 | 105 | ||
106 | static void free_peerlist( ot_peerlist *peer_list ) { | 106 | static void free_peerlist( ot_peerlist *peer_list ) { |
107 | int i; | 107 | size_t i; |
108 | for( i=0; i<OT_POOLS_COUNT; ++i ) | 108 | for( i=0; i<OT_POOLS_COUNT; ++i ) |
109 | if( peer_list->peers[i].data ) | 109 | if( peer_list->peers[i].data ) |
110 | free( peer_list->peers[i].data ); | 110 | free( peer_list->peers[i].data ); |
@@ -227,9 +227,9 @@ ot_torrent *add_peer_to_torrent( ot_hash *hash, ot_peer *peer ) { | |||
227 | * RANDOM may return huge values | 227 | * RANDOM may return huge values |
228 | * does not yet check not to return self | 228 | * does not yet check not to return self |
229 | */ | 229 | */ |
230 | size_t return_peers_for_torrent( ot_torrent *torrent, unsigned int amount, char *reply ) { | 230 | size_t return_peers_for_torrent( ot_torrent *torrent, size_t amount, char *reply ) { |
231 | char *r = reply; | 231 | char *r = reply; |
232 | unsigned int peer_count, seed_count, index; | 232 | size_t peer_count, seed_count, index; |
233 | 233 | ||
234 | #ifdef WANT_CLOSED_TRACKER | 234 | #ifdef WANT_CLOSED_TRACKER |
235 | if( torrent == OT_TORRENT_NOT_ON_WHITELIST ) { | 235 | if( torrent == OT_TORRENT_NOT_ON_WHITELIST ) { |
@@ -247,13 +247,13 @@ size_t return_peers_for_torrent( ot_torrent *torrent, unsigned int amount, char | |||
247 | } | 247 | } |
248 | #endif | 248 | #endif |
249 | 249 | ||
250 | for( peer_count=seed_count=index=0; index<OT_POOLS_COUNT; ++index) { | 250 | for( peer_count = seed_count = index = 0; index < OT_POOLS_COUNT; ++index ) { |
251 | peer_count += torrent->peer_list->peers[index].size; | 251 | peer_count += torrent->peer_list->peers[index].size; |
252 | seed_count += torrent->peer_list->seed_count[index]; | 252 | seed_count += torrent->peer_list->seed_count[index]; |
253 | } | 253 | } |
254 | if( peer_count < amount ) amount = peer_count; | 254 | if( peer_count < amount ) amount = peer_count; |
255 | 255 | ||
256 | r += sprintf( r, "d8:completei%ie10:incompletei%ie8:intervali%ie5:peers%i:", seed_count, peer_count-seed_count, OT_CLIENT_REQUEST_INTERVAL_RANDOM, 6*amount ); | 256 | r += sprintf( r, "d8:completei%zde10:incompletei%zde8:intervali%ie5:peers%zd:", seed_count, peer_count-seed_count, OT_CLIENT_REQUEST_INTERVAL_RANDOM, 6*amount ); |
257 | if( amount ) { | 257 | if( amount ) { |
258 | unsigned int pool_offset, pool_index = 0;; | 258 | unsigned int pool_offset, pool_index = 0;; |
259 | unsigned int shifted_pc = peer_count; | 259 | unsigned int shifted_pc = peer_count; |
@@ -292,8 +292,9 @@ size_t return_peers_for_torrent( ot_torrent *torrent, unsigned int amount, char | |||
292 | 292 | ||
293 | /* Fetch full scrape info for all torrents */ | 293 | /* Fetch full scrape info for all torrents */ |
294 | size_t return_fullscrape_for_tracker( char **reply ) { | 294 | size_t return_fullscrape_for_tracker( char **reply ) { |
295 | int torrent_count = 0, i, j, k; | 295 | size_t torrent_count = 0, j; |
296 | char* r; | 296 | int i, k; |
297 | char *r; | ||
297 | time_t time_now = NOW; | 298 | time_t time_now = NOW; |
298 | 299 | ||
299 | for( i=0; i<256; ++i ) { | 300 | for( i=0; i<256; ++i ) { |
@@ -301,16 +302,15 @@ size_t return_fullscrape_for_tracker( char **reply ) { | |||
301 | torrent_count += torrents_list->size; | 302 | torrent_count += torrents_list->size; |
302 | } | 303 | } |
303 | 304 | ||
304 | r = *reply = malloc( 128*torrent_count ); | 305 | if( !( r = *reply = malloc( 128*torrent_count ) ) ) return 0; |
305 | if( !reply ) return 0; | 306 | |
306 | |||
307 | memmove( r, "d5:filesd", 9 ); r += 9; | 307 | memmove( r, "d5:filesd", 9 ); r += 9; |
308 | for( i=0; i<256; ++i ) { | 308 | for( i=0; i<256; ++i ) { |
309 | ot_vector *torrents_list = &all_torrents[i]; | 309 | ot_vector *torrents_list = &all_torrents[i]; |
310 | for( j=0; j<torrents_list->size; ++j ) { | 310 | for( j=0; j<torrents_list->size; ++j ) { |
311 | ot_peerlist *peer_list = ( ((ot_torrent*)(torrents_list->data))[j] ).peer_list; | 311 | ot_peerlist *peer_list = ( ((ot_torrent*)(torrents_list->data))[j] ).peer_list; |
312 | ot_hash *hash =&( ((ot_torrent*)(torrents_list->data))[j] ).hash; | 312 | ot_hash *hash =&( ((ot_torrent*)(torrents_list->data))[j] ).hash; |
313 | int peers = 0, seeds = 0; | 313 | size_t peers = 0, seeds = 0; |
314 | clean_peerlist( time_now, peer_list ); | 314 | clean_peerlist( time_now, peer_list ); |
315 | for( k=0; k<OT_POOLS_COUNT; ++k ) { | 315 | for( k=0; k<OT_POOLS_COUNT; ++k ) { |
316 | peers += peer_list->peers[k].size; | 316 | peers += peer_list->peers[k].size; |
@@ -318,7 +318,7 @@ size_t return_fullscrape_for_tracker( char **reply ) { | |||
318 | } | 318 | } |
319 | memmove( r, "20:", 3 ); r+=3; | 319 | memmove( r, "20:", 3 ); r+=3; |
320 | memmove( r, hash, 20 ); r+=20; | 320 | memmove( r, hash, 20 ); r+=20; |
321 | r += sprintf( r, "d8:completei%de10:downloadedi%de10:incompletei%de", seeds, peer_list->downloaded, peers-seeds ); | 321 | r += sprintf( r, "d8:completei%zde10:downloadedi%zde10:incompletei%zde", seeds, peer_list->downloaded, peers-seeds ); |
322 | } | 322 | } |
323 | } | 323 | } |
324 | 324 | ||
@@ -329,7 +329,8 @@ size_t return_fullscrape_for_tracker( char **reply ) { | |||
329 | /* Fetches scrape info for a specific torrent */ | 329 | /* Fetches scrape info for a specific torrent */ |
330 | size_t return_scrape_for_torrent( ot_hash *hash, char *reply ) { | 330 | size_t return_scrape_for_torrent( ot_hash *hash, char *reply ) { |
331 | char *r = reply; | 331 | char *r = reply; |
332 | int exactmatch, peers = 0, seeds = 0, i; | 332 | int exactmatch, i; |
333 | size_t peers = 0, seeds = 0; | ||
333 | ot_vector *torrents_list = &all_torrents[*hash[0]]; | 334 | ot_vector *torrents_list = &all_torrents[*hash[0]]; |
334 | ot_torrent *torrent = binary_search( hash, torrents_list->data, torrents_list->size, sizeof( ot_torrent ), OT_HASH_COMPARE_SIZE, &exactmatch ); | 335 | ot_torrent *torrent = binary_search( hash, torrents_list->data, torrents_list->size, sizeof( ot_torrent ), OT_HASH_COMPARE_SIZE, &exactmatch ); |
335 | 336 | ||
@@ -342,20 +343,45 @@ size_t return_scrape_for_torrent( ot_hash *hash, char *reply ) { | |||
342 | } | 343 | } |
343 | 344 | ||
344 | memmove( r, "d5:filesd20:", 12 ); memmove( r+12, hash, 20 ); | 345 | memmove( r, "d5:filesd20:", 12 ); memmove( r+12, hash, 20 ); |
345 | r += sprintf( r+32, "d8:completei%de10:downloadedi%de10:incompletei%deeee", seeds, torrent->peer_list->downloaded, peers-seeds ) + 32; | 346 | r += sprintf( r+32, "d8:completei%zde10:downloadedi%zde10:incompletei%zdeeee", seeds, torrent->peer_list->downloaded, peers-seeds ) + 32; |
346 | 347 | ||
347 | return r - reply; | 348 | return r - reply; |
348 | } | 349 | } |
349 | 350 | ||
351 | size_t return_sync_for_torrent( ot_hash *hash, char **reply ) { | ||
352 | int exactmatch; | ||
353 | size_t peers = 0; | ||
354 | char *r; | ||
355 | ot_vector *torrents_list = &all_torrents[*hash[0]]; | ||
356 | ot_torrent *torrent = binary_search( hash, torrents_list->data, torrents_list->size, sizeof( ot_torrent ), OT_HASH_COMPARE_SIZE, &exactmatch ); | ||
357 | |||
358 | if( exactmatch ) { | ||
359 | clean_peerlist( NOW, torrent->peer_list ); | ||
360 | peers = torrent->peer_list->peers[0].size; | ||
361 | } | ||
362 | |||
363 | if( !( r = *reply = malloc( 10 + peers * sizeof( ot_peer ) ) ) ) return 0; | ||
364 | |||
365 | memmove( r, "d4:sync", 7 ); | ||
366 | r += 7; | ||
367 | r += sprintf( r, "%zd:", peers * sizeof( ot_peer ) ); | ||
368 | if( peers ) { | ||
369 | memmove( r, torrent->peer_list->peers[0].data, peers * sizeof( ot_peer ) ); | ||
370 | r += peers * sizeof( ot_peer ); | ||
371 | } | ||
372 | *r++ = 'e'; | ||
373 | return r - *reply; | ||
374 | } | ||
375 | |||
350 | typedef struct { int val; ot_torrent * torrent; } ot_record; | 376 | typedef struct { int val; ot_torrent * torrent; } ot_record; |
351 | 377 | ||
352 | /* Fetches stats from tracker */ | 378 | /* Fetches stats from tracker */ |
353 | size_t return_stats_for_tracker( char *reply, int mode ) { | 379 | size_t return_stats_for_tracker( char *reply, int mode ) { |
354 | time_t time_now = NOW; | 380 | time_t time_now = NOW; |
355 | int torrent_count = 0, peer_count = 0, seed_count = 0; | 381 | size_t torrent_count = 0, peer_count = 0, seed_count = 0, j; |
356 | ot_record top5s[5], top5c[5]; | 382 | ot_record top5s[5], top5c[5]; |
357 | char *r = reply; | 383 | char *r = reply; |
358 | int i,j,k; | 384 | int i,k; |
359 | 385 | ||
360 | byte_zero( top5s, sizeof( top5s ) ); | 386 | byte_zero( top5s, sizeof( top5s ) ); |
361 | byte_zero( top5c, sizeof( top5c ) ); | 387 | byte_zero( top5c, sizeof( top5c ) ); |
@@ -365,7 +391,7 @@ size_t return_stats_for_tracker( char *reply, int mode ) { | |||
365 | torrent_count += torrents_list->size; | 391 | torrent_count += torrents_list->size; |
366 | for( j=0; j<torrents_list->size; ++j ) { | 392 | for( j=0; j<torrents_list->size; ++j ) { |
367 | ot_peerlist *peer_list = ( ((ot_torrent*)(torrents_list->data))[j] ).peer_list; | 393 | ot_peerlist *peer_list = ( ((ot_torrent*)(torrents_list->data))[j] ).peer_list; |
368 | int local_peers = 0, local_seeds = 0; | 394 | size_t local_peers = 0, local_seeds = 0; |
369 | clean_peerlist( time_now, peer_list ); | 395 | clean_peerlist( time_now, peer_list ); |
370 | for( k=0; k<OT_POOLS_COUNT; ++k ) { | 396 | for( k=0; k<OT_POOLS_COUNT; ++k ) { |
371 | local_peers += peer_list->peers[k].size; | 397 | local_peers += peer_list->peers[k].size; |
@@ -399,7 +425,7 @@ size_t return_stats_for_tracker( char *reply, int mode ) { | |||
399 | if( top5s[idx].torrent ) | 425 | if( top5s[idx].torrent ) |
400 | r += sprintf( r, "\t%i\t%s\n", top5s[idx].val, to_hex(top5s[idx].torrent->hash) ); | 426 | r += sprintf( r, "\t%i\t%s\n", top5s[idx].val, to_hex(top5s[idx].torrent->hash) ); |
401 | } else { | 427 | } else { |
402 | r += sprintf( r, "%i\n%i\nopentracker serving %i torrents\nSomething else.", peer_count, seed_count, torrent_count ); | 428 | r += sprintf( r, "%zd\n%zd\nopentracker serving %zd torrents\nopentracker", peer_count, seed_count, torrent_count ); |
403 | } | 429 | } |
404 | 430 | ||
405 | return r - reply; | 431 | return r - reply; |
@@ -429,7 +455,7 @@ void remove_peer_from_torrent( ot_hash *hash, ot_peer *peer ) { | |||
429 | } | 455 | } |
430 | } | 456 | } |
431 | 457 | ||
432 | int init_logic( char *serverdir ) { | 458 | int init_logic( const char * const serverdir ) { |
433 | if( serverdir && chdir( serverdir ) ) { | 459 | if( serverdir && chdir( serverdir ) ) { |
434 | fprintf( stderr, "Could not chdir() to %s\n", serverdir ); | 460 | fprintf( stderr, "Could not chdir() to %s\n", serverdir ); |
435 | return -1; | 461 | return -1; |
@@ -443,8 +469,9 @@ int init_logic( char *serverdir ) { | |||
443 | return 0; | 469 | return 0; |
444 | } | 470 | } |
445 | 471 | ||
446 | void deinit_logic( ) { | 472 | void deinit_logic( void ) { |
447 | int i, j; | 473 | int i; |
474 | size_t j; | ||
448 | 475 | ||
449 | /* Free all torrents... */ | 476 | /* Free all torrents... */ |
450 | for(i=0; i<256; ++i ) { | 477 | for(i=0; i<256; ++i ) { |