Changeset 13651


Ignore:
Timestamp:
Dec 12, 2012, 8:22:57 PM (8 years ago)
Author:
jordan
Message:

(trunk) #5168 'make libtransmission's public funcs nonblocking when possible' -- first attempt.

Location:
trunk
Files:
12 edited

Legend:

Unmodified
Added
Removed
  • trunk/gtk/details.c

    r13625 r13651  
    13771377    for (i=0; i<n; ++i) {
    13781378        int j;
    1379         const tr_torrent * tor = torrents[i];
     1379        tr_torrent * tor = torrents[i];
    13801380        const tr_info * inf = tr_torrentInfo (tor);
    13811381        double * speeds_KBps = tr_torrentWebSpeeds_KBps (tor);
  • trunk/gtk/torrent-cell-renderer.c

    r13625 r13651  
    4141
    4242static void
    43 getProgressString (GString          * gstr,
    44                    const tr_torrent * tor,
    45                    const tr_info    * info,
    46                    const tr_stat    * st)
     43getProgressString (GString        * gstr,
     44                   tr_torrent    * tor,
     45                   const tr_info  * info,
     46                   const tr_stat  * st)
    4747{
    4848    const int      isDone = st->leftUntilDone == 0;
     
    444444
    445445    struct TorrentCellRendererPrivate * p = cell->priv;
    446     const tr_torrent * tor = p->tor;
     446    tr_torrent * tor = p->tor;
    447447    const tr_stat * st = tr_torrentStatCached ((tr_torrent*)tor);
    448448    const tr_info * inf = tr_torrentInfo (tor);
     
    526526get_text_color (GtkWidget * w, const tr_stat * st, GtrColor * setme)
    527527{
    528     static const GdkRGBA red = { 1.0, 0, 0, 0 };
    529     if (st->error)
    530         *setme = red;
    531     else if (st->activity == TR_STATUS_STOPPED)
    532         gtk_style_context_get_color (gtk_widget_get_style_context (w), GTK_STATE_FLAG_INSENSITIVE, setme);
    533     else
    534         gtk_style_context_get_color (gtk_widget_get_style_context (w), GTK_STATE_FLAG_NORMAL, setme);
     528  static const GdkRGBA red = { 1.0, 0, 0, 0 };
     529
     530  if (st->error)
     531    *setme = red;
     532  else if (st->activity == TR_STATUS_STOPPED)
     533    gtk_style_context_get_color (gtk_widget_get_style_context (w), GTK_STATE_FLAG_INSENSITIVE, setme);
     534  else
     535    gtk_style_context_get_color (gtk_widget_get_style_context (w), GTK_STATE_FLAG_NORMAL, setme);
    535536}
    536537
    537538
    538539static double
    539 get_percent_done (const tr_torrent * tor, const tr_stat * st, bool * seed)
    540 {
    541     double d;
    542 
    543     if ((st->activity == TR_STATUS_SEED) && tr_torrentGetSeedRatio (tor, &d))
    544     {
    545         *seed = true;
    546         d = MAX (0.0, st->seedRatioPercentDone);
    547     }
    548     else
    549     {
    550         *seed = false;
    551         d = MAX (0.0, st->percentDone);
    552     }
    553 
    554     return d;
     540get_percent_done (tr_torrent * tor, const tr_stat * st, bool * seed)
     541{
     542  double d;
     543
     544  if ((st->activity == TR_STATUS_SEED) && tr_torrentGetSeedRatio (tor, &d))
     545    {
     546      *seed = true;
     547      d = MAX (0.0, st->seedRatioPercentDone);
     548    }
     549  else
     550    {
     551      *seed = false;
     552      d = MAX (0.0, st->percentDone);
     553    }
     554
     555  return d;
    555556}
    556557
     
    588589
    589590    struct TorrentCellRendererPrivate * p = cell->priv;
    590     const tr_torrent * tor = p->tor;
     591    tr_torrent * tor = p->tor;
    591592    const tr_stat * st = tr_torrentStatCached ((tr_torrent*)tor);
    592593    const gboolean active = (st->activity != TR_STATUS_STOPPED) && (st->activity != TR_STATUS_DOWNLOAD_WAIT) && (st->activity != TR_STATUS_SEED_WAIT);
     
    666667
    667668    struct TorrentCellRendererPrivate * p = cell->priv;
    668     const tr_torrent * tor = p->tor;
     669    tr_torrent * tor = p->tor;
    669670    const tr_stat * st = tr_torrentStatCached ((tr_torrent*)tor);
    670671    const tr_info * inf = tr_torrentInfo (tor);
  • trunk/libtransmission/handshake.c

    r13625 r13651  
    11301130            NULL;
    11311131        /* Don't mark a peer as non-uTP unless it's really a connect failure. */
    1132         if (tor && (errcode == ETIMEDOUT || errcode == ECONNREFUSED)) {
    1133             tr_torrentLock (tor);
    1134             tr_peerMgrSetUtpFailed (tor,
    1135                                     tr_peerIoGetAddress (io, NULL),
    1136                                     true);
    1137             tr_torrentUnlock (tor);
     1132        if ((errcode == ETIMEDOUT || errcode == ECONNREFUSED) && tr_torrentRef(tor)) {
     1133            tr_peerMgrSetUtpFailed (tor, tr_peerIoGetAddress (io, NULL), true);
     1134            tr_torrentUnref (tor);
    11381135        }
    11391136
  • trunk/libtransmission/peer-mgr.c

    r13631 r13651  
    25502550
    25512551void
    2552 tr_peerMgrTorrentAvailability (const tr_torrent * tor, int8_t * tab, unsigned int tabCount)
    2553 {
    2554     assert (tr_isTorrent (tor));
    2555     assert (torrentIsLocked (tor->torrentPeers));
    2556     assert (tab != NULL);
    2557     assert (tabCount > 0);
    2558 
    2559     memset (tab, 0, tabCount);
    2560 
    2561     if (tr_torrentHasMetadata (tor))
    2562     {
    2563         tr_piece_index_t i;
    2564         const int peerCount = tr_ptrArraySize (&tor->torrentPeers->peers);
    2565         const tr_peer ** peers = (const tr_peer**) tr_ptrArrayBase (&tor->torrentPeers->peers);
    2566         const float interval = tor->info.pieceCount / (float)tabCount;
    2567         const bool isSeed = tr_cpGetStatus (&tor->completion) == TR_SEED;
    2568 
    2569         for (i=0; i<tabCount; ++i)
     2552tr_peerMgrTorrentAvailability (tr_torrent * tor, int8_t * tab, unsigned int tabCount)
     2553{
     2554  assert (tab != NULL);
     2555  assert (tabCount > 0);
     2556
     2557  if (tr_torrentRef (tor))
     2558    {
     2559      memset (tab, 0, tabCount);
     2560
     2561      if (tr_torrentHasMetadata (tor))
    25702562        {
    2571             const int piece = i * interval;
    2572 
    2573             if (isSeed || tr_cpPieceIsComplete (&tor->completion, piece))
    2574                 tab[i] = -1;
    2575             else if (peerCount) {
    2576                 int j;
    2577                 for (j=0; j<peerCount; ++j)
     2563          tr_piece_index_t i;
     2564          const int peerCount = tr_ptrArraySize (&tor->torrentPeers->peers);
     2565          const tr_peer ** peers = (const tr_peer**) tr_ptrArrayBase (&tor->torrentPeers->peers);
     2566          const float interval = tor->info.pieceCount / (float)tabCount;
     2567          const bool isSeed = tr_cpGetStatus (&tor->completion) == TR_SEED;
     2568
     2569          for (i=0; i<tabCount; ++i)
     2570            {
     2571              const int piece = i * interval;
     2572
     2573              if (isSeed || tr_cpPieceIsComplete (&tor->completion, piece))
     2574                {
     2575                  tab[i] = -1;
     2576                }
     2577              else if (peerCount)
     2578                {
     2579                  int j;
     2580                  for (j=0; j<peerCount; ++j)
    25782581                    if (tr_bitfieldHas (&peers[j]->have, piece))
    2579                         ++tab[i];
     2582                      ++tab[i];
     2583                }
    25802584            }
    25812585        }
     2586
     2587      tr_torrentUnref (tor);
    25822588    }
    25832589}
     
    26442650                        int         * setmePeersFrom)
    26452651{
    2646     int i, size;
    2647     const Torrent * t = tor->torrentPeers;
    2648     const tr_peer ** peers;
    2649 
    2650     assert (tr_torrentIsLocked (tor));
    2651 
    2652     peers = (const tr_peer **) tr_ptrArrayBase (&t->peers);
    2653     size = tr_ptrArraySize (&t->peers);
    2654 
    2655     *setmePeersConnected       = 0;
    2656     *setmePeersGettingFromUs   = 0;
    2657     *setmePeersSendingToUs     = 0;
    2658     *setmeWebseedsSendingToUs  = 0;
    2659 
    2660     for (i=0; i<TR_PEER_FROM__MAX; ++i)
     2652  *setmePeersConnected       = 0;
     2653  *setmePeersGettingFromUs   = 0;
     2654  *setmePeersSendingToUs     = 0;
     2655  *setmeWebseedsSendingToUs  = 0;
     2656
     2657  if (tr_torrentRef (tor))
     2658    {
     2659      int i;
     2660      const Torrent * t = tor->torrentPeers;
     2661      const int size = tr_ptrArraySize (&t->peers);
     2662      const tr_peer ** peers = (const tr_peer **) tr_ptrArrayBase (&t->peers);
     2663
     2664      for (i=0; i<TR_PEER_FROM__MAX; ++i)
    26612665        setmePeersFrom[i] = 0;
    26622666
    2663     for (i=0; i<size; ++i)
    2664     {
    2665         const tr_peer * peer = peers[i];
    2666         const struct peer_atom * atom = peer->atom;
    2667 
    2668         if (peer->io == NULL) /* not connected */
     2667      for (i=0; i<size; ++i)
     2668        {
     2669          const tr_peer * peer = peers[i];
     2670          const struct peer_atom * atom = peer->atom;
     2671
     2672          if (peer->io == NULL) /* not connected */
    26692673            continue;
    26702674
    2671         ++*setmePeersConnected;
    2672 
    2673         ++setmePeersFrom[atom->fromFirst];
    2674 
    2675         if (clientIsDownloadingFrom (tor, peer))
     2675          ++*setmePeersConnected;
     2676
     2677          ++setmePeersFrom[atom->fromFirst];
     2678
     2679          if (clientIsDownloadingFrom (tor, peer))
    26762680            ++*setmePeersSendingToUs;
    26772681
    2678         if (clientIsUploadingTo (peer))
     2682          if (clientIsUploadingTo (peer))
    26792683            ++*setmePeersGettingFromUs;
    2680     }
    2681 
    2682     *setmeWebseedsSendingToUs = countActiveWebseeds (t);
     2684        }
     2685
     2686      *setmeWebseedsSendingToUs = countActiveWebseeds (t);
     2687      tr_torrentUnref (tor);
     2688    }
    26832689}
    26842690
    26852691double*
    2686 tr_peerMgrWebSpeeds_KBps (const tr_torrent * tor)
    2687 {
    2688     int i;
    2689     const Torrent * t = tor->torrentPeers;
    2690     const int webseedCount = tr_ptrArraySize (&t->webseeds);
    2691     const tr_webseed ** webseeds = (const tr_webseed**) tr_ptrArrayBase (&t->webseeds);
    2692     const uint64_t now = tr_time_msec ();
    2693     double * ret = tr_new0 (double, webseedCount);
    2694 
    2695     assert (tr_isTorrent (tor));
    2696     assert (tr_torrentIsLocked (tor));
    2697     assert (t->manager != NULL);
    2698     assert (webseedCount == tor->info.webseedCount);
    2699 
    2700     for (i=0; i<webseedCount; ++i) {
    2701         unsigned int Bps;
    2702         if (tr_webseedGetSpeed_Bps (webseeds[i], now, &Bps))
     2692tr_peerMgrWebSpeeds_KBps (tr_torrent * tor)
     2693{
     2694  double * ret = NULL;
     2695
     2696  if (tr_torrentRef (tor))
     2697    {
     2698      int i;
     2699      const Torrent * t = tor->torrentPeers;
     2700      const int webseedCount = tr_ptrArraySize (&t->webseeds);
     2701      const tr_webseed ** webseeds = (const tr_webseed**) tr_ptrArrayBase (&t->webseeds);
     2702      const uint64_t now = tr_time_msec ();
     2703
     2704      ret = tr_new0 (double, webseedCount);
     2705
     2706      assert (t->manager != NULL);
     2707      assert (webseedCount == tor->info.webseedCount);
     2708
     2709      for (i=0; i<webseedCount; ++i)
     2710        {
     2711          unsigned int Bps;
     2712          if (tr_webseedGetSpeed_Bps (webseeds[i], now, &Bps))
    27032713            ret[i] = Bps / (double)tr_speed_K;
    2704         else
     2714          else
    27052715            ret[i] = -1.0;
    2706     }
    2707 
    2708     return ret;
     2716        }
     2717
     2718      tr_torrentUnref (tor);
     2719    }
     2720
     2721  return ret;
    27092722}
    27102723
     
    27162729
    27172730struct tr_peer_stat *
    2718 tr_peerMgrPeerStats (const tr_torrent * tor, int * setmeCount)
    2719 {
    2720     int i;
    2721     const Torrent * t = tor->torrentPeers;
    2722     const int size = tr_ptrArraySize (&t->peers);
    2723     const tr_peer ** peers = (const tr_peer**) tr_ptrArrayBase (&t->peers);
    2724     const uint64_t now_msec = tr_time_msec ();
    2725     const time_t now = tr_time ();
    2726     tr_peer_stat * ret = tr_new0 (tr_peer_stat, size);
    2727 
    2728     assert (tr_isTorrent (tor));
    2729     assert (tr_torrentIsLocked (tor));
    2730     assert (t->manager);
    2731 
    2732     for (i=0; i<size; ++i)
    2733     {
    2734         char *                   pch;
    2735         const tr_peer *          peer = peers[i];
    2736         const struct peer_atom * atom = peer->atom;
    2737         tr_peer_stat *           stat = ret + i;
    2738 
    2739         tr_address_to_string_with_buf (&atom->addr, stat->addr, sizeof (stat->addr));
    2740         tr_strlcpy (stat->client, (peer->client ? peer->client : ""),
    2741                    sizeof (stat->client));
    2742         stat->port                = ntohs (peer->atom->port);
    2743         stat->from                = atom->fromFirst;
    2744         stat->progress            = peer->progress;
    2745         stat->isUTP               = peer->io->utp_socket != NULL;
    2746         stat->isEncrypted         = tr_peerIoIsEncrypted (peer->io) ? 1 : 0;
    2747         stat->rateToPeer_KBps     = toSpeedKBps (tr_peerGetPieceSpeed_Bps (peer, now_msec, TR_CLIENT_TO_PEER));
    2748         stat->rateToClient_KBps   = toSpeedKBps (tr_peerGetPieceSpeed_Bps (peer, now_msec, TR_PEER_TO_CLIENT));
    2749         stat->peerIsChoked        = peer->peerIsChoked;
    2750         stat->peerIsInterested    = peer->peerIsInterested;
    2751         stat->clientIsChoked      = peer->clientIsChoked;
    2752         stat->clientIsInterested  = peer->clientIsInterested;
    2753         stat->isIncoming          = tr_peerIoIsIncoming (peer->io);
    2754         stat->isDownloadingFrom   = clientIsDownloadingFrom (tor, peer);
    2755         stat->isUploadingTo       = clientIsUploadingTo (peer);
    2756         stat->isSeed              = peerIsSeed (peer);
    2757 
    2758         stat->blocksToPeer        = tr_historyGet (&peer->blocksSentToPeer,    now, CANCEL_HISTORY_SEC);
    2759         stat->blocksToClient      = tr_historyGet (&peer->blocksSentToClient,  now, CANCEL_HISTORY_SEC);
    2760         stat->cancelsToPeer       = tr_historyGet (&peer->cancelsSentToPeer,   now, CANCEL_HISTORY_SEC);
    2761         stat->cancelsToClient     = tr_historyGet (&peer->cancelsSentToClient, now, CANCEL_HISTORY_SEC);
    2762 
    2763         stat->pendingReqsToPeer   = peer->pendingReqsToPeer;
    2764         stat->pendingReqsToClient = peer->pendingReqsToClient;
    2765 
    2766         pch = stat->flagStr;
    2767         if (stat->isUTP) *pch++ = 'T';
    2768         if (t->optimistic == peer) *pch++ = 'O';
    2769         if (stat->isDownloadingFrom) *pch++ = 'D';
    2770         else if (stat->clientIsInterested) *pch++ = 'd';
    2771         if (stat->isUploadingTo) *pch++ = 'U';
    2772         else if (stat->peerIsInterested) *pch++ = 'u';
    2773         if (!stat->clientIsChoked && !stat->clientIsInterested) *pch++ = 'K';
    2774         if (!stat->peerIsChoked && !stat->peerIsInterested) *pch++ = '?';
    2775         if (stat->isEncrypted) *pch++ = 'E';
    2776         if (stat->from == TR_PEER_FROM_DHT) *pch++ = 'H';
    2777         else if (stat->from == TR_PEER_FROM_PEX) *pch++ = 'X';
    2778         if (stat->isIncoming) *pch++ = 'I';
    2779         *pch = '\0';
    2780     }
    2781 
    2782     *setmeCount = size;
    2783 
    2784     return ret;
     2731tr_peerMgrPeerStats (tr_torrent * tor, int * setmeCount)
     2732{
     2733  int size = 0;
     2734  tr_peer_stat * ret = NULL;
     2735
     2736  if (tr_torrentRef (tor))
     2737    {
     2738      int i;
     2739      const Torrent * t = tor->torrentPeers;
     2740      const tr_peer ** peers = (const tr_peer**) tr_ptrArrayBase (&t->peers);
     2741      const uint64_t now_msec = tr_time_msec ();
     2742      const time_t now = tr_time ();
     2743
     2744      assert (t->manager != NULL);
     2745
     2746      size = tr_ptrArraySize (&t->peers);
     2747      ret = tr_new0 (tr_peer_stat, size);
     2748
     2749      for (i=0; i<size; ++i)
     2750        {
     2751          char *                   pch;
     2752          const tr_peer *          peer = peers[i];
     2753          const struct peer_atom * atom = peer->atom;
     2754          tr_peer_stat *           stat = ret + i;
     2755
     2756          tr_address_to_string_with_buf (&atom->addr, stat->addr, sizeof (stat->addr));
     2757          tr_strlcpy (stat->client, (peer->client ? peer->client : ""), sizeof (stat->client));
     2758          stat->port                = ntohs (peer->atom->port);
     2759          stat->from                = atom->fromFirst;
     2760          stat->progress            = peer->progress;
     2761          stat->isUTP               = peer->io->utp_socket != NULL;
     2762          stat->isEncrypted         = tr_peerIoIsEncrypted (peer->io) ? 1 : 0;
     2763          stat->rateToPeer_KBps     = toSpeedKBps (tr_peerGetPieceSpeed_Bps (peer, now_msec, TR_CLIENT_TO_PEER));
     2764          stat->rateToClient_KBps   = toSpeedKBps (tr_peerGetPieceSpeed_Bps (peer, now_msec, TR_PEER_TO_CLIENT));
     2765          stat->peerIsChoked        = peer->peerIsChoked;
     2766          stat->peerIsInterested    = peer->peerIsInterested;
     2767          stat->clientIsChoked      = peer->clientIsChoked;
     2768          stat->clientIsInterested  = peer->clientIsInterested;
     2769          stat->isIncoming          = tr_peerIoIsIncoming (peer->io);
     2770          stat->isDownloadingFrom   = clientIsDownloadingFrom (tor, peer);
     2771          stat->isUploadingTo       = clientIsUploadingTo (peer);
     2772          stat->isSeed              = peerIsSeed (peer);
     2773
     2774          stat->blocksToPeer        = tr_historyGet (&peer->blocksSentToPeer,    now, CANCEL_HISTORY_SEC);
     2775          stat->blocksToClient      = tr_historyGet (&peer->blocksSentToClient,  now, CANCEL_HISTORY_SEC);
     2776          stat->cancelsToPeer       = tr_historyGet (&peer->cancelsSentToPeer,   now, CANCEL_HISTORY_SEC);
     2777          stat->cancelsToClient     = tr_historyGet (&peer->cancelsSentToClient, now, CANCEL_HISTORY_SEC);
     2778
     2779          stat->pendingReqsToPeer   = peer->pendingReqsToPeer;
     2780          stat->pendingReqsToClient = peer->pendingReqsToClient;
     2781
     2782          pch = stat->flagStr;
     2783          if (stat->isUTP) *pch++ = 'T';
     2784          if (t->optimistic == peer) *pch++ = 'O';
     2785          if (stat->isDownloadingFrom) *pch++ = 'D';
     2786          else if (stat->clientIsInterested) *pch++ = 'd';
     2787          if (stat->isUploadingTo) *pch++ = 'U';
     2788          else if (stat->peerIsInterested) *pch++ = 'u';
     2789          if (!stat->clientIsChoked && !stat->clientIsInterested) *pch++ = 'K';
     2790          if (!stat->peerIsChoked && !stat->peerIsInterested) *pch++ = '?';
     2791          if (stat->isEncrypted) *pch++ = 'E';
     2792          if (stat->from == TR_PEER_FROM_DHT) *pch++ = 'H';
     2793          else if (stat->from == TR_PEER_FROM_PEX) *pch++ = 'X';
     2794          if (stat->isIncoming) *pch++ = 'I';
     2795          *pch = '\0';
     2796        }
     2797
     2798      tr_torrentUnref (tor);
     2799    }
     2800
     2801  *setmeCount = size;
     2802  return ret;
    27852803}
    27862804
     
    28092827/* does this peer have any pieces that we want? */
    28102828static bool
    2811 isPeerInteresting (const tr_torrent  * const tor,
    2812                    const bool        * const piece_is_interesting,
    2813                    const tr_peer     * const peer)
    2814 {
    2815     tr_piece_index_t i, n;
    2816 
    2817     /* these cases should have already been handled by the calling code... */
    2818     assert (!tr_torrentIsSeed (tor));
    2819     assert (tr_torrentIsPieceTransferAllowed (tor, TR_PEER_TO_CLIENT));
    2820 
    2821     if (peerIsSeed (peer))
    2822         return true;
    2823 
    2824     for (i=0, n=tor->info.pieceCount; i<n; ++i)
    2825         if (piece_is_interesting[i] && tr_bitfieldHas (&peer->have, i))
    2826             return true;
    2827 
    2828     return false;
     2829isPeerInteresting (tr_torrent     * const tor,
     2830                   const bool     * const piece_is_interesting,
     2831                   const tr_peer  * const peer)
     2832{
     2833  tr_piece_index_t i, n;
     2834
     2835  /* these cases should have already been handled by the calling code... */
     2836  assert (!tr_torrentIsSeed (tor));
     2837  assert (tr_torrentIsPieceTransferAllowed (tor, TR_PEER_TO_CLIENT));
     2838
     2839  if (peerIsSeed (peer))
     2840    return true;
     2841
     2842  for (i=0, n=tor->info.pieceCount; i<n; ++i)
     2843    if (piece_is_interesting[i] && tr_bitfieldHas (&peer->have, i))
     2844      return true;
     2845
     2846  return false;
    28292847}
    28302848
  • trunk/libtransmission/peer-mgr.h

    r13625 r13651  
    226226void tr_peerMgrRemoveTorrent (tr_torrent * tor);
    227227
    228 void tr_peerMgrTorrentAvailability (const tr_torrent * tor,
    229                                     int8_t           * tab,
    230                                     unsigned int       tabCount);
     228void tr_peerMgrTorrentAvailability (tr_torrent  * tor,
     229                                    int8_t       * tab,
     230                                    unsigned int   tabCount);
    231231
    232232uint64_t tr_peerMgrGetDesiredAvailable (const tr_torrent * tor);
     
    243243                             int * setmePeersFrom); /* TR_PEER_FROM__MAX */
    244244
    245 struct tr_peer_stat* tr_peerMgrPeerStats (const tr_torrent * tor,
    246                                           int              * setmeCount);
    247 
    248 double* tr_peerMgrWebSpeeds_KBps (const tr_torrent * tor);
     245struct tr_peer_stat* tr_peerMgrPeerStats (tr_torrent * tor,
     246                                          int        * setmeCount);
     247
     248double* tr_peerMgrWebSpeeds_KBps (tr_torrent * tor);
    249249
    250250
  • trunk/libtransmission/peer-msgs.c

    r13631 r13651  
    16671667updateDesiredRequestCount (tr_peermsgs * msgs)
    16681668{
    1669     const tr_torrent * const torrent = msgs->torrent;
     1669    tr_torrent * const torrent = msgs->torrent;
    16701670
    16711671    /* there are lots of reasons we might not want to request any blocks... */
  • trunk/libtransmission/resume.c

    r13625 r13651  
    264264
    265265static void
    266 saveSingleSpeedLimit (tr_benc * d, const tr_torrent * tor, tr_direction dir)
     266saveSingleSpeedLimit (tr_benc * d, tr_torrent * tor, tr_direction dir)
    267267{
    268268    tr_bencDictReserve (d, 3);
     
    273273
    274274static void
    275 saveSpeedLimits (tr_benc * dict, const tr_torrent * tor)
     275saveSpeedLimits (tr_benc * dict, tr_torrent * tor)
    276276{
    277277    saveSingleSpeedLimit (tr_bencDictAddDict (dict, KEY_SPEEDLIMIT_DOWN, 0), tor, TR_DOWN);
     
    280280
    281281static void
    282 saveRatioLimits (tr_benc * dict, const tr_torrent * tor)
     282saveRatioLimits (tr_benc * dict, tr_torrent * tor)
    283283{
    284284    tr_benc * d = tr_bencDictAddDict (dict, KEY_RATIOLIMIT, 2);
     
    288288
    289289static void
    290 saveIdleLimits (tr_benc * dict, const tr_torrent * tor)
     290saveIdleLimits (tr_benc * dict, tr_torrent * tor)
    291291{
    292292    tr_benc * d = tr_bencDictAddDict (dict, KEY_IDLELIMIT, 2);
  • trunk/libtransmission/rpcimpl.c

    r13631 r13651  
    513513
    514514static void
    515 addPeers (const tr_torrent * tor,
    516           tr_benc *          list)
    517 {
    518     int            i;
    519     int            peerCount;
    520     tr_peer_stat * peers = tr_torrentPeers (tor, &peerCount);
    521 
    522     tr_bencInitList (list, peerCount);
    523 
    524     for (i = 0; i < peerCount; ++i)
     515addPeers (tr_torrent * tor, tr_benc * list)
     516{
     517  int i;
     518  int peerCount;
     519  tr_peer_stat * peers = tr_torrentPeers (tor, &peerCount);
     520
     521  tr_bencInitList (list, peerCount);
     522
     523  for (i=0; i<peerCount; ++i)
    525524    {
    526525        tr_benc *            d = tr_bencListAddDict (list, 16);
     
    553552
    554553static void
    555 addField (const tr_torrent * const tor,
     554addField (tr_torrent      * const tor,
    556555          const tr_info    * const inf,
    557556          const tr_stat    * const st,
     
    735734
    736735static void
    737 addInfo (const tr_torrent * tor, tr_benc * d, tr_benc * fields)
     736addInfo (tr_torrent * tor, tr_benc * d, tr_benc * fields)
    738737{
    739738    const char * str;
  • trunk/libtransmission/session.c

    r13638 r13651  
    17671767    qsort (torrents, n, sizeof (tr_torrent*), compareTorrentByCur);
    17681768    for (i = 0; i < n; ++i)
    1769         tr_torrentFree (torrents[i]);
     1769        tr_torrentUnref (torrents[i]);
    17701770    tr_free (torrents);
    17711771
  • trunk/libtransmission/torrent.c

    r13631 r13651  
    153153
    154154bool
    155 tr_torrentIsPieceTransferAllowed (const tr_torrent  * tor,
    156                                   tr_direction        direction)
    157 {
    158     unsigned int limit;
    159     bool allowed = true;
    160 
    161     if (tr_torrentUsesSpeedLimit (tor, direction))
     155tr_torrentIsPieceTransferAllowed (tr_torrent   * tor,
     156                                  tr_direction   direction)
     157{
     158  bool allowed = false;
     159
     160  assert (tr_isDirection (direction));
     161
     162  if (tr_torrentRef (tor))
     163    {
     164      unsigned int limit;
     165
     166      allowed = true;
     167
     168      if (tr_torrentUsesSpeedLimit (tor, direction))
    162169        if (tr_torrentGetSpeedLimit_Bps (tor, direction) <= 0)
     170          allowed = false;
     171
     172      if (tr_torrentUsesSessionLimits (tor))
     173        if (tr_sessionGetActiveSpeedLimit_Bps (tor->session, direction, &limit))
     174          if (limit <= 0)
    163175            allowed = false;
    164 
    165     if (tr_torrentUsesSessionLimits (tor))
    166         if (tr_sessionGetActiveSpeedLimit_Bps (tor->session, direction, &limit))
    167             if (limit <= 0)
    168                 allowed = false;
    169 
    170     return allowed;
     176    }
     177
     178  return allowed;
    171179}
    172180
     
    199207}
    200208unsigned int
    201 tr_torrentGetSpeedLimit_KBps (const tr_torrent * tor, tr_direction dir)
    202 {
    203     return toSpeedKBps (tr_torrentGetSpeedLimit_Bps (tor, dir));
     209tr_torrentGetSpeedLimit_KBps (tr_torrent * tor, tr_direction dir)
     210{
     211  unsigned int limit = 0;
     212
     213  assert (tr_isDirection (dir));
     214
     215  if (tr_torrentRef (tor))
     216    {
     217      limit = toSpeedKBps (tr_torrentGetSpeedLimit_Bps (tor, dir));
     218      tr_torrentUnref (tor);
     219    }
     220
     221  return limit;
    204222}
    205223
     
    207225tr_torrentUseSpeedLimit (tr_torrent * tor, tr_direction dir, bool do_use)
    208226{
    209     assert (tr_isTorrent (tor));
    210     assert (tr_isDirection (dir));
    211 
    212     if (tr_bandwidthSetLimited (&tor->bandwidth, dir, do_use))
    213         tr_torrentSetDirty (tor);
     227  assert (tr_isTorrent (tor));
     228  assert (tr_isDirection (dir));
     229
     230  if (tr_bandwidthSetLimited (&tor->bandwidth, dir, do_use))
     231    tr_torrentSetDirty (tor);
    214232}
    215233
    216234bool
    217 tr_torrentUsesSpeedLimit (const tr_torrent * tor, tr_direction dir)
    218 {
    219     assert (tr_isTorrent (tor));
    220     assert (tr_isDirection (dir));
    221 
    222     return tr_bandwidthIsLimited (&tor->bandwidth, dir);
     235tr_torrentUsesSpeedLimit (tr_torrent * tor, tr_direction dir)
     236{
     237  bool limited = false;
     238
     239  if (tr_torrentRef (tor))
     240    {
     241      limited = tr_bandwidthIsLimited (&tor->bandwidth, dir);
     242      tr_torrentUnref (tor);
     243    }
     244
     245  return limited;
    223246}
    224247
     
    226249tr_torrentUseSessionLimits (tr_torrent * tor, bool doUse)
    227250{
    228     bool changed;
    229 
    230     assert (tr_isTorrent (tor));
    231 
    232     changed = tr_bandwidthHonorParentLimits (&tor->bandwidth, TR_UP, doUse);
    233     changed |= tr_bandwidthHonorParentLimits (&tor->bandwidth, TR_DOWN, doUse);
    234 
    235     if (changed)
    236         tr_torrentSetDirty (tor);
     251  bool changed;
     252
     253  assert (tr_isTorrent (tor));
     254
     255  changed = tr_bandwidthHonorParentLimits (&tor->bandwidth, TR_UP, doUse);
     256  changed |= tr_bandwidthHonorParentLimits (&tor->bandwidth, TR_DOWN, doUse);
     257
     258  if (changed)
     259    tr_torrentSetDirty (tor);
    237260}
    238261
    239262bool
    240 tr_torrentUsesSessionLimits (const tr_torrent * tor)
    241 {
    242     assert (tr_isTorrent (tor));
    243 
    244     return tr_bandwidthAreParentLimitsHonored (&tor->bandwidth, TR_UP);
     263tr_torrentUsesSessionLimits (tr_torrent * tor)
     264{
     265  bool limited = false;
     266
     267  if (tr_torrentRef (tor))
     268    {
     269      limited = tr_bandwidthAreParentLimitsHonored (&tor->bandwidth, TR_UP);
     270      tr_torrentUnref (tor);
     271    }
     272
     273  return limited;
    245274}
    246275
     
    252281tr_torrentSetRatioMode (tr_torrent *  tor, tr_ratiolimit mode)
    253282{
    254     assert (tr_isTorrent (tor));
    255     assert (mode==TR_RATIOLIMIT_GLOBAL || mode==TR_RATIOLIMIT_SINGLE || mode==TR_RATIOLIMIT_UNLIMITED);
    256 
    257     if (mode != tor->ratioLimitMode)
    258     {
    259         tor->ratioLimitMode = mode;
    260 
    261         tr_torrentSetDirty (tor);
     283  assert (tr_isTorrent (tor));
     284  assert (mode==TR_RATIOLIMIT_GLOBAL || mode==TR_RATIOLIMIT_SINGLE || mode==TR_RATIOLIMIT_UNLIMITED);
     285
     286  if (mode != tor->ratioLimitMode)
     287    {
     288      tor->ratioLimitMode = mode;
     289
     290      tr_torrentSetDirty (tor);
    262291    }
    263292}
     
    266295tr_torrentGetRatioMode (const tr_torrent * tor)
    267296{
    268     assert (tr_isTorrent (tor));
    269 
    270     return tor->ratioLimitMode;
     297  assert (tr_isTorrent (tor));
     298
     299  return tor->ratioLimitMode;
    271300}
    272301
     
    274303tr_torrentSetRatioLimit (tr_torrent * tor, double desiredRatio)
    275304{
    276     assert (tr_isTorrent (tor));
    277 
    278     if ((int)(desiredRatio*100.0) != (int)(tor->desiredRatio*100.0))
    279     {
    280         tor->desiredRatio = desiredRatio;
    281 
    282         tr_torrentSetDirty (tor);
     305  assert (tr_isTorrent (tor));
     306
     307  if ((int)(desiredRatio*100.0) != (int)(tor->desiredRatio*100.0))
     308    {
     309      tor->desiredRatio = desiredRatio;
     310
     311      tr_torrentSetDirty (tor);
    283312    }
    284313}
    285314
    286315double
    287 tr_torrentGetRatioLimit (const tr_torrent * tor)
    288 {
    289     assert (tr_isTorrent (tor));
    290 
    291     return tor->desiredRatio;
     316tr_torrentGetRatioLimit (tr_torrent * tor)
     317{
     318  double limit = 0;
     319
     320  if (tr_torrentRef (tor))
     321    {
     322      limit = tor->desiredRatio;
     323      tr_torrentUnref (tor);
     324    }
     325
     326  return limit;
    292327}
    293328
    294329bool
    295 tr_torrentGetSeedRatio (const tr_torrent * tor, double * ratio)
    296 {
    297     bool isLimited;
    298 
    299     switch (tr_torrentGetRatioMode (tor))
    300     {
    301         case TR_RATIOLIMIT_SINGLE:
     330tr_torrentGetSeedRatio (tr_torrent * tor, double * ratio)
     331{
     332  bool isLimited = false;
     333
     334  if (tr_torrentRef (tor))
     335    {
     336      switch (tr_torrentGetRatioMode (tor))
     337        {
     338          case TR_RATIOLIMIT_SINGLE:
    302339            isLimited = true;
    303340            if (ratio)
    304                 *ratio = tr_torrentGetRatioLimit (tor);
     341              *ratio = tr_torrentGetRatioLimit (tor);
    305342            break;
    306343
    307         case TR_RATIOLIMIT_GLOBAL:
     344          case TR_RATIOLIMIT_GLOBAL:
    308345            isLimited = tr_sessionIsRatioLimited (tor->session);
    309346            if (isLimited && ratio)
    310                 *ratio = tr_sessionGetRatioLimit (tor->session);
     347              *ratio = tr_sessionGetRatioLimit (tor->session);
    311348            break;
    312349
    313         default: /* TR_RATIOLIMIT_UNLIMITED */
     350          default: /* TR_RATIOLIMIT_UNLIMITED */
    314351            isLimited = false;
    315352            break;
    316     }
    317 
    318     return isLimited;
     353        }
     354
     355      tr_torrentUnref (tor);
     356    }
     357
     358  return isLimited;
    319359}
    320360
     
    809849    tor->uniqueId = nextUniqueId++;
    810850    tor->magicNumber = TORRENT_MAGIC_NUMBER;
     851    tor->refCount = 1;
    811852    tor->queuePosition = session->torrentCount;
    812853
     
    10971138}
    10981139
    1099 static tr_torrent_activity
    1100 torrentGetActivity (const tr_torrent * tor)
    1101 {
    1102     const bool is_seed = tr_torrentIsSeed (tor);
    1103     assert (tr_isTorrent (tor));
    1104 
    1105     if (tor->verifyState == TR_VERIFY_NOW)
    1106         return TR_STATUS_CHECK;
    1107 
    1108     if (tor->verifyState == TR_VERIFY_WAIT)
    1109         return TR_STATUS_CHECK_WAIT;
    1110 
    1111     if (tor->isRunning)
    1112         return is_seed ? TR_STATUS_SEED : TR_STATUS_DOWNLOAD;
    1113 
    1114     if (tr_torrentIsQueued (tor)) {
    1115         if (is_seed && tr_sessionGetQueueEnabled (tor->session, TR_UP))
    1116             return TR_STATUS_SEED_WAIT;
    1117         if (!is_seed && tr_sessionGetQueueEnabled (tor->session, TR_DOWN))
    1118             return TR_STATUS_DOWNLOAD_WAIT;
    1119     }
    1120 
    1121     return TR_STATUS_STOPPED;
    1122 }
    1123 
    11241140tr_torrent_activity
    1125 tr_torrentGetActivity (tr_torrent * tor)
    1126 {
    1127     /* FIXME: is this call still needed? */
    1128     tr_torrentRecheckCompleteness (tor);
    1129 
    1130     return torrentGetActivity (tor);
     1141tr_torrentGetActivity (const tr_torrent * tor)
     1142{
     1143  tr_torrent_activity ret = TR_STATUS_STOPPED;
     1144
     1145  const bool is_seed = tr_torrentIsSeed (tor);
     1146
     1147  if (tor->verifyState == TR_VERIFY_NOW)
     1148    {
     1149      ret = TR_STATUS_CHECK;
     1150    }
     1151  else if (tor->verifyState == TR_VERIFY_WAIT)
     1152    {
     1153      ret = TR_STATUS_CHECK_WAIT;
     1154    }
     1155  else if (tor->isRunning)
     1156    {
     1157      ret = is_seed ? TR_STATUS_SEED : TR_STATUS_DOWNLOAD;
     1158    }
     1159  else if (tr_torrentIsQueued (tor))
     1160    {
     1161      if (is_seed && tr_sessionGetQueueEnabled (tor->session, TR_UP))
     1162        ret = TR_STATUS_SEED_WAIT;
     1163      else if (!is_seed && tr_sessionGetQueueEnabled (tor->session, TR_DOWN))
     1164        ret = TR_STATUS_DOWNLOAD_WAIT;
     1165    }
     1166
     1167  return ret;
    11311168}
    11321169
     
    11351172{
    11361173    int idle_secs;
    1137     const tr_torrent_activity activity = torrentGetActivity (tor);
     1174    const tr_torrent_activity activity = tr_torrentGetActivity (tor);
    11381175
    11391176    if ((activity == TR_STATUS_DOWNLOAD || activity == TR_STATUS_SEED) && tor->startDate != 0)
     
    11541191
    11551192static double
    1156 getVerifyProgress (const tr_torrent * tor)
    1157 {
    1158     double d = 0;
    1159 
    1160     assert (tr_isTorrent (tor));
    1161 
    1162     if (tr_torrentHasMetadata (tor))
    1163     {
    1164         tr_piece_index_t i, n;
    1165         tr_piece_index_t checked = 0;
    1166 
    1167         for (i=0, n=tor->info.pieceCount; i!=n; ++i)
     1193getVerifyProgress (tr_torrent * tor)
     1194{
     1195  double d = 0;
     1196
     1197  if (tr_torrentRef (tor))
     1198    {
     1199      if (tr_torrentHasMetadata (tor))
     1200        {
     1201          tr_piece_index_t i, n;
     1202          tr_piece_index_t checked = 0;
     1203
     1204          for (i=0, n=tor->info.pieceCount; i!=n; ++i)
    11681205            if (tor->info.pieces[i].timeChecked)
    1169                 ++checked;
    1170 
    1171         d = checked / (double)tor->info.pieceCount;
    1172     }
    1173 
    1174     return d;
     1206              ++checked;
     1207
     1208          d = checked / (double)tor->info.pieceCount;
     1209        }
     1210
     1211      tr_torrentUnref (tor);
     1212    }
     1213
     1214  return d;
    11751215}
    11761216
     
    11851225    uint16_t                seedIdleMinutes;
    11861226
    1187     if (!tor)
     1227    if (!tr_torrentRef(tor))
    11881228        return NULL;
    1189 
    1190     assert (tr_isTorrent (tor));
    1191     tr_torrentLock (tor);
    11921229
    11931230    tor->lastStatTime = tr_time ();
     
    13091346        s->seedRatioPercentDone = (double)(seedRatioBytesGoal - seedRatioBytesLeft) / seedRatioBytesGoal;
    13101347
    1311     tr_torrentUnlock (tor);
    1312 
    13131348    /* test some of the constraints */
    13141349    assert (s->sizeWhenDone <= tor->info.totalSize);
    13151350    assert (s->leftUntilDone <= s->sizeWhenDone);
    13161351    assert (s->desiredAvailable <= s->leftUntilDone);
     1352
     1353    tr_torrentUnref (tor);
     1354
    13171355    return s;
    13181356}
     
    13971435
    13981436double*
    1399 tr_torrentWebSpeeds_KBps (const tr_torrent * tor)
    1400 {
    1401     double * ret = NULL;
    1402 
    1403     if (tr_isTorrent (tor))
    1404     {
    1405         tr_torrentLock (tor);
    1406         ret = tr_peerMgrWebSpeeds_KBps (tor);
    1407         tr_torrentUnlock (tor);
    1408     }
    1409 
    1410     return ret;
     1437tr_torrentWebSpeeds_KBps (tr_torrent * tor)
     1438{
     1439  double * ret = NULL;
     1440
     1441  if (tr_torrentRef (tor))
     1442    {
     1443      ret = tr_peerMgrWebSpeeds_KBps (tor);
     1444      tr_torrentUnref (tor);
     1445    }
     1446
     1447  return ret;
    14111448}
    14121449
    14131450tr_peer_stat *
    1414 tr_torrentPeers (const tr_torrent * tor, int * peerCount)
    1415 {
    1416     tr_peer_stat * ret = NULL;
    1417 
    1418     if (tr_isTorrent (tor))
    1419     {
    1420         tr_torrentLock (tor);
    1421         ret = tr_peerMgrPeerStats (tor, peerCount);
    1422         tr_torrentUnlock (tor);
    1423     }
    1424 
    1425     return ret;
     1451tr_torrentPeers (tr_torrent * tor, int * peerCount)
     1452{
     1453  tr_peer_stat * ret = NULL;
     1454
     1455  if (tr_torrentRef (tor))
     1456    {
     1457      ret = tr_peerMgrPeerStats (tor, peerCount);
     1458      tr_torrentUnref (tor);
     1459    }
     1460
     1461  return ret;
    14261462}
    14271463
     
    14291465tr_torrentPeersFree (tr_peer_stat * peers, int peerCount UNUSED)
    14301466{
    1431     tr_free (peers);
     1467  tr_free (peers);
    14321468}
    14331469
    14341470tr_tracker_stat *
    1435 tr_torrentTrackers (const tr_torrent * torrent, int * setmeTrackerCount)
    1436 {
    1437     tr_tracker_stat * ret = NULL;
    1438 
    1439     if (tr_isTorrent (torrent))
    1440     {
    1441         tr_torrentLock (torrent);
    1442         ret = tr_announcerStats (torrent, setmeTrackerCount);
    1443         tr_torrentUnlock (torrent);
    1444     }
    1445 
    1446     return ret;
     1471tr_torrentTrackers (tr_torrent * torrent, int * setmeTrackerCount)
     1472{
     1473  tr_tracker_stat * ret = NULL;
     1474
     1475  if (tr_torrentRef (torrent))
     1476    {
     1477      ret = tr_announcerStats (torrent, setmeTrackerCount);
     1478      tr_torrentUnref (torrent);
     1479    }
     1480
     1481  return ret;
    14471482}
    14481483
     
    14541489
    14551490void
    1456 tr_torrentAvailability (const tr_torrent * tor, int8_t * tab, int size)
    1457 {
    1458     if (tr_isTorrent (tor) && (tab != NULL) && (size > 0))
    1459     {
    1460         tr_torrentLock (tor);
    1461         tr_peerMgrTorrentAvailability (tor, tab, size);
    1462         tr_torrentUnlock (tor);
    1463     }
    1464 }
    1465 
    1466 void
    1467 tr_torrentAmountFinished (const tr_torrent * tor,
    1468                           float *            tab,
    1469                           int                size)
    1470 {
    1471     assert (tr_isTorrent (tor));
    1472 
    1473     tr_torrentLock (tor);
    1474     tr_cpGetAmountDone (&tor->completion, tab, size);
    1475     tr_torrentUnlock (tor);
     1491tr_torrentAvailability (tr_torrent * tor, int8_t * tab, int size)
     1492{
     1493  if ((tab != NULL) && (size > 0) && tr_torrentRef (tor))
     1494    {
     1495      tr_peerMgrTorrentAvailability (tor, tab, size);
     1496      tr_torrentUnref (tor);
     1497    }
     1498}
     1499
     1500void
     1501tr_torrentAmountFinished (tr_torrent * tor, float * tab, int size)
     1502{
     1503  if (tr_torrentRef (tor))
     1504    {
     1505      tr_cpGetAmountDone (&tor->completion, tab, size);
     1506      tr_torrentUnref (tor);
     1507    }
    14761508}
    14771509
     
    16371669torrentStart (tr_torrent * tor, bool bypass_queue)
    16381670{
    1639     switch (torrentGetActivity (tor))
     1671    switch (tr_torrentGetActivity (tor))
    16401672    {
    16411673        case TR_STATUS_SEED:
     
    17761808stopTorrent (void * vtor)
    17771809{
    1778     tr_torrent * tor = vtor;
    1779     tr_torinf (tor, "Pausing");
    1780 
    1781     assert (tr_isTorrent (tor));
    1782 
    1783     tr_torrentLock (tor);
    1784 
    1785     tr_verifyRemove (tor);
    1786     torrentSetQueued (tor, false);
    1787     tr_peerMgrStopTorrent (tor);
    1788     tr_announcerTorrentStopped (tor);
    1789     tr_cacheFlushTorrent (tor->session->cache, tor);
    1790 
    1791     tr_fdTorrentClose (tor->session, tor->uniqueId);
    1792 
    1793     if (!tor->isDeleting)
     1810  tr_torrent * tor = vtor;
     1811  tr_torinf (tor, "Pausing");
     1812
     1813  if (tr_torrentLock (tor))
     1814    {
     1815      tr_verifyRemove (tor);
     1816      torrentSetQueued (tor, false);
     1817      tr_peerMgrStopTorrent (tor);
     1818      tr_announcerTorrentStopped (tor);
     1819      tr_cacheFlushTorrent (tor->session->cache, tor);
     1820
     1821      tr_fdTorrentClose (tor->session, tor->uniqueId);
     1822
     1823      if (!tor->isDeleting)
    17941824        tr_torrentSave (tor);
    17951825
    1796     tr_torrentUnlock (tor);
     1826      tr_torrentUnlock (tor);
     1827    }
    17971828}
    17981829
     
    18421873
    18431874void
    1844 tr_torrentFree (tr_torrent * tor)
    1845 {
    1846     if (tr_isTorrent (tor))
    1847     {
    1848         tr_session * session = tor->session;
    1849         assert (tr_isSession (session));
    1850         tr_sessionLock (session);
    1851 
    1852         tr_torrentClearCompletenessCallback (tor);
    1853         tr_runInEventThread (session, closeTorrent, tor);
    1854 
    1855         tr_sessionUnlock (session);
    1856     }
     1875tr_torrentUnref (tr_torrent * tor)
     1876{
     1877  assert (tr_isTorrent (tor));
     1878
     1879  if (--tor->refCount == 0)
     1880    {
     1881      tr_session * session = tor->session;
     1882
     1883      tr_sessionLock (session);
     1884      tr_torrentClearCompletenessCallback (tor);
     1885      tr_runInEventThread (session, closeTorrent, tor);
     1886      tr_sessionUnlock (session);
     1887    }
     1888}
     1889
     1890bool
     1891tr_torrentLock (const tr_torrent * tor)
     1892{
     1893  if (!tr_isTorrent (tor))
     1894    return false;
     1895
     1896  tr_sessionLock (tor->session);
     1897  return true;
     1898}
     1899
     1900bool
     1901tr_torrentRef (tr_torrent * tor)
     1902{
     1903  if (!tr_isTorrent (tor))
     1904    return false;
     1905
     1906  ++tor->refCount;
     1907  return true;
    18571908}
    18581909
     
    20382089tr_torrentRecheckCompleteness (tr_torrent * tor)
    20392090{
    2040     tr_completeness completeness;
    2041 
    2042     assert (tr_isTorrent (tor));
    2043 
    2044     tr_torrentLock (tor);
    2045 
    2046     completeness = tr_cpGetStatus (&tor->completion);
    2047 
    2048     if (completeness != tor->completeness)
    2049     {
    2050         const int recentChange = tor->downloadedCur != 0;
    2051         const bool wasLeeching = !tr_torrentIsSeed (tor);
    2052         const bool wasRunning = tor->isRunning;
    2053 
    2054         if (recentChange)
     2091  if (tr_torrentLock (tor))
     2092    {
     2093      const tr_completeness completeness = tr_cpGetStatus (&tor->completion);
     2094
     2095      if (completeness != tor->completeness)
    20552096        {
     2097          const int recentChange = tor->downloadedCur != 0;
     2098          const bool wasLeeching = !tr_torrentIsSeed (tor);
     2099          const bool wasRunning = tor->isRunning;
     2100
     2101          if (recentChange)
    20562102            tr_torinf (tor, _("State changed from \"%1$s\" to \"%2$s\""),
    2057                       getCompletionString (tor->completeness),
    2058                       getCompletionString (completeness));
     2103                       getCompletionString (tor->completeness),
     2104                       getCompletionString (completeness));
     2105
     2106          tor->completeness = completeness;
     2107          tr_fdTorrentClose (tor->session, tor->uniqueId);
     2108
     2109          fireCompletenessChange (tor, completeness, wasRunning);
     2110
     2111          if (tr_torrentIsSeed (tor))
     2112            {
     2113              if (recentChange)
     2114                {
     2115                  tr_announcerTorrentCompleted (tor);
     2116                  tor->doneDate = tor->anyDate = tr_time ();
     2117                }
     2118
     2119              if (wasLeeching && wasRunning)
     2120                {
     2121                  /* clear interested flag on all peers */
     2122                  tr_peerMgrClearInterest (tor);
     2123
     2124                  /* if completeness was TR_LEECH then the seed limit check will have been skipped in bandwidthPulse */
     2125                  tr_torrentCheckSeedLimit (tor);
     2126                }
     2127
     2128              if (tor->currentDir == tor->incompleteDir)
     2129                tr_torrentSetLocation (tor, tor->downloadDir, true, NULL, NULL);
     2130
     2131              if (tr_sessionIsTorrentDoneScriptEnabled (tor->session))
     2132                torrentCallScript (tor, tr_sessionGetTorrentDoneScript (tor->session));
     2133            }
     2134
     2135          tr_torrentSetDirty (tor);
    20592136        }
    20602137
    2061         tor->completeness = completeness;
    2062         tr_fdTorrentClose (tor->session, tor->uniqueId);
    2063 
    2064         fireCompletenessChange (tor, completeness, wasRunning);
    2065 
    2066         if (tr_torrentIsSeed (tor))
    2067         {
    2068             if (recentChange)
    2069             {
    2070                 tr_announcerTorrentCompleted (tor);
    2071                 tor->doneDate = tor->anyDate = tr_time ();
    2072             }
    2073 
    2074             if (wasLeeching && wasRunning)
    2075             {
    2076                 /* clear interested flag on all peers */
    2077                 tr_peerMgrClearInterest (tor);
    2078 
    2079                 /* if completeness was TR_LEECH then the seed limit check will have been skipped in bandwidthPulse */
    2080                 tr_torrentCheckSeedLimit (tor);
    2081             }
    2082 
    2083             if (tor->currentDir == tor->incompleteDir)
    2084                 tr_torrentSetLocation (tor, tor->downloadDir, true, NULL, NULL);
    2085 
    2086             if (tr_sessionIsTorrentDoneScriptEnabled (tor->session))
    2087                 torrentCallScript (tor, tr_sessionGetTorrentDoneScript (tor->session));
    2088         }
    2089 
    2090         tr_torrentSetDirty (tor);
    2091     }
    2092 
    2093     tr_torrentUnlock (tor);
     2138      tr_torrentUnlock (tor);
     2139    }
    20942140}
    20952141
     
    21612207
    21622208tr_priority_t*
    2163 tr_torrentGetFilePriorities (const tr_torrent * tor)
    2164 {
    2165     tr_file_index_t i;
    2166     tr_priority_t * p;
    2167 
    2168     assert (tr_isTorrent (tor));
    2169 
    2170     tr_torrentLock (tor);
    2171     p = tr_new0 (tr_priority_t, tor->info.fileCount);
    2172     for (i = 0; i < tor->info.fileCount; ++i)
     2209tr_torrentGetFilePriorities (tr_torrent * tor)
     2210{
     2211  tr_file_index_t i;
     2212  tr_priority_t * p = NULL;
     2213
     2214  if (tr_torrentRef (tor))
     2215    {
     2216      p = tr_new0 (tr_priority_t, tor->info.fileCount);
     2217
     2218      for (i=0; i<tor->info.fileCount; ++i)
    21732219        p[i] = tor->info.files[i].priority;
    2174     tr_torrentUnlock (tor);
    2175 
    2176     return p;
     2220
     2221      tr_torrentUnref (tor);
     2222    }
     2223
     2224  return p;
    21772225}
    21782226
  • trunk/libtransmission/torrent.h

    r13625 r13651  
    6363                                              const uint8_t * hash);
    6464
    65 bool        tr_torrentIsPieceTransferAllowed (const tr_torrent * torrent,
    66                                               tr_direction       direction);
     65bool        tr_torrentIsPieceTransferAllowed (tr_torrent    * torrent,
     66                                              tr_direction    direction);
    6767
    6868
     
    128128                                           tr_verify_state   state);
    129129
    130 tr_torrent_activity tr_torrentGetActivity (tr_torrent * tor);
     130tr_torrent_activity tr_torrentGetActivity (const tr_torrent * tor);
    131131
    132132struct tr_incomplete_metadata;
     
    139139
    140140    int                      magicNumber;
     141
     142    size_t                   refCount;
    141143
    142144    tr_stat_errtype          error;
     
    301303}
    302304
    303 static inline void tr_torrentLock (const tr_torrent * tor)
    304 {
    305     tr_sessionLock (tor->session);
    306 }
     305bool tr_torrentLock (const tr_torrent * tor);
    307306
    308307static inline bool tr_torrentIsLocked (const tr_torrent * tor)
     
    367366    return (tor != NULL)
    368367        && (tor->magicNumber == TORRENT_MAGIC_NUMBER)
     368        && (tor->refCount > 0)
    369369        && (tr_isSession (tor->session));
    370370}
  • trunk/libtransmission/transmission.h

    r13625 r13651  
    11481148    @{ */
    11491149
    1150 /** @brief Frees memory allocated by tr_torrentNew ().
    1151            Running torrents are stopped first. */
    1152 void tr_torrentFree (tr_torrent * torrent);
     1150/**
     1151 * @brief Decrements a torrent's refcount.
     1152 *
     1153 * If its refcount becomes zero, the torrent is stopped and its memory is freed.
     1154 */
     1155void tr_torrentUnref (tr_torrent * torrent);
     1156
     1157/**
     1158 * @brief Increments a torrent's refcount.
     1159 *
     1160 * @return true if the pointer is a live torrent object.
     1161 *         This is a convenience for validity checking before use:
     1162 *         if (tr_torrentRef (tor)) { foo(); bar(); tr_torrentUnref(tor); }
     1163 */
     1164bool tr_torrentRef (tr_torrent * torrent);
    11531165
    11541166typedef int tr_fileFunc (const char * filename);
     
    12291241
    12301242void         tr_torrentSetSpeedLimit_KBps (tr_torrent *, tr_direction, unsigned int KBps);
    1231 unsigned int tr_torrentGetSpeedLimit_KBps (const tr_torrent *, tr_direction);
    1232 
    1233 void     tr_torrentUseSpeedLimit    (tr_torrent *, tr_direction, bool);
    1234 bool     tr_torrentUsesSpeedLimit   (const tr_torrent *, tr_direction);
    1235 
    1236 void     tr_torrentUseSessionLimits (tr_torrent *, bool);
    1237 bool     tr_torrentUsesSessionLimits (const tr_torrent *);
     1243unsigned int tr_torrentGetSpeedLimit_KBps (tr_torrent *, tr_direction);
     1244
     1245void         tr_torrentUseSpeedLimit      (tr_torrent *, tr_direction, bool);
     1246bool         tr_torrentUsesSpeedLimit     (tr_torrent *, tr_direction);
     1247
     1248void         tr_torrentUseSessionLimits  (tr_torrent *, bool);
     1249bool         tr_torrentUsesSessionLimits  (tr_torrent *);
    12381250
    12391251
     
    12631275                                       double              ratio);
    12641276
    1265 double        tr_torrentGetRatioLimit (const tr_torrent  * tor);
    1266 
    1267 
    1268 bool          tr_torrentGetSeedRatio (const tr_torrent *, double * ratio);
     1277double        tr_torrentGetRatioLimit (tr_torrent  * tor);
     1278
     1279
     1280bool          tr_torrentGetSeedRatio  (tr_torrent *, double * ratio);
    12691281
    12701282
     
    13351347 *         It's the caller's responsibility to free () this.
    13361348 */
    1337 tr_priority_t*  tr_torrentGetFilePriorities (const tr_torrent * torrent);
     1349tr_priority_t*  tr_torrentGetFilePriorities (tr_torrent * torrent);
    13381350
    13391351/** @brief Set a batch of files to be downloaded or not. */
     
    15701582tr_peer_stat;
    15711583
    1572 tr_peer_stat * tr_torrentPeers (const tr_torrent * torrent,
    1573                                 int *              peerCount);
     1584tr_peer_stat * tr_torrentPeers (tr_torrent * torrent,
     1585                                int        * peerCount);
    15741586
    15751587void           tr_torrentPeersFree (tr_peer_stat * peerStats,
     
    16931705tr_tracker_stat;
    16941706
    1695 tr_tracker_stat * tr_torrentTrackers (const tr_torrent * torrent,
    1696                                       int              * setmeTrackerCount);
     1707tr_tracker_stat * tr_torrentTrackers (tr_torrent * torrent,
     1708                                      int        * setmeTrackerCount);
    16971709
    16981710void tr_torrentTrackersFree (tr_tracker_stat * trackerStats,
     
    17111723 *         NOTE: always free this array with tr_free () when you're done with it.
    17121724 */
    1713 double*  tr_torrentWebSpeeds_KBps (const tr_torrent * torrent);
     1725double*  tr_torrentWebSpeeds_KBps (tr_torrent * torrent);
    17141726
    17151727typedef struct tr_file_stat
     
    17351747 * of connected peers who have the piece.
    17361748 **********************************************************************/
    1737 void tr_torrentAvailability (const tr_torrent  * torrent,
    1738                              int8_t            * tab,
    1739                              int                  size);
    1740 
    1741 void tr_torrentAmountFinished (const tr_torrent  * torrent,
    1742                                float *            tab,
    1743                                int                 size);
     1749void tr_torrentAvailability (tr_torrent  * torrent,
     1750                             int8_t      * tab,
     1751                             int           size);
     1752
     1753void tr_torrentAmountFinished (tr_torrent  * torrent,
     1754                               float       * tab,
     1755                               int           size);
    17441756
    17451757void tr_torrentVerify (tr_torrent * torrent);
Note: See TracChangeset for help on using the changeset viewer.