-fixes
[oweals/gnunet.git] / src / fs / gnunet-service-fs_cp.c
index 7560975db9c43401c33ec2c4f48fc85e223784d2..e84993bd38b07c402da69e3866c339e3ea2dd2f9 100644 (file)
@@ -746,6 +746,32 @@ copy_reply (void *cls, size_t buf_size, void *buf)
 }
 
 
+/**
+ * Free resources associated with the given peer request.
+ *
+ * @param peerreq request to free
+ * @param query associated key for the request
+ */
+static void
+free_pending_request (struct PeerRequest *peerreq,
+                     const GNUNET_HashCode *query)
+{
+  struct GSF_ConnectedPeer *cp = peerreq->cp;
+
+  if (peerreq->kill_task != GNUNET_SCHEDULER_NO_TASK)
+  {
+    GNUNET_SCHEDULER_cancel (peerreq->kill_task);
+    peerreq->kill_task = GNUNET_SCHEDULER_NO_TASK;
+  }
+  GNUNET_STATISTICS_update (GSF_stats, gettext_noop ("# P2P searches active"),
+                            -1, GNUNET_NO);
+  GNUNET_break (GNUNET_YES ==
+                GNUNET_CONTAINER_multihashmap_remove (cp->request_map,
+                                                      query, peerreq));
+  GNUNET_free (peerreq);
+}
+
+
 /**
  * Cancel all requests associated with the peer.
  *
@@ -759,22 +785,11 @@ cancel_pending_request (void *cls, const GNUNET_HashCode * query, void *value)
 {
   struct PeerRequest *peerreq = value;
   struct GSF_PendingRequest *pr = peerreq->pr;
-  struct GSF_ConnectedPeer *cp = peerreq->cp;
   struct GSF_PendingRequestData *prd;
 
-  if (peerreq->kill_task != GNUNET_SCHEDULER_NO_TASK)
-  {
-    GNUNET_SCHEDULER_cancel (peerreq->kill_task);
-    peerreq->kill_task = GNUNET_SCHEDULER_NO_TASK;
-  }
-  GNUNET_STATISTICS_update (GSF_stats, gettext_noop ("# P2P searches active"),
-                            -1, GNUNET_NO);
   prd = GSF_pending_request_get_data_ (pr);
-  GNUNET_break (GNUNET_YES ==
-                GNUNET_CONTAINER_multihashmap_remove (cp->request_map,
-                                                      &prd->query, peerreq));
   GSF_pending_request_cancel_ (pr, GNUNET_NO);
-  GNUNET_free (peerreq);
+  free_pending_request (peerreq, &prd->query);
   return GNUNET_OK;
 }
 
@@ -860,6 +875,7 @@ get_randomized_delay ()
  * @param pr handle to the original pending request
  * @param reply_anonymity_level anonymity level for the reply, UINT32_MAX for "unknown"
  * @param expiration when does 'data' expire?
+ * @param last_transmission when did we last transmit a request for this block
  * @param type type of the block
  * @param data response data, NULL on request expiration
  * @param data_len number of bytes in data
@@ -868,6 +884,7 @@ static void
 handle_p2p_reply (void *cls, enum GNUNET_BLOCK_EvaluationResult eval,
                   struct GSF_PendingRequest *pr, uint32_t reply_anonymity_level,
                   struct GNUNET_TIME_Absolute expiration,
+                  struct GNUNET_TIME_Absolute last_transmission,
                   enum GNUNET_BLOCK_Type type, const void *data,
                   size_t data_len)
 {
@@ -883,25 +900,21 @@ handle_p2p_reply (void *cls, enum GNUNET_BLOCK_EvaluationResult eval,
   prd = GSF_pending_request_get_data_ (pr);
   if (NULL == data)
   {
-    GNUNET_STATISTICS_update (GSF_stats, gettext_noop ("# P2P searches active"),
-                              -1, GNUNET_NO);
-    GNUNET_break (GNUNET_YES ==
-                  GNUNET_CONTAINER_multihashmap_remove (cp->request_map,
-                                                        &prd->query, peerreq));
-    GNUNET_free (peerreq);
+    free_pending_request (peerreq, &prd->query);
     return;
   }
   GNUNET_break (type != GNUNET_BLOCK_TYPE_ANY);
   if ((prd->type != type) && (prd->type != GNUNET_BLOCK_TYPE_ANY))
   {
-    GNUNET_break (0);
+    GNUNET_STATISTICS_update (GSF_stats,
+                             gettext_noop
+                             ("# replies dropped due to type mismatch"),
+                                1, GNUNET_NO);
     return;
   }
-#if DEBUG_FS
   GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
               "Transmitting result for query `%s' to peer\n",
               GNUNET_h2s (&prd->query));
-#endif
   GNUNET_STATISTICS_update (GSF_stats,
                             gettext_noop ("# replies received for other peers"),
                             1, GNUNET_NO);
@@ -1179,7 +1192,6 @@ GSF_handle_p2p_query_ (const struct GNUNET_PeerIdentity *other,
     cp = cps;
   if (cp == NULL)
   {
-#if DEBUG_FS
     if (0 != (bm & GET_MESSAGE_BIT_RETURN_TO))
       GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
                   "Failed to find RETURN-TO peer `%4s' in connection set. Dropping query.\n",
@@ -1190,7 +1202,6 @@ GSF_handle_p2p_query_ (const struct GNUNET_PeerIdentity *other,
       GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
                   "Failed to find peer `%4s' in connection set. Dropping query.\n",
                   GNUNET_i2s (other));
-#endif
     GNUNET_STATISTICS_update (GSF_stats,
                               gettext_noop
                               ("# requests dropped due to missing reverse route"),
@@ -1203,19 +1214,15 @@ GSF_handle_p2p_query_ (const struct GNUNET_PeerIdentity *other,
   priority = bound_priority (ntohl (gm->priority), cps);
   if (priority < 0)
   {
-#if DEBUG_FS
     GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
                 "Dropping query from `%s', this peer is too busy.\n",
                 GNUNET_i2s (other));
-#endif
     return NULL;
   }
-#if DEBUG_FS
   GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
               "Received request for `%s' of type %u from peer `%4s' with flags %u\n",
               GNUNET_h2s (&gm->query), (unsigned int) type, GNUNET_i2s (other),
               (unsigned int) bm);
-#endif
   namespace = (0 != (bm & GET_MESSAGE_BIT_SKS_NAMESPACE)) ? &opt[bits++] : NULL;
   if ((type == GNUNET_BLOCK_TYPE_FS_SBLOCK) && (namespace == NULL))
   {
@@ -1231,7 +1238,7 @@ GSF_handle_p2p_query_ (const struct GNUNET_PeerIdentity *other,
       (0 !=
        (bm & GET_MESSAGE_BIT_TRANSMIT_TO)) ? ((const struct GNUNET_PeerIdentity
                                                *) &opt[bits++]) : NULL;
-  options = 0;
+  options = GSF_PRO_DEFAULTS;
   spid = 0;
   if ((GNUNET_LOAD_get_load (cp->ppd.transmission_delay) > 3 * (1 + priority))
       || (GNUNET_LOAD_get_average (cp->ppd.transmission_delay) >
@@ -1252,11 +1259,9 @@ GSF_handle_p2p_query_ (const struct GNUNET_PeerIdentity *other,
                                                     TTL_DECREMENT);
   if ((ttl < 0) && (((int32_t) (ttl - ttl_decrement)) > 0))
   {
-#if DEBUG_FS
     GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
                 "Dropping query from `%s' due to TTL underflow (%d - %u).\n",
                 GNUNET_i2s (other), ttl, ttl_decrement);
-#endif
     GNUNET_STATISTICS_update (GSF_stats,
                               gettext_noop
                               ("# requests dropped due TTL underflow"), 1,
@@ -1280,11 +1285,9 @@ GSF_handle_p2p_query_ (const struct GNUNET_PeerIdentity *other,
       {
         /* existing request has higher TTL, drop new one! */
         prd->priority += priority;
-#if DEBUG_FS
         GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
                     "Have existing request with higher TTL, dropping new request.\n",
                     GNUNET_i2s (other));
-#endif
         GNUNET_STATISTICS_update (GSF_stats,
                                   gettext_noop
                                   ("# requests dropped due to higher-TTL request"),
@@ -1292,21 +1295,9 @@ GSF_handle_p2p_query_ (const struct GNUNET_PeerIdentity *other,
         return NULL;
       }
       /* existing request has lower TTL, drop old one! */
-      GNUNET_STATISTICS_update (GSF_stats,
-                                gettext_noop ("# P2P searches active"), -1,
-                                GNUNET_NO);
       priority += prd->priority;
       GSF_pending_request_cancel_ (pr, GNUNET_YES);
-      GNUNET_assert (GNUNET_YES ==
-                     GNUNET_CONTAINER_multihashmap_remove (cp->request_map,
-                                                           &gm->query,
-                                                           peerreq));
-      if (peerreq->kill_task != GNUNET_SCHEDULER_NO_TASK)
-      {
-        GNUNET_SCHEDULER_cancel (peerreq->kill_task);
-        peerreq->kill_task = GNUNET_SCHEDULER_NO_TASK;
-      }
-      GNUNET_free (peerreq);
+      free_pending_request (peerreq, &gm->query);
     }
   }
 
@@ -1349,10 +1340,8 @@ peer_transmit_timeout (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc)
   struct GSF_PeerTransmitHandle *pth = cls;
   struct GSF_ConnectedPeer *cp;
 
-#if DEBUG_FS
   GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
               "Timeout trying to transmit to other peer\n");
-#endif
   pth->timeout_task = GNUNET_SCHEDULER_NO_TASK;
   cp = pth->cp;
   GNUNET_CONTAINER_DLL_remove (cp->pth_head, cp->pth_tail, pth);
@@ -1710,25 +1699,20 @@ create_migration_stop_message (void *cls, size_t size, void *buf)
  */
 void
 GSF_block_peer_migration_ (struct GSF_ConnectedPeer *cp,
-                           struct GNUNET_TIME_Relative block_time)
+                           struct GNUNET_TIME_Absolute block_time)
 {
-  if (GNUNET_TIME_absolute_get_remaining (cp->last_migration_block).rel_value >
-      block_time.rel_value)
+  if (cp->last_migration_block.abs_value > block_time.abs_value)
   {
-#if DEBUG_FS && 0
     GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
                 "Migration already blocked for another %llu ms\n",
                 (unsigned long long)
                 GNUNET_TIME_absolute_get_remaining
                 (cp->last_migration_block).rel_value);
-#endif
     return;                     /* already blocked */
   }
-#if DEBUG_FS && 0
   GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Asking to stop migration for %llu ms\n",
-              (unsigned long long) block_time.rel_value);
-#endif
-  cp->last_migration_block = GNUNET_TIME_relative_to_absolute (block_time);
+              (unsigned long long) GNUNET_TIME_absolute_get_remaining (block_time).rel_value);
+  cp->last_migration_block = block_time;
   if (cp->migration_pth != NULL)
     GSF_peer_transmit_cancel_ (cp->migration_pth);
   cp->migration_pth =
@@ -1816,7 +1800,9 @@ cron_flush_trust (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc)
     return;
   if (0 != (tc->reason & GNUNET_SCHEDULER_REASON_SHUTDOWN))
     return;
-  GNUNET_SCHEDULER_add_delayed (TRUST_FLUSH_FREQ, &cron_flush_trust, NULL);
+  GNUNET_SCHEDULER_add_delayed_with_priority (TRUST_FLUSH_FREQ,
+                                             GNUNET_SCHEDULER_PRIORITY_HIGH,
+                                             &cron_flush_trust, NULL);
 }