View | Details | Raw Unified | Return to bug 779
Collapse All | Expand All

(-)a/src/routing/nix-vector-routing/ipv4-nix-vector-routing.cc (-159 / +144 lines)
 Lines 117-123   Ipv4NixVectorRouting::FlushIpv4RouteCach Link Here 
117
}
117
}
118
118
119
Ptr<NixVector>
119
Ptr<NixVector>
120
Ipv4NixVectorRouting::GetNixVector (Ptr<Node> source, Ipv4Address dest)
120
Ipv4NixVectorRouting::GetNixVector (Ptr<Node> source, Ipv4Address dest, Ptr<NetDevice> oif)
121
{
121
{
122
  NS_LOG_FUNCTION_NOARGS ();
122
  NS_LOG_FUNCTION_NOARGS ();
123
123
 Lines 146-152   Ipv4NixVectorRouting::GetNixVector (Ptr< Link Here 
146
      // otherwise proceed as normal 
146
      // otherwise proceed as normal 
147
      // and build the nix vector
147
      // and build the nix vector
148
      std::vector< Ptr<Node> > parentVector;
148
      std::vector< Ptr<Node> > parentVector;
149
      BFS (NodeList::GetNNodes (), source, destNode, parentVector);
149
150
      BFS (NodeList::GetNNodes (), source, destNode, parentVector, oif);
150
151
151
      if (BuildNixVector (parentVector, source->GetId (), destNode->GetId (), nixVector))
152
      if (BuildNixVector (parentVector, source->GetId (), destNode->GetId (), nixVector))
152
        {
153
        {
 Lines 495-501   Ipv4NixVectorRouting::RouteOutput (Ptr<P Link Here 
495
      NS_LOG_LOGIC ("Nix-vector not in cache, build: ");
496
      NS_LOG_LOGIC ("Nix-vector not in cache, build: ");
496
      // Build the nix-vector, given this node and the
497
      // Build the nix-vector, given this node and the
497
      // dest IP address
498
      // dest IP address
498
      nixVectorInCache = GetNixVector (m_node, header.GetDestination ());
499
      nixVectorInCache = GetNixVector (m_node, header.GetDestination (), oif);
499
500
500
      // cache it
501
      // cache it
501
      m_nixCache.insert (NixMap_t::value_type (header.GetDestination (), nixVectorInCache));
502
      m_nixCache.insert (NixMap_t::value_type (header.GetDestination (), nixVectorInCache));
 Lines 523-540   Ipv4NixVectorRouting::RouteOutput (Ptr<P Link Here 
523
      uint32_t numberOfBits = nixVectorForPacket->BitCount (m_totalNeighbors);
524
      uint32_t numberOfBits = nixVectorForPacket->BitCount (m_totalNeighbors);
524
      uint32_t nodeIndex = nixVectorForPacket->ExtractNeighborIndex (numberOfBits);
525
      uint32_t nodeIndex = nixVectorForPacket->ExtractNeighborIndex (numberOfBits);
525
526
526
      // Possibly search here in a cache for this node index 
527
      // Search here in a cache for this node index 
527
      // and look for a Ipv4Route.  If we have it, don't 
528
      // and look for a Ipv4Route, if output device, 
528
      // need to do the next 3 lines.
529
      // oif, is not specified
529
      rtentry = GetIpv4RouteInCache (header.GetDestination ());
530
      if (!oif)
530
      // not in cache
531
        {
532
          rtentry = GetIpv4RouteInCache (header.GetDestination ());
533
        }
534
      // not in cache or a specified output
535
      // device is to be used
531
      if (!rtentry)
536
      if (!rtentry)
532
        {
537
        {
533
          NS_LOG_LOGIC ("Ipv4Route not in cache, build: ");
538
          NS_LOG_LOGIC ("Ipv4Route not in cache, build: ");
534
          Ipv4Address gatewayIp;
539
          Ipv4Address gatewayIp;
535
          uint32_t index = FindNetDeviceForNixIndex (nodeIndex, gatewayIp);
540
          uint32_t index = FindNetDeviceForNixIndex (nodeIndex, gatewayIp);
541
          int32_t interfaceIndex = 0;
536
542
537
          uint32_t interfaceIndex = (m_ipv4)->GetInterfaceForDevice(m_node->GetDevice(index));
543
          if (!oif)
544
            {
545
              interfaceIndex = (m_ipv4)->GetInterfaceForDevice(m_node->GetDevice(index));
546
            }
547
          else
548
            {
549
              interfaceIndex = (m_ipv4)->GetInterfaceForDevice(oif);
550
            }
551
552
          NS_ASSERT_MSG (interfaceIndex != -1, "Interface index not found for device");
553
538
          Ipv4InterfaceAddress ifAddr = m_ipv4->GetAddress (interfaceIndex, 0);
554
          Ipv4InterfaceAddress ifAddr = m_ipv4->GetAddress (interfaceIndex, 0);
539
555
540
          // start filling in the Ipv4Route info
556
          // start filling in the Ipv4Route info
 Lines 543-549   Ipv4NixVectorRouting::RouteOutput (Ptr<P Link Here 
543
559
544
          rtentry->SetGateway (gatewayIp);
560
          rtentry->SetGateway (gatewayIp);
545
          rtentry->SetDestination (header.GetDestination ());
561
          rtentry->SetDestination (header.GetDestination ());
546
          rtentry->SetOutputDevice (m_ipv4->GetNetDevice (interfaceIndex));
562
563
          if (!oif)
564
            {
565
              rtentry->SetOutputDevice (m_ipv4->GetNetDevice (interfaceIndex));
566
            }
567
          else
568
            {
569
              rtentry->SetOutputDevice (oif);
570
            }
547
571
548
          sockerr = Socket::ERROR_NOTERROR;
572
          sockerr = Socket::ERROR_NOTERROR;
549
573
 Lines 582-724   Ipv4NixVectorRouting::RouteInput (Ptr<co Link Here 
582
  // Get the nix-vector from the packet
606
  // Get the nix-vector from the packet
583
  Ptr<NixVector> nixVector = p->GetNixVector();
607
  Ptr<NixVector> nixVector = p->GetNixVector();
584
608
585
  // make sure it exists, if not something
609
  // If nixVector isn't in packet, something went wrong
586
  // went wrong
610
  NS_ASSERT (nixVector);
587
  if (!nixVector)
611
612
  // Get the interface number that we go out of, by extracting
613
  // from the nix-vector
614
  if (m_totalNeighbors == 0)
588
    {
615
    {
589
      NS_LOG_ERROR ("Nix-vector wasn't in the packet! Rebuild.");
616
      m_totalNeighbors = FindTotalNeighbors ();
617
    }
618
  uint32_t numberOfBits = nixVector->BitCount (m_totalNeighbors);
619
  uint32_t nodeIndex = nixVector->ExtractNeighborIndex (numberOfBits);
590
620
591
      Ptr<NixVector> nixVectorInCache;
621
  rtentry = GetIpv4RouteInCache (header.GetDestination ());
622
  // not in cache
623
  if (!rtentry)
624
    {
625
      NS_LOG_LOGIC ("Ipv4Route not in cache, build: ");
626
      Ipv4Address gatewayIp;
627
      uint32_t index = FindNetDeviceForNixIndex (nodeIndex, gatewayIp);
628
      uint32_t interfaceIndex = (m_ipv4)->GetInterfaceForDevice(m_node->GetDevice(index));
629
      Ipv4InterfaceAddress ifAddr = m_ipv4->GetAddress (interfaceIndex, 0);
592
630
593
      NS_LOG_DEBUG ("Dest IP from header: " << header.GetDestination ());
631
      // start filling in the Ipv4Route info
632
      rtentry = Create<Ipv4Route> ();
633
      rtentry->SetSource (ifAddr.GetLocal ());
594
634
595
      // check if cache
635
      rtentry->SetGateway (gatewayIp);
596
      nixVectorInCache = GetNixVectorInCache(header.GetDestination ());
636
      rtentry->SetDestination (header.GetDestination ());
637
      rtentry->SetOutputDevice (m_ipv4->GetNetDevice (interfaceIndex));
597
638
598
      // not in cache
639
      // add rtentry to cache
599
      if (!nixVectorInCache)
640
      m_ipv4RouteCache.insert(Ipv4RouteMap_t::value_type(header.GetDestination (), rtentry));
600
        {
641
    }
601
          NS_LOG_LOGIC ("RouteInput(): Nix-vector not in cache, build: ");
602
642
603
          // Build the nix-vector, given this node and the
643
  NS_LOG_LOGIC ("At Node " << m_node->GetId() << ", Extracting " << numberOfBits << 
604
          // dest IP address
644
                       " bits from Nix-vector: " << nixVector << " : " << *nixVector);
605
          nixVectorInCache = GetNixVector (m_node, header.GetDestination ());
606
        }
607
645
608
      // path exists
646
  // call the unicast callback
609
      if (nixVectorInCache)
647
  // local deliver is handled by Ipv4StaticRoutingImpl
610
        {
648
  // so this code is never even called if the packet is
611
          NS_LOG_LOGIC ("Nix-vector contents: " << *nixVectorInCache);
649
  // destined for this node.
650
  ucb (rtentry, p, header);
612
651
613
          // cache it
652
  return true;
614
          m_nixCache.insert(NixMap_t::value_type(header.GetDestination (), nixVectorInCache));
615
616
          // create a new nix vector to be used, 
617
          // we want to keep the cached version clean
618
          Ptr<NixVector> nixVectorForPacket;
619
          nixVectorForPacket = CreateObject<NixVector> ();
620
          nixVectorForPacket = nixVectorInCache->Copy(); 
621
622
          // Get the interface number that we go out of, by extracting
623
          // from the nix-vector
624
          if (m_totalNeighbors == 0)
625
            {
626
              m_totalNeighbors = FindTotalNeighbors ();
627
            }
628
          uint32_t numberOfBits = nixVectorForPacket->BitCount (m_totalNeighbors);
629
          uint32_t nodeIndex = nixVectorForPacket->ExtractNeighborIndex (numberOfBits);
630
631
          rtentry = GetIpv4RouteInCache (header.GetDestination ());
632
          // not in cache
633
          if (!rtentry)
634
            {
635
              NS_LOG_LOGIC ("Ipv4Route not in cache, build: ");
636
              Ipv4Address gatewayIp;
637
              uint32_t index = FindNetDeviceForNixIndex (nodeIndex, gatewayIp);
638
639
              uint32_t interfaceIndex = (m_ipv4)->GetInterfaceForDevice(m_node->GetDevice(index));
640
              Ipv4InterfaceAddress ifAddr = m_ipv4->GetAddress (interfaceIndex, 0);
641
642
              // start filling in the Ipv4Route info
643
              rtentry = Create<Ipv4Route> ();
644
              rtentry->SetSource (ifAddr.GetLocal ());
645
646
              rtentry->SetGateway (Ipv4Address(gatewayIp));
647
              rtentry->SetDestination (header.GetDestination ());
648
              rtentry->SetOutputDevice (m_ipv4->GetNetDevice (interfaceIndex));
649
650
              // add rtentry to cache
651
              m_ipv4RouteCache.insert(Ipv4RouteMap_t::value_type(header.GetDestination (), rtentry));
652
            }
653
654
          NS_LOG_LOGIC ("Nix-vector contents: " << *nixVectorInCache << " : Remaining bits: " << nixVectorForPacket->GetRemainingBits());
655
656
          // Add  nix-vector in the packet class 
657
          // have to copy the packet first b/c 
658
          // it is const
659
          Ptr<Packet> newPacket = Create<Packet> ();
660
          newPacket = p->Copy();
661
662
          NS_LOG_LOGIC ("Adding Nix-vector to packet: " << *nixVectorForPacket);
663
          newPacket->SetNixVector(nixVectorForPacket);
664
665
          // call the unicast callback
666
          // local deliver is handled by Ipv4StaticRoutingImpl
667
          // so this code is never even called if the packet is
668
          // destined for this node.
669
          ucb (rtentry, newPacket, header);
670
          return true;
671
        }
672
      else // path doesn't exist
673
        {
674
          NS_LOG_ERROR ("No path to the dest: " << header.GetDestination ());
675
          return false;
676
        }
677
    }
678
  else
679
    {
680
      // Get the interface number that we go out of, by extracting
681
      // from the nix-vector
682
      if (m_totalNeighbors == 0)
683
        {
684
          m_totalNeighbors = FindTotalNeighbors ();
685
        }
686
      uint32_t numberOfBits = nixVector->BitCount (m_totalNeighbors);
687
      uint32_t nodeIndex = nixVector->ExtractNeighborIndex (numberOfBits);
688
689
      rtentry = GetIpv4RouteInCache (header.GetDestination ());
690
      // not in cache
691
      if (!rtentry)
692
        {
693
          NS_LOG_LOGIC ("Ipv4Route not in cache, build: ");
694
          Ipv4Address gatewayIp;
695
          uint32_t index = FindNetDeviceForNixIndex (nodeIndex, gatewayIp);
696
          uint32_t interfaceIndex = (m_ipv4)->GetInterfaceForDevice(m_node->GetDevice(index));
697
          Ipv4InterfaceAddress ifAddr = m_ipv4->GetAddress (interfaceIndex, 0);
698
699
          // start filling in the Ipv4Route info
700
          rtentry = Create<Ipv4Route> ();
701
          rtentry->SetSource (ifAddr.GetLocal ());
702
703
          rtentry->SetGateway (gatewayIp);
704
          rtentry->SetDestination (header.GetDestination ());
705
          rtentry->SetOutputDevice (m_ipv4->GetNetDevice (interfaceIndex));
706
707
          // add rtentry to cache
708
          m_ipv4RouteCache.insert(Ipv4RouteMap_t::value_type(header.GetDestination (), rtentry));
709
        }
710
711
      NS_LOG_LOGIC ("At Node " << m_node->GetId() << ", Extracting " << numberOfBits << 
712
                           " bits from Nix-vector: " << nixVector << " : " << *nixVector);
713
714
      // call the unicast callback
715
      // local deliver is handled by Ipv4StaticRoutingImpl
716
      // so this code is never even called if the packet is
717
      // destined for this node.
718
      ucb (rtentry, p, header);
719
720
      return true;
721
    }
722
}
653
}
723
654
724
// virtual functions from Ipv4RoutingProtocol 
655
// virtual functions from Ipv4RoutingProtocol 
 Lines 744-750   Ipv4NixVectorRouting::NotifyRemoveAddres Link Here 
744
}
675
}
745
676
746
bool
677
bool
747
Ipv4NixVectorRouting::BFS (uint32_t numberOfNodes, Ptr<Node> source, Ptr<Node> dest, std::vector< Ptr<Node> > & parentVector)
678
Ipv4NixVectorRouting::BFS (uint32_t numberOfNodes, Ptr<Node> source, 
679
                           Ptr<Node> dest, std::vector< Ptr<Node> > & parentVector,
680
                           Ptr<NetDevice> oif)
748
{
681
{
749
  NS_LOG_FUNCTION_NOARGS ();
682
  NS_LOG_FUNCTION_NOARGS ();
750
683
 Lines 772-812   Ipv4NixVectorRouting::BFS (uint32_t numb Link Here 
772
          return true;
705
          return true;
773
        }
706
        }
774
707
775
708
      // if this is the first iteration of the loop and a 
776
      // Iterate over the current node's adjacent vertices
709
      // specific output interface was given, make sure 
777
      // and push them into the queue
710
      // we go this way
778
      for (uint32_t i = 0; i < (currNode->GetNDevices ()); i++)
711
      if (currNode == source && oif)
779
        {
712
        {
780
          // Get a net device from the node
781
          // as well as the channel, and figure
782
          // out the adjacent net device
783
          Ptr<NetDevice> localNetDevice = currNode->GetDevice (i);
784
785
          // make sure that we can go this way
713
          // make sure that we can go this way
786
          if (ipv4)
714
          if (ipv4)
787
            {
715
            {
788
              uint32_t interfaceIndex = (ipv4)->GetInterfaceForDevice(currNode->GetDevice(i));
716
              uint32_t interfaceIndex = (ipv4)->GetInterfaceForDevice(oif);
789
              if (!(ipv4->IsUp (interfaceIndex)))
717
              if (!(ipv4->IsUp (interfaceIndex)))
790
                {
718
                {
791
                  NS_LOG_LOGIC ("Ipv4Interface is down");
719
                  NS_LOG_LOGIC ("Ipv4Interface is down");
792
                  continue;
720
                  return false;
793
                }
721
                }
794
            }
722
            }
795
            if (!(localNetDevice->IsLinkUp ()))
723
          if (!(oif->IsLinkUp ()))
796
              {
724
            {
797
                NS_LOG_LOGIC ("Link is down.");
725
              NS_LOG_LOGIC ("Link is down.");
798
                continue;
726
              return false;
799
              }
727
            }
800
          Ptr<Channel> channel = localNetDevice->GetChannel ();
728
          Ptr<Channel> channel = oif->GetChannel ();
801
          if (channel == 0)
729
          if (channel == 0)
802
            { 
730
            { 
803
              continue;
731
              return false;
804
            }
732
            }
805
733
806
          // this function takes in the local net dev, and channnel, and
734
          // this function takes in the local net dev, and channnel, and
807
          // writes to the netDeviceContainer the adjacent net devs
735
          // writes to the netDeviceContainer the adjacent net devs
808
          NetDeviceContainer netDeviceContainer;
736
          NetDeviceContainer netDeviceContainer;
809
          GetAdjacentNetDevices (localNetDevice, channel, netDeviceContainer);
737
          GetAdjacentNetDevices (oif, channel, netDeviceContainer);
810
738
811
          // Finally we can get the adjacent nodes
739
          // Finally we can get the adjacent nodes
812
          // and scan through them.  We push them
740
          // and scan through them.  We push them
 Lines 827-832   Ipv4NixVectorRouting::BFS (uint32_t numb Link Here 
827
                }
755
                }
828
            }
756
            }
829
        }
757
        }
758
      else
759
        {
760
          // Iterate over the current node's adjacent vertices
761
          // and push them into the queue
762
          for (uint32_t i = 0; i < (currNode->GetNDevices ()); i++)
763
            {
764
              // Get a net device from the node
765
              // as well as the channel, and figure
766
              // out the adjacent net device
767
              Ptr<NetDevice> localNetDevice = currNode->GetDevice (i);
768
769
              // make sure that we can go this way
770
              if (ipv4)
771
                {
772
                  uint32_t interfaceIndex = (ipv4)->GetInterfaceForDevice(currNode->GetDevice(i));
773
                  if (!(ipv4->IsUp (interfaceIndex)))
774
                    {
775
                      NS_LOG_LOGIC ("Ipv4Interface is down");
776
                      continue;
777
                    }
778
                }
779
                if (!(localNetDevice->IsLinkUp ()))
780
                  {
781
                    NS_LOG_LOGIC ("Link is down.");
782
                    continue;
783
                  }
784
              Ptr<Channel> channel = localNetDevice->GetChannel ();
785
              if (channel == 0)
786
                { 
787
                  continue;
788
                }
789
790
              // this function takes in the local net dev, and channnel, and
791
              // writes to the netDeviceContainer the adjacent net devs
792
              NetDeviceContainer netDeviceContainer;
793
              GetAdjacentNetDevices (localNetDevice, channel, netDeviceContainer);
794
795
              // Finally we can get the adjacent nodes
796
              // and scan through them.  We push them
797
              // to the greyNode queue, if they aren't 
798
              // already there.
799
              for (NetDeviceContainer::Iterator iter = netDeviceContainer.Begin (); iter != netDeviceContainer.End (); iter++)
800
                {
801
                  Ptr<Node> remoteNode = (*iter)->GetNode ();
802
803
                  // check to see if this node has been pushed before
804
                  // by checking to see if it has a parent
805
                  // if it doesn't (null or 0), then set its parent and 
806
                  // push to the queue
807
                  if (parentVector.at (remoteNode->GetId ()) == 0)
808
                    {
809
                      parentVector.at (remoteNode->GetId ()) = currNode;
810
                      greyNodeList.push (remoteNode);
811
                    }
812
                }
813
            }
814
        }
830
815
831
      // Pop off the head grey node.  We have all its children.
816
      // Pop off the head grey node.  We have all its children.
832
      // It is now black.
817
      // It is now black.
(-)a/src/routing/nix-vector-routing/ipv4-nix-vector-routing.h (-4 / +5 lines)
 Lines 78-86   class Ipv4NixVectorRouting : public Ipv4 Link Here 
78
    void ResetTotalNeighbors (void);
78
    void ResetTotalNeighbors (void);
79
79
80
    /*  takes in the source node and dest IP and calls GetNodeByIp, 
80
    /*  takes in the source node and dest IP and calls GetNodeByIp, 
81
     *  BFS, and BuildNixVector to finally return the built 
81
     *  BFS, accounting for any output interface specified, and finally 
82
     *  nix-vector */
82
     *  BuildNixVector to return the built nix-vector */
83
    Ptr<NixVector> GetNixVector (Ptr<Node>, Ipv4Address);
83
    Ptr<NixVector> GetNixVector (Ptr<Node>, Ipv4Address, Ptr<NetDevice>);
84
84
85
    /* checks the cache based on dest IP for the nix-vector */
85
    /* checks the cache based on dest IP for the nix-vector */
86
    Ptr<NixVector> GetNixVectorInCache (Ipv4Address);
86
    Ptr<NixVector> GetNixVectorInCache (Ipv4Address);
 Lines 124-130   class Ipv4NixVectorRouting : public Ipv4 Link Here 
124
    bool BFS (uint32_t numberOfNodes, 
124
    bool BFS (uint32_t numberOfNodes, 
125
             Ptr<Node> source, 
125
             Ptr<Node> source, 
126
             Ptr<Node> dest, 
126
             Ptr<Node> dest, 
127
             std::vector< Ptr<Node> > & parentVector);
127
             std::vector< Ptr<Node> > & parentVector,
128
             Ptr<NetDevice> oif);
128
129
129
    void DoDispose (void);
130
    void DoDispose (void);
130
131

Return to bug 779