+}
+
+
+/**
+ * Connection notifies us about failure or success of a transmission
+ * request. Either pass it on to our user or, if possible, retry.
+ *
+ * @param cls our "struct GNUNET_CLIENT_TransmissionHandle"
+ * @param size number of bytes available for transmission
+ * @param buf where to write them
+ * @return number of bytes written to buf
+ */
+static size_t
+client_notify (void *cls, size_t size, void *buf)
+{
+ struct GNUNET_CLIENT_TransmitHandle *th = cls;
+ size_t ret;
+ struct GNUNET_TIME_Relative delay;
+
+ th->th = NULL;
+ th->sock->th = NULL;
+ if (buf == NULL)
+ {
+ delay = GNUNET_TIME_absolute_get_remaining (th->timeout);
+ delay.rel_value /= 2;
+ if ( (0 != (GNUNET_SCHEDULER_REASON_SHUTDOWN & GNUNET_SCHEDULER_get_reason ())) ||
+ (GNUNET_YES != th->auto_retry) ||
+ (0 == --th->attempts_left) ||
+ (delay.rel_value < 1) )
+ {
+#if DEBUG_CLIENT
+ GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
+ "Transmission failed %u times, giving up.\n",
+ MAX_ATTEMPTS - th->attempts_left);
+#endif
+ GNUNET_break (0 == th->notify (th->notify_cls, 0, NULL));
+ GNUNET_free (th);
+ return 0;
+ }
+ /* auto-retry */
+ GNUNET_CONNECTION_destroy (th->sock->sock, GNUNET_NO);
+ th->sock->sock = do_connect (th->sock->service_name,
+ th->sock->cfg,
+ th->sock->attempts++);
+ GNUNET_assert (NULL != th->sock->sock);
+ GNUNET_CONNECTION_ignore_shutdown (th->sock->sock,
+ th->sock->ignore_shutdown);
+ delay = GNUNET_TIME_relative_min (delay, th->sock->back_off);
+ th->sock->back_off
+ = GNUNET_TIME_relative_min (GNUNET_TIME_relative_multiply (th->sock->back_off, 2),
+ GNUNET_TIME_UNIT_SECONDS);
+#if DEBUG_CLIENT
+ GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
+ "Transmission failed %u times, trying again in %llums.\n",
+ MAX_ATTEMPTS - th->attempts_left,
+ (unsigned long long) delay.rel_value);
+#endif
+ th->reconnect_task = GNUNET_SCHEDULER_add_delayed (delay,
+ &client_delayed_retry,
+ th);
+ th->sock->th = th;
+ return 0;
+ }
+ GNUNET_assert (size >= th->size);
+ ret = th->notify (th->notify_cls, size, buf);
+ GNUNET_free (th);
+ return ret;