diff --git a/src/mgmt/nfd/rib-entry.cpp b/src/mgmt/nfd/rib-entry.cpp
index ed7fd67..17b53d6 100644
--- a/src/mgmt/nfd/rib-entry.cpp
+++ b/src/mgmt/nfd/rib-entry.cpp
@@ -20,34 +20,24 @@
  */
 
 #include "rib-entry.hpp"
-#include "encoding/tlv-nfd.hpp"
 #include "encoding/block-helpers.hpp"
+#include "encoding/encoding-buffer.hpp"
+#include "encoding/tlv-nfd.hpp"
 #include "util/concepts.hpp"
 
+#include <boost/range/adaptor/reversed.hpp>
+
 namespace ndn {
 namespace nfd {
 
-//BOOST_CONCEPT_ASSERT((boost::EqualityComparable<Route>));
-BOOST_CONCEPT_ASSERT((WireEncodable<Route>));
-BOOST_CONCEPT_ASSERT((WireDecodable<Route>));
-static_assert(std::is_base_of<tlv::Error, Route::Error>::value,
-              "Route::Error must inherit from tlv::Error");
-
-//BOOST_CONCEPT_ASSERT((boost::EqualityComparable<RibEntry>));
-BOOST_CONCEPT_ASSERT((WireEncodable<RibEntry>));
-BOOST_CONCEPT_ASSERT((WireDecodable<RibEntry>));
-static_assert(std::is_base_of<tlv::Error, RibEntry::Error>::value,
-              "RibEntry::Error must inherit from tlv::Error");
-
-const time::milliseconds Route::INFINITE_EXPIRATION_PERIOD(time::milliseconds::max());
+BOOST_CONCEPT_ASSERT((StatusDatasetItem<Route>));
+BOOST_CONCEPT_ASSERT((StatusDatasetItem<RibEntry>));
 
 Route::Route()
   : m_faceId(INVALID_FACE_ID)
   , m_origin(0)
   , m_cost(0)
   , m_flags(ROUTE_FLAG_CHILD_INHERIT)
-  , m_expirationPeriod(INFINITE_EXPIRATION_PERIOD)
-  , m_hasInfiniteExpirationPeriod(true)
 {
 }
 
@@ -91,8 +81,18 @@
 Route&
 Route::setExpirationPeriod(time::milliseconds expirationPeriod)
 {
+  if (expirationPeriod == time::milliseconds::max())
+    return unsetExpirationPeriod();
+
   m_expirationPeriod = expirationPeriod;
-  m_hasInfiniteExpirationPeriod = m_expirationPeriod == INFINITE_EXPIRATION_PERIOD;
+  m_wire.reset();
+  return *this;
+}
+
+Route&
+Route::unsetExpirationPeriod()
+{
+  m_expirationPeriod = nullopt;
   m_wire.reset();
   return *this;
 }
@@ -103,10 +103,9 @@
 {
   size_t totalLength = 0;
 
-  // Absence of an ExpirationPeriod signifies non-expiration
-  if (!m_hasInfiniteExpirationPeriod) {
+  if (m_expirationPeriod) {
     totalLength += prependNonNegativeIntegerBlock(block, ndn::tlv::nfd::ExpirationPeriod,
-                                                  static_cast<uint64_t>(m_expirationPeriod.count()));
+                                                  static_cast<uint64_t>(m_expirationPeriod->count()));
   }
   totalLength += prependNonNegativeIntegerBlock(block, ndn::tlv::nfd::Flags, m_flags);
   totalLength += prependNonNegativeIntegerBlock(block, ndn::tlv::nfd::Cost, m_cost);
@@ -141,25 +140,13 @@
 }
 
 void
-Route::wireDecode(const Block& wire)
+Route::wireDecode(const Block& block)
 {
-  m_faceId = 0;
-  m_origin = 0;
-  m_cost = 0;
-  m_flags = 0;
-  m_expirationPeriod = time::milliseconds::min();
-
-  m_wire = wire;
-
-  if (m_wire.type() != tlv::nfd::Route) {
-    std::stringstream error;
-    error << "Expected Route Block, but Block is of a different type: #"
-          << m_wire.type();
-    BOOST_THROW_EXCEPTION(Error(error.str()));
+  if (block.type() != tlv::nfd::Route) {
+    BOOST_THROW_EXCEPTION(Error("expecting Route, but Block has type " + to_string(block.type())));
   }
-
+  m_wire = block;
   m_wire.parse();
-
   Block::element_const_iterator val = m_wire.elements_begin();
 
   if (val != m_wire.elements_end() && val->type() == tlv::nfd::FaceId) {
@@ -167,7 +154,7 @@
     ++val;
   }
   else {
-    BOOST_THROW_EXCEPTION(Error("Missing required FaceId field"));
+    BOOST_THROW_EXCEPTION(Error("missing required FaceId field"));
   }
 
   if (val != m_wire.elements_end() && val->type() == tlv::nfd::Origin) {
@@ -175,7 +162,7 @@
     ++val;
   }
   else {
-    BOOST_THROW_EXCEPTION(Error("Missing required Origin field"));
+    BOOST_THROW_EXCEPTION(Error("missing required Origin field"));
   }
 
   if (val != m_wire.elements_end() && val->type() == tlv::nfd::Cost) {
@@ -183,7 +170,7 @@
     ++val;
   }
   else {
-    BOOST_THROW_EXCEPTION(Error("Missing required Cost field"));
+    BOOST_THROW_EXCEPTION(Error("missing required Cost field"));
   }
 
   if (val != m_wire.elements_end() && val->type() == tlv::nfd::Flags) {
@@ -191,38 +178,50 @@
     ++val;
   }
   else {
-    BOOST_THROW_EXCEPTION(Error("Missing required Flags field"));
+    BOOST_THROW_EXCEPTION(Error("missing required Flags field"));
   }
 
   if (val != m_wire.elements_end() && val->type() == tlv::nfd::ExpirationPeriod) {
-    m_expirationPeriod = time::milliseconds(readNonNegativeInteger(*val));
-    m_hasInfiniteExpirationPeriod = false;
+    m_expirationPeriod.emplace(readNonNegativeInteger(*val));
+    ++val;
   }
   else {
-    m_expirationPeriod = INFINITE_EXPIRATION_PERIOD;
-    m_hasInfiniteExpirationPeriod = true;
+    m_expirationPeriod = nullopt;
   }
 }
 
+bool
+operator==(const Route& a, const Route& b)
+{
+  return a.getFaceId() == b.getFaceId() &&
+      a.getOrigin() == b.getOrigin() &&
+      a.getCost() == b.getCost() &&
+      a.getFlags() == b.getFlags() &&
+      a.getExpirationPeriod() == b.getExpirationPeriod();
+}
+
 std::ostream&
 operator<<(std::ostream& os, const Route& route)
 {
   os << "Route("
      << "FaceId: " << route.getFaceId() << ", "
      << "Origin: " << route.getOrigin() << ", "
-     << "Cost: " << route.getCost() << ", "
-     << "Flags: " << route.getFlags() << ", ";
+     << "Cost: " << route.getCost() << ", ";
 
-  if (!route.hasInfiniteExpirationPeriod()) {
+  auto osFlags = os.flags();
+  // std::showbase doesn't work with number 0
+  os << "Flags: 0x" << std::noshowbase << std::noshowpos << std::nouppercase
+     << std::hex << route.getFlags() << ", ";
+  os.flags(osFlags);
+
+  if (route.hasExpirationPeriod()) {
     os << "ExpirationPeriod: " << route.getExpirationPeriod();
   }
   else {
-    os << "ExpirationPeriod: Infinity";
+    os << "ExpirationPeriod: infinite";
   }
 
-  os << ")";
-
-  return os;
+  return os << ")";
 }
 
 ////////////////////
@@ -264,12 +263,9 @@
 {
   size_t totalLength = 0;
 
-  for (std::list<Route>::const_reverse_iterator it = m_routes.rbegin();
-       it != m_routes.rend(); ++it)
-    {
-      totalLength += it->wireEncode(block);
-    }
-
+  for (const auto& route : m_routes | boost::adaptors::reversed) {
+    totalLength += route.wireEncode(block);
+  }
   totalLength += m_prefix.wireEncode(block);
 
   totalLength += block.prependVarNumber(totalLength);
@@ -300,59 +296,72 @@
 }
 
 void
-RibEntry::wireDecode(const Block& wire)
+RibEntry::wireDecode(const Block& block)
 {
-  m_prefix.clear();
-  m_routes.clear();
-
-  m_wire = wire;
-
-  if (m_wire.type() != tlv::nfd::RibEntry) {
-    std::stringstream error;
-    error << "Expected RibEntry Block, but Block is of a different type: #"
-          << m_wire.type();
-    BOOST_THROW_EXCEPTION(Error(error.str()));
+  if (block.type() != tlv::nfd::RibEntry) {
+    BOOST_THROW_EXCEPTION(Error("expecting RibEntry, but Block has type " + to_string(block.type())));
   }
-
+  m_wire = block;
   m_wire.parse();
-
   Block::element_const_iterator val = m_wire.elements_begin();
 
-  if (val != m_wire.elements_end() && val->type() == tlv::Name) {
-    m_prefix.wireDecode(*val);
-    ++val;
+  if (val == m_wire.elements_end()) {
+    BOOST_THROW_EXCEPTION(Error("unexpected end of RibEntry"));
   }
-  else {
-    BOOST_THROW_EXCEPTION(Error("Missing required Name field"));
+  else if (val->type() != tlv::Name) {
+    BOOST_THROW_EXCEPTION(Error("expecting Name, but Block has type " + to_string(val->type())));
   }
+  m_prefix.wireDecode(*val);
+  ++val;
 
+  m_routes.clear();
   for (; val != m_wire.elements_end(); ++val) {
-
-    if (val->type() == tlv::nfd::Route) {
-      m_routes.push_back(Route(*val));
+    if (val->type() != tlv::nfd::Route) {
+      BOOST_THROW_EXCEPTION(Error("expecting Route, but Block has type " + to_string(val->type())));
     }
-    else {
-      std::stringstream error;
-      error << "Expected Route Block, but Block is of a different type: #"
-            << m_wire.type();
-      BOOST_THROW_EXCEPTION(Error(error.str()));
-    }
+    m_routes.emplace_back(*val);
   }
 }
 
+bool
+operator==(const RibEntry& a, const RibEntry& b)
+{
+  const auto& aRoutes = a.getRoutes();
+  const auto& bRoutes = b.getRoutes();
+
+  if (a.getName() != b.getName() ||
+      aRoutes.size() != bRoutes.size())
+    return false;
+
+  std::vector<bool> matched(bRoutes.size(), false);
+  return std::all_of(aRoutes.begin(), aRoutes.end(),
+                     [&] (const Route& route) {
+                       for (size_t i = 0; i < bRoutes.size(); ++i) {
+                         if (!matched[i] && bRoutes[i] == route) {
+                           matched[i] = true;
+                           return true;
+                         }
+                       }
+                       return false;
+                     });
+}
+
 std::ostream&
 operator<<(std::ostream& os, const RibEntry& entry)
 {
-  os << "RibEntry{\n"
-     << "  Name: " << entry.getName() << "\n";
+  os << "RibEntry(Prefix: " << entry.getName() << ",\n"
+     << "         Routes: [";
 
-  for (RibEntry::iterator it = entry.begin(); it != entry.end(); ++it) {
-    os << "  " << *it << "\n";
+  bool isFirst = true;
+  for (const auto& route : entry.getRoutes()) {
+    if (!isFirst)
+      os << ",\n                  ";
+    isFirst = false;
+    os << route;
   }
+  os << "]\n";
 
-  os << "}";
-
-  return os;
+  return os << "         )";
 }
 
 } // namespace nfd
diff --git a/src/mgmt/nfd/rib-entry.hpp b/src/mgmt/nfd/rib-entry.hpp
index b0d7289..0c2071d 100644
--- a/src/mgmt/nfd/rib-entry.hpp
+++ b/src/mgmt/nfd/rib-entry.hpp
@@ -23,30 +23,21 @@
 #define NDN_MGMT_NFD_RIB_ENTRY_HPP
 
 #include "rib-flags.hpp"
+#include "../../encoding/block.hpp"
 #include "../../name.hpp"
 #include "../../util/time.hpp"
 
-#include <list>
-
 namespace ndn {
 namespace nfd {
 
 /**
- * @ingroup management
- *
- * @brief Data abstraction for Route
+ * \ingroup management
+ * \brief represents a route in a RibEntry
  *
  * A route indicates the availability of content via a certain face and
  * provides meta-information about the face.
  *
- *     Route := ROUTE-TYPE TLV-LENGTH
- *                FaceId
- *                Origin
- *                Cost
- *                Flags
- *                ExpirationPeriod?
- *
- * @sa http://redmine.named-data.net/projects/nfd/wiki/RibMgmt
+ * \sa https://redmine.named-data.net/projects/nfd/wiki/RibMgmt#Route
  */
 class Route : public RibFlagsTraits<Route>
 {
@@ -108,22 +99,23 @@
   Route&
   setFlags(uint64_t flags);
 
-  static const time::milliseconds INFINITE_EXPIRATION_PERIOD;
+  bool
+  hasExpirationPeriod() const
+  {
+    return !!m_expirationPeriod;
+  }
 
   time::milliseconds
   getExpirationPeriod() const
   {
-    return m_expirationPeriod;
+    return m_expirationPeriod ? *m_expirationPeriod : time::milliseconds::max();
   }
 
   Route&
   setExpirationPeriod(time::milliseconds expirationPeriod);
 
-  bool
-  hasInfiniteExpirationPeriod() const
-  {
-    return m_hasInfiniteExpirationPeriod;
-  }
+  Route&
+  unsetExpirationPeriod();
 
   template<encoding::Tag TAG>
   size_t
@@ -133,34 +125,38 @@
   wireEncode() const;
 
   void
-  wireDecode(const Block& wire);
+  wireDecode(const Block& block);
 
 private:
   uint64_t m_faceId;
   uint64_t m_origin;
   uint64_t m_cost;
   uint64_t m_flags;
-  time::milliseconds m_expirationPeriod;
-  bool m_hasInfiniteExpirationPeriod;
+  optional<time::milliseconds> m_expirationPeriod;
 
   mutable Block m_wire;
 };
 
+bool
+operator==(const Route& a, const Route& b);
+
+inline bool
+operator!=(const Route& a, const Route& b)
+{
+  return !(a == b);
+}
+
 std::ostream&
 operator<<(std::ostream& os, const Route& route);
 
+
 /**
- * @ingroup management
+ * \ingroup management
+ * \brief represents an item in NFD RIB dataset
  *
- * @brief Data abstraction for RIB entry
+ * A RIB entry contains one or more routes for a name prefix
  *
- * A RIB entry contains one or more routes for the name prefix
- *
- *     RibEntry := RIB-ENTRY-TYPE TLV-LENGTH
- *                Name
- *                Route+
- *
- * @sa http://redmine.named-data.net/projects/nfd/wiki/RibMgmt
+ * \sa https://redmine.named-data.net/projects/nfd/wiki/RibMgmt#RIB-Dataset
  */
 class RibEntry
 {
@@ -175,9 +171,6 @@
     }
   };
 
-  typedef std::list<Route> RouteList;
-  typedef RouteList::const_iterator iterator;
-
   RibEntry();
 
   explicit
@@ -192,12 +185,21 @@
   RibEntry&
   setName(const Name& prefix);
 
-  const std::list<Route>&
+  const std::vector<Route>&
   getRoutes() const
   {
     return m_routes;
   }
 
+  template<typename InputIt>
+  RibEntry&
+  setRoutes(InputIt first, InputIt last)
+  {
+    m_routes.assign(first, last);
+    m_wire.reset();
+    return *this;
+  }
+
   RibEntry&
   addRoute(const Route& route);
 
@@ -212,31 +214,22 @@
   wireEncode() const;
 
   void
-  wireDecode(const Block& wire);
-
-  iterator
-  begin() const;
-
-  iterator
-  end() const;
+  wireDecode(const Block& block);
 
 private:
   Name m_prefix;
-  RouteList m_routes;
+  std::vector<Route> m_routes;
 
   mutable Block m_wire;
 };
 
-inline RibEntry::iterator
-RibEntry::begin() const
-{
-  return m_routes.begin();
-}
+bool
+operator==(const RibEntry& a, const RibEntry& b);
 
-inline RibEntry::iterator
-RibEntry::end() const
+inline bool
+operator!=(const RibEntry& a, const RibEntry& b)
 {
-  return m_routes.end();
+  return !(a == b);
 }
 
 std::ostream&
diff --git a/src/mgmt/nfd/rib-flags.hpp b/src/mgmt/nfd/rib-flags.hpp
index 158048f..ebc2b9e 100644
--- a/src/mgmt/nfd/rib-flags.hpp
+++ b/src/mgmt/nfd/rib-flags.hpp
@@ -1,6 +1,6 @@
 /* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
 /**
- * Copyright (c) 2013-2016 Regents of the University of California.
+ * Copyright (c) 2013-2017 Regents of the University of California.
  *
  * This file is part of ndn-cxx library (NDN C++ library with eXperimental eXtensions).
  *
@@ -29,10 +29,10 @@
 
 /**
  * \ingroup management
- * \brief implements getters to each RIB flag
+ * \brief defines getters for each route inheritance flag
  *
- * \tparam T class containing a RibFlags field and implements
- *           `RibFlags getFlags() const` method
+ * \tparam T class containing a RouteFlags field and implementing
+ *           a `RouteFlags getFlags() const` member function
  */
 template<typename T>
 class RibFlagsTraits
@@ -49,6 +49,9 @@
   {
     return static_cast<const T*>(this)->getFlags() & ROUTE_FLAG_CAPTURE;
   }
+
+protected:
+  RibFlagsTraits() = default;
 };
 
 } // namespace nfd
diff --git a/tests/unit-tests/mgmt/nfd/rib-entry.t.cpp b/tests/unit-tests/mgmt/nfd/rib-entry.t.cpp
index 415be29..cc3ed58 100644
--- a/tests/unit-tests/mgmt/nfd/rib-entry.t.cpp
+++ b/tests/unit-tests/mgmt/nfd/rib-entry.t.cpp
@@ -1,6 +1,6 @@
 /* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
 /**
- * Copyright (c) 2013-2016 Regents of the University of California.
+ * Copyright (c) 2013-2017 Regents of the University of California.
  *
  * This file is part of ndn-cxx library (NDN C++ library with eXperimental eXtensions).
  *
@@ -20,9 +20,9 @@
  */
 
 #include "mgmt/nfd/rib-entry.hpp"
-#include "mgmt/nfd/control-command.hpp"
 
 #include "boost-test.hpp"
+#include <boost/lexical_cast.hpp>
 
 namespace ndn {
 namespace nfd {
@@ -32,310 +32,182 @@
 BOOST_AUTO_TEST_SUITE(Nfd)
 BOOST_AUTO_TEST_SUITE(TestRibEntry)
 
-const uint8_t RouteData[] =
+static Route
+makeRoute()
 {
-  0x81, 0x10, 0x69, 0x01, 0x01, 0x6f, 0x01, 0x80, 0x6a, 0x01, 0x64, 0x6c, 0x01, 0x02,
-  0x6d, 0x02, 0x27, 0x10
-};
+  return Route()
+      .setFaceId(1)
+      .setOrigin(128)
+      .setCost(100)
+      .setFlags(ndn::nfd::ROUTE_FLAG_CAPTURE);
+}
 
-const uint8_t RouteInfiniteExpirationPeriod[] =
+static RibEntry
+makeRibEntry()
 {
-  0x81, 0x0C, 0x69, 0x01, 0x01, 0x6f, 0x01, 0x80, 0x6a, 0x01, 0x64, 0x6c, 0x01, 0x02
-};
-
-const uint8_t RibEntryData[] =
-{
-  // Header + Name
-  0x80, 0x34, 0x07, 0x0e, 0x08, 0x05, 0x68, 0x65, 0x6c, 0x6c, 0x6f,
-  0x08, 0x05, 0x77, 0x6f, 0x72, 0x6c, 0x64,
-  // Route
-  0x81, 0x10, 0x69, 0x01, 0x01, 0x6f, 0x01, 0x80, 0x6a, 0x01, 0x64, 0x6c, 0x01, 0x02,
-  0x6d, 0x02, 0x27, 0x10,
-  // Route
-  0x81, 0x10, 0x69, 0x01, 0x02, 0x6f, 0x01, 0x00, 0x6a, 0x01, 0x20, 0x6c, 0x01, 0x01,
-  0x6d, 0x02, 0x13, 0x88
-};
-
-const uint8_t RibEntryInfiniteExpirationPeriod[] =
-{
-  // Header + Name
-  0x80, 0x30, 0x07, 0x0e, 0x08, 0x05, 0x68, 0x65, 0x6c, 0x6c, 0x6f,
-  0x08, 0x05, 0x77, 0x6f, 0x72, 0x6c, 0x64,
-  // Route
-  0x81, 0x10, 0x69, 0x01, 0x01, 0x6f, 0x01, 0x80, 0x6a, 0x01, 0x64, 0x6c, 0x01, 0x02,
-  0x6d, 0x02, 0x27, 0x10,
-  // Route with no ExpirationPeriod
-  0x81, 0x0C, 0x69, 0x01, 0x02, 0x6f, 0x01, 0x00, 0x6a, 0x01, 0x20, 0x6c, 0x01, 0x01,
-};
+  return RibEntry()
+      .setName("/hello/world")
+      .addRoute(makeRoute()
+                .setExpirationPeriod(time::seconds(10)));
+}
 
 BOOST_AUTO_TEST_CASE(RouteEncode)
 {
-  Route route;
-  route.setFaceId(1);
-  route.setOrigin(128);
-  route.setCost(100);
-  route.setFlags(ndn::nfd::ROUTE_FLAG_CAPTURE);
-  route.setExpirationPeriod(time::milliseconds(10000));
+  Route route1 = makeRoute();
+  route1.setExpirationPeriod(time::seconds(10));
+  const Block& wire = route1.wireEncode();
 
-  const Block& wire = route.wireEncode();
+  static const uint8_t expected[] = {
+    0x81, 0x10, 0x69, 0x01, 0x01, 0x6f, 0x01, 0x80, 0x6a, 0x01, 0x64, 0x6c, 0x01, 0x02,
+    0x6d, 0x02, 0x27, 0x10
+  };
+  BOOST_CHECK_EQUAL_COLLECTIONS(expected, expected + sizeof(expected),
+                                wire.begin(), wire.end());
 
-  BOOST_REQUIRE_EQUAL_COLLECTIONS(RouteData,
-                                  RouteData + sizeof(RouteData),
-                                  wire.begin(), wire.end());
+  Route route2(wire);
+  BOOST_CHECK_EQUAL(route1, route2);
 }
 
-BOOST_AUTO_TEST_CASE(RouteDecode)
+BOOST_AUTO_TEST_CASE(RouteNoExpirationPeriodEncode)
 {
-  Route route;
+  Route route1 = makeRoute();
+  const Block& wire = route1.wireEncode();
 
-  BOOST_REQUIRE_NO_THROW(route.wireDecode(Block(RouteData, sizeof(RouteData))));
+  static const uint8_t expected[] = {
+    0x81, 0x0C, 0x69, 0x01, 0x01, 0x6f, 0x01, 0x80, 0x6a, 0x01, 0x64, 0x6c, 0x01, 0x02
+  };
+  BOOST_CHECK_EQUAL_COLLECTIONS(expected, expected + sizeof(expected),
+                                wire.begin(), wire.end());
 
-  BOOST_REQUIRE_EQUAL(route.getFaceId(), 1);
-  BOOST_REQUIRE_EQUAL(route.getOrigin(), 128);
-  BOOST_REQUIRE_EQUAL(route.getCost(), 100);
-  BOOST_REQUIRE_EQUAL(route.getFlags(), static_cast<uint64_t>(ndn::nfd::ROUTE_FLAG_CAPTURE));
-  BOOST_REQUIRE_EQUAL(route.getExpirationPeriod(), time::milliseconds(10000));
-  BOOST_REQUIRE_EQUAL(route.hasInfiniteExpirationPeriod(), false);
+  Route route2(wire);
+  BOOST_CHECK_EQUAL(route1, route2);
 }
 
-BOOST_AUTO_TEST_CASE(RouteInfiniteExpirationPeriodEncode)
+BOOST_AUTO_TEST_CASE(RouteEquality)
 {
-  Route route;
-  route.setFaceId(1);
-  route.setOrigin(128);
-  route.setCost(100);
-  route.setFlags(ndn::nfd::ROUTE_FLAG_CAPTURE);
-  route.setExpirationPeriod(Route::INFINITE_EXPIRATION_PERIOD);
+  Route route1, route2;
 
-  const Block& wire = route.wireEncode();
+  route1 = makeRoute();
+  route2 = route1;
+  BOOST_CHECK_EQUAL(route1, route2);
 
-  BOOST_REQUIRE_EQUAL_COLLECTIONS(RouteInfiniteExpirationPeriod,
-                                  RouteInfiniteExpirationPeriod + sizeof(RouteInfiniteExpirationPeriod),
-                                  wire.begin(), wire.end());
-}
+  route2.setFaceId(42);
+  BOOST_CHECK_NE(route1, route2);
 
-BOOST_AUTO_TEST_CASE(RouteInfiniteExpirationPeriodDecode)
-{
-  Route route;
-
-  BOOST_REQUIRE_NO_THROW(route.wireDecode(Block(RouteInfiniteExpirationPeriod,
-                                                sizeof(RouteInfiniteExpirationPeriod))));
-
-  BOOST_REQUIRE_EQUAL(route.getFaceId(), 1);
-  BOOST_REQUIRE_EQUAL(route.getOrigin(), 128);
-  BOOST_REQUIRE_EQUAL(route.getCost(), 100);
-  BOOST_REQUIRE_EQUAL(route.getFlags(), static_cast<uint64_t>(ndn::nfd::ROUTE_FLAG_CAPTURE));
-  BOOST_REQUIRE_EQUAL(route.getExpirationPeriod(), Route::INFINITE_EXPIRATION_PERIOD);
-  BOOST_REQUIRE_EQUAL(route.hasInfiniteExpirationPeriod(), true);
-}
-
-BOOST_AUTO_TEST_CASE(RouteOutputStream)
-{
-  Route route;
-  route.setFaceId(1);
-  route.setOrigin(128);
-  route.setCost(100);
-  route.setFlags(ndn::nfd::ROUTE_FLAG_CAPTURE);
-  route.setExpirationPeriod(time::milliseconds(10000));
-
-  std::ostringstream os;
-  os << route;
-
-  BOOST_CHECK_EQUAL(os.str(), "Route(FaceId: 1, Origin: 128, Cost: 100, "
-                              "Flags: 2, ExpirationPeriod: 10000 milliseconds)");
+  route2 = route1;
+  route2.setExpirationPeriod(time::minutes(1));
+  BOOST_CHECK_NE(route1, route2);
 }
 
 BOOST_AUTO_TEST_CASE(RibEntryEncode)
 {
-  RibEntry entry;
-  entry.setName("/hello/world");
+  RibEntry entry1 = makeRibEntry();
+  entry1.addRoute(Route()
+                  .setFaceId(2)
+                  .setOrigin(0)
+                  .setCost(32)
+                  .setFlags(ndn::nfd::ROUTE_FLAG_CHILD_INHERIT)
+                  .setExpirationPeriod(time::seconds(5)));
+  const Block& wire = entry1.wireEncode();
 
-  Route route1;
-  route1.setFaceId(1);
-  route1.setOrigin(128);
-  route1.setCost(100);
-  route1.setFlags(ndn::nfd::ROUTE_FLAG_CAPTURE);
-  route1.setExpirationPeriod(time::milliseconds(10000));
-  entry.addRoute(route1);
-
-  Route route2;
-  route2.setFaceId(2);
-  route2.setOrigin(0);
-  route2.setCost(32);
-  route2.setFlags(ndn::nfd::ROUTE_FLAG_CHILD_INHERIT);
-  route2.setExpirationPeriod(time::milliseconds(5000));
-  entry.addRoute(route2);
-
-  const Block& wire = entry.wireEncode();
-
-  BOOST_CHECK_EQUAL_COLLECTIONS(RibEntryData,
-                                RibEntryData + sizeof(RibEntryData),
+  static const uint8_t expected[] = {
+    0x80, 0x34, 0x07, 0x0e, 0x08, 0x05, 0x68, 0x65, 0x6c, 0x6c, 0x6f, 0x08, 0x05, 0x77,
+    0x6f, 0x72, 0x6c, 0x64, 0x81, 0x10, 0x69, 0x01, 0x01, 0x6f, 0x01, 0x80, 0x6a, 0x01,
+    0x64, 0x6c, 0x01, 0x02, 0x6d, 0x02, 0x27, 0x10, 0x81, 0x10, 0x69, 0x01, 0x02, 0x6f,
+    0x01, 0x00, 0x6a, 0x01, 0x20, 0x6c, 0x01, 0x01, 0x6d, 0x02, 0x13, 0x88
+  };
+  BOOST_CHECK_EQUAL_COLLECTIONS(expected, expected + sizeof(expected),
                                 wire.begin(), wire.end());
+
+  RibEntry entry2(wire);
+  BOOST_CHECK_EQUAL(entry1, entry2);
 }
 
-BOOST_AUTO_TEST_CASE(RibEntryDecode)
-{
-  RibEntry entry;
-  BOOST_REQUIRE_NO_THROW(entry.wireDecode(Block(RibEntryData,
-                                          sizeof(RibEntryData))));
-
-  BOOST_CHECK_EQUAL(entry.getName(), "/hello/world");
-  BOOST_CHECK_EQUAL(entry.getRoutes().size(), 2);
-
-  std::list<Route> routes = entry.getRoutes();
-
-  std::list<Route>::const_iterator it = routes.begin();
-  BOOST_CHECK_EQUAL(it->getFaceId(), 1);
-  BOOST_CHECK_EQUAL(it->getOrigin(), 128);
-  BOOST_CHECK_EQUAL(it->getCost(), 100);
-  BOOST_CHECK_EQUAL(it->getFlags(), static_cast<uint64_t>(ndn::nfd::ROUTE_FLAG_CAPTURE));
-  BOOST_CHECK_EQUAL(it->getExpirationPeriod(), time::milliseconds(10000));
-  BOOST_CHECK_EQUAL(it->hasInfiniteExpirationPeriod(), false);
-
-  ++it;
-  BOOST_CHECK_EQUAL(it->getFaceId(), 2);
-  BOOST_CHECK_EQUAL(it->getOrigin(), 0);
-  BOOST_CHECK_EQUAL(it->getCost(), 32);
-  BOOST_CHECK_EQUAL(it->getFlags(), static_cast<uint64_t>(ndn::nfd::ROUTE_FLAG_CHILD_INHERIT));
-  BOOST_CHECK_EQUAL(it->getExpirationPeriod(), time::milliseconds(5000));
-  BOOST_CHECK_EQUAL(it->hasInfiniteExpirationPeriod(), false);
-}
-
-BOOST_AUTO_TEST_CASE(RibEntryInfiniteExpirationPeriodEncode)
+BOOST_AUTO_TEST_CASE(RibEntryClearRoutes)
 {
   RibEntry entry;
   entry.setName("/hello/world");
+  BOOST_CHECK_EQUAL(entry.getRoutes().size(), 0);
 
   Route route1;
-  route1.setFaceId(1);
-  route1.setOrigin(128);
-  route1.setCost(100);
-  route1.setFlags(ndn::nfd::ROUTE_FLAG_CAPTURE);
-  route1.setExpirationPeriod(time::milliseconds(10000));
-  entry.addRoute(route1);
-
-  Route route2;
-  route2.setFaceId(2);
-  route2.setOrigin(0);
-  route2.setCost(32);
-  route2.setFlags(ndn::nfd::ROUTE_FLAG_CHILD_INHERIT);
-  route2.setExpirationPeriod(Route::INFINITE_EXPIRATION_PERIOD);
-  entry.addRoute(route2);
-
-  const Block& wire = entry.wireEncode();
-
-  BOOST_CHECK_EQUAL_COLLECTIONS(RibEntryInfiniteExpirationPeriod,
-                                RibEntryInfiniteExpirationPeriod +
-                                sizeof(RibEntryInfiniteExpirationPeriod),
-                                wire.begin(), wire.end());
-}
-
-BOOST_AUTO_TEST_CASE(RibEntryInfiniteExpirationPeriodDecode)
-{
-  RibEntry entry;
-  BOOST_REQUIRE_NO_THROW(entry.wireDecode(Block(RibEntryInfiniteExpirationPeriod,
-                                          sizeof(RibEntryInfiniteExpirationPeriod))));
-
-  BOOST_CHECK_EQUAL(entry.getName(), "/hello/world");
-  BOOST_CHECK_EQUAL(entry.getRoutes().size(), 2);
-
-  std::list<Route> routes = entry.getRoutes();
-
-  std::list<Route>::const_iterator it = routes.begin();
-  BOOST_CHECK_EQUAL(it->getFaceId(), 1);
-  BOOST_CHECK_EQUAL(it->getOrigin(), 128);
-  BOOST_CHECK_EQUAL(it->getCost(), 100);
-  BOOST_CHECK_EQUAL(it->getFlags(), static_cast<uint64_t>(ndn::nfd::ROUTE_FLAG_CAPTURE));
-  BOOST_CHECK_EQUAL(it->getExpirationPeriod(), time::milliseconds(10000));
-  BOOST_CHECK_EQUAL(it->hasInfiniteExpirationPeriod(), false);
-
-  ++it;
-  BOOST_CHECK_EQUAL(it->getFaceId(), 2);
-  BOOST_CHECK_EQUAL(it->getOrigin(), 0);
-  BOOST_CHECK_EQUAL(it->getCost(), 32);
-  BOOST_CHECK_EQUAL(it->getFlags(), static_cast<uint64_t>(ndn::nfd::ROUTE_FLAG_CHILD_INHERIT));
-  BOOST_CHECK_EQUAL(it->getExpirationPeriod(), Route::INFINITE_EXPIRATION_PERIOD);
-  BOOST_CHECK_EQUAL(it->hasInfiniteExpirationPeriod(), true);
-}
-
-BOOST_AUTO_TEST_CASE(RibEntryClear)
-{
-  RibEntry entry;
-  entry.setName("/hello/world");
-
-  Route route1;
-  route1.setFaceId(1);
-  route1.setOrigin(128);
-  route1.setCost(100);
-  route1.setFlags(ndn::nfd::ROUTE_FLAG_CAPTURE);
-  route1.setExpirationPeriod(time::milliseconds(10000));
+  route1.setFaceId(42);
   entry.addRoute(route1);
   BOOST_REQUIRE_EQUAL(entry.getRoutes().size(), 1);
-
-  std::list<Route> routes = entry.getRoutes();
-
-  std::list<Route>::const_iterator it = routes.begin();
-  BOOST_CHECK_EQUAL(it->getFaceId(), 1);
-  BOOST_CHECK_EQUAL(it->getOrigin(), 128);
-  BOOST_CHECK_EQUAL(it->getCost(), 100);
-  BOOST_CHECK_EQUAL(it->getFlags(), static_cast<uint64_t>(ndn::nfd::ROUTE_FLAG_CAPTURE));
-  BOOST_CHECK_EQUAL(it->getExpirationPeriod(), time::milliseconds(10000));
-  BOOST_CHECK_EQUAL(it->hasInfiniteExpirationPeriod(), false);
+  BOOST_CHECK_EQUAL(entry.getRoutes().front(), route1);
 
   entry.clearRoutes();
   BOOST_CHECK_EQUAL(entry.getRoutes().size(), 0);
-
-  Route route2;
-  route2.setFaceId(2);
-  route2.setOrigin(0);
-  route2.setCost(32);
-  route2.setFlags(ndn::nfd::ROUTE_FLAG_CHILD_INHERIT);
-  route2.setExpirationPeriod(Route::INFINITE_EXPIRATION_PERIOD);
-  entry.addRoute(route2);
-  BOOST_REQUIRE_EQUAL(entry.getRoutes().size(), 1);
-
-  routes = entry.getRoutes();
-
-  it = routes.begin();
-  BOOST_CHECK_EQUAL(it->getFaceId(), 2);
-  BOOST_CHECK_EQUAL(it->getOrigin(), 0);
-  BOOST_CHECK_EQUAL(it->getCost(), 32);
-  BOOST_CHECK_EQUAL(it->getFlags(), static_cast<uint64_t>(ndn::nfd::ROUTE_FLAG_CHILD_INHERIT));
-  BOOST_CHECK_EQUAL(it->getExpirationPeriod(), Route::INFINITE_EXPIRATION_PERIOD);
-  BOOST_CHECK_EQUAL(it->hasInfiniteExpirationPeriod(), true);
 }
 
-BOOST_AUTO_TEST_CASE(RibEntryOutputStream)
+BOOST_AUTO_TEST_CASE(RibEntryEquality)
 {
+  RibEntry entry1, entry2;
+  BOOST_CHECK_EQUAL(entry1, entry2);
+
+  entry1 = entry2 = makeRibEntry();
+  BOOST_CHECK_EQUAL(entry1, entry2);
+  BOOST_CHECK_EQUAL(entry2, entry1);
+
+  entry2.setName("/different/name");
+  BOOST_CHECK_NE(entry1, entry2);
+
+  entry2 = entry1;
+  std::vector<Route> empty;
+  entry2.setRoutes(empty.begin(), empty.end());
+  BOOST_CHECK_NE(entry1, entry2);
+  BOOST_CHECK_NE(entry2, entry1);
+
+  entry2 = entry1;
+  auto r1 = Route()
+            .setFaceId(1)
+            .setCost(1000);
+  entry1.addRoute(r1);
+  BOOST_CHECK_NE(entry1, entry2);
+  BOOST_CHECK_NE(entry2, entry1);
+
+  auto r42 = Route()
+             .setFaceId(42)
+             .setCost(42);
+  entry1.addRoute(r42);
+  entry2.addRoute(r42)
+      .addRoute(r1);
+  BOOST_CHECK_EQUAL(entry1, entry2); // order of Routes is irrelevant
+  BOOST_CHECK_EQUAL(entry2, entry1);
+
+  entry1 = entry2 = makeRibEntry();
+  entry1.addRoute(r1)
+      .addRoute(r42);
+  entry2.addRoute(r42)
+      .addRoute(r42);
+  BOOST_CHECK_NE(entry1, entry2); // match each Route at most once
+  BOOST_CHECK_NE(entry2, entry1);
+}
+
+BOOST_AUTO_TEST_CASE(Print)
+{
+  Route route;
+  BOOST_CHECK_EQUAL(boost::lexical_cast<std::string>(route),
+                    "Route(FaceId: 0, Origin: 0, Cost: 0, Flags: 0x1, ExpirationPeriod: infinite)");
+
   RibEntry entry;
-  entry.setName("/hello/world");
+  BOOST_CHECK_EQUAL(boost::lexical_cast<std::string>(entry),
+                    "RibEntry(Prefix: /,\n"
+                    "         Routes: []\n"
+                    "         )");
 
-  Route route1;
-  route1.setFaceId(1);
-  route1.setOrigin(128);
-  route1.setCost(100);
-  route1.setFlags(ndn::nfd::ROUTE_FLAG_CAPTURE);
-  route1.setExpirationPeriod(time::milliseconds(10000));
-  entry.addRoute(route1);
-
-  Route route2;
-  route2.setFaceId(2);
-  route2.setOrigin(0);
-  route2.setCost(32);
-  route2.setFlags(ndn::nfd::ROUTE_FLAG_CHILD_INHERIT);
-  route2.setExpirationPeriod(Route::INFINITE_EXPIRATION_PERIOD);
-  entry.addRoute(route2);
-
-  std::ostringstream os;
-  os << entry;
-
-  BOOST_CHECK_EQUAL(os.str(), "RibEntry{\n"
-                              "  Name: /hello/world\n"
-                              "  Route(FaceId: 1, Origin: 128, Cost: 100, "
-                              "Flags: 2, ExpirationPeriod: 10000 milliseconds)\n"
-                              "  Route(FaceId: 2, Origin: 0, Cost: 32, "
-                              "Flags: 1, ExpirationPeriod: Infinity)\n"
-                              "}");
+  entry = makeRibEntry();
+  entry.addRoute(Route()
+                 .setFaceId(2)
+                 .setOrigin(0)
+                 .setCost(32)
+                 .setFlags(ndn::nfd::ROUTE_FLAG_CHILD_INHERIT));
+  BOOST_CHECK_EQUAL(boost::lexical_cast<std::string>(entry),
+                    "RibEntry(Prefix: /hello/world,\n"
+                    "         Routes: [Route(FaceId: 1, Origin: 128, Cost: 100, Flags: 0x2, "
+                    "ExpirationPeriod: 10000 milliseconds),\n"
+                    "                  Route(FaceId: 2, Origin: 0, Cost: 32, Flags: 0x1, "
+                    "ExpirationPeriod: infinite)]\n"
+                    "         )");
 }
 
 BOOST_AUTO_TEST_SUITE_END() // TestRibEntry
