implement SPFIntraAddRouter
authorCraig Dowell <craigdo@ee.washington.edu>
Thu, 12 Jul 2007 22:15:59 -0700
changeset 1084 0be920a99cc4
parent 1083 33b6a589141d
child 1085 c12d61407468
implement SPFIntraAddRouter
src/routing/static-route-manager.cc
src/routing/static-route-manager.h
src/routing/static-router.cc
src/routing/static-router.h
--- a/src/routing/static-route-manager.cc	Thu Jul 12 11:41:59 2007 -0700
+++ b/src/routing/static-route-manager.cc	Thu Jul 12 22:15:59 2007 -0700
@@ -20,6 +20,7 @@
 #include "ns3/fatal-error.h"
 #include "ns3/debug.h"
 #include "ns3/node-list.h"
+#include "ns3/ipv4.h"
 #include "static-router.h"
 #include "static-route-manager.h"
 #include "candidate-queue.h"
@@ -352,6 +353,10 @@
   return 1;
 }
 
+//
+// Figure out which interface that the node represented by v will want to use
+// to send packets to the node represented by w over the link represented by l
+//
 uint32_t
 StaticRouteManager::FindOutgoingInterface (
   SPFVertex* v,
@@ -359,6 +364,12 @@
   StaticRouterLinkRecord* l
   ) 
 {
+  NS_ASSERT_MSG(v == m_spfroot, 
+    "StaticRouterManager""FindOutgoingInterface (): "
+    "The node of interest must be the root node");
+
+  // want interface that v uses to send packets
+
   // Using the Ipv4 public APIs of a node, find the outgoing
   // interface ID corresponding to the link l between vertex v and w
   // where v is the root of the tree
@@ -444,7 +455,6 @@
 void
 StaticRouteManager::SPFIntraAddRouter(SPFVertex* v)
 {
-
    // This vertex has just been added to the SPF tree
    // - the vertex should have a valid m_root_oid corresponding
    //   to the outgoing interface on the root router of the tree
@@ -460,6 +470,75 @@
    //    i.e. Query Interface for the IPv4-route interface
    // ii) for each point-to-point link in v->m_lsa
    //    ipv4-route::AddHostRouteTo(m_linkData, m_root_oid);
+
+  NS_ASSERT_MSG(m_spfroot, 
+    "StaticRouteManager::SPFIntraAddRouter (): Root pointer not set");
+
+  Ipv4Address routerId = m_spfroot->m_vertexId;
+
+  std::vector<Ptr<Node> >::iterator i = NodeList::Begin(); 
+  for (; i != NodeList::End(); i++)
+    {
+      Ptr<Node> node = *i;
+
+      Ptr<StaticRouter> rtr = 
+        node->QueryInterface<StaticRouter> (StaticRouter::iid);
+      NS_ASSERT_MSG(rtr, 
+        "StaticRouteManager::SPFIntraAddRouter (): "
+        "QI for <StaticRouter> interface failed");
+
+      if (rtr->GetRouterId () == routerId)
+        {
+          NS_DEBUG_UNCOND("StaticRouteManager::SPFIntraAddRouter (): "
+            "setting routes for node " << node->GetId ());
+
+          Ptr<Ipv4> ipv4 = node->QueryInterface<Ipv4> (Ipv4::iid);
+          NS_ASSERT_MSG(ipv4, 
+            "StaticRouteManager::SPFIntraAddRouter (): "
+            "QI for <Ipv4> interface failed");
+
+          StaticRouterLSA *lsa = v->m_lsa;
+          NS_ASSERT_MSG(lsa, 
+            "StaticRouteManager::SPFIntraAddRouter (): "
+            "Expected valid LSA in SPFVertex* v");
+
+          uint32_t nLinkRecords = lsa->GetNLinkRecords ();
+
+          NS_ASSERT_MSG((nLinkRecords & 1) == 0,
+            "StaticRouteManager::SPFIntraAddRouter (): "
+            "Expected exen number of Link Records");
+
+          for (uint32_t j = 0; j < nLinkRecords; j += 2)
+            {
+              StaticRouterLinkRecord *lrp2p = lsa->GetLinkRecord (j);
+              NS_ASSERT_MSG(
+                lrp2p->m_linkType == StaticRouterLinkRecord::PointToPoint,
+                "StaticRouteManager::SPFIntraAddRouter (): "
+                "Expected PointToPoint Link Record");
+
+              StaticRouterLinkRecord *lrstub = lsa->GetLinkRecord (j + 1);
+              NS_ASSERT_MSG(
+                lrstub->m_linkType == StaticRouterLinkRecord::StubNetwork,
+                "StaticRouteManager::SPFIntraAddRouter (): "
+                "Expected StubNetwork Link Record");
+//
+// BUGBUG
+//
+// Where does the next hop address come from?
+//
+              NS_ASSERT_MSG(false, "BUGBUG");
+
+              NS_DEBUG_UNCOND("StaticRouteManager::SPFIntraAddRouter (): "
+                "Add route to " << lrp2p->m_linkData <<
+                " using next hop " << lrp2p->m_linkData <<
+                " via interface " << v->m_root_oif);
+
+              ipv4->AddHostRouteTo(lrp2p->m_linkData, lrp2p->m_linkData, 
+                v->m_root_oif);
+            }
+          break;
+        }
+    }
 }
 
 // Add a vertex to the list of children in each of its parents. 
@@ -529,21 +608,21 @@
 {
   bool ok = true;
 
-  CandidateQueue candidate;     // <----------------
+  CandidateQueue candidate;
 
   for (int i = 0; i < 100; ++i)
     {
       SPFVertex *v = new SPFVertex;
       v->m_distanceFromRoot = rand () % 100;
-      candidate.Push (v);               // <----------------
+      candidate.Push (v);
     }
 
   uint32_t lastDistance = 0;
 
   for (int i = 0; i < 100; ++i)
     {
-      SPFVertex *v = candidate.Top ();  // <----------------
-      candidate.Pop ();                 // <----------------
+      SPFVertex *v = candidate.Top ();
+      candidate.Pop ();
       if (v->m_distanceFromRoot < lastDistance)
         {
           ok = false;
--- a/src/routing/static-route-manager.h	Thu Jul 12 11:41:59 2007 -0700
+++ b/src/routing/static-route-manager.h	Thu Jul 12 22:15:59 2007 -0700
@@ -49,7 +49,7 @@
     VertexNetwork
   } m_vertexType;
 
-  Ipv4Address m_vertexId;
+  Ipv4Address m_vertexId;  // router id
 
   StaticRouterLSA* m_lsa;  // This pointer owns LSA for mem. mgmt purposes
 
--- a/src/routing/static-router.cc	Thu Jul 12 11:41:59 2007 -0700
+++ b/src/routing/static-router.cc	Thu Jul 12 22:15:59 2007 -0700
@@ -40,7 +40,8 @@
   : m_linkStateId(lsa.m_linkStateId), m_advertisingRtr(lsa.m_advertisingRtr),
     m_stat(lsa.m_stat)
 {
-  NS_ASSERT_MSG(IsEmpty(), "The LSA must be empty in its constructor!");
+  NS_ASSERT_MSG(IsEmpty(), 
+    "StaticRouterLSA::StaticRouterLSA (): Non-empty LSA in constructor");
   CopyLinkRecords (lsa);
 }
 
@@ -105,6 +106,30 @@
   return m_linkRecords.size ();
 }
 
+  uint32_t
+StaticRouterLSA::GetNLinkRecords (void)
+{
+  return m_linkRecords.size ();
+}
+
+  StaticRouterLinkRecord *
+StaticRouterLSA::GetLinkRecord (uint32_t n)
+{
+  uint32_t j = 0;
+  for ( ListOfLinkRecords_t::iterator i = m_linkRecords.begin ();
+        i != m_linkRecords.end (); 
+        i++, j++)
+    {
+      if (j == n) 
+        {
+          return *i;
+        }
+    }
+  NS_ASSERT_MSG(false, "StaticRouterLSA::GetLinkRecord (): invalid index");
+  return 0;
+}
+
+
   bool
 StaticRouterLSA::IsEmpty (void)
 {
@@ -186,7 +211,9 @@
 StaticRouter::DiscoverLSAs (void)
 {
   NS_DEBUG("StaticRouter::DiscoverLSAs ()");
-  NS_ASSERT_MSG(m_node, "<Node> interface not set");
+  NS_ASSERT_MSG(m_node, 
+    "StaticRouter::DiscoverLSAs (): <Node> interface not set");
+
   ClearLSAs ();
 //
 // We're aggregated to a node.  We need to ask the node for a pointer to its
@@ -194,7 +221,8 @@
 // interfaces lives.
 //
   Ptr<Ipv4> ipv4Local = m_node->QueryInterface<Ipv4> (Ipv4::iid);
-  NS_ASSERT_MSG(ipv4Local, "QI for <Ipv4> interface failed");
+  NS_ASSERT_MSG(ipv4Local, 
+    "StaticRouter::DiscoverLSAs (): QI for <Ipv4> interface failed");
 //
 // We are, for now at least, only going to report RouterLSAs in this method.
 // What this means is that there is going to be one advertisement with some
@@ -257,14 +285,16 @@
 //
       Ptr<Node> nodeRemote = ndRemote->GetNode();
       Ptr<Ipv4> ipv4Remote = nodeRemote->QueryInterface<Ipv4> (Ipv4::iid);
-      NS_ASSERT_MSG(ipv4Remote, "QI for remote <Ipv4> interface failed");
+      NS_ASSERT_MSG(ipv4Remote, 
+        "StaticRouter::DiscoverLSAs (): QI for remote <Ipv4> failed");
 //
 // Per the OSPF spec, we're going to need the remote router ID, so we might as
 // well get it now.
 //
       Ptr<StaticRouter> srRemote = 
         nodeRemote->QueryInterface<StaticRouter> (StaticRouter::iid);
-      NS_ASSERT_MSG(srRemote, "QI for remote <StaticRouter> failed");
+      NS_ASSERT_MSG(srRemote, 
+        "StaticRouter::DiscoverLSAs (): QI for remote <StaticRouter> failed");
       Ipv4Address rtrIdRemote = srRemote->GetRouterId();
       NS_DEBUG("Working with remote router " << rtrIdRemote);
 //
@@ -319,7 +349,7 @@
   bool
 StaticRouter::GetLSA (uint32_t n, StaticRouterLSA &lsa)
 {
-  NS_ASSERT_MSG(lsa.IsEmpty(), "Must pass empty LSA");
+  NS_ASSERT_MSG(lsa.IsEmpty(), "StaticRouter::GetLSA (): Must pass empty LSA");
 //
 // All of the work was done in GetNumLSAs.  All we have to do here is to
 // walk the list of link state advertisements created there and return the 
@@ -355,7 +385,7 @@
 
   uint32_t nDevices = ch->GetNDevices();
   NS_ASSERT_MSG(nDevices == 2, 
-    "Point to point channel with other than two devices is not expected");
+    "StaticRouter::GetAdjacent (): Channel with other than two devices");
 //
 // This is a point to point channel with two endpoints.  Get both of them.
 //
@@ -376,8 +406,8 @@
     }
   else
     {
-      NS_ASSERT_MSG(0, 
-        "Neither channel endpoint thinks it is connected to this net device");
+      NS_ASSERT_MSG(false,
+        "StaticRouter::GetAdjacent (): Wrong or confused channel?");
       return 0;
     }
 }
--- a/src/routing/static-router.h	Thu Jul 12 11:41:59 2007 -0700
+++ b/src/routing/static-router.h	Thu Jul 12 22:15:59 2007 -0700
@@ -125,14 +125,26 @@
    */
   void CopyLinkRecords (StaticRouterLSA& lsa);
   /**
-   * Add a given Static Router Link Record to a given Static Router Link
-   * State Advertisement.
+   * Add a given Static Router Link Record to the LSA.
    *
    * @param lr The Static Router Link Record to be added.
    * @returns The number of link records in the list.
    */
   uint32_t AddLinkRecord (StaticRouterLinkRecord* lr);
   /**
+   * Return the number of Static Router Link Records in the LSA.
+   *
+   * @returns The number of link records in the list.
+   */
+  uint32_t GetNLinkRecords (void);
+  /**
+   * Return a pointer to the specified Static Router Link Record.
+   *
+   * @param n The LSA number desired.
+   * @returns The number of link records in the list.
+   */
+  StaticRouterLinkRecord* GetLinkRecord (uint32_t n);
+  /**
    * Release all of the Static Router Link Records present in the Static
    * Router Link State Advertisement and make the list of link records empty.
    */