Update to latest (really :) ospf6d from Zebra repository and some tiny
fixes.
diff --git a/ospf6d/.cvsignore b/ospf6d/.cvsignore
index cec4061..a5b24c9 100644
--- a/ospf6d/.cvsignore
+++ b/ospf6d/.cvsignore
@@ -1,3 +1,4 @@
+Makefile.in
 Makefile
 *.o
 *.patch
diff --git a/ospf6d/ChangeLog b/ospf6d/ChangeLog
index b74dead..96490b0 100644
--- a/ospf6d/ChangeLog
+++ b/ospf6d/ChangeLog
@@ -3,6 +3,21 @@
 	* *.*: Merge rewritten ospf6d from Zebra repository.
 	* ospf6_network.c, ospf6_main.c: Merged privs stuff back in.
 	* ospf6_zebra.c: Sync back to zclient changes.
+	* ospf6_asbr.c: Added isis to the routings list.
+	* ospf6_main.c: "version.h" -> <lib/version.h>
+
+2004-05-17  Yasuhiro Ohara  <yasu@sfc.wide.ad.jp>
+
+	* ospf6_flood.[ch], ospf6_lsa.[ch], ospf6_lsdb.h, ospf6_message.c
+	ospf6_neighbor.c: Fix crash bug and change the way to count
+        how many neighbors include paticular LSA on its retrans-list.
+	* ospf6d.h: version 0.9.7c
+
+2004-05-03  Yasuhiro Ohara  <yasu@sfc.wide.ad.jp>
+
+	* ospf6_message.[ch], ospf6_interface.c: adjust send/recv buffer
+	size to interface MTUs.
+	* ospf6d.h: version 0.9.7b
 
 2003-08-18  Yasuhiro Ohara  <yasu@sfc.wide.ad.jp>
 
diff --git a/ospf6d/ospf6_asbr.c b/ospf6d/ospf6_asbr.c
index 81edb60..b990129 100644
--- a/ospf6d/ospf6_asbr.c
+++ b/ospf6d/ospf6_asbr.c
@@ -47,10 +47,10 @@
 
 char *zroute_name[] =
 { "system", "kernel", "connected", "static",
-  "rip", "ripng", "ospf", "ospf6", "bgp", "unknown" };
+  "rip", "ripng", "ospf", "ospf6", "isis", "bgp", "unknown" };
 
 char *zroute_abname[] =
-{ "X", "K", "C", "S", "R", "R", "O", "O", "B", "?" };
+{ "X", "K", "C", "S", "R", "R", "O", "O", "I", "B", "?" };
 
 #define ZROUTE_NAME(x)                                     \
   (0 < (x) && (x) < ZEBRA_ROUTE_MAX ? zroute_name[(x)] :   \
diff --git a/ospf6d/ospf6_flood.c b/ospf6d/ospf6_flood.c
index e049455..6e84a03 100644
--- a/ospf6d/ospf6_flood.c
+++ b/ospf6d/ospf6_flood.c
@@ -93,6 +93,28 @@
 }
 
 void
+ospf6_decrement_onretrans (struct ospf6_lsa *lsa)
+{
+  struct ospf6_lsdb *lsdb;
+  struct ospf6_lsa *src;
+
+  lsdb = ospf6_get_scoped_lsdb (lsa->header->type, lsa->scope);
+  if (lsdb == NULL)
+    {
+      zlog_warn ("Decrement onretrans: no such scope: %s", lsa->name);
+      return;
+    }
+
+  src = ospf6_lsdb_lookup (lsa->header->type, lsa->header->id,
+                           lsa->header->adv_router, lsdb);
+  if (src && src != lsa)
+    src->onretrans--;
+
+  if (src->onretrans < 0)
+    zlog_warn ("internal error: onretrans");
+}
+
+void
 ospf6_flood_clear (struct ospf6_lsa *lsa)
 {
   struct ospf6_neighbor *on;
@@ -159,6 +181,7 @@
               if (IS_OSPF6_DEBUG_LSA (DATABASE))
                 zlog_info ("Remove %s from retrans_list of %s",
                            rxmt->name, on->name);
+              ospf6_decrement_onretrans (rxmt);
               ospf6_lsdb_remove (rxmt, on->retrans_list);
             }
         }
@@ -308,6 +331,7 @@
           if (IS_OSPF6_DEBUG_LSA (SEND) || IS_OSPF6_DEBUG_LSA (DATABASE))
             zlog_info ("  Add copy of %s to retrans-list of %s",
                        lsa->name, on->name);
+          lsa->onretrans++;
           ospf6_lsdb_add (ospf6_lsa_copy (lsa), on->retrans_list);
           if (on->thread_send_lsupdate == NULL)
             on->thread_send_lsupdate =
@@ -811,6 +835,7 @@
           if (IS_OSPF6_DEBUG_LSA (DATABASE))
             zlog_info ("Remove %s from retrans_list of %s",
                        rem->name, from->name);
+          ospf6_decrement_onretrans (rem);
           ospf6_lsdb_remove (rem, from->retrans_list);
         }
 
diff --git a/ospf6d/ospf6_flood.h b/ospf6d/ospf6_flood.h
index 4f2d157..f639f63 100644
--- a/ospf6d/ospf6_flood.h
+++ b/ospf6d/ospf6_flood.h
@@ -26,6 +26,7 @@
 void *ospf6_get_lsa_scope (u_int16_t type, struct ospf6_neighbor *from);
 struct ospf6_lsdb *ospf6_get_scoped_lsdb (u_int16_t type, void *scope);
 
+void ospf6_decrement_onretrans (struct ospf6_lsa *lsa);
 void ospf6_flood_clear (struct ospf6_lsa *lsa);
 void ospf6_flood_lsa (struct ospf6_lsa *lsa, struct ospf6_neighbor *from);
 void ospf6_install_lsa (struct ospf6_lsa *lsa, struct ospf6_lsdb *lsdb);
diff --git a/ospf6d/ospf6_interface.c b/ospf6d/ospf6_interface.c
index 8f01e7d..9a02920 100644
--- a/ospf6d/ospf6_interface.c
+++ b/ospf6d/ospf6_interface.c
@@ -113,6 +113,7 @@
 ospf6_interface_create (struct interface *ifp)
 {
   struct ospf6_interface *oi;
+  int iobuflen;
 
   oi = (struct ospf6_interface *)
     XMALLOC (MTYPE_OSPF6_IF, sizeof (struct ospf6_interface));
@@ -137,10 +138,20 @@
   oi->dead_interval = 40;
   oi->rxmt_interval = 5;
   oi->cost = 1;
-  oi->ifmtu = ifp->mtu;
   oi->state = OSPF6_INTERFACE_DOWN;
   oi->flag = 0;
 
+  /* Try to adust I/O buffer size with IfMtu */
+  iobuflen = ospf6_iobuf_size (ifp->mtu);
+  if (iobuflen < ifp->mtu)
+    {
+      zlog_info ("Interface %s: IfMtu is adjusted to I/O buffer size: %d.",
+                 ifp->name, iobuflen);
+      oi->ifmtu = iobuflen;
+    }
+  else
+    oi->ifmtu = ifp->mtu;
+
   oi->lsupdate_list = ospf6_lsdb_create ();
   oi->lsack_list = ospf6_lsdb_create ();
   oi->lsdb = ospf6_lsdb_create ();
@@ -253,12 +264,22 @@
 ospf6_interface_if_add (struct interface *ifp)
 {
   struct ospf6_interface *oi;
+  int iobuflen;
 
   oi = (struct ospf6_interface *) ifp->info;
   if (oi == NULL)
     return;
 
-  oi->ifmtu = ifp->mtu;
+  /* Try to adust I/O buffer size with IfMtu */
+  iobuflen = ospf6_iobuf_size (ifp->mtu);
+  if (iobuflen < ifp->mtu)
+    {
+      zlog_info ("Interface %s: IfMtu is adjusted to I/O buffer size: %d.",
+                 ifp->name, iobuflen);
+      oi->ifmtu = iobuflen;
+    }
+  else
+    oi->ifmtu = ifp->mtu;
 
   /* interface start */
   if (oi->area)
diff --git a/ospf6d/ospf6_lsa.c b/ospf6d/ospf6_lsa.c
index 13e9a07..5204c23 100644
--- a/ospf6d/ospf6_lsa.c
+++ b/ospf6d/ospf6_lsa.c
@@ -386,10 +386,6 @@
            ntohs (lsa->header->length), VTY_NEWLINE);
   vty_out (vty, "    Prev: %p This: %p Next: %p%s",
            lsa->prev, lsa, lsa->next, VTY_NEWLINE);
-  vty_out (vty, "    Reference count: %ld%s", lsa->refcnt, VTY_NEWLINE);
-  vty_out (vty, "    Reference source: %s (%p) %s",
-           (lsa->refsrc ? lsa->refsrc->name : "None"),
-           lsa->refsrc, VTY_NEWLINE);
   vty_out (vty, "%s", VTY_NEWLINE);
 }
 
@@ -535,9 +531,6 @@
   copy->originated = lsa->originated;
   copy->scope = lsa->scope;
 
-  copy->refsrc = lsa;
-  copy->refsrc->refcnt++;
-
   return copy;
 }
 
@@ -560,9 +553,6 @@
   if (lsa->lock != 0)
     return;
 
-  if (lsa->refsrc)
-    lsa->refsrc->refcnt--;
-
   ospf6_lsa_delete (lsa);
 }
 
diff --git a/ospf6d/ospf6_lsa.h b/ospf6d/ospf6_lsa.h
index 8b9d5f3..1f88f92 100644
--- a/ospf6d/ospf6_lsa.h
+++ b/ospf6d/ospf6_lsa.h
@@ -120,9 +120,7 @@
 
   void                *scope;      /* pointer to scope data structure */
   int                  headeronly; /* indicate this is LS header only */
-
-  unsigned long        refcnt;
-  struct ospf6_lsa    *refsrc;
+  int                  onretrans;
 
   /* lsa instance */
   struct ospf6_lsa_header *header;
diff --git a/ospf6d/ospf6_lsdb.h b/ospf6d/ospf6_lsdb.h
index 94dfcb6..4ec722b 100644
--- a/ospf6d/ospf6_lsdb.h
+++ b/ospf6d/ospf6_lsdb.h
@@ -121,7 +121,7 @@
       {                                                                  \
         if (! OSPF6_LSA_IS_MAXAGE (lsa))                                 \
           continue;                                                      \
-        if (lsa->refcnt != 0)                                            \
+        if (lsa->onretrans != 0)                                         \
           continue;                                                      \
         if (IS_OSPF6_DEBUG_LSA (TIMER))                                  \
           zlog_info (" remove maxage %s", lsa->name);                    \
diff --git a/ospf6d/ospf6_main.c b/ospf6d/ospf6_main.c
index 4dfcdee..c22e90b 100644
--- a/ospf6d/ospf6_main.c
+++ b/ospf6d/ospf6_main.c
@@ -20,11 +20,11 @@
  */
 
 #include <zebra.h>
+#include <lib/version.h>
 
 #include "getopt.h"
 #include "thread.h"
 #include "log.h"
-#include "version.h"
 #include "command.h"
 #include "vty.h"
 #include "memory.h"
diff --git a/ospf6d/ospf6_message.c b/ospf6d/ospf6_message.c
index 21b799e..19ea2c7 100644
--- a/ospf6d/ospf6_message.c
+++ b/ospf6d/ospf6_message.c
@@ -21,6 +21,7 @@
 
 #include <zebra.h>
 
+#include "memory.h"
 #include "log.h"
 #include "vty.h"
 #include "command.h"
@@ -1090,6 +1091,7 @@
       if (IS_OSPF6_DEBUG_LSA (DATABASE))
         zlog_info ("remove %s from retrans_list of %s",
                    mine->name, on->name);
+      ospf6_decrement_onretrans (mine);
       ospf6_lsdb_remove (mine, on->retrans_list);
       ospf6_lsa_delete (his);
     }
@@ -1101,8 +1103,36 @@
     }
 }
 
-char recvbuf[OSPF6_MESSAGE_BUFSIZ];
-char sendbuf[OSPF6_MESSAGE_BUFSIZ];
+char *recvbuf = NULL;
+char *sendbuf = NULL;
+int iobuflen = 0;
+
+int
+ospf6_iobuf_size (int size)
+{
+  char *recvnew, *sendnew;
+
+  if (size <= iobuflen)
+    return iobuflen;
+
+  recvnew = XMALLOC (MTYPE_OSPF6_MESSAGE, size);
+  sendnew = XMALLOC (MTYPE_OSPF6_MESSAGE, size);
+  if (recvnew == NULL || sendnew == NULL)
+    {
+      zlog_info ("Could not allocate I/O buffer of size %d.", size);
+      return iobuflen;
+    }
+
+  if (recvbuf)
+    XFREE (MTYPE_OSPF6_MESSAGE, recvbuf);
+  if (sendbuf)
+    XFREE (MTYPE_OSPF6_MESSAGE, sendbuf);
+  recvbuf = recvnew;
+  sendbuf = sendnew;
+  iobuflen = size;
+
+  return iobuflen;
+}
 
 int
 ospf6_receive (struct thread *thread)
@@ -1120,15 +1150,15 @@
   thread_add_read (master, ospf6_receive, NULL, sockfd);
 
   /* initialize */
-  memset (recvbuf, 0, sizeof (recvbuf));
+  memset (recvbuf, 0, iobuflen);
   iovector[0].iov_base = recvbuf;
-  iovector[0].iov_len = sizeof (recvbuf);
+  iovector[0].iov_len = iobuflen;
   iovector[1].iov_base = NULL;
   iovector[1].iov_len = 0;
 
   /* receive message */
   len = ospf6_recvmsg (&src, &dst, &ifindex, iovector);
-  if (len > sizeof (recvbuf))
+  if (len > iobuflen)
     {
       zlog_err ("Excess message read");
       return 0;
@@ -1314,7 +1344,7 @@
   oi->thread_send_hello = thread_add_timer (master, ospf6_hello_send,
                                             oi, oi->hello_interval);
 
-  memset (sendbuf, 0, sizeof (sendbuf));
+  memset (sendbuf, 0, iobuflen);
   oh = (struct ospf6_header *) sendbuf;
   hello = (struct ospf6_hello *)((caddr_t) oh + sizeof (struct ospf6_header));
 
@@ -1381,7 +1411,7 @@
       thread_add_timer (master, ospf6_dbdesc_send, on,
                         on->ospf6_if->rxmt_interval);
 
-  memset (sendbuf, 0, sizeof (sendbuf));
+  memset (sendbuf, 0, iobuflen);
   oh = (struct ospf6_header *) sendbuf;
   dbdesc = (struct ospf6_dbdesc *)((caddr_t) oh +
                                    sizeof (struct ospf6_header));
@@ -1510,7 +1540,7 @@
     thread_add_timer (master, ospf6_lsreq_send, on,
                       on->ospf6_if->rxmt_interval);
 
-  memset (sendbuf, 0, sizeof (sendbuf));
+  memset (sendbuf, 0, iobuflen);
   oh = (struct ospf6_header *) sendbuf;
 
   /* set Request entries in lsreq */
@@ -1569,7 +1599,7 @@
   if (IS_OSPF6_DEBUG_LSA (SEND))
     zlog_info ("LSA Send to %s", on->name);
 
-  memset (sendbuf, 0, sizeof (sendbuf));
+  memset (sendbuf, 0, iobuflen);
   oh = (struct ospf6_header *) sendbuf;
   lsupdate = (struct ospf6_lsupdate *)
     ((caddr_t) oh + sizeof (struct ospf6_header));
@@ -1671,7 +1701,7 @@
   if (IS_OSPF6_DEBUG_LSA (SEND))
     zlog_info ("LSA Send to %s", oi->interface->name);
 
-  memset (sendbuf, 0, sizeof (sendbuf));
+  memset (sendbuf, 0, iobuflen);
   oh = (struct ospf6_header *) sendbuf;
   lsupdate = (struct ospf6_lsupdate *)((caddr_t) oh +
                                        sizeof (struct ospf6_header));
@@ -1744,7 +1774,7 @@
   if (on->lsack_list->count == 0)
     return 0;
 
-  memset (sendbuf, 0, sizeof (sendbuf));
+  memset (sendbuf, 0, iobuflen);
   oh = (struct ospf6_header *) sendbuf;
 
   p = (char *)((caddr_t) oh + sizeof (struct ospf6_header));
@@ -1804,7 +1834,7 @@
   if (oi->lsack_list->count == 0)
     return 0;
 
-  memset (sendbuf, 0, sizeof (sendbuf));
+  memset (sendbuf, 0, iobuflen);
   oh = (struct ospf6_header *) sendbuf;
 
   p = (char *)((caddr_t) oh + sizeof (struct ospf6_header));
diff --git a/ospf6d/ospf6_message.h b/ospf6d/ospf6_message.h
index f8be627..186fc74 100644
--- a/ospf6d/ospf6_message.h
+++ b/ospf6d/ospf6_message.h
@@ -122,6 +122,7 @@
 void ospf6_lsupdate_print (struct ospf6_header *);
 void ospf6_lsack_print (struct ospf6_header *);
 
+int ospf6_iobuf_size (int size);
 int ospf6_receive (struct thread *thread);
 
 int ospf6_hello_send (struct thread *thread);
diff --git a/ospf6d/ospf6_neighbor.c b/ospf6d/ospf6_neighbor.c
index acfd1a4..1dc0c7b 100644
--- a/ospf6d/ospf6_neighbor.c
+++ b/ospf6d/ospf6_neighbor.c
@@ -38,6 +38,7 @@
 #include "ospf6_interface.h"
 #include "ospf6_neighbor.h"
 #include "ospf6_intra.h"
+#include "ospf6_flood.h"
 
 unsigned char conf_debug_ospf6_neighbor = 0;
 
@@ -109,9 +110,16 @@
 void
 ospf6_neighbor_delete (struct ospf6_neighbor *on)
 {
+  struct ospf6_lsa *lsa;
+
   ospf6_lsdb_remove_all (on->summary_list);
   ospf6_lsdb_remove_all (on->request_list);
-  ospf6_lsdb_remove_all (on->retrans_list);
+  for (lsa = ospf6_lsdb_head (on->retrans_list); lsa;
+       lsa = ospf6_lsdb_next (lsa))
+    {
+      ospf6_decrement_onretrans (lsa);
+      ospf6_lsdb_remove (lsa, on->retrans_list);
+    }
 
   ospf6_lsdb_remove_all (on->dbdesc_list);
   ospf6_lsdb_remove_all (on->lsreq_list);
@@ -275,7 +283,12 @@
   /* clear ls-list */
   ospf6_lsdb_remove_all (on->summary_list);
   ospf6_lsdb_remove_all (on->request_list);
-  ospf6_lsdb_remove_all (on->retrans_list);
+  for (lsa = ospf6_lsdb_head (on->retrans_list); lsa;
+       lsa = ospf6_lsdb_next (lsa))
+    {
+      ospf6_decrement_onretrans (lsa);
+      ospf6_lsdb_remove (lsa, on->retrans_list);
+    }
 
   /* Interface scoped LSAs */
   for (lsa = ospf6_lsdb_head (on->ospf6_if->lsdb); lsa;
@@ -286,7 +299,10 @@
                    (OSPF6_LSA_IS_MAXAGE (lsa) ? "retrans_list" :
                     "summary_list"), on->name);
       if (OSPF6_LSA_IS_MAXAGE (lsa))
-        ospf6_lsdb_add (ospf6_lsa_copy (lsa), on->retrans_list);
+        {
+          lsa->onretrans++;
+          ospf6_lsdb_add (ospf6_lsa_copy (lsa), on->retrans_list);
+        }
       else
         ospf6_lsdb_add (ospf6_lsa_copy (lsa), on->summary_list);
     }
@@ -300,7 +316,10 @@
                    (OSPF6_LSA_IS_MAXAGE (lsa) ? "retrans_list" :
                     "summary_list"), on->name);
       if (OSPF6_LSA_IS_MAXAGE (lsa))
-        ospf6_lsdb_add (ospf6_lsa_copy (lsa), on->retrans_list);
+        {
+          lsa->onretrans++;
+          ospf6_lsdb_add (ospf6_lsa_copy (lsa), on->retrans_list);
+        }
       else
         ospf6_lsdb_add (ospf6_lsa_copy (lsa), on->summary_list);
     }
@@ -314,7 +333,10 @@
                    (OSPF6_LSA_IS_MAXAGE (lsa) ? "retrans_list" :
                     "summary_list"), on->name);
       if (OSPF6_LSA_IS_MAXAGE (lsa))
-        ospf6_lsdb_add (ospf6_lsa_copy (lsa), on->retrans_list);
+        {
+          lsa->onretrans++;
+          ospf6_lsdb_add (ospf6_lsa_copy (lsa), on->retrans_list);
+        }
       else
         ospf6_lsdb_add (ospf6_lsa_copy (lsa), on->summary_list);
     }
@@ -380,6 +402,7 @@
 adj_ok (struct thread *thread)
 {
   struct ospf6_neighbor *on;
+  struct ospf6_lsa *lsa;
 
   on = (struct ospf6_neighbor *) THREAD_ARG (thread);
   assert (on);
@@ -405,7 +428,12 @@
       ospf6_neighbor_state_change (OSPF6_NEIGHBOR_TWOWAY, on);
       ospf6_lsdb_remove_all (on->summary_list);
       ospf6_lsdb_remove_all (on->request_list);
-      ospf6_lsdb_remove_all (on->retrans_list);
+      for (lsa = ospf6_lsdb_head (on->retrans_list); lsa;
+           lsa = ospf6_lsdb_next (lsa))
+        {
+          ospf6_decrement_onretrans (lsa);
+          ospf6_lsdb_remove (lsa, on->retrans_list);
+        }
     }
 
   return 0;
@@ -415,6 +443,7 @@
 seqnumber_mismatch (struct thread *thread)
 {
   struct ospf6_neighbor *on;
+  struct ospf6_lsa *lsa;
 
   on = (struct ospf6_neighbor *) THREAD_ARG (thread);
   assert (on);
@@ -432,7 +461,12 @@
 
   ospf6_lsdb_remove_all (on->summary_list);
   ospf6_lsdb_remove_all (on->request_list);
-  ospf6_lsdb_remove_all (on->retrans_list);
+  for (lsa = ospf6_lsdb_head (on->retrans_list); lsa;
+       lsa = ospf6_lsdb_next (lsa))
+    {
+      ospf6_decrement_onretrans (lsa);
+      ospf6_lsdb_remove (lsa, on->retrans_list);
+    }
 
   THREAD_OFF (on->thread_send_dbdesc);
   on->thread_send_dbdesc =
@@ -445,6 +479,7 @@
 bad_lsreq (struct thread *thread)
 {
   struct ospf6_neighbor *on;
+  struct ospf6_lsa *lsa;
 
   on = (struct ospf6_neighbor *) THREAD_ARG (thread);
   assert (on);
@@ -462,7 +497,12 @@
 
   ospf6_lsdb_remove_all (on->summary_list);
   ospf6_lsdb_remove_all (on->request_list);
-  ospf6_lsdb_remove_all (on->retrans_list);
+  for (lsa = ospf6_lsdb_head (on->retrans_list); lsa;
+       lsa = ospf6_lsdb_next (lsa))
+    {
+      ospf6_decrement_onretrans (lsa);
+      ospf6_lsdb_remove (lsa, on->retrans_list);
+    }
 
   THREAD_OFF (on->thread_send_dbdesc);
   on->thread_send_dbdesc =
@@ -475,6 +515,7 @@
 oneway_received (struct thread *thread)
 {
   struct ospf6_neighbor *on;
+  struct ospf6_lsa *lsa;
 
   on = (struct ospf6_neighbor *) THREAD_ARG (thread);
   assert (on);
@@ -490,7 +531,12 @@
 
   ospf6_lsdb_remove_all (on->summary_list);
   ospf6_lsdb_remove_all (on->request_list);
-  ospf6_lsdb_remove_all (on->retrans_list);
+  for (lsa = ospf6_lsdb_head (on->retrans_list); lsa;
+       lsa = ospf6_lsdb_next (lsa))
+    {
+      ospf6_decrement_onretrans (lsa);
+      ospf6_lsdb_remove (lsa, on->retrans_list);
+    }
 
   THREAD_OFF (on->thread_send_dbdesc);
   THREAD_OFF (on->thread_send_lsreq);
diff --git a/ospf6d/ospf6d.h b/ospf6d/ospf6d.h
index c08007f..9e261bc 100644
--- a/ospf6d/ospf6d.h
+++ b/ospf6d/ospf6d.h
@@ -22,7 +22,7 @@
 #ifndef OSPF6D_H
 #define OSPF6D_H
 
-#define OSPF6_DAEMON_VERSION    "0.9.7a"
+#define OSPF6_DAEMON_VERSION    "0.9.7c"
 
 /* global variables */
 extern int errno;