gnunet-svn
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[GNUnet-SVN] r10118 - in gnunet: . src/core src/datastore src/fs src/inc


From: gnunet
Subject: [GNUnet-SVN] r10118 - in gnunet: . src/core src/datastore src/fs src/include src/peerinfo src/transport src/util
Date: Fri, 22 Jan 2010 16:14:39 +0100

Author: grothoff
Date: 2010-01-22 16:14:39 +0100 (Fri, 22 Jan 2010)
New Revision: 10118

Modified:
   gnunet/TODO
   gnunet/src/core/gnunet-service-core.c
   gnunet/src/datastore/gnunet-service-datastore.c
   gnunet/src/fs/gnunet-service-fs.c
   gnunet/src/include/gnunet_server_lib.h
   gnunet/src/peerinfo/gnunet-service-peerinfo.c
   gnunet/src/transport/gnunet-service-transport.c
   gnunet/src/transport/plugin_transport_tcp.c
   gnunet/src/util/server.c
   gnunet/src/util/server_nc.c
   gnunet/src/util/test_server_disconnect.c
   gnunet/src/util/test_server_with_client.c
Log:
updates to peerinfo to use new nc API

Modified: gnunet/TODO
===================================================================
--- gnunet/TODO 2010-01-22 14:47:45 UTC (rev 10117)
+++ gnunet/TODO 2010-01-22 15:14:39 UTC (rev 10118)
@@ -18,8 +18,8 @@
     of having each service queue messages and "send when ready", 
     simply have a way to add a client to the notification set
     and to 'notify client' or 'notify all clients'
-    (useful for peerinfo (new hellos), transport (our hello; blacklist), 
-     core (misc monitoring features), statistics (change notifications)
+    (transport (our hello), 
+     core (misc monitoring features)
      and likely others)
   - server/service API change for ARM inetd'ing
     (listen as well as support for start with multiple, already
@@ -66,7 +66,8 @@
            (async peerinfo would not be right)
   - OS: existing waitpid call is not nice (not integratable with scheduler! 
fix this!)
 * STATISTICS:
-  - synchronous/asynchronous API (& implementation) is not nice
+  - synchronous/asynchronous API (& implementation) is not nice;
+    => provide notification-based API
   - does not seem to work with timeouts (especially if service is not running)
 * ARM:
   - need to get rid of synchronous API for service starts (cause all kinds of 
problems)

Modified: gnunet/src/core/gnunet-service-core.c
===================================================================
--- gnunet/src/core/gnunet-service-core.c       2010-01-22 14:47:45 UTC (rev 
10117)
+++ gnunet/src/core/gnunet-service-core.c       2010-01-22 15:14:39 UTC (rev 
10118)
@@ -1034,6 +1034,8 @@
   struct Client *prev;
   struct Event *e;
 
+  if (client == NULL)
+    return;
 #if DEBUG_CORE_CLIENT
   GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
               "Client has disconnected from core service.\n");

Modified: gnunet/src/datastore/gnunet-service-datastore.c
===================================================================
--- gnunet/src/datastore/gnunet-service-datastore.c     2010-01-22 14:47:45 UTC 
(rev 10117)
+++ gnunet/src/datastore/gnunet-service-datastore.c     2010-01-22 15:14:39 UTC 
(rev 10118)
@@ -1233,6 +1233,8 @@
   struct ReservationList *prev;
   struct ReservationList *next;
 
+  if (client == NULL)
+    return;
   prev = NULL;
   pos = reservations;
   while (NULL != pos)

Modified: gnunet/src/fs/gnunet-service-fs.c
===================================================================
--- gnunet/src/fs/gnunet-service-fs.c   2010-01-22 14:47:45 UTC (rev 10117)
+++ gnunet/src/fs/gnunet-service-fs.c   2010-01-22 15:14:39 UTC (rev 10118)
@@ -2273,6 +2273,8 @@
   struct ClientList *cprev;
   struct ClientRequestList *rl;
 
+  if (client == NULL)
+    return;
   lgc = lgc_head;
   while ( (NULL != lgc) &&
          (lgc->client != client) )

Modified: gnunet/src/include/gnunet_server_lib.h
===================================================================
--- gnunet/src/include/gnunet_server_lib.h      2010-01-22 14:47:45 UTC (rev 
10117)
+++ gnunet/src/include/gnunet_server_lib.h      2010-01-22 15:14:39 UTC (rev 
10118)
@@ -394,7 +394,8 @@
  * is disconnected on the network level.
  *
  * @param cls closure
- * @param client identification of the client
+ * @param client identification of the client; NULL
+ *        for the last call when the server is destroyed
  */
 typedef void (*GNUNET_SERVER_DisconnectCallback) (void *cls,
                                                   struct GNUNET_SERVER_Client
@@ -405,7 +406,11 @@
  * Ask the server to notify us whenever a client disconnects.
  * This function is called whenever the actual network connection
  * is closed; the reference count may be zero or larger than zero
- * at this point.
+ * at this point.  If the server is destroyed before this 
+ * notification is explicitly cancelled, the 'callback' will
+ * once be called with a 'client' argument of NULL to indicate
+ * that the server itself is now gone (and that the callback
+ * won't be called anymore and also can no longer be cancelled).
  *
  * @param server the server manageing the clients
  * @param callback function to call on disconnect

Modified: gnunet/src/peerinfo/gnunet-service-peerinfo.c
===================================================================
--- gnunet/src/peerinfo/gnunet-service-peerinfo.c       2010-01-22 14:47:45 UTC 
(rev 10117)
+++ gnunet/src/peerinfo/gnunet-service-peerinfo.c       2010-01-22 15:14:39 UTC 
(rev 10118)
@@ -89,54 +89,6 @@
 
 
 /**
- * Entries that we still need to tell the client about.
- */
-struct PendingEntry
-{
-
-  /**
-   * This is a linked list.
-   */
-  struct PendingEntry *next;
-
-  /**
-   * Entry to tell the client about.
-   */
-  struct HostEntry *he;
-
-};
-
-
-/**
- * Clients to notify of changes to the peer information.
- */
-struct NotifyList
-{
-
-  /**
-   * This is a linked list.
-   */
-  struct NotifyList *next;
-
-  /**
-   * Client to notify.
-   */ 
-  struct GNUNET_SERVER_Client *client;
-
-  /**
-   * Notifications pending for this entry.
-   */
-  struct PendingEntry *pending;
-
-  /**
-   * Handle for a transmit ready request.
-   */
-  struct GNUNET_CONNECTION_TransmitHandle *transmit_ctx;
-
-};
-
-
-/**
  * The in-memory list of known hosts.
  */
 static struct HostEntry *hosts;
@@ -144,7 +96,7 @@
 /**
  * Clients to immediately notify about all changes.
  */
-static struct NotifyList *notify_list;
+static struct GNUNET_SERVER_NotificationContext *notify_list;
 
 /**
  * Directory where the hellos are stored in (data/hosts)
@@ -158,116 +110,23 @@
 
 
 /**
- * Transmit peer information messages from the pending queue
- * to the client.
- *
- * @param cls the 'struct NotifyList' that we are processing
- * @param size number of bytes we can transmit
- * @param vbuf where to write the messages
- * @return number of bytes written to vbuf
- */
-static size_t
-transmit_pending_notification (void *cls,
-                              size_t size,
-                              void *vbuf)
-{
-  struct NotifyList *nl = cls;
-  char *buf = vbuf;
-  struct PendingEntry *pos;
-  struct PendingEntry *next;
-  struct InfoMessage im;
-  uint16_t hs;
-  size_t left;
-
-  nl->transmit_ctx = NULL;
-  next = nl->pending;
-  pos = nl->pending;
-  left = size;
-  while (pos != NULL) 
-    {
-      hs = (pos->he->hello == NULL) ? 0 : GNUNET_HELLO_size (pos->he->hello);
-      if (left < sizeof (struct InfoMessage) + hs)
-       break;
-      next = pos->next;
-      im.header.size = htons (hs + sizeof (struct InfoMessage));
-      im.header.type = htons (GNUNET_MESSAGE_TYPE_PEERINFO_INFO);
-      im.trust = htonl (pos->he->trust);
-      im.peer = pos->he->identity;
-      memcpy (&buf[size - left], &im, sizeof (struct InfoMessage));      
-      memcpy (&buf[size - left + sizeof (struct InfoMessage)], pos->he->hello, 
hs);
-      left -= hs + sizeof (struct InfoMessage);
-      GNUNET_free (pos);
-      pos = next;      
-    }
-  nl->pending = next;
-  if (nl->pending != NULL)
-    {
-      nl->transmit_ctx 
-       = GNUNET_SERVER_notify_transmit_ready (nl->client,
-                                              sizeof (struct InfoMessage) + hs,
-                                              GNUNET_TIME_UNIT_FOREVER_REL,
-                                              &transmit_pending_notification,
-                                              nl);
-    }
-  return size - left;
-}
-
-
-
-/**
- * Notify client about host change.  Checks if the
- * respective host entry is already in the list of things
- * to send to the client, and if not, adds it.  Also
- * triggers a new request for transmission if the pending
- * list was previously empty.
- *
- * @param nl client to notify
- * @param he entry to notify about
- */
-static void
-do_notify (struct NotifyList *nl,
-          struct HostEntry *he)
-{
-  struct PendingEntry *pe;
-  uint16_t hsize;
-
-  pe = nl->pending;
-  while (NULL != pe)
-    {
-      if (pe->he == he)
-       return; /* already in list */
-      pe = pe->next;
-    }
-  pe = GNUNET_malloc (sizeof (struct PendingEntry));
-  pe->next = nl->pending;
-  pe->he = he;
-  nl->pending = pe;
-  if (nl->transmit_ctx != NULL)
-    return; /* already trying to transmit */
-  hsize = (he->hello == NULL) ? 0 : GNUNET_HELLO_size (he->hello);
-  nl->transmit_ctx = GNUNET_SERVER_notify_transmit_ready (nl->client,
-                                                         sizeof (struct 
InfoMessage) + hsize,
-                                                         
GNUNET_TIME_UNIT_FOREVER_REL,
-                                                         
&transmit_pending_notification,
-                                                         nl);
-}
-
-
-/**
  * Notify all clients in the notify list about the
  * given host entry changing.
  */
-static void
-notify_all (struct HostEntry *he)
+static struct InfoMessage *
+make_info_message (const struct HostEntry *he)
 {
-  struct NotifyList *nl;
+  struct InfoMessage *im;
+  size_t hs;
 
-  nl = notify_list;
-  while (NULL != nl)
-    {
-      do_notify (nl, he);
-      nl = nl->next;
-    }
+  hs = (he->hello == NULL) ? 0 : GNUNET_HELLO_size (he->hello);
+  im = GNUNET_malloc (sizeof (struct InfoMessage) + hs);
+  im->header.size = htons (hs + sizeof (struct InfoMessage));
+  im->header.type = htons (GNUNET_MESSAGE_TYPE_PEERINFO_INFO);
+  im->trust = htonl (he->trust);
+  im->peer = he->identity;
+  memcpy (&im[1], he->hello, hs);
+  return im;
 }
 
 
@@ -328,6 +187,7 @@
   return fn;
 }
 
+
 /**
  * Find the host entry for the given peer.  Call
  * only when synchronized!
@@ -348,6 +208,25 @@
 
 
 /**
+ * Broadcast information about the given entry to all 
+ * clients that care.
+ *
+ * @param entry entry to broadcast about
+ */
+static void
+notify_all (struct HostEntry *entry)
+{
+  struct InfoMessage *msg;
+
+  msg = make_info_message (entry);
+  GNUNET_SERVER_notification_context_broadcast (notify_list,
+                                               &msg->header,
+                                               GNUNET_NO);
+  GNUNET_free (msg);
+}
+
+
+/**
  * Add a host to the list.
  *
  * @param identity the identity of the host
@@ -451,7 +330,7 @@
         host->trust += value;
     }
   if (host->trust != old_trust)
-    notify_all (host);
+    notify_all (host);    
   return value;
 }
 
@@ -834,18 +713,20 @@
             struct GNUNET_SERVER_Client *client,
             const struct GNUNET_MessageHeader *message)
 {
-  struct NotifyList *nl;
+  struct InfoMessage *msg;
   struct HostEntry *pos;
 
-  nl = GNUNET_malloc (sizeof (struct NotifyList));
-  nl->next = notify_list;
-  nl->client = client;
-  GNUNET_SERVER_client_keep (client);  
-  notify_list = nl;
+  GNUNET_SERVER_notification_context_add (notify_list,
+                                         client);
   pos = hosts;
   while (NULL != pos)
     {
-      do_notify (nl, pos);
+      msg = make_info_message (pos);
+      GNUNET_SERVER_notification_context_unicast (notify_list,
+                                                 client,
+                                                 &msg->header,
+                                                 GNUNET_NO);
+      GNUNET_free (msg);
       pos = pos->next;
     }
 }
@@ -868,48 +749,17 @@
 
 
 /**
- * Function that is called when a client disconnects.
+ * Clean up our state.  Called during shutdown.
+ *
+ * @param cls unused
+ * @param tc scheduler task context, unused
  */
 static void
-notify_disconnect (void *cls,
-                  struct GNUNET_SERVER_Client *client)
+shutdown_task (void *cls,
+              const struct GNUNET_SCHEDULER_TaskContext *tc)
 {
-  struct NotifyList *pos;
-  struct NotifyList *prev;
-  struct NotifyList *next;
-  struct PendingEntry *p;
-
-  pos = notify_list;
-  prev = NULL;
-  while (pos != NULL)
-    {
-      next = pos->next;
-      if (pos->client == client)
-       {
-         while (NULL != (p = pos->pending))
-           {
-             pos->pending = p->next;
-             GNUNET_free (p);
-           }
-         if (pos->transmit_ctx != NULL)
-           {
-             GNUNET_CONNECTION_notify_transmit_ready_cancel 
(pos->transmit_ctx);
-             pos->transmit_ctx = NULL;
-           }
-         if (prev == NULL)
-           notify_list = next;
-         else
-           prev->next = next;
-          GNUNET_SERVER_client_drop (client);
-         GNUNET_free (pos);
-       }
-      else
-       {
-         prev = pos;
-       }
-      pos = next;
-    }
-
+  GNUNET_SERVER_notification_context_destroy (notify_list);
+  notify_list = NULL;
 }
 
 
@@ -927,6 +777,7 @@
      struct GNUNET_SERVER_Handle *server,
      const struct GNUNET_CONFIGURATION_Handle *cfg)
 {
+  notify_list = GNUNET_SERVER_notification_context_create (server, 0);
   GNUNET_assert (GNUNET_OK ==
                  GNUNET_CONFIGURATION_get_value_filename (cfg,
                                                           "peerinfo",
@@ -948,7 +799,9 @@
   GNUNET_SCHEDULER_add_with_priority (sched,
                                      GNUNET_SCHEDULER_PRIORITY_IDLE,
                                      &cron_clean_data_hosts, NULL);
-  GNUNET_SERVER_disconnect_notify (server, &notify_disconnect, NULL);
+  GNUNET_SCHEDULER_add_delayed (sched,
+                               GNUNET_TIME_UNIT_FOREVER_REL,
+                               &shutdown_task, NULL);
   GNUNET_SERVER_add_handlers (server, handlers);
 }
 

Modified: gnunet/src/transport/gnunet-service-transport.c
===================================================================
--- gnunet/src/transport/gnunet-service-transport.c     2010-01-22 14:47:45 UTC 
(rev 10117)
+++ gnunet/src/transport/gnunet-service-transport.c     2010-01-22 15:14:39 UTC 
(rev 10118)
@@ -2743,6 +2743,8 @@
   struct TransportClient *prev;
   struct ClientMessageQueueEntry *mqe;
 
+  if (client == NULL) 
+    return;
 #if DEBUG_TRANSPORT
   GNUNET_log (GNUNET_ERROR_TYPE_DEBUG | GNUNET_ERROR_TYPE_BULK,
               "Client disconnected, cleaning up.\n");

Modified: gnunet/src/transport/plugin_transport_tcp.c
===================================================================
--- gnunet/src/transport/plugin_transport_tcp.c 2010-01-22 14:47:45 UTC (rev 
10117)
+++ gnunet/src/transport/plugin_transport_tcp.c 2010-01-22 15:14:39 UTC (rev 
10118)
@@ -1146,6 +1146,8 @@
   struct Plugin *plugin = cls;
   struct Session *session;
 
+  if (client == NULL)
+    return;
   session = find_session_by_client (plugin, client);
   if (session == NULL)
     return;                     /* unknown, nothing to do */

Modified: gnunet/src/util/server.c
===================================================================
--- gnunet/src/util/server.c    2010-01-22 14:47:45 UTC (rev 10117)
+++ gnunet/src/util/server.c    2010-01-22 15:14:39 UTC (rev 10118)
@@ -538,6 +538,7 @@
     }
   while (NULL != (npos = s->disconnect_notify_list))
     {
+      npos->callback (npos->callback_cls, NULL);
       s->disconnect_notify_list = npos->next;
       GNUNET_free (npos);
     }

Modified: gnunet/src/util/server_nc.c
===================================================================
--- gnunet/src/util/server_nc.c 2010-01-22 14:47:45 UTC (rev 10117)
+++ gnunet/src/util/server_nc.c 2010-01-22 15:14:39 UTC (rev 10118)
@@ -146,6 +146,11 @@
   struct ClientList *prev;
   struct PendingMessageList *pml;
 
+  if (client == NULL)
+    {
+      nc->server = NULL;
+      return;
+    }
   prev = NULL;
   pos = nc->clients;
   while (NULL != pos)
@@ -219,9 +224,10 @@
        }
       GNUNET_free (pos);
     }
-  GNUNET_SERVER_disconnect_notify_cancel (nc->server,
-                                         &handle_client_disconnect,
-                                         nc);
+  if (nc->server != NULL)
+    GNUNET_SERVER_disconnect_notify_cancel (nc->server,
+                                           &handle_client_disconnect,
+                                           nc);
   GNUNET_free (nc);
 }
 

Modified: gnunet/src/util/test_server_disconnect.c
===================================================================
--- gnunet/src/util/test_server_disconnect.c    2010-01-22 14:47:45 UTC (rev 
10117)
+++ gnunet/src/util/test_server_disconnect.c    2010-01-22 15:14:39 UTC (rev 
10118)
@@ -138,6 +138,8 @@
 static void
 notify_disconnect (void *cls, struct GNUNET_SERVER_Client *clientarg)
 {
+  if (clientarg == NULL)
+    return;
   GNUNET_assert (ok == 6);
   ok++;
   GNUNET_CLIENT_receive (client,

Modified: gnunet/src/util/test_server_with_client.c
===================================================================
--- gnunet/src/util/test_server_with_client.c   2010-01-22 14:47:45 UTC (rev 
10117)
+++ gnunet/src/util/test_server_with_client.c   2010-01-22 15:14:39 UTC (rev 
10118)
@@ -123,6 +123,8 @@
 static void
 notify_disconnect (void *cls, struct GNUNET_SERVER_Client *client)
 {
+  if (client == NULL)
+    return;
   GNUNET_assert (ok == 5);
   ok = 0;
   GNUNET_SCHEDULER_add_now (sched,





reply via email to

[Prev in Thread] Current Thread [Next in Thread]