[quagga-dev 4153] Re: Bug in long delay networks

Paul Jakma paul at clubi.ie
Tue May 30 12:26:28 BST 2006


On Thu, 11 May 2006, Spagnolo, Phillip A wrote:

> As for the best default value, I don't know the answer.  However, 
> the same problem does not occur with a Cisco router because it 
> keeps the LSAs around for at least a couple hundred seconds.

> This is the sequence of function calls
> -ospf_lsa_flush_area()
>  -MAXAGE LSA   --> set LSA to maxage
>  -ospf_flood_through_area()  --> LSA is flooded throughout area
>  -ospf_lsa_maxage()
>     -OSPF_TIMER_ON (ospf->t_maxage, ospf_maxage_lsa_remover, 2);  -->
> add to maxage list and schedule remover
> -ospf_maxage_lsa_remover()
>  -check if the LSA can be removed????
>    -ospf_flood_through()
>      -ospf_lsa_flush_area() --> already flooded above, so there is no
> need to do it again
>
> Does this make sense?

Not completely ;)

> I don't see why an LSA that has already been maxaged and flooded 
> needs to be reflooded after it has been checked for neighbor state 
> and retransmission count.

It's a bit confused alright, however there is at least one place that 
expects ospf_lsa_maxage() will result in flooding - premature aging 
of sequence-number wrapped LSAs. However, that's something that 
doesn't generally work at the moment anyway. Opaque seems to have 
same expectation.

So the problem is differing expectations of what ospf_lsa_maxage() 
ought to be doing, really.

Something like the attached and completely-untested patch (expanding 
slightly on your proposal) might do the trick - what do you think?

regards,
-- 
Paul Jakma	paul at clubi.ie	paul at jakma.org	Key ID: 64A2FF6A
Fortune:
When it's dark enough you can see the stars.
 		-- Ralph Waldo Emerson,
-------------- next part --------------
diff --git a/ospfd/ospf_flood.c b/ospfd/ospf_flood.c
index d7ab859..71ece7f 100644
--- a/ospfd/ospf_flood.c
+++ b/ospfd/ospf_flood.c
@@ -994,3 +994,33 @@ ospf_lsa_flush_as (struct ospf *ospf, st
   ospf_flood_through_as (ospf, NULL, lsa);
   ospf_lsa_maxage (ospf, lsa);
 }
+
+void
+ospf_lsa_flush (struct ospf *ospf, struct ospf_lsa *lsa)
+{
+  lsa->data->ls_age = htons (OSPF_LSA_MAXAGE);
+  
+  switch (lsa->data->type)
+    {
+      case OSPF_ROUTER_LSA:
+      case OSPF_NETWORK_LSA:
+      case OSPF_SUMMARY_LSA:
+      case OSPF_ASBR_SUMMARY_LSA:
+      case OSPF_AS_NSSA_LSA:
+#ifdef HAVE_OPAQUE_LSA
+      case OSPF_OPAQUE_LINK_LSA:
+      case OSPF_OPAQUE_AREA_LSA:
+#endif /* HAVE_OPAQUE_LSA */
+        ospf_flood_through_area (lsa->area, NULL, lsa);
+        break;
+      case OSPF_AS_EXTERNAL_LSA:
+#ifdef HAVE_OPAQUE_LSA
+      case OSPF_OPAQUE_AS_LSA:
+#endif /* HAVE_OPAQUE_LSA */
+        ospf_flood_through_as (ospf, NULL, lsa);
+        break;
+      default:
+        zlog_info ("%s: Unknown LSA type %u", __func__, lsa->data->type);
+        break;
+    }
+}
diff --git a/ospfd/ospf_flood.h b/ospfd/ospf_flood.h
index 5382e8f..1ab11b8 100644
--- a/ospfd/ospf_flood.h
+++ b/ospfd/ospf_flood.h
@@ -66,6 +66,7 @@ extern void ospf_flood_lsa_area (struct 
 extern void ospf_flood_lsa_as (struct ospf_lsa *);
 extern void ospf_lsa_flush_area (struct ospf_lsa *, struct ospf_area *);
 extern void ospf_lsa_flush_as (struct ospf *, struct ospf_lsa *);
+extern void ospf_lsa_flush (struct ospf *, struct ospf_lsa *);
 extern struct external_info *ospf_external_info_check (struct ospf_lsa *);
 
 extern void ospf_lsdb_init (struct ospf_lsdb *);
diff --git a/ospfd/ospf_lsa.c b/ospfd/ospf_lsa.c
index 7c3be3d..dc93c6f 100644
--- a/ospfd/ospf_lsa.c
+++ b/ospfd/ospf_lsa.c
@@ -2902,7 +2902,7 @@ #endif /* HAVE_OPAQUE_LSA */
                    new->data->type, 
                    inet_ntoa (new->data->id), 
                    lsa);
-      ospf_lsa_maxage (ospf, lsa);
+      ospf_lsa_flush (ospf, lsa);
     }
 
   return new;
@@ -2934,35 +2934,6 @@ ospf_check_nbr_status (struct ospf *ospf
 }
 
 
-#ifdef ORIGINAL_CODING
-/* This function flood the maxaged LSA to DR. */
-void
-ospf_maxage_flood (struct ospf_lsa *lsa)
-{
-  switch (lsa->data->type)
-    {
-    case OSPF_ROUTER_LSA:
-    case OSPF_NETWORK_LSA:
-    case OSPF_SUMMARY_LSA:
-    case OSPF_ASBR_SUMMARY_LSA:
-    case OSPF_AS_NSSA_LSA:
-#ifdef HAVE_OPAQUE_LSA
-    case OSPF_OPAQUE_LINK_LSA:
-    case OSPF_OPAQUE_AREA_LSA:
-#endif /* HAVE_OPAQUE_LSA */
-      ospf_flood_through_area (lsa->area, NULL, lsa);
-      break;
-    case OSPF_AS_EXTERNAL_LSA:
-#ifdef HAVE_OPAQUE_LSA
-    case OSPF_OPAQUE_AS_LSA:
-#endif /* HAVE_OPAQUE_LSA */
-      ospf_flood_through_as (NULL, lsa);
-      break;
-    default:
-      break;
-    }
-}
-#endif /* ORIGINAL_CODING */
 
 static int
 ospf_maxage_lsa_remover (struct thread *thread)
@@ -2998,13 +2969,6 @@ ospf_maxage_lsa_remover (struct thread *
           zlog_debug ("LSA[Type%d:%s]: MaxAge LSA removed from list",
                      lsa->data->type, inet_ntoa (lsa->data->id));
 
-	/* Flood max age LSA. */
-#ifdef ORIGINAL_CODING
-	ospf_maxage_flood (lsa);
-#else /* ORIGINAL_CODING */
-        ospf_flood_through (ospf, NULL, lsa);
-#endif /* ORIGINAL_CODING */
-
 	if (lsa->flags & OSPF_LSA_PREMATURE_AGE)  
           {
             if (IS_DEBUG_OSPF (lsa, LSA_FLOODING))
@@ -3023,7 +2987,8 @@ #endif /* ORIGINAL_CODING */
         neighbor Link state retransmission lists and b) none of the router's
         neighbors are in states Exchange or Loading. */
   if (reschedule)
-    OSPF_TIMER_ON (ospf->t_maxage, ospf_maxage_lsa_remover, 2);
+    OSPF_TIMER_ON (ospf->t_maxage, ospf_maxage_lsa_remover,
+                   ospf->maxage_delay);
 
   return 0;
 }
@@ -3071,7 +3036,8 @@ ospf_lsa_maxage (struct ospf *ospf, stru
   if (IS_DEBUG_OSPF (lsa, LSA_FLOODING))
     zlog_debug ("LSA[%s]: MaxAge LSA remover scheduled.", dump_lsa_key (lsa));
 
-  OSPF_TIMER_ON (ospf->t_maxage, ospf_maxage_lsa_remover, 2);
+  OSPF_TIMER_ON (ospf->t_maxage, ospf_maxage_lsa_remover,
+                 ospf->maxage_delay);
 }
 
 static int
@@ -3431,6 +3397,7 @@ ospf_lsa_flush_schedule (struct ospf *os
   switch (lsa->data->type)
     {
 #ifdef HAVE_OPAQUE_LSA
+    /* Opaque wants to be notified of flushes */
     case OSPF_OPAQUE_LINK_LSA:
     case OSPF_OPAQUE_AREA_LSA:
     case OSPF_OPAQUE_AS_LSA:
@@ -3438,7 +3405,7 @@ #ifdef HAVE_OPAQUE_LSA
       break;
 #endif /* HAVE_OPAQUE_LSA */
     default:
-      ospf_lsa_maxage (ospf, lsa);
+      ospf_lsa_flush (ospf, lsa);
       break;
     }
 
diff --git a/ospfd/ospf_opaque.c b/ospfd/ospf_opaque.c
index f2496cf..a32f4ce 100644
--- a/ospfd/ospf_opaque.c
+++ b/ospfd/ospf_opaque.c
@@ -1630,7 +1630,7 @@ ospf_opaque_lsa_refresh (struct ospf_lsa
         zlog_debug ("LSA[Type%d:%s]: Flush stray Opaque-LSA", lsa->data->type, inet_ntoa (lsa->data->id));
 
       lsa->data->ls_age = htons (OSPF_LSA_MAXAGE);
-      ospf_lsa_maxage (ospf, lsa);
+      ospf_lsa_flush (ospf, lsa);
     }
   else
     (* functab->lsa_refresher)(lsa);
@@ -2108,7 +2108,7 @@ ospf_opaque_lsa_flush_schedule (struct o
     zlog_debug ("Schedule Type-%u Opaque-LSA to FLUSH: [opaque-type=%u, opaque-id=%x]", lsa->data->type, GET_OPAQUE_TYPE (ntohl (lsa->data->id.s_addr)), GET_OPAQUE_ID (ntohl (lsa->data->id.s_addr)));
 
   /* This lsa will be flushed and removed eventually. */
-  ospf_lsa_maxage (lsa0->area->ospf, lsa);
+  ospf_lsa_flush (lsa0->area->ospf, lsa);
 
 out:
   return;
diff --git a/ospfd/ospfd.c b/ospfd/ospfd.c
index 79c4543..e52774f 100644
--- a/ospfd/ospfd.c
+++ b/ospfd/ospfd.c
@@ -181,6 +181,7 @@ ospf_new (void)
   new->spf_hold_multiplier = 1;
 
   /* MaxAge init. */
+  new->maxage_delay = OSFP_LSA_MAXAGE_REMOVE_DELAY_DEFAULT;
   new->maxage_lsa = list_new ();
   new->t_maxage_walker =
     thread_add_timer (master, ospf_lsa_maxage_walker,
diff --git a/ospfd/ospfd.h b/ospfd/ospfd.h
index f2a6109..fb52349 100644
--- a/ospfd/ospfd.h
+++ b/ospfd/ospfd.h
@@ -64,7 +64,6 @@ #define OSPF_DEFAULT_DESTINATION        
 #define OSPF_INITIAL_SEQUENCE_NUMBER    0x80000001
 #define OSPF_MAX_SEQUENCE_NUMBER        0x7fffffff
 
-#define OSPF_LSA_MAXAGE_CHECK_INTERVAL          30
 #define OSPF_NSSA_TRANS_STABLE_DEFAULT		40
 
 #define OSPF_ALLSPFROUTERS              0xe0000005      /* 224.0.0.5 */
@@ -256,8 +255,13 @@ #endif /* HAVE_OPAQUE_LSA */
 #ifdef HAVE_OPAQUE_LSA
   struct thread *t_opaque_lsa_self;	/* Type-11 Opaque-LSAs origin event. */
 #endif /* HAVE_OPAQUE_LSA */
+
+#define OSFP_LSA_MAXAGE_REMOVE_DELAY_DEFAULT	60
+  unsigned int maxage_delay;		/* Delay on Maxage remover timer, sec */
   struct thread *t_maxage;              /* MaxAge LSA remover timer. */
+#define OSPF_LSA_MAXAGE_CHECK_INTERVAL		30
   struct thread *t_maxage_walker;       /* MaxAge LSA checking timer. */
+
   struct thread *t_deferred_shutdown;	/* deferred/stub-router shutdown timer*/
 
   struct thread *t_write;


More information about the Quagga-dev mailing list