Second part of fixes from Laurent Rabret.
diff --git a/isisd/ChangeLog b/isisd/ChangeLog
index 3dc341f..abaa7e8 100644
--- a/isisd/ChangeLog
+++ b/isisd/ChangeLog
@@ -1,3 +1,15 @@
+2004-09-15 Laurent Rabret <laurent.rabret at francetelecom.com>
+
+	* isis_pdu.c: Fix error in same subnet comparison. The previous
+	  algorithm only worked when netmask % 8 == 0.
+	* isisd.c: Show domain and area passwords in configuration.
+	* iso_checksum.c: Fixed error in the checksum calculation. The previous
+	  algorithm could produce a bad checksum if the 2 complement's vs 1
+	  complement's adaptation was required.
+	* isis_pdu.c: Authentication in LSPs does not mean authentication in
+	  SNPs.
+	* isis_tlv.c: Fix errors in password checking.
+
 2004-09-14 Hasso Tepper <hasso at quagga.net>
 
 	* isis_circuit.c: Mostly cosmetical changes in isis_circuit_add_addr()
diff --git a/isisd/isis_pdu.c b/isisd/isis_pdu.c
index 1ecdab4..cd68528 100644
--- a/isisd/isis_pdu.c
+++ b/isisd/isis_pdu.c
@@ -106,7 +106,7 @@
 ip_same_subnet (struct prefix_ipv4 *ip1, struct in_addr *ip2)
 {
   u_char *addr1, *addr2;
-  int shift, offset;
+  int shift, offset, offsetloop;
   int len;
 
   addr1 = (u_char *) & ip1->prefix.s_addr;
@@ -114,23 +114,15 @@
   len = ip1->prefixlen;
 
   shift = len % PNBBY;
-  offset = len / PNBBY;
+  offsetloop = offset = len / PNBBY;
 
-  while (offset--)
-    {
-      if (addr1[offset] != addr2[offset])
-	{
-	  return 0;
-	}
-    }
+  while (offsetloop--)
+    if (addr1[offsetloop] != addr2[offsetloop])
+      return 0;
 
   if (shift)
-    {
-      if (maskbit[shift] & (addr1[offset] ^ addr2[offset]))
-	{
-	  return 0;
-	}
-    }
+    if (maskbit[shift] & (addr1[offset] ^ addr2[offset]))
+      return 0;
 
   return 1;			/* match  */
 }
@@ -1414,6 +1406,13 @@
       return retval;
     }
 
+  /* FIXME: Authentication in LSPs does not mean authentication in SNPs...
+   * In fact by default IOS only deals with LSPs authentication!!
+   * To force authentication in SNPs, one must specify the 'authenticate
+   * snp' command after 'area-password WORD' or 'domain-password WORD'.
+   * This command is not supported for the moment.
+   */
+#if 0
   (level == 1) ? (passwd = &circuit->area->area_passwd) :
     (passwd = &circuit->area->domain_passwd);
   if (passwd->type)
@@ -1427,6 +1426,7 @@
 	  return ISIS_OK;
 	}
     }
+#endif /* 0 */
 
   /* debug isis snp-packets */
   if (isis->debugs & DEBUG_SNP_PACKETS)
diff --git a/isisd/isis_tlv.c b/isisd/isis_tlv.c
index 273d19c..70b3c17 100644
--- a/isisd/isis_tlv.c
+++ b/isisd/isis_tlv.c
@@ -463,6 +463,7 @@
 	  if (*expected & TLVFLAG_AUTH_INFO)
 	    {
 	      tlvs->auth_info.type = *pnt;
+	      tlvs->auth_info.len = length-1;
 	      pnt++;
 	      memcpy (tlvs->auth_info.passwd, pnt, length - 1);
 	      pnt += length - 1;
@@ -885,7 +886,7 @@
 {
   u_char value[255];
   u_char *pos = value;
-  pos++;
+  *pos++ = ISIS_PASSWD_TYPE_CLEARTXT;
   memcpy (pos, auth_value, auth_len);
 
   return add_tlv (AUTH_INFO, auth_len + 1, value, stream);
diff --git a/isisd/isisd.c b/isisd/isisd.c
index 3c499dc..3fbed0b 100644
--- a/isisd/isisd.c
+++ b/isisd/isisd.c
@@ -1901,6 +1901,19 @@
 		write++;
 	      }
 	  }
+	/* Authentication passwords. */
+	if (area->area_passwd.len > 0)
+	  {
+	    vty_out(vty, " area-password %s%s",
+		    area->area_passwd.passwd, VTY_NEWLINE);
+	    write++; 
+	  }  
+	if (area->domain_passwd.len > 0)
+	  {
+	    vty_out(vty, " domain-password %s%s",
+		    area->domain_passwd.passwd, VTY_NEWLINE);
+	    write++;
+	  }
 #ifdef TOPOLOGY_GENERATE
 	/* seems we save the whole command line here */
 	if (area->top_params)
diff --git a/isisd/iso_checksum.c b/isisd/iso_checksum.c
index e65f6ef..eabe281 100644
--- a/isisd/iso_checksum.c
+++ b/isisd/iso_checksum.c
@@ -42,7 +42,6 @@
  * Verifies that the checksum is correct.
  * Return 0 on correct and 1 on invalid checksum.
  * Based on Annex C.4 of ISO/IEC 8473
- * FIXME: Check for overflow 
  */
 
 int
@@ -52,7 +51,7 @@
   u_int32_t c0;
   u_int32_t c1;
   u_int16_t checksum;
-  int i;
+  int i, partial_len;
 
   p = buffer;
   checksum = 0;
@@ -77,14 +76,21 @@
   c0 = 0;
   c1 = 0;
 
-  for (i = 0; i < len; i++)
+  while (len)
     {
-      c0 = c0 + *(p++);
-      c1 += c0;
-    }
+      partial_len = MIN(len, 5803);
 
-  c0 = c0 % 255;
-  c1 = c1 % 255;
+      for (i = 0; i < partial_len; i++)
+	{
+	  c0 = c0 + *(p++);
+	  c1 += c0;
+	}
+
+      c0 = c0 % 255;
+      c1 = c1 % 255;
+
+      len -= partial_len;
+    }
 
   if (c0 == 0 && c1 == 0)
     return 0;
@@ -96,9 +102,6 @@
  * Creates the checksum. *csum points to the position of the checksum in the 
  * PDU. 
  * Based on Annex C.4 of ISO/IEC 8473
- * we will not overflow until about length of 6000,
- * which is the answer to (255+255n)*n/2 > 2^32
- * so if we have a length of over 5000 we will return zero (for now)
  */
 #define FIXED_CODE
 u_int16_t
@@ -113,7 +116,7 @@
   u_int32_t c1;
   u_int16_t checksum;
   u_int16_t *csum;
-  int i;
+  int i, init_len, partial_len;
 
   checksum = 0;
 
@@ -123,32 +126,34 @@
   csum = (u_int16_t *) (buffer + n);
   *(csum) = checksum;
 
-  /* for the limitation of our implementation */
-  if (len > 5000)
-    {
-      return 0;
-    }
-
   p = buffer;
   c0 = 0;
   c1 = 0;
+  init_len = len;
 
-  for (i = 0; i < len; i++)
+  while (len != 0)
     {
-      c0 = c0 + *(p++);
-      c1 += c0;
+      partial_len = MIN(len, 5803);
+
+      for (i = 0; i < partial_len; i++)
+	{
+	  c0 = c0 + *(p++);
+	  c1 += c0;
+	}
+
+      c0 = c0 % 255;
+      c1 = c1 % 255;
+
+      len -= partial_len;
     }
 
-  c0 = c0 % 255;
-  c1 = c1 % 255;
-
-  mul = (len - n) * (c0);
+  mul = (init_len - n)*(c0);
 
 #ifdef FIXED_CODE
   x = mul - c0 - c1;
   y = c1 - mul - 1;
 
-  if (y >= 0)
+  if (y > 0)
     y++;
   if (x < 0)
     x--;
@@ -159,11 +164,9 @@
   if (x == 0)
     x = 255;
   if (y == 0)
-    y = 255;
+    y = 1;
 
-  x &= 0x00FF;
-
-  checksum = ((y << 8) | x);
+  checksum = (y << 8) | (x & 0xFF);
 
 #else
   x = mul - c0 - c1;