diff --git a/src/route/fib-entry.cpp b/src/route/fib-entry.cpp
new file mode 100644
index 0000000..ddb5dbd
--- /dev/null
+++ b/src/route/fib-entry.cpp
@@ -0,0 +1,47 @@
+#include <list>
+#include "fib-entry.hpp"
+#include "nexthop.hpp"
+
+namespace nlsr {
+
+using namespace std;
+
+bool
+FibEntry::isEqualNextHops(Nhl& nhlOther)
+{
+  if (m_nhl.getSize() != nhlOther.getSize())
+  {
+    return false;
+  }
+  else
+  {
+    int nhCount = 0;
+    std::list<NextHop>::iterator it1, it2;
+    for (it1 = m_nhl.getNextHopList().begin(),
+         it2 = nhlOther.getNextHopList().begin() ;
+         it1 != m_nhl.getNextHopList().end() ; it1++, it2++)
+    {
+      if (it1->getConnectingFace() == it2->getConnectingFace())
+      {
+        it1->setRouteCost(it2->getRouteCost());
+        nhCount++;
+      }
+      else
+      {
+        break;
+      }
+    }
+    return nhCount == m_nhl.getSize();
+  }
+}
+
+ostream&
+operator<<(ostream& os, FibEntry fe)
+{
+  os << "Name Prefix: " << fe.getName() << endl;
+  os << "Time to Refresh: " << fe.getTimeToRefresh() << endl;
+  os << fe.getNhl() << endl;
+  return os;
+}
+
+}//namespace nlsr
diff --git a/src/route/fib-entry.hpp b/src/route/fib-entry.hpp
new file mode 100644
index 0000000..66e2e8b
--- /dev/null
+++ b/src/route/fib-entry.hpp
@@ -0,0 +1,98 @@
+#ifndef NLSR_FE_HPP
+#define NLSR_FE_HPP
+
+#include <list>
+#include <iostream>
+#include <ndn-cpp-dev/util/scheduler.hpp>
+
+#include "nexthop.hpp"
+#include "nhl.hpp"
+
+namespace nlsr {
+
+using namespace std;
+
+class FibEntry
+{
+public:
+  FibEntry()
+    : m_name()
+    , m_timeToRefresh(0)
+    , m_seqNo(0)
+    , m_nhl()
+  {
+  }
+
+  FibEntry(string n)
+    : m_timeToRefresh(0)
+    , m_seqNo(0)
+    , m_nhl()
+  {
+    m_name = n;
+  }
+
+  std::string
+  getName() const
+  {
+    return m_name;
+  }
+
+  Nhl&
+  getNhl()
+  {
+    return m_nhl;
+  }
+
+  int
+  getTimeToRefresh() const
+  {
+    return m_timeToRefresh;
+  }
+
+  void
+  setTimeToRefresh(int ttr)
+  {
+    m_timeToRefresh = ttr;
+  }
+
+  void
+  setExpiringEventId(ndn::EventId feid)
+  {
+    m_expiringEventId = feid;
+  }
+
+  ndn::EventId
+  getExpiringEventId() const
+  {
+    return m_expiringEventId;
+  }
+
+  void
+  setSeqNo(int fsn)
+  {
+    m_seqNo = fsn;
+  }
+
+  int
+  getSeqNo()
+  {
+    return m_seqNo;
+  }
+
+  bool
+  isEqualNextHops(Nhl& nhlOther);
+
+private:
+  std::string m_name;
+  int m_timeToRefresh;
+  ndn::EventId m_expiringEventId;
+  int m_seqNo;
+  Nhl m_nhl;
+};
+
+std::ostream&
+operator<<(std::ostream& os, FibEntry fe);
+
+} //namespace nlsr
+
+#endif //NLSR_FE_HPP
diff --git a/src/route/fib.cpp b/src/route/fib.cpp
new file mode 100644
index 0000000..5304d0e
--- /dev/null
+++ b/src/route/fib.cpp
@@ -0,0 +1,186 @@
+#include <list>
+#include "fib-entry.hpp"
+#include "fib.hpp"
+#include "nhl.hpp"
+#include "nlsr.hpp"
+
+
+namespace nlsr {
+
+using namespace std;
+using namespace ndn;
+
+static bool
+fibEntryNameCompare(FibEntry& fe, string name)
+{
+  return fe.getName() == name ;
+}
+
+void
+Fib::cancelScheduledExpiringEvent(Nlsr& pnlsr, EventId eid)
+{
+  pnlsr.getScheduler().cancelEvent(eid);
+}
+
+
+ndn::EventId
+Fib::scheduleEntryRefreshing(Nlsr& pnlsr, string name, int feSeqNum,
+                             int refreshTime)
+{
+  return pnlsr.getScheduler().scheduleEvent(ndn::time::seconds(refreshTime),
+                                            ndn::bind(&Fib::refreshEntry, this, name, feSeqNum));
+}
+
+void
+Fib::refreshEntry(string name, int feSeqNum)
+{
+}
+
+void
+Fib::remove(Nlsr& pnlsr, string name)
+{
+  std::list<FibEntry>::iterator it = std::find_if(m_table.begin(),
+                                                  m_table.end(), bind(&fibEntryNameCompare, _1, name));
+  if (it != m_table.end())
+  {
+    for (std::list<NextHop>::iterator nhit =
+           (*it).getNhl().getNextHopList().begin();
+         nhit != (*it).getNhl().getNextHopList().begin(); nhit++)
+    {
+      //remove entry from NDN-FIB
+    }
+    cancelScheduledExpiringEvent(pnlsr, (*it).getExpiringEventId());
+    m_table.erase(it);
+  }
+}
+
+
+void
+Fib::update(Nlsr& pnlsr, string name, Nhl& nextHopList)
+{
+  std::cout << "Fib::updateFib Called" << std::endl;
+  int startFace = 0;
+  int endFace = getNumberOfFacesForName(nextHopList,
+                                        pnlsr.getConfParameter().getMaxFacesPerPrefix());
+  std::list<FibEntry>::iterator it = std::find_if(m_table.begin(),
+                                                  m_table.end(),
+                                                  bind(&fibEntryNameCompare, _1, name));
+  if (it == m_table.end())
+  {
+    if (nextHopList.getSize() > 0)
+    {
+      nextHopList.sort();
+      FibEntry newEntry(name);
+      std::list<NextHop> nhl = nextHopList.getNextHopList();
+      std::list<NextHop>::iterator nhit = nhl.begin();
+      for (int i = startFace; i < endFace && nhit != nhl.end(); ++nhit, i++)
+      {
+        newEntry.getNhl().addNextHop((*nhit));
+        //Add entry to NDN-FIB
+      }
+      newEntry.getNhl().sort();
+      newEntry.setTimeToRefresh(m_refreshTime);
+      newEntry.setSeqNo(1);
+      newEntry.setExpiringEventId(scheduleEntryRefreshing(pnlsr,
+                                                          name , 1, m_refreshTime));
+      m_table.push_back(newEntry);
+    }
+  }
+  else
+  {
+    std::cout << "Old FIB Entry" << std::endl;
+    if (nextHopList.getSize() > 0)
+    {
+      nextHopList.sort();
+      if (!it->isEqualNextHops(nextHopList))
+      {
+        std::list<NextHop> nhl = nextHopList.getNextHopList();
+        std::list<NextHop>::iterator nhit = nhl.begin();
+        // Add first Entry to NDN-FIB
+        removeHop(pnlsr, it->getNhl(), nhit->getConnectingFace());
+        it->getNhl().reset();
+        it->getNhl().addNextHop((*nhit));
+        ++startFace;
+        ++nhit;
+        for (int i = startFace; i < endFace && nhit != nhl.end(); ++nhit, i++)
+        {
+          it->getNhl().addNextHop((*nhit));
+          //Add Entry to NDN_FIB
+        }
+      }
+      it->setTimeToRefresh(m_refreshTime);
+      cancelScheduledExpiringEvent(pnlsr, it->getExpiringEventId());
+      it->setSeqNo(it->getSeqNo() + 1);
+      (*it).setExpiringEventId(scheduleEntryRefreshing(pnlsr,
+                                                       it->getName() ,
+                                                       it->getSeqNo(), m_refreshTime));
+    }
+    else
+    {
+      remove(pnlsr, name);
+    }
+  }
+}
+
+
+
+void
+Fib::clean(Nlsr& pnlsr)
+{
+  for (std::list<FibEntry>::iterator it = m_table.begin(); it != m_table.end();
+       ++it)
+  {
+    for (std::list<NextHop>::iterator nhit =
+           (*it).getNhl().getNextHopList().begin();
+         nhit != (*it).getNhl().getNextHopList().begin(); nhit++)
+    {
+      cancelScheduledExpiringEvent(pnlsr, (*it).getExpiringEventId());
+      //Remove entry from NDN-FIB
+    }
+  }
+  if (m_table.size() > 0)
+  {
+    m_table.clear();
+  }
+}
+
+int
+Fib::getNumberOfFacesForName(Nhl& nextHopList, int maxFacesPerPrefix)
+{
+  int endFace = 0;
+  if ((maxFacesPerPrefix == 0) || (nextHopList.getSize() <= maxFacesPerPrefix))
+  {
+    return nextHopList.getSize();
+  }
+  else
+  {
+    return maxFacesPerPrefix;
+  }
+  return endFace;
+}
+
+void
+Fib::removeHop(Nlsr& pnlsr, Nhl& nl, int doNotRemoveHopFaceId)
+{
+  for (std::list<NextHop>::iterator it = nl.getNextHopList().begin();
+       it != nl.getNextHopList().end();   ++it)
+  {
+    if (it->getConnectingFace() != doNotRemoveHopFaceId)
+    {
+      //Remove FIB Entry from NDN-FIB
+    }
+  }
+}
+
+void
+Fib::print()
+{
+  cout << "-------------------FIB-----------------------------" << endl;
+  for (std::list<FibEntry>::iterator it = m_table.begin(); it != m_table.end();
+       ++it)
+  {
+    cout << (*it);
+  }
+}
+
+} //namespace nlsr
diff --git a/src/route/fib.hpp b/src/route/fib.hpp
new file mode 100644
index 0000000..f042362
--- /dev/null
+++ b/src/route/fib.hpp
@@ -0,0 +1,63 @@
+#ifndef NLSR_FIB_HPP
+#define NLSR_FIB_HPP
+
+#include <list>
+#include "fib-entry.hpp"
+
+namespace nlsr {
+
+class Nlsr;
+
+using namespace std;
+using namespace ndn;
+
+class Fib
+{
+public:
+  Fib()
+    : m_table()
+    , m_refreshTime(0)
+  {
+  }
+
+  void
+  remove(Nlsr& pnlsr, string name);
+
+  void
+  update(Nlsr& pnlsr, string name, Nhl& nextHopList);
+
+  void
+  clean(Nlsr& pnlsr);
+
+  void
+  setEntryRefreshTime(int fert)
+  {
+    m_refreshTime = fert;
+  }
+
+  void
+  print();
+
+private:
+  void
+  removeHop(Nlsr& pnlsr, Nhl& nl, int doNotRemoveHopFaceId);
+
+  int
+  getNumberOfFacesForName(Nhl& nextHopList, int maxFacesPerPrefix);
+
+  ndn::EventId
+  scheduleEntryRefreshing(Nlsr& pnlsr, string name, int feSeqNum,
+                          int refreshTime);
+  void
+  cancelScheduledExpiringEvent(Nlsr& pnlsr, EventId eid);
+
+  void
+  refreshEntry(string name, int feSeqNum);
+
+private:
+  std::list<FibEntry> m_table;
+  int m_refreshTime;
+};
+
+}//namespace nlsr
+#endif //NLSR_FIB_HPP
diff --git a/src/route/map.cpp b/src/route/map.cpp
new file mode 100644
index 0000000..e7ab979
--- /dev/null
+++ b/src/route/map.cpp
@@ -0,0 +1,125 @@
+#include <iostream>
+#include <list>
+
+#include "nlsr.hpp"
+#include "adjacent.hpp"
+#include "lsa.hpp"
+#include "lsdb.hpp"
+#include "map.hpp"
+
+namespace nlsr {
+
+using namespace std;
+
+ostream&
+operator<< (ostream& os, MapEntry& mpe)
+{
+  os << "MapEntry: ( Router: " << mpe.getRouter() << " Mapping No: ";
+  os << mpe.getMappingNumber() << " )" << endl;
+  return os;
+}
+
+static bool
+mapEntryCompareByRouter(MapEntry& mpe1, string& rtrName)
+{
+  return mpe1.getRouter() == rtrName;
+}
+
+static bool
+mapEntryCompareByMappingNo(MapEntry& mpe1, int mappingNo)
+{
+  return mpe1.getMappingNumber() == mappingNo;
+}
+
+void
+Map::addElement(string& rtrName)
+{
+  MapEntry me(rtrName, m_mappingIndex);
+  if (addElement(me))
+  {
+    m_mappingIndex++;
+  }
+}
+
+bool
+Map::addElement(MapEntry& mpe)
+{
+  //cout << mpe;
+  std::list<MapEntry>::iterator it = std::find_if(m_table.begin(),
+                                                  m_table.end(),
+                                                  bind(&mapEntryCompareByRouter, _1, mpe.getRouter()));
+  if (it == m_table.end())
+  {
+    m_table.push_back(mpe);
+    return true;
+  }
+  return false;
+}
+
+string
+Map::getRouterNameByMappingNo(int mn)
+{
+  std::list<MapEntry>::iterator it = std::find_if(m_table.begin(),
+                                                  m_table.end(),
+                                                  bind(&mapEntryCompareByMappingNo,
+                                                       _1, mn));
+  if (it != m_table.end())
+  {
+    return (*it).getRouter();
+  }
+  return "";
+}
+
+int
+Map::getMappingNoByRouterName(string& rName)
+{
+  std::list<MapEntry>::iterator it = std::find_if(m_table.begin(),
+                                                  m_table.end(),
+                                                  bind(&mapEntryCompareByRouter,
+                                                       _1, rName));
+  if (it != m_table.end())
+  {
+    return (*it).getMappingNumber();
+  }
+  return -1;
+}
+
+void
+Map::createFromAdjLsdb(Nlsr& pnlsr)
+{
+  std::list<AdjLsa> adjLsdb = pnlsr.getLsdb().getAdjLsdb();
+  for (std::list<AdjLsa>::iterator it = adjLsdb.begin();
+       it != adjLsdb.end() ; it++)
+  {
+    string linkStartRouter = (*it).getOrigRouter();
+    addElement(linkStartRouter);
+    std::list<Adjacent> adl = (*it).getAdl().getAdjList();
+    for (std::list<Adjacent>::iterator itAdl = adl.begin();
+         itAdl != adl.end() ; itAdl++)
+    {
+      string linkEndRouter = (*itAdl).getName();
+      addElement(linkEndRouter);
+    }
+  }
+}
+
+void
+Map::reset()
+{
+  m_table.clear();
+  m_mappingIndex = 0;
+}
+
+ostream&
+operator<<(ostream& os, Map& map)
+{
+  os << "---------------Map----------------------" << endl;
+  std::list<MapEntry> ml = map.getMapList();
+  for (std::list<MapEntry>::iterator it = ml.begin(); it != ml.end() ; it++)
+  {
+    os << (*it);
+  }
+  return os;
+}
+
+} //namespace nlsr
diff --git a/src/route/map.hpp b/src/route/map.hpp
new file mode 100644
index 0000000..9c9e6e8
--- /dev/null
+++ b/src/route/map.hpp
@@ -0,0 +1,101 @@
+#ifndef NLSR_MAP_HPP
+#define NLSR_MAP_HPP
+
+#include <iostream>
+#include <list>
+
+#include <ndn-cpp-dev/face.hpp>
+
+namespace nlsr {
+
+class Nlsr;
+
+class MapEntry
+{
+public:
+  MapEntry()
+    : m_router()
+    , m_mappingNumber(-1)
+  {
+  }
+
+  ~MapEntry()
+  {
+  }
+
+  MapEntry(std::string rtr, int mn)
+  {
+    m_router = rtr;
+    m_mappingNumber = mn;
+  }
+
+  std::string
+  getRouter() const
+  {
+    return m_router;
+  }
+
+  int
+  getMappingNumber() const
+  {
+    return m_mappingNumber;
+  }
+
+private:
+  std::string m_router;
+  int m_mappingNumber;
+};
+
+std::ostream&
+operator<<(std::ostream& os, MapEntry& mpe);
+
+class Map
+{
+public:
+  Map()
+    : m_mappingIndex(0)
+  {
+  }
+
+
+  void
+  addElement(std::string& rtrName);
+
+  void
+  createFromAdjLsdb(Nlsr& pnlsr);
+
+  std::string
+  getRouterNameByMappingNo(int mn);
+
+  int
+  getMappingNoByRouterName(std::string& rName);
+
+  void
+  reset();
+
+  std::list<MapEntry>&
+  getMapList()
+  {
+    return m_table;
+  }
+
+  int
+  getMapSize() const
+  {
+    return m_table.size();
+  }
+
+
+private:
+  bool
+  addElement(MapEntry& mpe);
+
+  int m_mappingIndex;
+  std::list<MapEntry> m_table;
+};
+
+std::ostream&
+operator<<(std::ostream& os, Map& map);
+
+} // namespace nlsr
+#endif //NLSR_MAP_HPP
diff --git a/src/route/nexthop.cpp b/src/route/nexthop.cpp
new file mode 100644
index 0000000..0a375b0
--- /dev/null
+++ b/src/route/nexthop.cpp
@@ -0,0 +1,13 @@
+#include "nexthop.hpp"
+
+namespace nlsr {
+
+std::ostream&
+operator<<(std::ostream& os, NextHop& nh)
+{
+  os << "Face: " << nh.getConnectingFace() << "  Route Cost: " <<
+     nh.getRouteCost();
+  return os;
+}
+
+}//namespace nlsr
diff --git a/src/route/nexthop.hpp b/src/route/nexthop.hpp
new file mode 100644
index 0000000..7153e0f
--- /dev/null
+++ b/src/route/nexthop.hpp
@@ -0,0 +1,57 @@
+#ifndef NLSR_NEXTHOP_HPP
+#define NLSR_NEXTHOP_HPP
+
+#include <iostream>
+
+namespace nlsr {
+class NextHop
+{
+public:
+  NextHop()
+    : m_connectingFace(0)
+    , m_routeCost(0)
+  {
+  }
+
+  NextHop(int cf, double rc)
+  {
+    m_connectingFace = cf;
+    m_routeCost = rc;
+  }
+
+  int
+  getConnectingFace() const
+  {
+    return m_connectingFace;
+  }
+
+  void
+  setConnectingFace(int cf)
+  {
+    m_connectingFace = cf;
+  }
+
+  double
+  getRouteCost() const
+  {
+    return m_routeCost;
+  }
+
+  void
+  setRouteCost(double rc)
+  {
+    m_routeCost = rc;
+  }
+
+private:
+  int m_connectingFace;
+  double m_routeCost;
+};
+
+
+std::ostream&
+operator<<(std::ostream& os, NextHop& nh);
+
+}//namespace nlsr
+
+#endif //NLSR_NEXTHOP_HPP
diff --git a/src/route/nhl.cpp b/src/route/nhl.cpp
new file mode 100644
index 0000000..50d6303
--- /dev/null
+++ b/src/route/nhl.cpp
@@ -0,0 +1,88 @@
+#include <iostream>
+#include "nhl.hpp"
+#include "nexthop.hpp"
+
+namespace nlsr {
+
+using namespace std;
+
+static bool
+nexthopCompare(NextHop& nh1, NextHop& nh2)
+{
+  return nh1.getConnectingFace() == nh2.getConnectingFace();
+}
+
+static bool
+nexthopRemoveCompare(NextHop& nh1, NextHop& nh2)
+{
+  return (nh1.getConnectingFace() == nh2.getConnectingFace() &&
+          nh1.getRouteCost() == nh2.getRouteCost()) ;
+}
+
+static bool
+nextHopSortingComparator(const NextHop& nh1, const NextHop& nh2)
+{
+  return nh1.getRouteCost() < nh2.getRouteCost();
+}
+
+/**
+Add next hop to the Next Hop list
+If next hop is new it is added
+If next hop already exists in next
+hop list then updates the route
+cost with new next hop's route cost
+*/
+
+void
+Nhl::addNextHop(NextHop& nh)
+{
+  std::list<NextHop>::iterator it = std::find_if(m_nexthopList.begin(),
+                                                 m_nexthopList.end(),
+                                                 bind(&nexthopCompare, _1, nh));
+  if (it == m_nexthopList.end())
+  {
+    m_nexthopList.push_back(nh);
+  }
+  if ((*it).getRouteCost() > nh.getRouteCost())
+  {
+    (*it).setRouteCost(nh.getRouteCost());
+  }
+}
+
+/**
+Remove a next hop only if both next hop face and route cost are same
+
+*/
+
+void
+Nhl::removeNextHop(NextHop& nh)
+{
+  std::list<NextHop>::iterator it = std::find_if(m_nexthopList.begin(),
+                                                 m_nexthopList.end(),
+                                                 bind(&nexthopRemoveCompare, _1, nh));
+  if (it != m_nexthopList.end())
+  {
+    m_nexthopList.erase(it);
+  }
+}
+
+void
+Nhl::sort()
+{
+  m_nexthopList.sort(nextHopSortingComparator);
+}
+
+ostream&
+operator<<(ostream& os, Nhl& nhl)
+{
+  std::list<NextHop> nexthopList = nhl.getNextHopList();
+  int i = 1;
+  for (std::list<NextHop>::iterator it = nexthopList.begin();
+       it != nexthopList.end() ; it++, i++)
+  {
+    os << "Nexthop " << i << ": " << (*it) << endl;
+  }
+  return os;
+}
+
+}//namespace nlsr
diff --git a/src/route/nhl.hpp b/src/route/nhl.hpp
new file mode 100644
index 0000000..ef43373
--- /dev/null
+++ b/src/route/nhl.hpp
@@ -0,0 +1,63 @@
+#ifndef NLSR_NHL_HPP
+#define NLSR_NHL_HPP
+
+#include <ndn-cpp-dev/face.hpp>
+#include <list>
+#include <iostream>
+
+#include "nexthop.hpp"
+#include "adjacent.hpp"
+
+namespace nlsr {
+
+class Nhl
+{
+public:
+  Nhl()
+    : m_nexthopList()
+  {
+  }
+
+  ~Nhl()
+  {
+  }
+  void
+  addNextHop(NextHop& nh);
+
+  void
+  removeNextHop(NextHop& nh);
+
+  void
+  sort();
+
+  int
+  getSize()
+  {
+    return m_nexthopList.size();
+  }
+
+  void
+  reset()
+  {
+    if (m_nexthopList.size() > 0)
+    {
+      m_nexthopList.clear();
+    }
+  }
+
+  std::list<NextHop>&
+  getNextHopList()
+  {
+    return m_nexthopList;
+  }
+
+private:
+  std::list<NextHop> m_nexthopList;
+};
+
+std::ostream&
+operator<<(std::ostream& os, Nhl& nhl);
+
+}//namespace nlsr
+
+#endif //NLSR_NLH_HPP
diff --git a/src/route/nlsr_fe.cpp b/src/route/nlsr_fe.cpp
deleted file mode 100644
index cc724fe..0000000
--- a/src/route/nlsr_fe.cpp
+++ /dev/null
@@ -1,51 +0,0 @@
-#include <list>
-#include "nlsr_fe.hpp"
-#include "nlsr_nexthop.hpp"
-#include "utility/nlsr_logger.hpp"
-
-#define THIS_FILE "nlsr_fe.cpp"
-
-namespace nlsr
-{
-
-  using namespace std;
-
-  bool
-  FibEntry::isEqualNextHops(Nhl& nhlOther)
-  {
-    if ( m_nhl.getSize() != nhlOther.getSize() )
-    {
-      return false;
-    }
-    else
-    {
-      int nhCount=0;
-      std::list<NextHop>::iterator it1, it2;
-      for ( it1=m_nhl.getNextHopList().begin(),
-            it2 = nhlOther.getNextHopList().begin() ;
-            it1 != m_nhl.getNextHopList().end() ; it1++, it2++)
-      {
-        if (it1->getConnectingFace() == it2->getConnectingFace() )
-        {
-          it1->setRouteCost(it2->getRouteCost());
-          nhCount++;
-        }
-        else
-        {
-          break;
-        }
-      }
-      return nhCount == m_nhl.getSize();
-    }
-  }
-
-  ostream&
-  operator<<(ostream& os, FibEntry fe)
-  {
-    os<<"Name Prefix: "<<fe.getName()<<endl;
-    os<<"Time to Refresh: "<<fe.getTimeToRefresh()<<endl;
-    os<<fe.getNhl()<<endl;
-    return os;
-  }
-
-}//namespace nlsr
diff --git a/src/route/nlsr_fe.hpp b/src/route/nlsr_fe.hpp
deleted file mode 100644
index 3cac2fc..0000000
--- a/src/route/nlsr_fe.hpp
+++ /dev/null
@@ -1,89 +0,0 @@
-#ifndef NLSR_FE_HPP
-#define NLSR_FE_HPP
-
-#include<list>
-#include <iostream>
-#include <ndn-cpp-dev/util/scheduler.hpp>
-
-#include "nlsr_nexthop.hpp"
-#include "nlsr_nhl.hpp"
-
-namespace nlsr
-{
-
-  using namespace std;
-
-  class FibEntry
-  {
-  public:
-    FibEntry()
-      : m_name()
-      , m_timeToRefresh(0)
-      , m_seqNo(0)
-      , m_nhl()
-    {
-    }
-
-    FibEntry(string n)
-      : m_timeToRefresh(0)
-      , m_seqNo(0)
-      , m_nhl()
-    {
-      m_name=n;
-    }
-
-    string getName()
-    {
-      return m_name;
-    }
-
-    Nhl& getNhl()
-    {
-      return m_nhl;
-    }
-
-    int getTimeToRefresh()
-    {
-      return m_timeToRefresh;
-    }
-
-    void setTimeToRefresh(int ttr)
-    {
-      m_timeToRefresh=ttr;
-    }
-
-    void setExpiringEventId(ndn::EventId feid)
-    {
-      m_expiringEventId=feid;
-    }
-
-    ndn::EventId getExpiringEventId()
-    {
-      return m_expiringEventId;
-    }
-
-    void setSeqNo(int fsn)
-    {
-      m_seqNo=fsn;
-    }
-
-    int getSeqNo()
-    {
-      return m_seqNo;
-    }
-
-    bool isEqualNextHops(Nhl& nhlOther);
-
-  private:
-    string m_name;
-    int m_timeToRefresh;
-    ndn::EventId m_expiringEventId;
-    int m_seqNo;
-    Nhl m_nhl;
-  };
-
-  ostream& operator<<(ostream& os,FibEntry fe);
-
-} //namespace nlsr
-
-#endif
diff --git a/src/route/nlsr_fib.cpp b/src/route/nlsr_fib.cpp
deleted file mode 100644
index 141bf3a..0000000
--- a/src/route/nlsr_fib.cpp
+++ /dev/null
@@ -1,186 +0,0 @@
-#include<list>
-#include "nlsr_fe.hpp"
-#include "nlsr_fib.hpp"
-#include "nlsr_nhl.hpp"
-#include "nlsr.hpp"
-#include "utility/nlsr_logger.hpp"
-
-#define THIS_FILE "nlsr_fib.cpp"
-
-namespace nlsr
-{
-
-  using namespace std;
-  using namespace ndn;
-
-  static bool
-  fibEntryNameCompare(FibEntry& fe, string name)
-  {
-    return fe.getName() == name ;
-  }
-
-  void
-  Fib::cancelScheduledExpiringEvent(Nlsr& pnlsr, EventId eid)
-  {
-    pnlsr.getScheduler().cancelEvent(eid);
-  }
-
-
-  ndn::EventId
-  Fib::scheduleEntryRefreshing(Nlsr& pnlsr, string name, int feSeqNum,
-                                  int refreshTime)
-  {
-    return pnlsr.getScheduler().scheduleEvent(ndn::time::seconds(refreshTime),
-           ndn::bind(&Fib::refreshEntry,this,name,feSeqNum));
-  }
-
-  void
-  Fib::refreshEntry(string name, int feSeqNum)
-  {
-  }
-
-  void
-  Fib::remove(Nlsr& pnlsr, string name)
-  {
-    std::list<FibEntry >::iterator it = std::find_if( m_table.begin(),
-                                        m_table.end(), bind(&fibEntryNameCompare, _1, name));
-    if( it != m_table.end() )
-    {
-      for(std::list<NextHop>::iterator nhit=(*it).getNhl().getNextHopList().begin();
-          nhit != (*it).getNhl().getNextHopList().begin(); nhit++)
-      {
-        //remove entry from NDN-FIB
-      }
-      cancelScheduledExpiringEvent(pnlsr, (*it).getExpiringEventId());
-      m_table.erase(it);
-    }
-  }
-
-
-  void
-  Fib::update(Nlsr& pnlsr,string name, Nhl& nextHopList)
-  {
-    std::cout<<"Fib::updateFib Called"<<std::endl;
-    int startFace=0;
-    int endFace=getNumberOfFacesForName(nextHopList,
-                                        pnlsr.getConfParameter().getMaxFacesPerPrefix());
-    std::list<FibEntry >::iterator it = std::find_if( m_table.begin(),
-                                        m_table.end(),
-                                        bind(&fibEntryNameCompare, _1, name));
-    if( it == m_table.end() )
-    {
-      if( nextHopList.getSize() > 0 )
-      {
-        nextHopList.sort();
-        FibEntry newEntry(name);
-        std::list<NextHop> nhl=nextHopList.getNextHopList();
-        std::list<NextHop>::iterator nhit=nhl.begin();
-        for(int i=startFace; i< endFace && nhit!=nhl.end(); ++nhit, i++)
-        {
-          newEntry.getNhl().addNextHop((*nhit));
-          //Add entry to NDN-FIB
-        }
-        newEntry.getNhl().sort();
-        newEntry.setTimeToRefresh(m_refreshTime);
-        newEntry.setSeqNo(1);
-        newEntry.setExpiringEventId(scheduleEntryRefreshing(pnlsr,
-                                      name ,1,m_refreshTime));
-        m_table.push_back(newEntry);
-      }
-    }
-    else
-    {
-      std::cout<<"Old FIB Entry"<<std::endl;
-      if( nextHopList.getSize() > 0 )
-      {
-        nextHopList.sort();
-        if ( !it->isEqualNextHops(nextHopList) )
-        {
-          std::list<NextHop> nhl=nextHopList.getNextHopList();
-          std::list<NextHop>::iterator nhit=nhl.begin();
-          // Add first Entry to NDN-FIB
-          removeHop(pnlsr, it->getNhl(),nhit->getConnectingFace());
-          it->getNhl().reset();
-          it->getNhl().addNextHop((*nhit));
-          ++startFace;
-          ++nhit;
-          for(int i=startFace; i< endFace && nhit!=nhl.end(); ++nhit, i++)
-          {
-            it->getNhl().addNextHop((*nhit));
-            //Add Entry to NDN_FIB
-          }
-        }
-        it->setTimeToRefresh(m_refreshTime);
-        cancelScheduledExpiringEvent(pnlsr, it->getExpiringEventId());
-        it->setSeqNo(it->getSeqNo()+1);
-        (*it).setExpiringEventId(scheduleEntryRefreshing(pnlsr,
-                                   it->getName() ,
-                                   it->getSeqNo(),m_refreshTime));
-      }
-      else
-      {
-        remove(pnlsr,name);
-      }
-    }
-  }
-
-
-
-  void Fib::clean(Nlsr& pnlsr)
-  {
-    for( std::list<FibEntry >::iterator it=m_table.begin(); it != m_table.end();
-         ++it)
-    {
-      for(std::list<NextHop>::iterator nhit=(*it).getNhl().getNextHopList().begin();
-          nhit != (*it).getNhl().getNextHopList().begin(); nhit++)
-      {
-        cancelScheduledExpiringEvent(pnlsr,(*it).getExpiringEventId());
-        //Remove entry from NDN-FIB
-      }
-    }
-    if ( m_table.size() > 0 )
-    {
-      m_table.clear();
-    }
-  }
-
-  int
-  Fib::getNumberOfFacesForName(Nhl& nextHopList, int maxFacesPerPrefix)
-  {
-    int endFace=0;
-    if((maxFacesPerPrefix == 0) || (nextHopList.getSize() <= maxFacesPerPrefix))
-    {
-      return nextHopList.getSize();
-    }
-    else
-    {
-      return maxFacesPerPrefix;
-    }
-    return endFace;
-  }
-
-  void
-  Fib::removeHop(Nlsr& pnlsr, Nhl& nl, int doNotRemoveHopFaceId)
-  {
-    for( std::list<NextHop >::iterator it=nl.getNextHopList().begin();
-         it != nl.getNextHopList().end();   ++it)
-    {
-      if ( it->getConnectingFace() != doNotRemoveHopFaceId )
-      {
-        //Remove FIB Entry from NDN-FIB
-      }
-    }
-  }
-
-  void
-  Fib::print()
-  {
-    cout<<"-------------------FIB-----------------------------"<<endl;
-    for(std::list<FibEntry>::iterator it = m_table.begin(); it!=m_table.end();
-        ++it)
-    {
-      cout<<(*it);
-    }
-  }
-
-} //namespace nlsr
diff --git a/src/route/nlsr_fib.hpp b/src/route/nlsr_fib.hpp
deleted file mode 100644
index b36d0d8..0000000
--- a/src/route/nlsr_fib.hpp
+++ /dev/null
@@ -1,49 +0,0 @@
-#ifndef NLSR_FIB_HPP
-#define NLSR_FIB_HPP
-
-#include <list>
-#include "nlsr_fe.hpp"
-
-namespace nlsr
-{
-
-  class Nlsr;
-
-  using namespace std;
-  using namespace ndn;
-
-  class Fib
-  {
-  public:
-    Fib()
-      : m_table()
-      , m_refreshTime(0)
-    {
-    }
-
-    void remove(Nlsr& pnlsr, string name);
-    void update(Nlsr& pnlsr, string name, Nhl& nextHopList);
-    void clean(Nlsr& pnlsr);
-    void setEntryRefreshTime(int fert)
-    {
-      m_refreshTime=fert;
-    }
-
-    void print();
-
-  private:
-    void removeHop(Nlsr& pnlsr, Nhl& nl, int doNotRemoveHopFaceId);
-    int getNumberOfFacesForName(Nhl& nextHopList, int maxFacesPerPrefix);
-    ndn::EventId
-    scheduleEntryRefreshing(Nlsr& pnlsr, string name, int feSeqNum,
-                               int refreshTime);
-    void cancelScheduledExpiringEvent(Nlsr& pnlsr, EventId eid);
-    void refreshEntry(string name, int feSeqNum);
-
-  private:
-    std::list<FibEntry> m_table;
-    int m_refreshTime;
-  };
-
-}//namespace nlsr
-#endif
diff --git a/src/route/nlsr_map.cpp b/src/route/nlsr_map.cpp
deleted file mode 100644
index f08f1ae..0000000
--- a/src/route/nlsr_map.cpp
+++ /dev/null
@@ -1,127 +0,0 @@
-#include<iostream>
-#include<list>
-
-#include "nlsr.hpp"
-#include "nlsr_adjacent.hpp"
-#include "nlsr_lsa.hpp"
-#include "nlsr_lsdb.hpp"
-#include "nlsr_map.hpp"
-#include "utility/nlsr_logger.hpp"
-
-#define THIS_FILE "nlsr_map.cpp"
-
-namespace nlsr
-{
-
-  using namespace std;
-
-  ostream&
-  operator<<(ostream& os, MapEntry& mpe)
-  {
-    os<<"MapEntry: ( Router: "<<mpe.getRouter()<<" Mapping No: ";
-    os<<mpe.getMappingNumber()<<" )"<<endl;
-    return os;
-  }
-
-  static bool
-  mapEntryCompareByRouter(MapEntry& mpe1, string& rtrName)
-  {
-    return mpe1.getRouter()==rtrName;
-  }
-
-  static bool
-  mapEntryCompareByMappingNo(MapEntry& mpe1, int mappingNo)
-  {
-    return mpe1.getMappingNumber()==mappingNo;
-  }
-
-  void
-  Map::addElement(string& rtrName)
-  {
-    MapEntry me(rtrName,m_mappingIndex);
-    if (  addElement(me) )
-    {
-      m_mappingIndex++;
-    }
-  }
-
-  bool
-  Map::addElement(MapEntry& mpe)
-  {
-    //cout << mpe;
-    std::list<MapEntry >::iterator it = std::find_if( m_table.begin(),
-                                        m_table.end(),
-                                        bind(&mapEntryCompareByRouter, _1, mpe.getRouter()));
-    if ( it == m_table.end() )
-    {
-      m_table.push_back(mpe);
-      return true;
-    }
-    return false;
-  }
-
-  string
-  Map::getRouterNameByMappingNo(int mn)
-  {
-    std::list<MapEntry >::iterator it = std::find_if( m_table.begin(),
-                                        m_table.end(),
-                                        bind(&mapEntryCompareByMappingNo, _1, mn));
-    if ( it != m_table.end() )
-    {
-      return (*it).getRouter();
-    }
-    return "";
-  }
-
-  int
-  Map::getMappingNoByRouterName(string& rName)
-  {
-    std::list<MapEntry >::iterator it = std::find_if( m_table.begin(),
-                                        m_table.end(),
-                                        bind(&mapEntryCompareByRouter, _1, rName));
-    if ( it != m_table.end() )
-    {
-      return (*it).getMappingNumber();
-    }
-    return -1;
-  }
-
-  void
-  Map::createFromAdjLsdb(Nlsr& pnlsr)
-  {
-    std::list<AdjLsa> adjLsdb=pnlsr.getLsdb().getAdjLsdb();
-    for( std::list<AdjLsa>::iterator it=adjLsdb.begin();
-         it!= adjLsdb.end() ; it++)
-    {
-      string linkStartRouter=(*it).getOrigRouter();
-      addElement(linkStartRouter);
-      std::list<Adjacent> adl=(*it).getAdl().getAdjList();
-      for( std::list<Adjacent>::iterator itAdl=adl.begin();
-           itAdl!= adl.end() ; itAdl++)
-      {
-        string linkEndRouter=(*itAdl).getName();
-        addElement(linkEndRouter);
-      }
-    }
-  }
-
-  void
-  Map::reset()
-  {
-    m_table.clear();
-    m_mappingIndex=0;
-  }
-
-  ostream&
-  operator<<(ostream& os, Map& map)
-  {
-    os<<"---------------Map----------------------"<<endl;
-    std::list< MapEntry > ml=map.getMapList();
-    for( std::list<MapEntry>::iterator it=ml.begin(); it!= ml.end() ; it++)
-    {
-      os<< (*it);
-    }
-    return os;
-  }
-
-} //namespace nlsr
diff --git a/src/route/nlsr_map.hpp b/src/route/nlsr_map.hpp
deleted file mode 100644
index bf50aac..0000000
--- a/src/route/nlsr_map.hpp
+++ /dev/null
@@ -1,88 +0,0 @@
-#ifndef NLSR_MAP_HPP
-#define NLSR_MAP_HPP
-
-#include <iostream>
-#include <list>
-
-#include <ndn-cpp-dev/face.hpp>
-
-namespace nlsr
-{
-
-  class Nlsr;
-
-  using namespace std;
-
-  class MapEntry
-  {
-  public:
-    MapEntry()
-      : m_router()
-      , m_mappingNumber(-1)
-    {
-    }
-
-    ~MapEntry()
-    {
-    }
-
-    MapEntry(string rtr, int mn)
-    {
-      m_router=rtr;
-      m_mappingNumber=mn;
-    }
-
-    string getRouter()
-    {
-      return m_router;
-    }
-
-    int getMappingNumber()
-    {
-      return m_mappingNumber;
-    }
-  private:
-    string m_router;
-    int m_mappingNumber;
-  };
-
-  ostream&
-  operator<<(ostream& os, MapEntry& mpe);
-
-  class Map
-  {
-  public:
-    Map()
-      : m_mappingIndex(0)
-    {
-    }
-
-
-    void addElement(string& rtrName);
-    void createFromAdjLsdb(Nlsr& pnlsr);
-    string getRouterNameByMappingNo(int mn);
-    int getMappingNoByRouterName(string& rName);
-    void reset();
-    std::list< MapEntry >& getMapList()
-    {
-      return m_table;
-    }
-
-    int getMapSize()
-    {
-      return m_table.size();
-    }
-
-
-  private:
-    bool addElement(MapEntry& mpe);
-
-    int m_mappingIndex;
-    std::list< MapEntry > m_table;
-  };
-
-  ostream&
-  operator<<(ostream& os, Map& map);
-
-} // namespace nlsr
-#endif
diff --git a/src/route/nlsr_nexthop.cpp b/src/route/nlsr_nexthop.cpp
deleted file mode 100644
index 08dfe62..0000000
--- a/src/route/nlsr_nexthop.cpp
+++ /dev/null
@@ -1,15 +0,0 @@
-#include "nlsr_nexthop.hpp"
-#include "utility/nlsr_logger.hpp"
-#define THIS_FILE "nlsr_nexthop.cpp"
-
-namespace nlsr
-{
-
-  ostream&
-  operator<<(ostream& os, NextHop& nh)
-  {
-    os<<"Face: "<<nh.getConnectingFace()<<"  Route Cost: "<<nh.getRouteCost();
-    return os;
-  }
-
-}//namespace nlsr
diff --git a/src/route/nlsr_nexthop.hpp b/src/route/nlsr_nexthop.hpp
deleted file mode 100644
index 0105fb6..0000000
--- a/src/route/nlsr_nexthop.hpp
+++ /dev/null
@@ -1,56 +0,0 @@
-#ifndef NLSR_NEXTHOP_HPP
-#define NLSR_NEXTHOP_HPP
-
-#include<iostream>
-
-namespace nlsr
-{
-
-  using namespace std;
-
-  class NextHop
-  {
-  public:
-    NextHop()
-      : m_connectingFace(0)
-      , m_routeCost(0)
-    {
-    }
-
-    NextHop(int cf, double rc)
-    {
-      m_connectingFace=cf;
-      m_routeCost=rc;
-    }
-
-    int getConnectingFace() const
-    {
-      return m_connectingFace;
-    }
-
-    void setConnectingFace(int cf)
-    {
-      m_connectingFace=cf;
-    }
-
-    double getRouteCost() const
-    {
-      return m_routeCost;
-    }
-
-    void setRouteCost(double rc)
-    {
-      m_routeCost=rc;
-    }
-  private:
-    int m_connectingFace;
-    double m_routeCost;
-  };
-
-
-  ostream&
-  operator<<(ostream& os, NextHop& nh);
-
-}//namespace nlsr
-
-#endif
diff --git a/src/route/nlsr_nhl.cpp b/src/route/nlsr_nhl.cpp
deleted file mode 100644
index ed769c9..0000000
--- a/src/route/nlsr_nhl.cpp
+++ /dev/null
@@ -1,92 +0,0 @@
-#include <iostream>
-#include "utility/nlsr_logger.hpp"
-#include "nlsr_nhl.hpp"
-#include "nlsr_nexthop.hpp"
-
-#define THIS_FILE "nlsr_nhl.cpp"
-
-namespace nlsr
-{
-
-  using namespace std;
-
-  static bool
-  nexthopCompare(NextHop& nh1, NextHop& nh2)
-  {
-    return nh1.getConnectingFace()==nh2.getConnectingFace();
-  }
-
-  static bool
-  nexthopRemoveCompare(NextHop& nh1, NextHop& nh2)
-  {
-    return (nh1.getConnectingFace()==nh2.getConnectingFace() &&
-            nh1.getRouteCost() == nh2.getRouteCost()) ;
-  }
-
-  static bool
-  nextHopSortingComparator(const NextHop& nh1, const NextHop& nh2)
-  {
-    return nh1.getRouteCost() < nh2.getRouteCost();
-  }
-
-  /**
-  Add next hop to the Next Hop list
-  If next hop is new it is added
-  If next hop already exists in next
-  hop list then updates the route
-  cost with new next hop's route cost
-  */
-
-  void
-  Nhl::addNextHop(NextHop& nh)
-  {
-    std::list<NextHop >::iterator it = std::find_if( m_nexthopList.begin(),
-                                       m_nexthopList.end(),
-                                       bind(&nexthopCompare, _1, nh));
-    if ( it == m_nexthopList.end() )
-    {
-      m_nexthopList.push_back(nh);
-    }
-    if ( (*it).getRouteCost() > nh.getRouteCost() )
-    {
-      (*it).setRouteCost(nh.getRouteCost());
-    }
-  }
-
-  /**
-  Remove a next hop only if both next hop face and route cost are same
-
-  */
-
-  void
-  Nhl::removeNextHop(NextHop &nh)
-  {
-    std::list<NextHop >::iterator it = std::find_if( m_nexthopList.begin(),
-                                       m_nexthopList.end(),
-                                       bind(&nexthopRemoveCompare, _1, nh));
-    if ( it != m_nexthopList.end() )
-    {
-      m_nexthopList.erase(it);
-    }
-  }
-
-  void
-  Nhl::sort()
-  {
-    m_nexthopList.sort(nextHopSortingComparator);
-  }
-
-  ostream&
-  operator<<(ostream& os, Nhl& nhl)
-  {
-    std::list< NextHop > nexthopList = nhl.getNextHopList();
-    int i=1;
-    for( std::list<NextHop>::iterator it=nexthopList.begin();
-         it!= nexthopList.end() ; it++,i++)
-    {
-      os << "Nexthop "<<i<<": "<<(*it)<<endl;
-    }
-    return os;
-  }
-
-}//namespace nlsr
diff --git a/src/route/nlsr_nhl.hpp b/src/route/nlsr_nhl.hpp
deleted file mode 100644
index fd8b4ca..0000000
--- a/src/route/nlsr_nhl.hpp
+++ /dev/null
@@ -1,55 +0,0 @@
-#ifndef NLSR_NHL_HPP
-#define NLSR_NHL_HPP
-
-#include <ndn-cpp-dev/face.hpp>
-#include "nlsr_adjacent.hpp"
-#include <list>
-#include <iostream>
-
-#include "nlsr_nexthop.hpp"
-
-namespace nlsr
-{
-
-  using namespace std;
-
-  class Nhl
-  {
-  public:
-    Nhl()
-      : m_nexthopList()
-    {
-    }
-
-    ~Nhl()
-    {
-    }
-    void addNextHop(NextHop &nh);
-    void removeNextHop(NextHop &nh);
-    void sort();
-    int getSize()
-    {
-      return m_nexthopList.size();
-    }
-    void reset()
-    {
-      if (m_nexthopList.size() > 0 )
-      {
-        m_nexthopList.clear();
-      }
-    }
-    std::list< NextHop >& getNextHopList()
-    {
-      return m_nexthopList;
-    }
-
-  private:
-    std::list< NextHop > m_nexthopList;
-  };
-
-  ostream&
-  operator<<(ostream& os, Nhl& nhl);
-
-}//namespace nlsr
-
-#endif
diff --git a/src/route/nlsr_npt.cpp b/src/route/nlsr_npt.cpp
deleted file mode 100644
index 89eba30..0000000
--- a/src/route/nlsr_npt.cpp
+++ /dev/null
@@ -1,151 +0,0 @@
-#include <list>
-#include <utility>
-#include <algorithm>
-#include "utility/nlsr_logger.hpp"
-#include "nlsr_npt.hpp"
-#include "nlsr_npte.hpp"
-#include "nlsr.hpp"
-
-#define THIS_FILE "nlsr_npt.cpp"
-
-namespace nlsr
-{
-
-  using namespace std;
-
-  static bool
-  npteCompare(Npte& npte, string& name)
-  {
-    return npte.getNamePrefix()==name;
-  }
-
-
-
-  void
-  Npt::addNpte(string name, RoutingTableEntry& rte, Nlsr& pnlsr)
-  {
-    std::list<Npte >::iterator it = std::find_if( m_npteList.begin(),
-                                    m_npteList.end(), bind(&npteCompare, _1, name));
-    if ( it == m_npteList.end() )
-    {
-      Npte newEntry(name);
-      newEntry.addRoutingTableEntry(rte);
-      newEntry.generateNhlfromRteList();
-      newEntry.getNhl().sort();
-      m_npteList.push_back(newEntry);
-      if(rte.getNhl().getSize()> 0)
-      {
-        pnlsr.getFib().update(pnlsr, name,newEntry.getNhl());
-      }
-    }
-    else
-    {
-      if ( rte.getNhl().getSize()> 0 )
-      {
-        (*it).addRoutingTableEntry(rte);
-        (*it).generateNhlfromRteList();
-        (*it).getNhl().sort();
-        pnlsr.getFib().update(pnlsr, name,(*it).getNhl());
-      }
-      else
-      {
-        (*it).resetRteListNextHop();
-        (*it).getNhl().reset();
-        pnlsr.getFib().remove(pnlsr,name);
-      }
-    }
-  }
-
-  void
-  Npt::removeNpte(string name, RoutingTableEntry& rte, Nlsr& pnlsr)
-  {
-    std::list<Npte >::iterator it = std::find_if( m_npteList.begin(),
-                                    m_npteList.end(), bind(&npteCompare, _1, name));
-    if ( it != m_npteList.end() )
-    {
-      string destRouter=rte.getDestination();
-      (*it).removeRoutingTableEntry(rte);
-      if ( ((*it).getRteListSize() == 0 ) &&
-           (!pnlsr.getLsdb().doesLsaExist(destRouter+"/1",1) ) &&
-           (!pnlsr.getLsdb().doesLsaExist(destRouter+"/2",2) ) &&
-           (!pnlsr.getLsdb().doesLsaExist(destRouter+"/3",3) )   )
-      {
-        m_npteList.erase(it);
-        pnlsr.getFib().remove(pnlsr,name);
-      }
-      else
-      {
-        (*it).generateNhlfromRteList();
-        pnlsr.getFib().update(pnlsr, name,(*it).getNhl());
-      }
-    }
-  }
-
-
-  void
-  Npt::addNpteByDestName(string name, string destRouter, Nlsr& pnlsr)
-  {
-    std::pair<RoutingTableEntry& , bool> rteCheck=
-      pnlsr.getRoutingTable().findRoutingTableEntry(destRouter);
-    if(rteCheck.second)
-    {
-      addNpte(name,rteCheck.first,pnlsr);
-    }
-    else
-    {
-      RoutingTableEntry rte(destRouter);
-      addNpte(name, rte,pnlsr);
-    }
-  }
-
-  void
-  Npt::removeNpte(string name, string destRouter, Nlsr& pnlsr)
-  {
-    std::pair<RoutingTableEntry& , bool> rteCheck=
-      pnlsr.getRoutingTable().findRoutingTableEntry(destRouter);
-    if(rteCheck.second)
-    {
-      removeNpte(name,rteCheck.first,pnlsr);
-    }
-    else
-    {
-      RoutingTableEntry rte(destRouter);
-      removeNpte(name, rte,pnlsr);
-    }
-  }
-
-  void
-  Npt::updateWithNewRoute(Nlsr& pnlsr)
-  {
-    for(std::list<Npte >::iterator it=m_npteList.begin(); it!=m_npteList.end(); ++it)
-    {
-      std::list<RoutingTableEntry> rteList=(*it).getRteList();
-      for(std::list<RoutingTableEntry >::iterator rteit=rteList.begin();
-          rteit !=rteList.end(); ++rteit)
-      {
-        std::pair<RoutingTableEntry& , bool> rteCheck=
-          pnlsr.getRoutingTable().findRoutingTableEntry((*rteit).getDestination());
-        if(rteCheck.second)
-        {
-          addNpte((*it).getNamePrefix(),rteCheck.first,pnlsr);
-        }
-        else
-        {
-          RoutingTableEntry rte((*rteit).getDestination());
-          addNpte((*it).getNamePrefix(), rte,pnlsr);
-        }
-      }
-    }
-  }
-
-  void
-  Npt::print()
-  {
-    cout<<"----------------NPT----------------------"<<endl;
-    for(std::list<Npte >::iterator it=m_npteList.begin(); it!=m_npteList.end(); ++it)
-    {
-      cout <<(*it)<<endl;
-    }
-  }
-
-}
diff --git a/src/route/nlsr_npt.hpp b/src/route/nlsr_npt.hpp
deleted file mode 100644
index 89af33d..0000000
--- a/src/route/nlsr_npt.hpp
+++ /dev/null
@@ -1,34 +0,0 @@
-#ifndef NLSR_NPT_HPP
-#define NLSR_NPT_HPP
-
-#include <list>
-#include "nlsr_npte.hpp"
-#include "nlsr_rte.hpp"
-
-namespace nlsr
-{
-
-  using namespace std;
-
-  class Nlsr;
-
-  class Npt
-  {
-  public:
-    Npt()
-    {
-    }
-    void addNpteByDestName(string name, string destRouter, Nlsr& pnlsr);
-    void removeNpte(string name, string destRouter, Nlsr& pnlsr);
-    void updateWithNewRoute(Nlsr& pnlsr);
-    void print();
-  private:
-    void addNpte(string name, RoutingTableEntry& rte, Nlsr& pnlsr);
-    void removeNpte(string name, RoutingTableEntry& rte, Nlsr& pnlsr);
-  private:
-    std::list<Npte> m_npteList;
-  };
-
-}//namespace nlsr
-
-#endif
diff --git a/src/route/nlsr_npte.cpp b/src/route/nlsr_npte.cpp
deleted file mode 100644
index d8e83c3..0000000
--- a/src/route/nlsr_npte.cpp
+++ /dev/null
@@ -1,86 +0,0 @@
-#include <list>
-#include <utility>
-#include "nlsr_npte.hpp"
-#include "nlsr_rte.hpp"
-#include "nlsr_nexthop.hpp"
-#include "utility/nlsr_logger.hpp"
-
-#define THIS_FILE "nlsr_npte.cpp"
-
-namespace nlsr
-{
-
-  using namespace std;
-
-  void
-  Npte::generateNhlfromRteList()
-  {
-    m_nhl.reset();
-    for( std::list<RoutingTableEntry>::iterator it=m_rteList.begin();
-         it != m_rteList.end(); ++it )
-    {
-      for(std::list< NextHop >::iterator nhit=(*it).getNhl().getNextHopList().begin();
-          nhit != (*it).getNhl().getNextHopList().end(); ++nhit)
-      {
-        m_nhl.addNextHop((*nhit));
-      }
-    }
-  }
-
-
-
-  static bool
-  rteCompare(RoutingTableEntry& rte, string& destRouter)
-  {
-    return rte.getDestination()==destRouter;
-  }
-
-  void
-  Npte::removeRoutingTableEntry(RoutingTableEntry& rte)
-  {
-    std::list<RoutingTableEntry >::iterator it = std::find_if( m_rteList.begin(),
-        m_rteList.end(),
-        bind(&rteCompare, _1, rte.getDestination()));
-    if ( it != m_rteList.end() )
-    {
-      m_rteList.erase(it);
-    }
-  }
-
-  void
-  Npte::addRoutingTableEntry(RoutingTableEntry &rte)
-  {
-    std::list<RoutingTableEntry >::iterator it = std::find_if( m_rteList.begin(),
-        m_rteList.end(),
-        bind(&rteCompare, _1, rte.getDestination()));
-    if ( it == m_rteList.end() )
-    {
-      m_rteList.push_back(rte);
-    }
-    else
-    {
-      (*it).getNhl().reset(); // reseting existing routing table's next hop
-      for(std::list< NextHop >::iterator nhit=rte.getNhl().getNextHopList().begin();
-          nhit != rte.getNhl().getNextHopList().end(); ++nhit)
-      {
-        (*it).getNhl().addNextHop((*nhit));
-      }
-    }
-  }
-
-//debugging purpose
-  ostream&
-  operator<<(ostream& os, Npte& npte)
-  {
-    os<<"Name: "<<npte.getNamePrefix()<<endl;
-    std::list<RoutingTableEntry> rteList=npte.getRteList();
-    for(std::list<RoutingTableEntry >::iterator it=rteList.begin();
-        it !=rteList.end(); ++it)
-    {
-      cout<<(*it);
-    }
-    os<<npte.getNhl();
-    return os;
-  }
-
-}//namespace nlsr
diff --git a/src/route/nlsr_npte.hpp b/src/route/nlsr_npte.hpp
deleted file mode 100644
index bb4b1c8..0000000
--- a/src/route/nlsr_npte.hpp
+++ /dev/null
@@ -1,73 +0,0 @@
-#ifndef NLSR_NPTE_HPP
-#define NLSR_NPTE_HPP
-
-#include <list>
-#include <utility>
-#include "nlsr_rte.hpp"
-
-namespace nlsr
-{
-
-  using namespace std;
-
-  class Npte
-  {
-  public:
-    Npte()
-      : m_namePrefix()
-      , m_nhl()
-    {
-    }
-    Npte(string np)
-      : m_nhl()
-    {
-      m_namePrefix=np;
-    }
-
-    string getNamePrefix()
-    {
-      return m_namePrefix;
-    }
-
-    std::list<RoutingTableEntry>& getRteList()
-    {
-      return m_rteList;
-    }
-
-    void resetRteListNextHop()
-    {
-      if (m_rteList.size() > 0 )
-      {
-        for( std::list<RoutingTableEntry>::iterator it=m_rteList.begin();
-             it != m_rteList.end(); ++it )
-        {
-          (*it).getNhl().reset();
-        }
-      }
-    }
-
-    int getRteListSize()
-    {
-      return m_rteList.size();
-    }
-
-    Nhl& getNhl()
-    {
-      return m_nhl;
-    }
-    void generateNhlfromRteList();
-    void removeRoutingTableEntry(RoutingTableEntry& rte);
-    void addRoutingTableEntry(RoutingTableEntry &rte);
-
-  private:
-    string m_namePrefix;
-    std::list<RoutingTableEntry> m_rteList;
-    Nhl m_nhl;
-  };
-
-  ostream&
-  operator<<(ostream& os, Npte& npte);
-
-}//namespace nlsr
-
-#endif
diff --git a/src/route/nlsr_rt.cpp b/src/route/nlsr_rt.cpp
deleted file mode 100644
index 8267930..0000000
--- a/src/route/nlsr_rt.cpp
+++ /dev/null
@@ -1,236 +0,0 @@
-#include<iostream>
-#include<string>
-#include<list>
-
-#include "nlsr_rt.hpp"
-#include "nlsr.hpp"
-#include "nlsr_map.hpp"
-#include "nlsr_rtc.hpp"
-#include "nlsr_rte.hpp"
-#include "nlsr_npt.hpp"
-#include "utility/nlsr_logger.hpp"
-
-#define THIS_FILE "nlsr_rt.cpp"
-
-namespace nlsr
-{
-
-  using namespace std;
-
-  void
-  RoutingTable::calculate(Nlsr& pnlsr)
-  {
-    //debugging purpose
-    std::cout<<pnlsr.getConfParameter()<<std::endl;
-    pnlsr.getNpt().print();
-    pnlsr.getLsdb().printAdjLsdb();
-    pnlsr.getLsdb().printCorLsdb();
-    pnlsr.getLsdb().printNameLsdb();
-    if ( 	pnlsr.getIsRoutingTableCalculating() == 0 )
-    {
-      pnlsr.setIsRoutingTableCalculating(1); //setting routing table calculation
-      if ( pnlsr.getLsdb().doesLsaExist(
-             pnlsr.getConfParameter().getRouterPrefix()+"/"+"2",2) )
-      {
-        if(pnlsr.getIsBuildAdjLsaSheduled() != 1)
-        {
-          cout<<"CLearing old routing table ....."<<endl;
-          clearRoutingTable();
-          clearDryRoutingTable(); // for dry run options
-          // calculate Link State routing
-          if( (pnlsr.getConfParameter().getIsHyperbolicCalc() == 0 )
-              || (pnlsr.getConfParameter().getIsHyperbolicCalc() == 2 ) )
-          {
-            calculateLsRoutingTable(pnlsr);
-          }
-          //calculate hyperbolic routing
-          if ( pnlsr.getConfParameter().getIsHyperbolicCalc() == 1 )
-          {
-            calculateHypRoutingTable(pnlsr);
-          }
-          //calculate dry hyperbolic routing
-          if ( pnlsr.getConfParameter().getIsHyperbolicCalc() == 2 )
-          {
-            calculateHypDryRoutingTable(pnlsr);
-          }
-          //need to update NPT here
-          pnlsr.getNpt().updateWithNewRoute(pnlsr);
-          //debugging purpose
-          printRoutingTable();
-          pnlsr.getNpt().print();
-          pnlsr.getFib().print();
-          //debugging purpose end
-        }
-        else
-        {
-          cout<<"Adjacency building is scheduled, so ";
-          cout<<"routing table can not be calculated :("<<endl;
-        }
-      }
-      else
-      {
-        cout<<"No Adj LSA of router itself,";
-        cout<<	" so Routing table can not be calculated :("<<endl;
-        clearRoutingTable();
-        clearDryRoutingTable(); // for dry run options
-        // need to update NPT here
-        std::cout<<"Calling Update NPT With new Route"<<std::endl;
-        pnlsr.getNpt().updateWithNewRoute(pnlsr);
-        //debugging purpose
-        printRoutingTable();
-        pnlsr.getNpt().print();
-        pnlsr.getFib().print();
-        //debugging purpose end
-      }
-      pnlsr.setIsRouteCalculationScheduled(0); //clear scheduled flag
-      pnlsr.setIsRoutingTableCalculating(0); //unsetting routing table calculation
-    }
-    else
-    {
-      scheduleRoutingTableCalculation(pnlsr);
-    }
-  }
-
-
-  void
-  RoutingTable::calculateLsRoutingTable(Nlsr& pnlsr)
-  {
-    cout<<"RoutingTable::calculateLsRoutingTable Called"<<endl;
-    Map vMap;
-    vMap.createFromAdjLsdb(pnlsr);
-    int numOfRouter=vMap.getMapSize();
-    LinkStateRoutingTableCalculator lsrtc(numOfRouter);
-    lsrtc.calculatePath(vMap,boost::ref(*this),pnlsr);
-  }
-
-  void
-  RoutingTable::calculateHypRoutingTable(Nlsr& pnlsr)
-  {
-    Map vMap;
-    vMap.createFromAdjLsdb(pnlsr);
-    int numOfRouter=vMap.getMapSize();
-    HypRoutingTableCalculator hrtc(numOfRouter,0);
-    hrtc.calculatePath(vMap,boost::ref(*this),pnlsr);
-  }
-
-  void
-  RoutingTable::calculateHypDryRoutingTable(Nlsr& pnlsr)
-  {
-    Map vMap;
-    vMap.createFromAdjLsdb(pnlsr);
-    int numOfRouter=vMap.getMapSize();
-    HypRoutingTableCalculator hrtc(numOfRouter,1);
-    hrtc.calculatePath(vMap,boost::ref(*this),pnlsr);
-  }
-
-  void
-  RoutingTable::scheduleRoutingTableCalculation(Nlsr& pnlsr)
-  {
-    if ( pnlsr.getIsRouteCalculationScheduled() != 1 )
-    {
-      pnlsr.getScheduler().scheduleEvent(ndn::time::seconds(15),
-                                         ndn::bind(&RoutingTable::calculate,this,boost::ref(pnlsr)));
-      pnlsr.setIsRouteCalculationScheduled(1);
-    }
-  }
-
-  static bool
-  routingTableEntryCompare(RoutingTableEntry& rte, string& destRouter)
-  {
-    return rte.getDestination()==destRouter;
-  }
-
-// function related to manipulation of routing table
-  void
-  RoutingTable::addNextHop(string destRouter, NextHop& nh)
-  {
-    std::pair<RoutingTableEntry&, bool> rte=findRoutingTableEntry(destRouter);
-    if( !rte.second )
-    {
-      RoutingTableEntry rte(destRouter);
-      rte.getNhl().addNextHop(nh);
-      m_rTable.push_back(rte);
-    }
-    else
-    {
-      (rte.first).getNhl().addNextHop(nh);
-    }
-  }
-
-  std::pair<RoutingTableEntry&, bool>
-  RoutingTable::findRoutingTableEntry(string destRouter)
-  {
-    std::list<RoutingTableEntry >::iterator it = std::find_if( m_rTable.begin(),
-        m_rTable.end(),
-        bind(&routingTableEntryCompare, _1, destRouter));
-    if ( it != m_rTable.end() )
-    {
-      return std::make_pair(boost::ref((*it)),true);
-    }
-    RoutingTableEntry rteEmpty;
-    return std::make_pair(boost::ref(rteEmpty),false);
-  }
-
-  void
-  RoutingTable::printRoutingTable()
-  {
-    cout<<"---------------Routing Table------------------"<<endl;
-    for(std::list<RoutingTableEntry>::iterator it=m_rTable.begin() ;
-        it != m_rTable.end(); ++it)
-    {
-      cout<<(*it)<<endl;
-    }
-  }
-
-
-//function related to manipulation of dry routing table
-  void
-  RoutingTable::addNextHopToDryTable(string destRouter, NextHop& nh)
-  {
-    std::list<RoutingTableEntry >::iterator it = std::find_if( m_dryTable.begin(),
-        m_dryTable.end(),
-        bind(&routingTableEntryCompare, _1, destRouter));
-    if ( it == m_dryTable.end() )
-    {
-      RoutingTableEntry rte(destRouter);
-      rte.getNhl().addNextHop(nh);
-      m_dryTable.push_back(rte);
-    }
-    else
-    {
-      (*it).getNhl().addNextHop(nh);
-    }
-  }
-
-  void
-  RoutingTable::printDryRoutingTable()
-  {
-    cout<<"--------Dry Run's Routing Table--------------"<<endl;
-    for(std::list<RoutingTableEntry>::iterator it=m_dryTable.begin() ;
-        it != m_dryTable.end(); ++it)
-    {
-      cout<<(*it)<<endl;
-    }
-  }
-
-
-  void
-  RoutingTable::clearRoutingTable()
-  {
-    if( m_rTable.size() > 0 )
-    {
-      m_rTable.clear();
-    }
-  }
-
-  void
-  RoutingTable::clearDryRoutingTable()
-  {
-    if (m_dryTable.size()>0 )
-    {
-      m_dryTable.clear();
-    }
-  }
-
-}//namespace nlsr
-
diff --git a/src/route/nlsr_rt.hpp b/src/route/nlsr_rt.hpp
deleted file mode 100644
index e382b8b..0000000
--- a/src/route/nlsr_rt.hpp
+++ /dev/null
@@ -1,50 +0,0 @@
-#ifndef NLSR_RT_HPP
-#define NLSR_RT_HPP
-
-#include<iostream>
-#include<utility>
-#include<string>
-
-#include "nlsr_rte.hpp"
-
-namespace nlsr
-{
-
-  class Nlsr;
-  class NextHop;
-
-  using namespace std;
-
-  class RoutingTable
-  {
-  public:
-    RoutingTable()
-      : NO_NEXT_HOP(-12345)
-    {
-    }
-    void calculate(Nlsr& pnlsr);
-    void addNextHop(string destRouter, NextHop& nh);
-    void printRoutingTable();
-
-    void addNextHopToDryTable(string destRouter, NextHop& nh);
-    void printDryRoutingTable();
-    std::pair<RoutingTableEntry&, bool> findRoutingTableEntry(string destRouter);
-    void scheduleRoutingTableCalculation(Nlsr& pnlsr);
-
-  private:
-    void calculateLsRoutingTable(Nlsr& pnlsr);
-    void calculateHypRoutingTable(Nlsr& pnlsr);
-    void calculateHypDryRoutingTable(Nlsr& pnlsr);
-
-    void clearRoutingTable();
-    void clearDryRoutingTable();
-
-    const int NO_NEXT_HOP;
-
-    std::list< RoutingTableEntry > m_rTable;
-    std::list< RoutingTableEntry > m_dryTable;
-  };
-
-}//namespace nlsr
-
-#endif
diff --git a/src/route/nlsr_rtc.cpp b/src/route/nlsr_rtc.cpp
deleted file mode 100644
index c6499f7..0000000
--- a/src/route/nlsr_rtc.cpp
+++ /dev/null
@@ -1,511 +0,0 @@
-#include <iostream>
-#include <cmath>
-#include "nlsr_lsdb.hpp"
-#include "nlsr_rtc.hpp"
-#include "nlsr_map.hpp"
-#include "nlsr_lsa.hpp"
-#include "nlsr_nexthop.hpp"
-#include "nlsr.hpp"
-#include "utility/nlsr_logger.hpp"
-
-#define THIS_FILE "nlsr_rtc.cpp"
-
-namespace nlsr
-{
-
-  using namespace std;
-
-  void
-  RoutingTableCalculator::allocateAdjMatrix()
-  {
-    adjMatrix = new double*[numOfRouter];
-    for(int i = 0; i < numOfRouter; ++i)
-    {
-      adjMatrix[i] = new double[numOfRouter];
-    }
-  }
-
-  void
-  RoutingTableCalculator::initMatrix()
-  {
-    for(int i=0; i<numOfRouter; i++)
-    {
-      for(int j=0; j<numOfRouter; j++)
-        adjMatrix[i][j]=0;
-    }
-  }
-
-  void
-  RoutingTableCalculator::makeAdjMatrix(Nlsr& pnlsr, Map pMap)
-  {
-    std::list<AdjLsa> adjLsdb=pnlsr.getLsdb().getAdjLsdb();
-    for( std::list<AdjLsa>::iterator it=adjLsdb.begin();
-         it!= adjLsdb.end() ; it++)
-    {
-      string linkStartRouter=(*it).getOrigRouter();
-      int row=pMap.getMappingNoByRouterName(linkStartRouter);
-      std::list<Adjacent> adl=(*it).getAdl().getAdjList();
-      for( std::list<Adjacent>::iterator itAdl=adl.begin();
-           itAdl!= adl.end() ; itAdl++)
-      {
-        string linkEndRouter=(*itAdl).getName();
-        int col=pMap.getMappingNoByRouterName(linkEndRouter);
-        double cost=(*itAdl).getLinkCost();
-        if ( (row >= 0 && row<numOfRouter) && (col >= 0 && col<numOfRouter) )
-        {
-          adjMatrix[row][col]=cost;
-        }
-      }
-    }
-  }
-
-  void
-  RoutingTableCalculator::printAdjMatrix()
-  {
-    for(int i=0; i<numOfRouter; i++)
-    {
-      for(int j=0; j<numOfRouter; j++)
-        printf("%f ",adjMatrix[i][j]);
-      printf("\n");
-    }
-  }
-
-  void
-  RoutingTableCalculator::adjustAdMatrix(int source, int link, double linkCost)
-  {
-    for ( int i = 0; i < numOfRouter; i++ )
-    {
-      if ( i == link )
-      {
-        adjMatrix[source][i]=linkCost;
-      }
-      else
-      {
-        adjMatrix[source][i]=0;
-      }
-    }
-  }
-
-  int
-  RoutingTableCalculator::getNumOfLinkfromAdjMatrix(int sRouter)
-  {
-    int noLink=0;
-    for(int i=0; i<numOfRouter; i++)
-    {
-      if ( adjMatrix[sRouter][i] > 0 )
-      {
-        noLink++;
-      }
-    }
-    return noLink;
-  }
-
-  void
-  RoutingTableCalculator::getLinksFromAdjMatrix(int *links,
-      double *linkCosts, int source)
-  {
-    int j=0;
-    for (int i=0; i <numOfRouter; i++)
-    {
-      if ( adjMatrix[source][i] > 0 )
-      {
-        links[j]=i;
-        linkCosts[j]=adjMatrix[source][i];
-        j++;
-      }
-    }
-  }
-
-  void
-  RoutingTableCalculator::freeAdjMatrix()
-  {
-    for(int i = 0; i < numOfRouter; ++i)
-    {
-      delete [] adjMatrix[i];
-    }
-    delete [] adjMatrix;
-  }
-
-
-  void
-  RoutingTableCalculator::allocateLinks()
-  {
-    links=new int[vNoLink];
-  }
-
-  void RoutingTableCalculator::allocateLinkCosts()
-  {
-    linkCosts=new double[vNoLink];
-  }
-
-
-  void
-  RoutingTableCalculator::freeLinks()
-  {
-    delete [] links;
-  }
-  void
-  RoutingTableCalculator::freeLinksCosts()
-  {
-    delete [] linkCosts;
-  }
-
-  void
-  LinkStateRoutingTableCalculator::calculatePath(Map& pMap,
-      RoutingTable& rt, Nlsr& pnlsr)
-  {
-    cout<<"LinkStateRoutingTableCalculator::calculatePath Called"<<endl;
-    allocateAdjMatrix();
-    initMatrix();
-    makeAdjMatrix(pnlsr,pMap);
-    cout<<pMap;
-    printAdjMatrix();
-    string routerName=pnlsr.getConfParameter().getRouterPrefix();
-    int sourceRouter=pMap.getMappingNoByRouterName(routerName);
-    int noLink=getNumOfLinkfromAdjMatrix(sourceRouter);
-    allocateParent();
-    allocateDistance();
-    if ( pnlsr.getConfParameter().getMaxFacesPerPrefix() == 1 )
-    {
-      // Single Path
-      doDijkstraPathCalculation(sourceRouter);
-      // print all ls path -- debugging purpose
-      printAllLsPath(sourceRouter);
-      // update routing table
-      addAllLsNextHopsToRoutingTable(pnlsr, rt, pMap, sourceRouter);
-    }
-    else
-    {
-      // Multi Path
-      setNoLink(getNumOfLinkfromAdjMatrix(sourceRouter));
-      allocateLinks();
-      allocateLinkCosts();
-      getLinksFromAdjMatrix(links, linkCosts, sourceRouter);
-      for (int i=0 ; i < vNoLink; i++)
-      {
-        adjustAdMatrix(sourceRouter,links[i], linkCosts[i]);
-        printAdjMatrix();
-        doDijkstraPathCalculation(sourceRouter);
-        // print all ls path -- debugging purpose
-        printAllLsPath(sourceRouter);
-        //update routing table
-        addAllLsNextHopsToRoutingTable(pnlsr, rt, pMap, sourceRouter);
-      }
-      freeLinks();
-      freeLinksCosts();
-    }
-    freeParent();
-    freeDistance();
-    freeAdjMatrix();
-  }
-
-  void
-  LinkStateRoutingTableCalculator::doDijkstraPathCalculation(int sourceRouter)
-  {
-    int i;
-    int v,u;
-    int *Q=new int[numOfRouter];
-    int head=0;
-    /* Initiate the Parent */
-    for (i = 0 ; i < numOfRouter; i++)
-    {
-      m_parent[i]=EMPTY_PARENT;
-      m_distance[i]=INF_DISTANCE;
-      Q[i]=i;
-    }
-    if ( sourceRouter != NO_MAPPING_NUM )
-    {
-      m_distance[sourceRouter]=0;
-      sortQueueByDistance(Q,m_distance,head,numOfRouter);
-      while (head < numOfRouter )
-      {
-        u=Q[head];
-        if(m_distance[u] == INF_DISTANCE)
-        {
-          break;
-        }
-        for(v=0 ; v <numOfRouter; v++)
-        {
-          if( adjMatrix[u][v] > 0 )
-          {
-            if ( isNotExplored(Q,v,head+1,numOfRouter) )
-            {
-              if( m_distance[u] + adjMatrix[u][v] <  m_distance[v])
-              {
-                m_distance[v]=m_distance[u] + adjMatrix[u][v] ;
-                m_parent[v]=u;
-              }
-            }
-          }
-        }
-        head++;
-        sortQueueByDistance(Q,m_distance,head,numOfRouter);
-      }
-    }
-    delete [] Q;
-  }
-
-  void
-  LinkStateRoutingTableCalculator::addAllLsNextHopsToRoutingTable(Nlsr& pnlsr,
-      RoutingTable& rt, Map& pMap, int sourceRouter)
-  {
-    cout<<"LinkStateRoutingTableCalculator::addAllNextHopsToRoutingTable Called";
-    cout<<endl;
-    for(int i=0; i < numOfRouter ; i++)
-    {
-      if ( i!= sourceRouter )
-      {
-        int nextHopRouter=getLsNextHop(i,sourceRouter);
-        if ( nextHopRouter != NO_NEXT_HOP )
-        {
-          double routeCost=m_distance[i];
-          string nextHopRouterName=
-            pMap.getRouterNameByMappingNo(nextHopRouter);
-          int nxtHopFace=
-            pnlsr.getAdl().getAdjacent(nextHopRouterName).getConnectingFace();
-          cout<<"Dest Router: "<<pMap.getRouterNameByMappingNo(i)<<endl;
-          cout<<"Next hop Router: "<<nextHopRouterName<<endl;
-          cout<<"Next hop Face: "<<nxtHopFace<<endl;
-          cout<<"Route Cost: "<<routeCost<<endl;
-          cout<<endl;
-          // Add next hop to routing table
-          NextHop nh(nxtHopFace,routeCost);
-          rt.addNextHop(pMap.getRouterNameByMappingNo(i),nh);
-        }
-      }
-    }
-  }
-
-  int
-  LinkStateRoutingTableCalculator::getLsNextHop(int dest, int source)
-  {
-    int nextHop;
-    while ( m_parent[dest] != EMPTY_PARENT )
-    {
-      nextHop=dest;
-      dest=m_parent[dest];
-    }
-    if ( dest != source )
-    {
-      nextHop=NO_NEXT_HOP;
-    }
-    return nextHop;
-  }
-
-  void
-  LinkStateRoutingTableCalculator::printAllLsPath(int sourceRouter)
-  {
-    cout<<"LinkStateRoutingTableCalculator::printAllLsPath Called"<<endl;
-    cout<<"Source Router: "<<sourceRouter<<endl;
-    for(int i=0; i < numOfRouter ; i++)
-    {
-      if ( i!= sourceRouter )
-      {
-        printLsPath(i);
-        cout<<endl;
-      }
-    }
-  }
-
-  void
-  LinkStateRoutingTableCalculator::printLsPath(int destRouter)
-  {
-    if (m_parent[destRouter] != EMPTY_PARENT )
-    {
-      printLsPath(m_parent[destRouter]);
-    }
-    cout<<" "<<destRouter;
-  }
-
-  void
-  LinkStateRoutingTableCalculator::sortQueueByDistance(int *Q,
-      double *dist,int start,int element)
-  {
-    for ( int i=start ; i < element ; i ++)
-    {
-      for( int j=i+1; j<element; j ++)
-      {
-        if (dist[Q[j]] < dist[Q[i]])
-        {
-          int tempU=Q[j];
-          Q[j]=Q[i];
-          Q[i]=tempU;
-        }
-      }
-    }
-  }
-
-  int
-  LinkStateRoutingTableCalculator::isNotExplored(int *Q,
-      int u,int start, int element)
-  {
-    int ret=0;
-    for(int i=start; i< element; i++)
-    {
-      if ( Q[i] == u )
-      {
-        ret=1;
-        break;
-      }
-    }
-    return ret;
-  }
-
-  void
-  LinkStateRoutingTableCalculator::allocateParent()
-  {
-    m_parent=new int[numOfRouter];
-  }
-
-  void
-  LinkStateRoutingTableCalculator::allocateDistance()
-  {
-    m_distance= new double[numOfRouter];
-  }
-
-  void
-  LinkStateRoutingTableCalculator::freeParent()
-  {
-    delete [] m_parent;
-  }
-
-  void LinkStateRoutingTableCalculator::freeDistance()
-  {
-    delete [] m_distance;
-  }
-
-
-
-  void
-  HypRoutingTableCalculator::calculatePath(Map& pMap,
-      RoutingTable& rt, Nlsr& pnlsr)
-  {
-    makeAdjMatrix(pnlsr,pMap);
-    string routerName=pnlsr.getConfParameter().getRouterPrefix();
-    int sourceRouter=pMap.getMappingNoByRouterName(routerName);
-    int noLink=getNumOfLinkfromAdjMatrix(sourceRouter);
-    setNoLink(noLink);
-    allocateLinks();
-    allocateLinkCosts();
-    getLinksFromAdjMatrix(links, linkCosts, sourceRouter);
-    for(int i=0 ; i < numOfRouter ; ++i)
-    {
-      int k=0;
-      if ( i != sourceRouter)
-      {
-        allocateLinkFaces();
-        allocateDistanceToNeighbor();
-        allocateDistFromNbrToDest();
-        for(int j=0; j<vNoLink; j++)
-        {
-          string nextHopRouterName=pMap.getRouterNameByMappingNo(links[j]);
-          int nextHopFace=
-            pnlsr.getAdl().getAdjacent(nextHopRouterName).getConnectingFace();
-          double distToNbr=getHyperbolicDistance(pnlsr,pMap,
-                                                 sourceRouter,links[j]);
-          double distToDestFromNbr=getHyperbolicDistance(pnlsr,
-                                   pMap,links[j],i);
-          if ( distToDestFromNbr >= 0 )
-          {
-            m_linkFaces[k] = nextHopFace;
-            m_distanceToNeighbor[k] = distToNbr;
-            m_distFromNbrToDest[k] = distToDestFromNbr;
-            k++;
-          }
-        }
-        addHypNextHopsToRoutingTable(pnlsr,pMap,rt,k,i);
-        freeLinkFaces();
-        freeDistanceToNeighbor();
-        freeDistFromNbrToDest();
-      }
-    }
-    freeLinks();
-    freeLinksCosts();
-    freeAdjMatrix();
-  }
-
-  void
-  HypRoutingTableCalculator::addHypNextHopsToRoutingTable(Nlsr& pnlsr,Map& pMap,
-      RoutingTable& rt, int noFaces, int dest)
-  {
-    for(int i=0 ; i < noFaces ; ++i)
-    {
-      string destRouter=pMap.getRouterNameByMappingNo(dest);
-      NextHop nh(m_linkFaces[i],m_distFromNbrToDest[i]);
-      rt.addNextHop(destRouter,nh);
-      if( m_isDryRun)
-      {
-        rt.addNextHopToDryTable(destRouter,nh);
-      }
-    }
-  }
-
-  double
-  HypRoutingTableCalculator::getHyperbolicDistance(Nlsr& pnlsr,
-      Map& pMap, int src, int dest)
-  {
-    double distance=0.0;
-    string srcRouterKey=pMap.getRouterNameByMappingNo(src)+"/3";
-    string destRouterKey=pMap.getRouterNameByMappingNo(dest)+"/3";
-    double srcRadius=(pnlsr.getLsdb().getCorLsa(srcRouterKey).first).getCorRadius();
-    double srcTheta=(pnlsr.getLsdb().getCorLsa(srcRouterKey).first).getCorTheta();
-    double destRadius=(pnlsr.getLsdb().getCorLsa(
-                         destRouterKey).first).getCorRadius();
-    double destTheta=(pnlsr.getLsdb().getCorLsa(destRouterKey).first).getCorTheta();
-    double diffTheta = fabs (srcTheta - destTheta);
-    if (diffTheta > MATH_PI)
-    {
-      diffTheta = 2 * MATH_PI - diffTheta;
-    }
-    if ( srcRadius != -1 && destRadius != -1 )
-    {
-      if (diffTheta == 0)
-        distance = fabs (srcRadius - destRadius);
-      else
-        distance = acosh((cosh(srcRadius)*cosh(destRadius))-
-                         (sinh(srcRadius)*sinh(destRadius)*cos(diffTheta)));
-    }
-    else
-    {
-      distance = -1;
-    }
-    return distance;
-  }
-
-  void
-  HypRoutingTableCalculator::allocateLinkFaces()
-  {
-    m_linkFaces=new int[vNoLink];
-  }
-
-  void
-  HypRoutingTableCalculator::allocateDistanceToNeighbor()
-  {
-    m_distanceToNeighbor=new double[vNoLink];
-  }
-
-  void
-  HypRoutingTableCalculator::allocateDistFromNbrToDest()
-  {
-    m_distFromNbrToDest=new double[vNoLink];
-  }
-
-  void
-  HypRoutingTableCalculator::freeLinkFaces()
-  {
-    delete [] m_linkFaces;
-  }
-
-  void
-  HypRoutingTableCalculator::freeDistanceToNeighbor()
-  {
-    delete [] m_distanceToNeighbor;
-  }
-
-  void
-  HypRoutingTableCalculator::freeDistFromNbrToDest()
-  {
-    delete [] m_distFromNbrToDest;
-  }
-
-}//namespace nlsr
diff --git a/src/route/nlsr_rtc.hpp b/src/route/nlsr_rtc.hpp
deleted file mode 100644
index dba45ca..0000000
--- a/src/route/nlsr_rtc.hpp
+++ /dev/null
@@ -1,145 +0,0 @@
-#ifndef NLSR_RTC_HPP
-#define NLSR_RTC_HPP
-
-#include <list>
-#include <iostream>
-
-namespace nlsr
-{
-
-  class Map;
-  class RoutingTable;
-  class Nlsr;
-
-
-  using namespace std;
-
-  class RoutingTableCalculator
-  {
-  public:
-    RoutingTableCalculator()
-    {
-    }
-    RoutingTableCalculator(int rn)
-    {
-      numOfRouter=rn;
-    }
-  protected:
-    void allocateAdjMatrix();
-    void initMatrix();
-    void makeAdjMatrix(Nlsr& pnlsr,Map pMap);
-    void printAdjMatrix();
-    int getNumOfLinkfromAdjMatrix(int sRouter);
-    void freeAdjMatrix();
-    void adjustAdMatrix(int source, int link, double linkCost);
-    void getLinksFromAdjMatrix(int *links, double *linkCosts, int source);
-
-    void allocateLinks();
-    void allocateLinkCosts();
-    void freeLinks();
-    void freeLinksCosts();
-
-    void setNoLink(int nl)
-    {
-      vNoLink=nl;
-    }
-
-  protected:
-    double** adjMatrix;
-    int numOfRouter;
-
-    int vNoLink;
-    int* links;
-    double* linkCosts;
-  };
-
-  class LinkStateRoutingTableCalculator: public RoutingTableCalculator
-  {
-  public:
-    LinkStateRoutingTableCalculator(int rn)
-      : EMPTY_PARENT(-12345)
-      , INF_DISTANCE(2147483647)
-      , NO_MAPPING_NUM(-1)
-      , NO_NEXT_HOP(-12345)
-    {
-      numOfRouter=rn;
-    }
-
-
-    void calculatePath(Map& pMap, RoutingTable& rt, Nlsr& pnlsr);
-
-
-  private:
-    void doDijkstraPathCalculation(int sourceRouter);
-    void sortQueueByDistance(int* Q, double* dist,int start,int element);
-    int isNotExplored(int* Q, int u,int start, int element);
-    void printAllLsPath(int sourceRouter);
-    void printLsPath(int destRouter);
-    void addAllLsNextHopsToRoutingTable(Nlsr& pnlsr, RoutingTable& rt,
-                                        Map& pMap,int sourceRouter);
-    int getLsNextHop(int dest, int source);
-
-    void allocateParent();
-    void allocateDistance();
-    void freeParent();
-    void freeDistance();
-
-
-
-
-  private:
-    int* m_parent;
-    double* m_distance;
-
-
-    const int EMPTY_PARENT;
-    const double INF_DISTANCE;
-    const int NO_MAPPING_NUM;
-    const int NO_NEXT_HOP;
-
-  };
-
-  class HypRoutingTableCalculator: public RoutingTableCalculator
-  {
-  public:
-    HypRoutingTableCalculator(int rn)
-      :  MATH_PI(3.141592654)
-    {
-      numOfRouter=rn;
-      m_isDryRun=0;
-    }
-    HypRoutingTableCalculator(int rn, int idr)
-      :  MATH_PI(3.141592654)
-    {
-      numOfRouter=rn;
-      m_isDryRun=idr;
-    }
-
-    void calculatePath(Map& pMap, RoutingTable& rt, Nlsr& pnlsr);
-
-  private:
-    void allocateLinkFaces();
-    void allocateDistanceToNeighbor();
-    void allocateDistFromNbrToDest();
-    void freeLinkFaces();
-    void freeDistanceToNeighbor();
-    void freeDistFromNbrToDest();
-
-    double getHyperbolicDistance(Nlsr& pnlsr,Map& pMap, int src, int dest);
-    void addHypNextHopsToRoutingTable(Nlsr& pnlsr,Map& pMap,
-                                      RoutingTable& rt, int noFaces,int dest);
-
-  private:
-    bool m_isDryRun;
-
-    int* m_linkFaces;
-    double* m_distanceToNeighbor;
-    double* m_distFromNbrToDest;
-
-    const double MATH_PI;
-
-  };
-
-}//namespace nlsr
-
-#endif
diff --git a/src/route/nlsr_rte.cpp b/src/route/nlsr_rte.cpp
deleted file mode 100644
index 7c06b03..0000000
--- a/src/route/nlsr_rte.cpp
+++ /dev/null
@@ -1,29 +0,0 @@
-#include <iostream>
-#include <string>
-
-#include "nlsr_rte.hpp"
-#include "utility/nlsr_logger.hpp"
-
-#define THIS_FILE "nlsr_rte.cpp"
-
-namespace nlsr
-{
-
-  using namespace std;
-
-  ostream&
-  operator<<(ostream& os, RoutingTableEntry& rte)
-  {
-    os<<"Destination: "<<rte.getDestination()<<endl;
-    os<<"Nexthops: "<<endl;
-    int i=1;
-    std::list< NextHop > nhl = rte.getNhl().getNextHopList();
-    for( std::list<NextHop>::iterator it=nhl.begin();
-         it!= nhl.end() ; it++,i++)
-    {
-      os <<"  Nexthop "<<i<<": "<<(*it)<<endl;
-    }
-    return os;
-  }
-
-}//namespace nlsr
diff --git a/src/route/nlsr_rte.hpp b/src/route/nlsr_rte.hpp
deleted file mode 100644
index 484edab..0000000
--- a/src/route/nlsr_rte.hpp
+++ /dev/null
@@ -1,52 +0,0 @@
-#ifndef NLSR_RTE_HPP
-#define NLSR_RTE_HPP
-
-#include<iostream>
-
-#include "nlsr_nhl.hpp"
-
-namespace nlsr
-{
-
-  using namespace std;
-
-  class RoutingTableEntry
-  {
-  public:
-    RoutingTableEntry()
-      : m_destination()
-      , m_nhl()
-    {
-    }
-
-    ~RoutingTableEntry()
-    {
-    }
-
-    RoutingTableEntry(string dest)
-      : m_nhl()
-    {
-      m_destination=dest;
-    }
-
-    string getDestination()
-    {
-      return m_destination;
-    }
-
-    Nhl& getNhl()
-    {
-      return m_nhl;
-    }
-
-  private:
-    string m_destination;
-    Nhl m_nhl;
-  };
-
-  ostream&
-  operator<<(ostream& os, RoutingTableEntry& rte);
-
-}
-
-#endif
diff --git a/src/route/npt.cpp b/src/route/npt.cpp
new file mode 100644
index 0000000..665dbb2
--- /dev/null
+++ b/src/route/npt.cpp
@@ -0,0 +1,151 @@
+#include <list>
+#include <utility>
+#include <algorithm>
+
+#include "npt.hpp"
+#include "npte.hpp"
+#include "nlsr.hpp"
+
+
+namespace nlsr {
+
+using namespace std;
+
+static bool
+npteCompare(Npte& npte, string& name)
+{
+  return npte.getNamePrefix() == name;
+}
+
+
+
+void
+Npt::addNpte(string name, RoutingTableEntry& rte, Nlsr& pnlsr)
+{
+  std::list<Npte>::iterator it = std::find_if(m_npteList.begin(),
+                                              m_npteList.end(), bind(&npteCompare, _1, name));
+  if (it == m_npteList.end())
+  {
+    Npte newEntry(name);
+    newEntry.addRoutingTableEntry(rte);
+    newEntry.generateNhlfromRteList();
+    newEntry.getNhl().sort();
+    m_npteList.push_back(newEntry);
+    if (rte.getNhl().getSize() > 0)
+    {
+      pnlsr.getFib().update(pnlsr, name, newEntry.getNhl());
+    }
+  }
+  else
+  {
+    if (rte.getNhl().getSize() > 0)
+    {
+      (*it).addRoutingTableEntry(rte);
+      (*it).generateNhlfromRteList();
+      (*it).getNhl().sort();
+      pnlsr.getFib().update(pnlsr, name, (*it).getNhl());
+    }
+    else
+    {
+      (*it).resetRteListNextHop();
+      (*it).getNhl().reset();
+      pnlsr.getFib().remove(pnlsr, name);
+    }
+  }
+}
+
+void
+Npt::removeNpte(string name, RoutingTableEntry& rte, Nlsr& pnlsr)
+{
+  std::list<Npte>::iterator it = std::find_if(m_npteList.begin(),
+                                              m_npteList.end(), bind(&npteCompare, _1, name));
+  if (it != m_npteList.end())
+  {
+    string destRouter = rte.getDestination();
+    (*it).removeRoutingTableEntry(rte);
+    if (((*it).getRteListSize() == 0) &&
+        (!pnlsr.getLsdb().doesLsaExist(destRouter + "/1", 1)) &&
+        (!pnlsr.getLsdb().doesLsaExist(destRouter + "/2", 2)) &&
+        (!pnlsr.getLsdb().doesLsaExist(destRouter + "/3", 3)))
+    {
+      m_npteList.erase(it);
+      pnlsr.getFib().remove(pnlsr, name);
+    }
+    else
+    {
+      (*it).generateNhlfromRteList();
+      pnlsr.getFib().update(pnlsr, name, (*it).getNhl());
+    }
+  }
+}
+
+
+void
+Npt::addNpteByDestName(string name, string destRouter, Nlsr& pnlsr)
+{
+  std::pair<RoutingTableEntry&, bool> rteCheck =
+    pnlsr.getRoutingTable().findRoutingTableEntry(destRouter);
+  if (rteCheck.second)
+  {
+    addNpte(name, rteCheck.first, pnlsr);
+  }
+  else
+  {
+    RoutingTableEntry rte(destRouter);
+    addNpte(name, rte, pnlsr);
+  }
+}
+
+void
+Npt::removeNpte(string name, string destRouter, Nlsr& pnlsr)
+{
+  std::pair<RoutingTableEntry&, bool> rteCheck =
+    pnlsr.getRoutingTable().findRoutingTableEntry(destRouter);
+  if (rteCheck.second)
+  {
+    removeNpte(name, rteCheck.first, pnlsr);
+  }
+  else
+  {
+    RoutingTableEntry rte(destRouter);
+    removeNpte(name, rte, pnlsr);
+  }
+}
+
+void
+Npt::updateWithNewRoute(Nlsr& pnlsr)
+{
+  for (std::list<Npte>::iterator it = m_npteList.begin(); it != m_npteList.end();
+       ++it)
+  {
+    std::list<RoutingTableEntry> rteList = (*it).getRteList();
+    for (std::list<RoutingTableEntry>::iterator rteit = rteList.begin();
+         rteit != rteList.end(); ++rteit)
+    {
+      std::pair<RoutingTableEntry&, bool> rteCheck =
+        pnlsr.getRoutingTable().findRoutingTableEntry((*rteit).getDestination());
+      if (rteCheck.second)
+      {
+        addNpte((*it).getNamePrefix(), rteCheck.first, pnlsr);
+      }
+      else
+      {
+        RoutingTableEntry rte((*rteit).getDestination());
+        addNpte((*it).getNamePrefix(), rte, pnlsr);
+      }
+    }
+  }
+}
+
+void
+Npt::print()
+{
+  std::cout << "----------------NPT----------------------" << std::endl;
+  for (std::list<Npte>::iterator it = m_npteList.begin(); it != m_npteList.end();
+       ++it)
+  {
+    cout << (*it) << endl;
+  }
+}
+
+} //namespace nlsr
diff --git a/src/route/npt.hpp b/src/route/npt.hpp
new file mode 100644
index 0000000..8e6cd0a
--- /dev/null
+++ b/src/route/npt.hpp
@@ -0,0 +1,42 @@
+#ifndef NLSR_NPT_HPP
+#define NLSR_NPT_HPP
+
+#include <list>
+#include "npte.hpp"
+#include "routing-table-entry.hpp"
+
+namespace nlsr {
+class Nlsr;
+
+class Npt
+{
+public:
+  Npt()
+  {
+  }
+  void
+  addNpteByDestName(std::string name, std::string destRouter, Nlsr& pnlsr);
+
+  void
+  removeNpte(std::string name, std::string destRouter, Nlsr& pnlsr);
+
+  void
+  updateWithNewRoute(Nlsr& pnlsr);
+
+  void
+  print();
+
+private:
+  void
+  addNpte(std::string name, RoutingTableEntry& rte, Nlsr& pnlsr);
+
+  void
+  removeNpte(std::string name, RoutingTableEntry& rte, Nlsr& pnlsr);
+
+private:
+  std::list<Npte> m_npteList;
+};
+
+}//namespace nlsr
+
+#endif //NLSR_NPT_HPP
diff --git a/src/route/npte.cpp b/src/route/npte.cpp
new file mode 100644
index 0000000..3194635
--- /dev/null
+++ b/src/route/npte.cpp
@@ -0,0 +1,83 @@
+#include <list>
+#include <utility>
+#include "npte.hpp"
+#include "routing-table-entry.hpp"
+#include "nexthop.hpp"
+
+namespace nlsr {
+
+using namespace std;
+
+void
+Npte::generateNhlfromRteList()
+{
+  m_nhl.reset();
+  for (std::list<RoutingTableEntry>::iterator it = m_rteList.begin();
+       it != m_rteList.end(); ++it)
+  {
+    for (std::list<NextHop>::iterator nhit =
+           (*it).getNhl().getNextHopList().begin();
+         nhit != (*it).getNhl().getNextHopList().end(); ++nhit)
+    {
+      m_nhl.addNextHop((*nhit));
+    }
+  }
+}
+
+
+
+static bool
+rteCompare(RoutingTableEntry& rte, string& destRouter)
+{
+  return rte.getDestination() == destRouter;
+}
+
+void
+Npte::removeRoutingTableEntry(RoutingTableEntry& rte)
+{
+  std::list<RoutingTableEntry>::iterator it = std::find_if(m_rteList.begin(),
+                                                           m_rteList.end(),
+                                                           bind(&rteCompare, _1, rte.getDestination()));
+  if (it != m_rteList.end())
+  {
+    m_rteList.erase(it);
+  }
+}
+
+void
+Npte::addRoutingTableEntry(RoutingTableEntry& rte)
+{
+  std::list<RoutingTableEntry>::iterator it = std::find_if(m_rteList.begin(),
+                                                           m_rteList.end(),
+                                                           bind(&rteCompare, _1, rte.getDestination()));
+  if (it == m_rteList.end())
+  {
+    m_rteList.push_back(rte);
+  }
+  else
+  {
+    (*it).getNhl().reset(); // reseting existing routing table's next hop
+    for (std::list<NextHop>::iterator nhit = rte.getNhl().getNextHopList().begin();
+         nhit != rte.getNhl().getNextHopList().end(); ++nhit)
+    {
+      (*it).getNhl().addNextHop((*nhit));
+    }
+  }
+}
+
+//debugging purpose
+ostream&
+operator<<(ostream& os, Npte& npte)
+{
+  os << "Name: " << npte.getNamePrefix() << endl;
+  std::list<RoutingTableEntry> rteList = npte.getRteList();
+  for (std::list<RoutingTableEntry>::iterator it = rteList.begin();
+       it != rteList.end(); ++it)
+  {
+    cout << (*it);
+  }
+  os << npte.getNhl();
+  return os;
+}
+
+}//namespace nlsr
diff --git a/src/route/npte.hpp b/src/route/npte.hpp
new file mode 100644
index 0000000..57fdfec
--- /dev/null
+++ b/src/route/npte.hpp
@@ -0,0 +1,84 @@
+#ifndef NLSR_NPTE_HPP
+#define NLSR_NPTE_HPP
+
+#include <list>
+#include <utility>
+#include "routing-table-entry.hpp"
+
+namespace nlsr {
+
+using namespace std;
+
+class Npte
+{
+public:
+  Npte()
+    : m_namePrefix()
+    , m_nhl()
+  {
+  }
+
+  Npte(string np)
+    : m_nhl()
+  {
+    m_namePrefix = np;
+  }
+
+  std::string
+  getNamePrefix()
+  {
+    return m_namePrefix;
+  }
+
+  std::list<RoutingTableEntry>&
+  getRteList()
+  {
+    return m_rteList;
+  }
+
+  void
+  resetRteListNextHop()
+  {
+    if (m_rteList.size() > 0)
+    {
+      for (std::list<RoutingTableEntry>::iterator it = m_rteList.begin();
+           it != m_rteList.end(); ++it)
+      {
+        (*it).getNhl().reset();
+      }
+    }
+  }
+
+  int
+  getRteListSize()
+  {
+    return m_rteList.size();
+  }
+
+  Nhl&
+  getNhl()
+  {
+    return m_nhl;
+  }
+
+  void
+  generateNhlfromRteList();
+
+  void
+  removeRoutingTableEntry(RoutingTableEntry& rte);
+
+  void
+  addRoutingTableEntry(RoutingTableEntry& rte);
+
+private:
+  std::string m_namePrefix;
+  std::list<RoutingTableEntry> m_rteList;
+  Nhl m_nhl;
+};
+
+std::ostream&
+operator<<(std::ostream& os, Npte& npte);
+
+}//namespace nlsr
+
+#endif //NLSR_NPTE_HPP
diff --git a/src/route/routing-table-calculator.cpp b/src/route/routing-table-calculator.cpp
new file mode 100644
index 0000000..6c6dad3
--- /dev/null
+++ b/src/route/routing-table-calculator.cpp
@@ -0,0 +1,514 @@
+#include <iostream>
+#include <cmath>
+#include "lsdb.hpp"
+#include "routing-table-calculator.hpp"
+#include "map.hpp"
+#include "lsa.hpp"
+#include "nexthop.hpp"
+#include "nlsr.hpp"
+
+namespace nlsr {
+
+using namespace std;
+
+void
+RoutingTableCalculator::allocateAdjMatrix()
+{
+  adjMatrix = new double*[numOfRouter];
+  for (int i = 0; i < numOfRouter; ++i)
+  {
+    adjMatrix[i] = new double[numOfRouter];
+  }
+}
+
+void
+RoutingTableCalculator::initMatrix()
+{
+  for (int i = 0; i < numOfRouter; i++)
+  {
+    for (int j = 0; j < numOfRouter; j++)
+      adjMatrix[i][j] = 0;
+  }
+}
+
+void
+RoutingTableCalculator::makeAdjMatrix(Nlsr& pnlsr, Map pMap)
+{
+  std::list<AdjLsa> adjLsdb = pnlsr.getLsdb().getAdjLsdb();
+  for (std::list<AdjLsa>::iterator it = adjLsdb.begin();
+       it != adjLsdb.end() ; it++)
+  {
+    string linkStartRouter = (*it).getOrigRouter();
+    int row = pMap.getMappingNoByRouterName(linkStartRouter);
+    std::list<Adjacent> adl = (*it).getAdl().getAdjList();
+    for (std::list<Adjacent>::iterator itAdl = adl.begin();
+         itAdl != adl.end() ; itAdl++)
+    {
+      string linkEndRouter = (*itAdl).getName();
+      int col = pMap.getMappingNoByRouterName(linkEndRouter);
+      double cost = (*itAdl).getLinkCost();
+      if ((row >= 0 && row < numOfRouter) && (col >= 0 && col < numOfRouter))
+      {
+        adjMatrix[row][col] = cost;
+      }
+    }
+  }
+}
+
+void
+RoutingTableCalculator::printAdjMatrix()
+{
+  for (int i = 0; i < numOfRouter; i++)
+  {
+    for (int j = 0; j < numOfRouter; j++)
+      printf("%f ", adjMatrix[i][j]);
+    printf("\n");
+  }
+}
+
+void
+RoutingTableCalculator::adjustAdMatrix(int source, int link, double linkCost)
+{
+  for (int i = 0; i < numOfRouter; i++)
+  {
+    if (i == link)
+    {
+      adjMatrix[source][i] = linkCost;
+    }
+    else
+    {
+      adjMatrix[source][i] = 0;
+    }
+  }
+}
+
+int
+RoutingTableCalculator::getNumOfLinkfromAdjMatrix(int sRouter)
+{
+  int noLink = 0;
+  for (int i = 0; i < numOfRouter; i++)
+  {
+    if (adjMatrix[sRouter][i] > 0)
+    {
+      noLink++;
+    }
+  }
+  return noLink;
+}
+
+void
+RoutingTableCalculator::getLinksFromAdjMatrix(int* links,
+                                              double* linkCosts, int source)
+{
+  int j = 0;
+  for (int i = 0; i < numOfRouter; i++)
+  {
+    if (adjMatrix[source][i] > 0)
+    {
+      links[j] = i;
+      linkCosts[j] = adjMatrix[source][i];
+      j++;
+    }
+  }
+}
+
+void
+RoutingTableCalculator::freeAdjMatrix()
+{
+  for (int i = 0; i < numOfRouter; ++i)
+  {
+    delete [] adjMatrix[i];
+  }
+  delete [] adjMatrix;
+}
+
+
+void
+RoutingTableCalculator::allocateLinks()
+{
+  links = new int[vNoLink];
+}
+
+void
+RoutingTableCalculator::allocateLinkCosts()
+{
+  linkCosts = new double[vNoLink];
+}
+
+
+void
+RoutingTableCalculator::freeLinks()
+{
+  delete [] links;
+}
+void
+RoutingTableCalculator::freeLinksCosts()
+{
+  delete [] linkCosts;
+}
+
+void
+LinkStateRoutingTableCalculator::calculatePath(Map& pMap,
+                                               RoutingTable& rt, Nlsr& pnlsr)
+{
+  std::cout << "LinkStateRoutingTableCalculator::calculatePath Called" <<
+            std::endl;
+  allocateAdjMatrix();
+  initMatrix();
+  makeAdjMatrix(pnlsr, pMap);
+  std::cout << pMap;
+  printAdjMatrix();
+  string routerName = pnlsr.getConfParameter().getRouterPrefix();
+  int sourceRouter = pMap.getMappingNoByRouterName(routerName);
+  //int noLink=getNumOfLinkfromAdjMatrix(sourceRouter);
+  allocateParent();
+  allocateDistance();
+  if (pnlsr.getConfParameter().getMaxFacesPerPrefix() == 1)
+  {
+    // Single Path
+    doDijkstraPathCalculation(sourceRouter);
+    // print all ls path -- debugging purpose
+    printAllLsPath(sourceRouter);
+    // update routing table
+    addAllLsNextHopsToRoutingTable(pnlsr, rt, pMap, sourceRouter);
+  }
+  else
+  {
+    // Multi Path
+    setNoLink(getNumOfLinkfromAdjMatrix(sourceRouter));
+    allocateLinks();
+    allocateLinkCosts();
+    getLinksFromAdjMatrix(links, linkCosts, sourceRouter);
+    for (int i = 0 ; i < vNoLink; i++)
+    {
+      adjustAdMatrix(sourceRouter, links[i], linkCosts[i]);
+      printAdjMatrix();
+      doDijkstraPathCalculation(sourceRouter);
+      // print all ls path -- debugging purpose
+      printAllLsPath(sourceRouter);
+      //update routing table
+      addAllLsNextHopsToRoutingTable(pnlsr, rt, pMap, sourceRouter);
+    }
+    freeLinks();
+    freeLinksCosts();
+  }
+  freeParent();
+  freeDistance();
+  freeAdjMatrix();
+}
+
+void
+LinkStateRoutingTableCalculator::doDijkstraPathCalculation(int sourceRouter)
+{
+  int i;
+  int v, u;
+  int* Q = new int[numOfRouter];
+  int head = 0;
+  /* Initiate the Parent */
+  for (i = 0 ; i < numOfRouter; i++)
+  {
+    m_parent[i] = EMPTY_PARENT;
+    m_distance[i] = INF_DISTANCE;
+    Q[i] = i;
+  }
+  if (sourceRouter != NO_MAPPING_NUM)
+  {
+    m_distance[sourceRouter] = 0;
+    sortQueueByDistance(Q, m_distance, head, numOfRouter);
+    while (head < numOfRouter)
+    {
+      u = Q[head];
+      if (m_distance[u] == INF_DISTANCE)
+      {
+        break;
+      }
+      for (v = 0 ; v < numOfRouter; v++)
+      {
+        if (adjMatrix[u][v] > 0)
+        {
+          if (isNotExplored(Q, v, head + 1, numOfRouter))
+          {
+            if (m_distance[u] + adjMatrix[u][v] <  m_distance[v])
+            {
+              m_distance[v] = m_distance[u] + adjMatrix[u][v] ;
+              m_parent[v] = u;
+            }
+          }
+        }
+      }
+      head++;
+      sortQueueByDistance(Q, m_distance, head, numOfRouter);
+    }
+  }
+  delete [] Q;
+}
+
+void
+LinkStateRoutingTableCalculator::addAllLsNextHopsToRoutingTable(Nlsr& pnlsr,
+                                                                RoutingTable& rt, Map& pMap, int sourceRouter)
+{
+  std::cout <<
+            "LinkStateRoutingTableCalculator::addAllNextHopsToRoutingTable Called";
+  std::cout << std::endl;
+  int nextHopRouter = 0;
+  for (int i = 0; i < numOfRouter ; i++)
+  {
+    if (i != sourceRouter)
+    {
+      nextHopRouter = getLsNextHop(i, sourceRouter);
+      if (nextHopRouter != NO_NEXT_HOP)
+      {
+        double routeCost = m_distance[i];
+        string nextHopRouterName =
+          pMap.getRouterNameByMappingNo(nextHopRouter);
+        int nxtHopFace =
+          pnlsr.getAdl().getAdjacent(nextHopRouterName).getConnectingFace();
+        std::cout << "Dest Router: " << pMap.getRouterNameByMappingNo(i) << std::endl;
+        std::cout << "Next hop Router: " << nextHopRouterName << std::endl;
+        std::cout << "Next hop Face: " << nxtHopFace << std::endl;
+        std::cout << "Route Cost: " << routeCost << std::endl;
+        std::cout << std::endl;
+        // Add next hop to routing table
+        NextHop nh(nxtHopFace, routeCost);
+        rt.addNextHop(pMap.getRouterNameByMappingNo(i), nh);
+      }
+    }
+  }
+}
+
+int
+LinkStateRoutingTableCalculator::getLsNextHop(int dest, int source)
+{
+  int nextHop = NO_NEXT_HOP;
+  while (m_parent[dest] != EMPTY_PARENT)
+  {
+    nextHop = dest;
+    dest = m_parent[dest];
+  }
+  if (dest != source)
+  {
+    nextHop = NO_NEXT_HOP;
+  }
+  return nextHop;
+}
+
+void
+LinkStateRoutingTableCalculator::printAllLsPath(int sourceRouter)
+{
+  std::cout << "LinkStateRoutingTableCalculator::printAllLsPath Called" <<
+            std::endl;
+  std::cout << "Source Router: " << sourceRouter << std::endl;
+  for (int i = 0; i < numOfRouter ; i++)
+  {
+    if (i != sourceRouter)
+    {
+      printLsPath(i);
+      std::cout << std::endl;
+    }
+  }
+}
+
+void
+LinkStateRoutingTableCalculator::printLsPath(int destRouter)
+{
+  if (m_parent[destRouter] != EMPTY_PARENT)
+  {
+    printLsPath(m_parent[destRouter]);
+  }
+  std:: cout << " " << destRouter;
+}
+
+void
+LinkStateRoutingTableCalculator::sortQueueByDistance(int* Q,
+                                                     double* dist, int start, int element)
+{
+  for (int i = start ; i < element ; i++)
+  {
+    for (int j = i + 1; j < element; j++)
+    {
+      if (dist[Q[j]] < dist[Q[i]])
+      {
+        int tempU = Q[j];
+        Q[j] = Q[i];
+        Q[i] = tempU;
+      }
+    }
+  }
+}
+
+int
+LinkStateRoutingTableCalculator::isNotExplored(int* Q,
+                                               int u, int start, int element)
+{
+  int ret = 0;
+  for (int i = start; i < element; i++)
+  {
+    if (Q[i] == u)
+    {
+      ret = 1;
+      break;
+    }
+  }
+  return ret;
+}
+
+void
+LinkStateRoutingTableCalculator::allocateParent()
+{
+  m_parent = new int[numOfRouter];
+}
+
+void
+LinkStateRoutingTableCalculator::allocateDistance()
+{
+  m_distance = new double[numOfRouter];
+}
+
+void
+LinkStateRoutingTableCalculator::freeParent()
+{
+  delete [] m_parent;
+}
+
+void LinkStateRoutingTableCalculator::freeDistance()
+{
+  delete [] m_distance;
+}
+
+
+
+void
+HypRoutingTableCalculator::calculatePath(Map& pMap,
+                                         RoutingTable& rt, Nlsr& pnlsr)
+{
+  makeAdjMatrix(pnlsr, pMap);
+  string routerName = pnlsr.getConfParameter().getRouterPrefix();
+  int sourceRouter = pMap.getMappingNoByRouterName(routerName);
+  int noLink = getNumOfLinkfromAdjMatrix(sourceRouter);
+  setNoLink(noLink);
+  allocateLinks();
+  allocateLinkCosts();
+  getLinksFromAdjMatrix(links, linkCosts, sourceRouter);
+  for (int i = 0 ; i < numOfRouter ; ++i)
+  {
+    int k = 0;
+    if (i != sourceRouter)
+    {
+      allocateLinkFaces();
+      allocateDistanceToNeighbor();
+      allocateDistFromNbrToDest();
+      for (int j = 0; j < vNoLink; j++)
+      {
+        string nextHopRouterName = pMap.getRouterNameByMappingNo(links[j]);
+        int nextHopFace =
+          pnlsr.getAdl().getAdjacent(nextHopRouterName).getConnectingFace();
+        double distToNbr = getHyperbolicDistance(pnlsr, pMap,
+                                                 sourceRouter, links[j]);
+        double distToDestFromNbr = getHyperbolicDistance(pnlsr,
+                                                         pMap, links[j], i);
+        if (distToDestFromNbr >= 0)
+        {
+          m_linkFaces[k] = nextHopFace;
+          m_distanceToNeighbor[k] = distToNbr;
+          m_distFromNbrToDest[k] = distToDestFromNbr;
+          k++;
+        }
+      }
+      addHypNextHopsToRoutingTable(pnlsr, pMap, rt, k, i);
+      freeLinkFaces();
+      freeDistanceToNeighbor();
+      freeDistFromNbrToDest();
+    }
+  }
+  freeLinks();
+  freeLinksCosts();
+  freeAdjMatrix();
+}
+
+void
+HypRoutingTableCalculator::addHypNextHopsToRoutingTable(Nlsr& pnlsr, Map& pMap,
+                                                        RoutingTable& rt, int noFaces, int dest)
+{
+  for (int i = 0 ; i < noFaces ; ++i)
+  {
+    string destRouter = pMap.getRouterNameByMappingNo(dest);
+    NextHop nh(m_linkFaces[i], m_distFromNbrToDest[i]);
+    rt.addNextHop(destRouter, nh);
+    if (m_isDryRun)
+    {
+      rt.addNextHopToDryTable(destRouter, nh);
+    }
+  }
+}
+
+double
+HypRoutingTableCalculator::getHyperbolicDistance(Nlsr& pnlsr,
+                                                 Map& pMap, int src, int dest)
+{
+  double distance = 0.0;
+  string srcRouterKey = pMap.getRouterNameByMappingNo(src) + "/3";
+  string destRouterKey = pMap.getRouterNameByMappingNo(dest) + "/3";
+  double srcRadius = (pnlsr.getLsdb().getCorLsa(
+                        srcRouterKey).first).getCorRadius();
+  double srcTheta = (pnlsr.getLsdb().getCorLsa(srcRouterKey).first).getCorTheta();
+  double destRadius = (pnlsr.getLsdb().getCorLsa(
+                         destRouterKey).first).getCorRadius();
+  double destTheta = (pnlsr.getLsdb().getCorLsa(
+                        destRouterKey).first).getCorTheta();
+  double diffTheta = fabs(srcTheta - destTheta);
+  if (diffTheta > MATH_PI)
+  {
+    diffTheta = 2 * MATH_PI - diffTheta;
+  }
+  if (srcRadius != -1 && destRadius != -1)
+  {
+    if (diffTheta == 0)
+      distance = fabs(srcRadius - destRadius);
+    else
+      distance = acosh((cosh(srcRadius) * cosh(destRadius)) -
+                       (sinh(srcRadius) * sinh(destRadius) * cos(diffTheta)));
+  }
+  else
+  {
+    distance = -1;
+  }
+  return distance;
+}
+
+void
+HypRoutingTableCalculator::allocateLinkFaces()
+{
+  m_linkFaces = new int[vNoLink];
+}
+
+void
+HypRoutingTableCalculator::allocateDistanceToNeighbor()
+{
+  m_distanceToNeighbor = new double[vNoLink];
+}
+
+void
+HypRoutingTableCalculator::allocateDistFromNbrToDest()
+{
+  m_distFromNbrToDest = new double[vNoLink];
+}
+
+void
+HypRoutingTableCalculator::freeLinkFaces()
+{
+  delete [] m_linkFaces;
+}
+
+void
+HypRoutingTableCalculator::freeDistanceToNeighbor()
+{
+  delete [] m_distanceToNeighbor;
+}
+
+void
+HypRoutingTableCalculator::freeDistFromNbrToDest()
+{
+  delete [] m_distFromNbrToDest;
+}
+
+}//namespace nlsr
diff --git a/src/route/routing-table-calculator.hpp b/src/route/routing-table-calculator.hpp
new file mode 100644
index 0000000..b248b15
--- /dev/null
+++ b/src/route/routing-table-calculator.hpp
@@ -0,0 +1,201 @@
+#ifndef NLSR_RTC_HPP
+#define NLSR_RTC_HPP
+
+#include <list>
+#include <iostream>
+
+namespace nlsr {
+
+class Map;
+class RoutingTable;
+class Nlsr;
+
+class RoutingTableCalculator
+{
+public:
+  RoutingTableCalculator()
+  {
+  }
+  RoutingTableCalculator(int rn)
+  {
+    numOfRouter = rn;
+  }
+protected:
+  void
+  allocateAdjMatrix();
+
+  void
+  initMatrix();
+
+  void
+  makeAdjMatrix(Nlsr& pnlsr, Map pMap);
+
+  void
+  printAdjMatrix();
+
+  int
+  getNumOfLinkfromAdjMatrix(int sRouter);
+
+  void
+  freeAdjMatrix();
+
+  void
+  adjustAdMatrix(int source, int link, double linkCost);
+
+  void
+  getLinksFromAdjMatrix(int* links, double* linkCosts, int source);
+
+  void
+  allocateLinks();
+
+  void
+  allocateLinkCosts();
+
+  void
+  freeLinks();
+
+  void
+  freeLinksCosts();
+
+  void
+  setNoLink(int nl)
+  {
+    vNoLink = nl;
+  }
+
+protected:
+  double** adjMatrix;
+  int numOfRouter;
+
+  int vNoLink;
+  int* links;
+  double* linkCosts;
+};
+
+class LinkStateRoutingTableCalculator: public RoutingTableCalculator
+{
+public:
+  LinkStateRoutingTableCalculator(int rn)
+    : EMPTY_PARENT(-12345)
+    , INF_DISTANCE(2147483647)
+    , NO_MAPPING_NUM(-1)
+    , NO_NEXT_HOP(-12345)
+  {
+    numOfRouter = rn;
+  }
+
+
+  void
+  calculatePath(Map& pMap, RoutingTable& rt, Nlsr& pnlsr);
+
+
+private:
+  void
+  doDijkstraPathCalculation(int sourceRouter);
+
+  void
+  sortQueueByDistance(int* Q, double* dist, int start, int element);
+
+  int
+  isNotExplored(int* Q, int u, int start, int element);
+
+  void
+  printAllLsPath(int sourceRouter);
+
+  void
+  printLsPath(int destRouter);
+
+  void
+  addAllLsNextHopsToRoutingTable(Nlsr& pnlsr, RoutingTable& rt,
+                                 Map& pMap, int sourceRouter);
+
+  int
+  getLsNextHop(int dest, int source);
+
+  void
+  allocateParent();
+
+  void
+  allocateDistance();
+
+  void
+  freeParent();
+
+  void
+  freeDistance();
+
+
+
+
+private:
+  int* m_parent;
+  double* m_distance;
+
+
+  const int EMPTY_PARENT;
+  const double INF_DISTANCE;
+  const int NO_MAPPING_NUM;
+  const int NO_NEXT_HOP;
+
+};
+
+class HypRoutingTableCalculator: public RoutingTableCalculator
+{
+public:
+  HypRoutingTableCalculator(int rn)
+    :  MATH_PI(3.141592654)
+  {
+    numOfRouter = rn;
+    m_isDryRun = 0;
+  }
+
+  HypRoutingTableCalculator(int rn, int idr)
+    :  MATH_PI(3.141592654)
+  {
+    numOfRouter = rn;
+    m_isDryRun = idr;
+  }
+
+  void
+  calculatePath(Map& pMap, RoutingTable& rt, Nlsr& pnlsr);
+
+private:
+  void
+  allocateLinkFaces();
+
+  void
+  allocateDistanceToNeighbor();
+
+  void
+  allocateDistFromNbrToDest();
+
+  void
+  freeLinkFaces();
+
+  void
+  freeDistanceToNeighbor();
+
+  void
+  freeDistFromNbrToDest();
+
+  double
+  getHyperbolicDistance(Nlsr& pnlsr, Map& pMap, int src, int dest);
+
+  void
+  addHypNextHopsToRoutingTable(Nlsr& pnlsr, Map& pMap,
+                               RoutingTable& rt, int noFaces, int dest);
+
+private:
+  bool m_isDryRun;
+
+  int* m_linkFaces;
+  double* m_distanceToNeighbor;
+  double* m_distFromNbrToDest;
+
+  const double MATH_PI;
+
+};
+
+}//namespace nlsr
+
+#endif //NLSR_RTC_HPP
diff --git a/src/route/routing-table-entry.cpp b/src/route/routing-table-entry.cpp
new file mode 100644
index 0000000..5222cb9
--- /dev/null
+++ b/src/route/routing-table-entry.cpp
@@ -0,0 +1,25 @@
+#include <iostream>
+#include <string>
+
+#include "routing-table-entry.hpp"
+
+namespace nlsr {
+
+using namespace std;
+
+ostream&
+operator<<(ostream& os, RoutingTableEntry& rte)
+{
+  os << "Destination: " << rte.getDestination() << endl;
+  os << "Nexthops: " << endl;
+  int i = 1;
+  std::list<NextHop> nhl = rte.getNhl().getNextHopList();
+  for (std::list<NextHop>::iterator it = nhl.begin();
+       it != nhl.end() ; it++, i++)
+  {
+    os << "  Nexthop " << i << ": " << (*it) << endl;
+  }
+  return os;
+}
+
+}//namespace nlsr
diff --git a/src/route/routing-table-entry.hpp b/src/route/routing-table-entry.hpp
new file mode 100644
index 0000000..f185e61
--- /dev/null
+++ b/src/route/routing-table-entry.hpp
@@ -0,0 +1,51 @@
+#ifndef NLSR_RTE_HPP
+#define NLSR_RTE_HPP
+
+#include <iostream>
+
+#include "nhl.hpp"
+
+namespace nlsr {
+
+class RoutingTableEntry
+{
+public:
+  RoutingTableEntry()
+    : m_destination()
+    , m_nhl()
+  {
+  }
+
+  ~RoutingTableEntry()
+  {
+  }
+
+  RoutingTableEntry(std::string dest)
+    : m_nhl()
+  {
+    m_destination = dest;
+  }
+
+  std::string
+  getDestination()
+  {
+    return m_destination;
+  }
+
+  Nhl&
+  getNhl()
+  {
+    return m_nhl;
+  }
+
+private:
+  std::string m_destination;
+  Nhl m_nhl;
+};
+
+std::ostream&
+operator<<(std::ostream& os, RoutingTableEntry& rte);
+
+} //namespace nlsr
+
+#endif //NLSR_RTE_HPP
diff --git a/src/route/routing-table.cpp b/src/route/routing-table.cpp
new file mode 100644
index 0000000..9e2c19c
--- /dev/null
+++ b/src/route/routing-table.cpp
@@ -0,0 +1,232 @@
+#include <iostream>
+#include <string>
+#include <list>
+
+#include "routing-table.hpp"
+#include "nlsr.hpp"
+#include "map.hpp"
+#include "routing-table-calculator.hpp"
+#include "routing-table-entry.hpp"
+#include "npt.hpp"
+
+namespace nlsr {
+
+using namespace std;
+
+void
+RoutingTable::calculate(Nlsr& pnlsr)
+{
+  //debugging purpose
+  std::cout << pnlsr.getConfParameter() << std::endl;
+  pnlsr.getNpt().print();
+  pnlsr.getLsdb().printAdjLsdb();
+  pnlsr.getLsdb().printCorLsdb();
+  pnlsr.getLsdb().printNameLsdb();
+  if (pnlsr.getIsRoutingTableCalculating() == 0)
+  {
+    pnlsr.setIsRoutingTableCalculating(1); //setting routing table calculation
+    if (pnlsr.getLsdb().doesLsaExist(
+          pnlsr.getConfParameter().getRouterPrefix() + "/" + "2", 2))
+    {
+      if (pnlsr.getIsBuildAdjLsaSheduled() != 1)
+      {
+        std::cout << "CLearing old routing table ....." << std::endl;
+        clearRoutingTable();
+        clearDryRoutingTable(); // for dry run options
+        // calculate Link State routing
+        if ((pnlsr.getConfParameter().getIsHyperbolicCalc() == 0)
+            || (pnlsr.getConfParameter().getIsHyperbolicCalc() == 2))
+        {
+          calculateLsRoutingTable(pnlsr);
+        }
+        //calculate hyperbolic routing
+        if (pnlsr.getConfParameter().getIsHyperbolicCalc() == 1)
+        {
+          calculateHypRoutingTable(pnlsr);
+        }
+        //calculate dry hyperbolic routing
+        if (pnlsr.getConfParameter().getIsHyperbolicCalc() == 2)
+        {
+          calculateHypDryRoutingTable(pnlsr);
+        }
+        //need to update NPT here
+        pnlsr.getNpt().updateWithNewRoute(pnlsr);
+        //debugging purpose
+        printRoutingTable();
+        pnlsr.getNpt().print();
+        pnlsr.getFib().print();
+        //debugging purpose end
+      }
+      else
+      {
+        std::cout << "Adjacency building is scheduled, so ";
+        std::cout << "routing table can not be calculated :(" << std::endl;
+      }
+    }
+    else
+    {
+      std::cout << "No Adj LSA of router itself,";
+      std::cout <<	" so Routing table can not be calculated :(" << std::endl;
+      clearRoutingTable();
+      clearDryRoutingTable(); // for dry run options
+      // need to update NPT here
+      std::cout << "Calling Update NPT With new Route" << std::endl;
+      pnlsr.getNpt().updateWithNewRoute(pnlsr);
+      //debugging purpose
+      printRoutingTable();
+      pnlsr.getNpt().print();
+      pnlsr.getFib().print();
+      //debugging purpose end
+    }
+    pnlsr.setIsRouteCalculationScheduled(0); //clear scheduled flag
+    pnlsr.setIsRoutingTableCalculating(0); //unsetting routing table calculation
+  }
+  else
+  {
+    scheduleRoutingTableCalculation(pnlsr);
+  }
+}
+
+
+void
+RoutingTable::calculateLsRoutingTable(Nlsr& pnlsr)
+{
+  std::cout << "RoutingTable::calculateLsRoutingTable Called" << std::endl;
+  Map vMap;
+  vMap.createFromAdjLsdb(pnlsr);
+  int numOfRouter = vMap.getMapSize();
+  LinkStateRoutingTableCalculator lsrtc(numOfRouter);
+  lsrtc.calculatePath(vMap, boost::ref(*this), pnlsr);
+}
+
+void
+RoutingTable::calculateHypRoutingTable(Nlsr& pnlsr)
+{
+  Map vMap;
+  vMap.createFromAdjLsdb(pnlsr);
+  int numOfRouter = vMap.getMapSize();
+  HypRoutingTableCalculator hrtc(numOfRouter, 0);
+  hrtc.calculatePath(vMap, boost::ref(*this), pnlsr);
+}
+
+void
+RoutingTable::calculateHypDryRoutingTable(Nlsr& pnlsr)
+{
+  Map vMap;
+  vMap.createFromAdjLsdb(pnlsr);
+  int numOfRouter = vMap.getMapSize();
+  HypRoutingTableCalculator hrtc(numOfRouter, 1);
+  hrtc.calculatePath(vMap, boost::ref(*this), pnlsr);
+}
+
+void
+RoutingTable::scheduleRoutingTableCalculation(Nlsr& pnlsr)
+{
+  if (pnlsr.getIsRouteCalculationScheduled() != 1)
+  {
+    pnlsr.getScheduler().scheduleEvent(ndn::time::seconds(15),
+                                       ndn::bind(&RoutingTable::calculate, this, boost::ref(pnlsr)));
+    pnlsr.setIsRouteCalculationScheduled(1);
+  }
+}
+
+static bool
+routingTableEntryCompare(RoutingTableEntry& rte, string& destRouter)
+{
+  return rte.getDestination() == destRouter;
+}
+
+// function related to manipulation of routing table
+void
+RoutingTable::addNextHop(string destRouter, NextHop& nh)
+{
+  std::pair<RoutingTableEntry&, bool> rte = findRoutingTableEntry(destRouter);
+  if (!rte.second)
+  {
+    RoutingTableEntry rte(destRouter);
+    rte.getNhl().addNextHop(nh);
+    m_rTable.push_back(rte);
+  }
+  else
+  {
+    (rte.first).getNhl().addNextHop(nh);
+  }
+}
+
+std::pair<RoutingTableEntry&, bool>
+RoutingTable::findRoutingTableEntry(string destRouter)
+{
+  std::list<RoutingTableEntry>::iterator it = std::find_if(m_rTable.begin(),
+                                                           m_rTable.end(),
+                                                           bind(&routingTableEntryCompare, _1, destRouter));
+  if (it != m_rTable.end())
+  {
+    return std::make_pair(boost::ref((*it)), true);
+  }
+  RoutingTableEntry rteEmpty;
+  return std::make_pair(boost::ref(rteEmpty), false);
+}
+
+void
+RoutingTable::printRoutingTable()
+{
+  std::cout << "---------------Routing Table------------------" << std::endl;
+  for (std::list<RoutingTableEntry>::iterator it = m_rTable.begin() ;
+       it != m_rTable.end(); ++it)
+  {
+    std::cout << (*it) << std::endl;
+  }
+}
+
+
+//function related to manipulation of dry routing table
+void
+RoutingTable::addNextHopToDryTable(string destRouter, NextHop& nh)
+{
+  std::list<RoutingTableEntry>::iterator it = std::find_if(m_dryTable.begin(),
+                                                           m_dryTable.end(),
+                                                           bind(&routingTableEntryCompare, _1, destRouter));
+  if (it == m_dryTable.end())
+  {
+    RoutingTableEntry rte(destRouter);
+    rte.getNhl().addNextHop(nh);
+    m_dryTable.push_back(rte);
+  }
+  else
+  {
+    (*it).getNhl().addNextHop(nh);
+  }
+}
+
+void
+RoutingTable::printDryRoutingTable()
+{
+  std::cout << "--------Dry Run's Routing Table--------------" << std::endl;
+  for (std::list<RoutingTableEntry>::iterator it = m_dryTable.begin() ;
+       it != m_dryTable.end(); ++it)
+  {
+    cout << (*it) << endl;
+  }
+}
+
+
+void
+RoutingTable::clearRoutingTable()
+{
+  if (m_rTable.size() > 0)
+  {
+    m_rTable.clear();
+  }
+}
+
+void
+RoutingTable::clearDryRoutingTable()
+{
+  if (m_dryTable.size() > 0)
+  {
+    m_dryTable.clear();
+  }
+}
+
+}//namespace nlsr
+
diff --git a/src/route/routing-table.hpp b/src/route/routing-table.hpp
new file mode 100644
index 0000000..cc04915
--- /dev/null
+++ b/src/route/routing-table.hpp
@@ -0,0 +1,73 @@
+#ifndef NLSR_RT_HPP
+#define NLSR_RT_HPP
+
+#include <iostream>
+#include <utility>
+#include <string>
+
+#include "routing-table-entry.hpp"
+
+namespace nlsr {
+
+class Nlsr;
+class NextHop;
+
+class RoutingTable
+{
+public:
+  RoutingTable()
+    : m_NO_NEXT_HOP(-12345)
+  {
+  }
+  void
+  calculate(Nlsr& pnlsr);
+
+  void
+  addNextHop(std::string destRouter, NextHop& nh);
+
+  void
+  printRoutingTable();
+
+  void
+  addNextHopToDryTable(std::string destRouter, NextHop& nh);
+
+  void
+  printDryRoutingTable();
+
+  std::pair<RoutingTableEntry&, bool>
+  findRoutingTableEntry(std::string destRouter);
+
+  void
+  scheduleRoutingTableCalculation(Nlsr& pnlsr);
+
+  int
+  getNoNextHop()
+  {
+    return m_NO_NEXT_HOP;
+  }
+
+private:
+  void
+  calculateLsRoutingTable(Nlsr& pnlsr);
+
+  void
+  calculateHypRoutingTable(Nlsr& pnlsr);
+
+  void
+  calculateHypDryRoutingTable(Nlsr& pnlsr);
+
+  void
+  clearRoutingTable();
+
+  void
+  clearDryRoutingTable();
+
+  const int m_NO_NEXT_HOP;
+
+  std::list<RoutingTableEntry> m_rTable;
+  std::list<RoutingTableEntry> m_dryTable;
+};
+
+}//namespace nlsr
+
+#endif //NLSR_RT_HPP
