* A few more updates to the networker
authorArt Cancro <ajc@citadel.org>
Thu, 6 Sep 2001 04:02:34 +0000 (04:02 +0000)
committerArt Cancro <ajc@citadel.org>
Thu, 6 Sep 2001 04:02:34 +0000 (04:02 +0000)
citadel/ChangeLog
citadel/citadel.h
citadel/msgbase.c
citadel/serv_network.c

index 8cf81c12e28535f136d76f512593e4cc88d5b9d0..a4c53b9b7c1e93672c431a2ddfff5dc717ec7b16 100644 (file)
@@ -1,4 +1,7 @@
  $Log$
+ Revision 580.35  2001/09/06 04:02:34  ajc
+ * A few more updates to the networker
+
  Revision 580.34  2001/09/06 03:32:41  nbryant
  build fix for sparc-sun-solaris2.8; i think the dependencies should be
  set up properly for all platforms now.
@@ -2719,4 +2722,3 @@ Sat Jul 11 00:20:48 EDT 1998 Nathan Bryant <bryant@cs.usm.maine.edu>
 
 Fri Jul 10 1998 Art Cancro <ajc@uncensored.citadel.org>
        * Initial CVS import 
-
index a613b43baf1d394eecb29f44f3d6dc0e5748ae97..1c5a125414822d8a3bef78b05266e1334b3a8511 100644 (file)
@@ -264,6 +264,7 @@ struct floor {
 #define SPOOLMIME      "application/x-citadel-delivery-list"
 #define        INTERNETCFG     "application/x-citadel-internet-config"
 #define IGNETCFG       "application/x-citadel-ignet-config"
+#define IGNETMAP       "application/x-citadel-ignet-map"
 
 #define TRACE  lprintf(9, "Checkpoint: %s, %d\n", __FILE__, __LINE__)
 
index 15a3d614d93987e29ad0900f3204b0f043c96d2c..df567a28928fab473ecfe10cae5941813b090e3b 100644 (file)
@@ -2778,10 +2778,8 @@ char *CtdlGetSysConfig(char *sysconfname) {
 
        getroom(&CC->quickroom, hold_rm);
 
-       lprintf(9, "eggstracting...\n");
        if (conf != NULL) do {
                extract_token(buf, conf, 0, '\n');
-               lprintf(9, "eggstracted <%s>\n", buf);
                strcpy(conf, &conf[strlen(buf)+1]);
        } while ( (strlen(conf)>0) && (strlen(buf)>0) );
 
index 92a92fde15f739208420186acf3079a9dc9ef645..7f0af1a8ecb0b98361c6413fa0a283aba519f85d 100644 (file)
@@ -64,6 +64,83 @@ struct RoomProcList {
 struct RoomProcList *rplist = NULL;
 
 
+/*
+ * We build a map of the Citadel network during network runs.
+ */
+struct NetMap {
+       struct NetMap *next;
+       char nodename[SIZ];
+       time_t lastcontact;
+       char nexthop[SIZ];
+};
+
+struct NetMap *the_netmap = NULL;
+
+
+
+/* 
+ * Read the network map from its configuration file into memory.
+ */
+void read_network_map(void) {
+       char *serialized_map = NULL;
+       int i;
+       char buf[SIZ];
+       struct NetMap *nmptr;
+
+       serialized_map = CtdlGetSysConfig(IGNETMAP);
+       if (serialized_map == NULL) return;     /* if null, no entries */
+
+       /* Use the string tokenizer to grab one line at a time */
+       for (i=0; i<num_tokens(serialized_map, '\n'); ++i) {
+               extract_token(buf, serialized_map, i, '\n');
+               nmptr = (struct NetMap *) mallok(sizeof(struct NetMap));
+               extract(nmptr->nodename, buf, 0);
+               nmptr->lastcontact = extract_long(buf, 1);
+               extract(nmptr->nexthop, buf, 2);
+               nmptr->next = the_netmap;
+               the_netmap = nmptr;
+       }
+
+       phree(serialized_map);
+}
+
+
+/*
+ * Write the network map from memory back to the configuration file.
+ */
+void write_network_map(void) {
+       char *serialized_map = NULL;
+       struct NetMap *nmptr;
+
+       serialized_map = strdoop("");
+
+       if (the_netmap != NULL) {
+               for (nmptr = the_netmap; nmptr != NULL; nmptr = nmptr->next) {
+                       serialized_map = reallok(serialized_map,
+                                               (strlen(serialized_map)+SIZ) );
+                       if (strlen(nmptr->nodename) > 0) {
+                               sprintf(&serialized_map[strlen(serialized_map)],
+                                       "%s|%ld|%s\n",
+                                       nmptr->nodename,
+                                       nmptr->lastcontact,
+                                       nmptr->nexthop);
+                       }
+               }
+       }
+
+       CtdlPutSysConfig(IGNETMAP, serialized_map);
+       phree(serialized_map);
+
+       /* Now free the list */
+       while (the_netmap != NULL) {
+               nmptr = the_netmap->next;
+               phree(the_netmap);
+               the_netmap = nmptr;
+       }
+}
+
+
+
 
 
 void cmd_gnet(char *argbuf) {
@@ -407,6 +484,34 @@ void network_queue_room(struct quickroom *qrbuf, void *data) {
 }
 
 
+/*
+ * Learn topology from path fields
+ */
+void network_learn_topology(char *node, char *path) {
+       char nexthop[SIZ];
+       struct NetMap *nmptr;
+
+       strcpy(nexthop, "");
+
+       if (num_tokens(path, '!') < 3) return;
+       for (nmptr = the_netmap; nmptr != NULL; nmptr = nmptr->next) {
+               if (!strcasecmp(nmptr->nodename, node)) {
+                       extract_token(nmptr->nexthop, path, 0, '!');
+                       nmptr->lastcontact = time(NULL);
+                       return;
+               }
+       }
+
+       /* If we got here then it's not in the map, so add it. */
+       nmptr = (struct NetMap *) mallok(sizeof (struct NetMap));
+       strcpy(nmptr->nodename, node);
+       nmptr->lastcontact = time(NULL);
+       extract_token(nmptr->nexthop, path, 0, '!');
+       nmptr->next = the_netmap;
+       the_netmap = nmptr;
+}
+
+
 
 /*
  * Process a buffer containing a single message from a single file
@@ -441,6 +546,12 @@ void network_process_buffer(char *buffer, long size) {
                }
        }
 
+       /* Learn network topology from the path */
+       if ((msg->cm_fields['N'] != NULL) && (msg->cm_fields['P'] != NULL)) {
+               network_learn_topology(msg->cm_fields['N'], 
+                                       msg->cm_fields['P']);
+       }
+
        /* Does it have a recipient?  If so, validate it... */
        if (msg->cm_fields['D'] != NULL) {
 
@@ -580,6 +691,8 @@ void network_do_queue(void) {
        doing_queue = 1;
        last_run = time(NULL);
 
+       read_network_map();
+
        /* 
         * Go ahead and run the queue
         */
@@ -597,6 +710,8 @@ void network_do_queue(void) {
        lprintf(7, "network: processing inbound queue\n");
        network_do_spoolin();
 
+       write_network_map();
+
        lprintf(7, "network: queue run completed\n");
        doing_queue = 0;
 }