Esempio n. 1
0
/* Clean up all peers in current bucket, remove timedout pools and
 torrents */
static void * clean_worker( void * args ) {
  (void) args;
  while( 1 ) {
    int bucket = OT_BUCKET_COUNT;
    while( bucket-- ) {
      ot_vector *torrents_list = mutex_bucket_lock( bucket );
      size_t     toffs;
      int        delta_torrentcount = 0;

      for( toffs=0; toffs<torrents_list->size; ++toffs ) {
        ot_torrent *torrent = ((ot_torrent*)(torrents_list->data)) + toffs;
        if( clean_single_torrent( torrent ) ) {
          vector_remove_torrent( torrents_list, torrent );
          --delta_torrentcount;
          --toffs;
        }
      }
      mutex_bucket_unlock( bucket, delta_torrentcount );
      if( !g_opentracker_running )
        return NULL;
      usleep( OT_CLEAN_SLEEP );
    }
    stats_cleanup();
  }
  return NULL;
}
Esempio n. 2
0
/* Clean up all peers in current bucket, remove timedout pools and
 torrents */
static void * clean_worker( void * args ) {
#ifdef _DEBUG
  ts_log_debug("ot_clean::clean_worker: start");
#endif
  (void) args;
  while( 1 ) {
    int bucket = OT_BUCKET_COUNT;
    while( bucket-- ) {
      ot_vector *torrents_list = mutex_bucket_lock( bucket );
      size_t     toffs;
      int        delta_torrentcount = 0;

      for( toffs=0; toffs<torrents_list->size; ++toffs ) {
        ot_torrent *torrent = ((ot_torrent*)(torrents_list->data)) + toffs;
        if( clean_single_torrent( torrent ) ) {
            /* terasaur -- begin mod */
            /*
            torrent->peer_list->peer_count = 0;
            torrent->peer_list->seed_count = 0;
#ifdef _DEBUG
            ts_log_debug("ot_clean::clean_worker: calling ts_update_torrent_stats");
#endif
            ts_update_torrent_stats(torrent, 0);
#ifdef _DEBUG
            ts_log_debug("ot_clean::clean_worker: after ts_update_torrent_stats");
#endif
            */
            /* terasaur -- end mod */

          vector_remove_torrent( torrents_list, torrent );
#ifdef _DEBUG
          ts_log_debug("ot_clean::clean_worker: after vector_remove_torrent");
#endif
          --delta_torrentcount;
          --toffs;
        }
#ifdef _DEBUG
        ts_log_debug("ot_clean::clean_worker: after if clean_single_torrent block");
#endif
      }
      mutex_bucket_unlock( bucket, delta_torrentcount );
      if( !g_opentracker_running )
        return NULL;
      usleep( OT_CLEAN_SLEEP );
    }
#ifdef _DEBUG
    ts_log_debug("ot_clean::clean_worker: calling stats_cleanup");
#endif
    stats_cleanup();
  }

#ifdef _DEBUG
    ts_log_debug("ot_clean::clean_worker: returning");
#endif
  return NULL;
}
Esempio n. 3
0
static void * streamsync_worker( void * args ) {
  (void)args;
  while( 1 ) {
    int bucket;
    /* For each bucket... */
    for( bucket=0; bucket<OT_BUCKET_COUNT; ++bucket ) {
      /* Get exclusive access to that bucket */
      ot_vector *torrents_list = mutex_bucket_lock( bucket );
      size_t tor_offset, count_def = 0, count_one = 0, count_two = 0, count_peers = 0;
      size_t mem, mem_a = 0, mem_b = 0;
      uint8_t *ptr = 0, *ptr_a, *ptr_b, *ptr_c;

      if( !torrents_list->size ) goto unlock_continue;

      /* For each torrent in this bucket.. */
      for( tor_offset=0; tor_offset<torrents_list->size; ++tor_offset ) {
        /* Address torrents members */
        ot_peerlist *peer_list = ( ((ot_torrent*)(torrents_list->data))[tor_offset] ).peer_list;
        switch( peer_list->peer_count ) {
          case 2:  count_two++; break;
          case 1:  count_one++; break;
          case 0:               break;
          default: count_def++;
                   count_peers += peer_list->peer_count;
        }
      }

      /* Maximal memory requirement: max 3 blocks, max torrents * 20 + max peers * 7 */
      mem = 3 * ( 1 + 1 + 2 ) + ( count_one + count_two ) * ( 19 + 1 ) + count_def * ( 19 + 8 ) +
            ( count_one + 2 * count_two + count_peers ) * 7;

      fprintf( stderr, "Mem: %zd\n", mem );

      ptr = ptr_a = ptr_b = ptr_c = malloc( mem );
      if( !ptr ) goto unlock_continue;

      if( count_one > 4 || !count_def ) {
        mem_a = 1 + 1 + 2 + count_one * ( 19 + 7 );
        ptr_b += mem_a; ptr_c += mem_a;
        ptr_a[0] = 1;                                        /* Offset 0: packet type 1 */
        ptr_a[1] = (bucket << 8) >> OT_BUCKET_COUNT_BITS;    /* Offset 1: the shared prefix */
        ptr_a[2] = count_one >> 8;
        ptr_a[3] = count_one & 255;
        ptr_a += 4;
      } else
        count_def += count_one;

      if( count_two > 4 || !count_def ) {
        mem_b = 1 + 1 + 2 + count_two * ( 19 + 14 );
        ptr_c += mem_b;
        ptr_b[0] = 2;                                        /* Offset 0: packet type 2 */
        ptr_b[1] = (bucket << 8) >> OT_BUCKET_COUNT_BITS;    /* Offset 1: the shared prefix */
        ptr_b[2] = count_two >> 8;
        ptr_b[3] = count_two & 255;
        ptr_b += 4;
      } else
Esempio n. 4
0
static size_t stats_slash24s_txt( char *reply, size_t amount ) {
  stats_network_node *slash24s_network_counters_root = NULL;
  char *r=reply;
  int bucket;
  size_t i;

  for( bucket=0; bucket<OT_BUCKET_COUNT; ++bucket ) {
    ot_vector *torrents_list = mutex_bucket_lock( bucket );
    for( i=0; i<torrents_list->size; ++i ) {
      ot_peerlist *peer_list = ( ((ot_torrent*)(torrents_list->data))[i] ).peer_list;
      ot_vector   *bucket_list = &peer_list->peers;
      int          num_buckets = 1;

      if( OT_PEERLIST_HASBUCKETS( peer_list ) ) {
        num_buckets = bucket_list->size;
        bucket_list = (ot_vector *)bucket_list->data;
      }

      while( num_buckets-- ) {
        ot_peer *peers = (ot_peer*)bucket_list->data;
        size_t   numpeers = bucket_list->size;
        while( numpeers-- )
          if( stat_increase_network_count( &slash24s_network_counters_root, 0, (uintptr_t)(peers++) ) )
            goto bailout_unlock;
        ++bucket_list;
      }
    }
    mutex_bucket_unlock( bucket, 0 );
    if( !g_opentracker_running )
      goto bailout_error;
  }

  /* The tree is built. Now analyze */
  r += stats_return_busy_networks( r, slash24s_network_counters_root, amount, STATS_NETWORK_NODE_MAXDEPTH );
  r += stats_return_busy_networks( r, slash24s_network_counters_root, amount, STATS_NETWORK_NODE_LIMIT );
  goto success;

bailout_unlock:
  mutex_bucket_unlock( bucket, 0 );
bailout_error:
  r = reply;
success:
  stats_shift_down_network_count( &slash24s_network_counters_root, 0, sizeof(int)*8-1 );

  return r-reply;
}
Esempio n. 5
0
static void clean_make() {
  int bucket;

  for( bucket = OT_BUCKET_COUNT - 1; bucket >= 0; --bucket ) {
    ot_vector *torrents_list = mutex_bucket_lock( bucket );
    size_t     toffs;

    for( toffs=0; toffs<torrents_list->size; ++toffs ) {
      ot_torrent *torrent = ((ot_torrent*)(torrents_list->data)) + toffs;
      if( clean_single_torrent( torrent ) ) {
        vector_remove_torrent( torrents_list, torrent );
        --toffs; continue;
      }
    }
    mutex_bucket_unlock( bucket );
  }
}
Esempio n. 6
0
/* Fetches stats from tracker */
size_t stats_top_txt( char * reply, int amount ) {
  size_t    j;
  ot_record top100s[100], top100c[100];
  char     *r  = reply, hex_out[42];
  int       idx, bucket;

  if( amount > 100 )
    amount = 100;

  byte_zero( top100s, sizeof( top100s ) );
  byte_zero( top100c, sizeof( top100c ) );

  for( bucket=0; bucket<OT_BUCKET_COUNT; ++bucket ) {
    ot_vector *torrents_list = mutex_bucket_lock( bucket );
    for( j=0; j<torrents_list->size; ++j ) {
      ot_peerlist *peer_list = ( ((ot_torrent*)(torrents_list->data))[j] ).peer_list;
      int idx = amount - 1; while( (idx >= 0) && ( peer_list->peer_count > top100c[idx].val ) ) --idx;
      if ( idx++ != amount - 1 ) {
        memmove( top100c + idx + 1, top100c + idx, ( amount - 1 - idx ) * sizeof( ot_record ) );
        top100c[idx].val = peer_list->peer_count;
        top100c[idx].torrent = (ot_torrent*)(torrents_list->data) + j;
      }
      idx = amount - 1; while( (idx >= 0) && ( peer_list->seed_count > top100s[idx].val ) ) --idx;
      if ( idx++ != amount - 1 ) {
        memmove( top100s + idx + 1, top100s + idx, ( amount - 1 - idx ) * sizeof( ot_record ) );
        top100s[idx].val = peer_list->seed_count;
        top100s[idx].torrent = (ot_torrent*)(torrents_list->data) + j;
      }
    }
    mutex_bucket_unlock( bucket, 0 );
    if( !g_opentracker_running )
      return 0;
  }

  r += sprintf( r, "Top %d torrents by peers:\n", amount );
  for( idx=0; idx<amount; ++idx )
    if( top100c[idx].torrent )
      r += sprintf( r, "\t%zd\t%s\n", top100c[idx].val, to_hex( hex_out, top100c[idx].torrent->hash) );
  r += sprintf( r, "Top %d torrents by seeds:\n", amount );
  for( idx=0; idx<amount; ++idx )
    if( top100s[idx].torrent )
      r += sprintf( r, "\t%zd\t%s\n", top100s[idx].val, to_hex( hex_out, top100s[idx].torrent->hash) );

  return r - reply;
}
Esempio n. 7
0
static int persist_dump_make() {
  int bucket;
  size_t j;
  uint8_t c;
  FILE *fp;
  char tmpfile[256];

  snprintf(tmpfile, 256, "temp-%u.odb", (unsigned int)g_now_seconds);

  LOG_ERR("Start write odb file:%s\n", tmpfile);

  fp = fopen(tmpfile, "w");
  if (!fp) {
    LOG_ERR("%s: fopen odb file:%s failed: %s\n", __FUNCTION__, tmpfile, strerror(errno));
    return -1;
  }

  /* write identifier and version */
  if (fwrite(OT_DUMP_IDENTI_VERSION, OT_DUMP_IDENTI_VERSION_LEN, 1, fp) == 0) goto werr;

  /* Dump torrents and peers */
  for(bucket=0; bucket < OT_BUCKET_COUNT; ++bucket ) {
    ot_vector  *torrents_list = mutex_bucket_lock( bucket );
    ot_torrent *torrents = (ot_torrent*)(torrents_list->data);

    for( j=0; j < torrents_list->size; ++j )
      if( persist_dump_torrent( torrents + j, fp ) < 0 ) {
        mutex_bucket_unlock( bucket, 0 );
        goto werr;
      }

    mutex_bucket_unlock( bucket, 0 );
  }

  /* EOF opcode */
  c = OT_DUMP_EOF;
  if (fwrite(&c, 1, 1, fp) != 1) goto werr;

  /* Make sure data will not remain on the OS's output buffers. */
  fflush(fp);
  fsync(fileno(fp));
  fclose(fp);

  /* Use RENAME to make sure the dump file is changed atomically 
   * only if the generate dump file is ok. */
  if (!g_persistfile) {
      g_persistfile = strdup("opentracker.odb");
  }

  if (rename(tmpfile, g_persistfile) < 0) {
    unlink(tmpfile);
    return -1;
  }

  dump_dirty = 0;
  dump_lastsave = g_now_seconds;
  return 0;

werr:
  LOG_ERR("%s: persist dump odb file:%s failed: %s\n", __FUNCTION__, tmpfile, strerror(errno));
  fclose(fp);
  unlink(tmpfile);
  return -1;
}