util: FaceUri canonize dev scheme
refs #4027
Change-Id: Iee36b72c237824e8e2aed4a93786accc1464f62f
diff --git a/src/util/face-uri.cpp b/src/util/face-uri.cpp
index e58dd1d..83ad2eb 100644
--- a/src/util/face-uri.cpp
+++ b/src/util/face-uri.cpp
@@ -1,12 +1,12 @@
/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
/**
- * Copyright (c) 2014-2017, Regents of the University of California,
- * Arizona Board of Regents,
- * Colorado State University,
- * University Pierre & Marie Curie, Sorbonne University,
- * Washington University in St. Louis,
- * Beijing Institute of Technology,
- * The University of Memphis.
+ * Copyright (c) 2013-2017 Regents of the University of California,
+ * Arizona Board of Regents,
+ * Colorado State University,
+ * University Pierre & Marie Curie, Sorbonne University,
+ * Washington University in St. Louis,
+ * Beijing Institute of Technology,
+ * The University of Memphis.
*
* This file is part of ndn-cxx library (NDN C++ library with eXperimental eXtensions).
*
@@ -233,7 +233,7 @@
canonize(const FaceUri& faceUri,
const FaceUri::CanonizeSuccessCallback& onSuccess,
const FaceUri::CanonizeFailureCallback& onFailure,
- boost::asio::io_service& io, const time::nanoseconds& timeout) const = 0;
+ boost::asio::io_service& io, time::nanoseconds timeout) const = 0;
};
template<typename Protocol>
@@ -275,7 +275,7 @@
canonize(const FaceUri& faceUri,
const FaceUri::CanonizeSuccessCallback& onSuccess,
const FaceUri::CanonizeFailureCallback& onFailure,
- boost::asio::io_service& io, const time::nanoseconds& timeout) const override
+ boost::asio::io_service& io, time::nanoseconds timeout) const override
{
if (this->isCanonical(faceUri)) {
onSuccess(faceUri);
@@ -433,7 +433,7 @@
canonize(const FaceUri& faceUri,
const FaceUri::CanonizeSuccessCallback& onSuccess,
const FaceUri::CanonizeFailureCallback& onFailure,
- boost::asio::io_service& io, const time::nanoseconds& timeout) const override
+ boost::asio::io_service& io, time::nanoseconds timeout) const override
{
auto addr = ethernet::Address::fromString(faceUri.getHost());
if (addr.isNull()) {
@@ -446,6 +446,46 @@
}
};
+class DevCanonizeProvider : public CanonizeProvider
+{
+public:
+ std::set<std::string>
+ getSchemes() const override
+ {
+ return {"dev"};
+ }
+
+ bool
+ isCanonical(const FaceUri& faceUri) const override
+ {
+ return !faceUri.getHost().empty() && faceUri.getPort().empty() && faceUri.getPath().empty();
+ }
+
+ void
+ canonize(const FaceUri& faceUri,
+ const FaceUri::CanonizeSuccessCallback& onSuccess,
+ const FaceUri::CanonizeFailureCallback& onFailure,
+ boost::asio::io_service& io, time::nanoseconds timeout) const override
+ {
+ if (faceUri.getHost().empty()) {
+ onFailure("network interface name is missing");
+ return;
+ }
+ if (!faceUri.getPort().empty()) {
+ onFailure("port number is not allowed");
+ return;
+ }
+ if (!faceUri.getPath().empty() && faceUri.getPath() != "/") { // permit trailing slash only
+ onFailure("path is not allowed");
+ return;
+ }
+
+ FaceUri canonicalUri = FaceUri::fromDev(faceUri.getHost());
+ BOOST_ASSERT(canonicalUri.isCanonical());
+ onSuccess(canonicalUri);
+ }
+};
+
class UdpDevCanonizeProvider : public CanonizeProvider
{
public:
@@ -471,7 +511,7 @@
canonize(const FaceUri& faceUri,
const FaceUri::CanonizeSuccessCallback& onSuccess,
const FaceUri::CanonizeFailureCallback& onFailure,
- boost::asio::io_service& io, const time::nanoseconds& timeout) const override
+ boost::asio::io_service& io, time::nanoseconds timeout) const override
{
if (this->isCanonical(faceUri)) {
onSuccess(faceUri);
@@ -485,6 +525,7 @@
using CanonizeProviders = boost::mpl::vector<UdpCanonizeProvider*,
TcpCanonizeProvider*,
EtherCanonizeProvider*,
+ DevCanonizeProvider*,
UdpDevCanonizeProvider*>;
using CanonizeProviderTable = std::map<std::string, shared_ptr<CanonizeProvider>>;
@@ -549,7 +590,7 @@
void
FaceUri::canonize(const CanonizeSuccessCallback& onSuccess,
const CanonizeFailureCallback& onFailure,
- boost::asio::io_service& io, const time::nanoseconds& timeout) const
+ boost::asio::io_service& io, time::nanoseconds timeout) const
{
const CanonizeProvider* cp = getCanonizeProvider(this->getScheme());
if (cp == nullptr) {
diff --git a/src/util/face-uri.hpp b/src/util/face-uri.hpp
index f726388..09c8aaf 100644
--- a/src/util/face-uri.hpp
+++ b/src/util/face-uri.hpp
@@ -1,12 +1,12 @@
/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
/**
- * Copyright (c) 2014-2016, Regents of the University of California,
- * Arizona Board of Regents,
- * Colorado State University,
- * University Pierre & Marie Curie, Sorbonne University,
- * Washington University in St. Louis,
- * Beijing Institute of Technology,
- * The University of Memphis.
+ * Copyright (c) 2013-2017 Regents of the University of California,
+ * Arizona Board of Regents,
+ * Colorado State University,
+ * University Pierre & Marie Curie, Sorbonne University,
+ * Washington University in St. Louis,
+ * Beijing Institute of Technology,
+ * The University of Memphis.
*
* This file is part of ndn-cxx library (NDN C++ library with eXperimental eXtensions).
*
@@ -43,7 +43,7 @@
} // namespace ethernet
/** \brief represents the underlying protocol and address used by a Face
- * \sa http://redmine.named-data.net/projects/nfd/wiki/FaceMgmt#FaceUri
+ * \sa https://redmine.named-data.net/projects/nfd/wiki/FaceMgmt#FaceUri
*/
class FaceUri
{
@@ -181,7 +181,7 @@
canonize(const CanonizeSuccessCallback& onSuccess,
const CanonizeFailureCallback& onFailure,
boost::asio::io_service& io,
- const time::nanoseconds& timeout) const;
+ time::nanoseconds timeout) const;
private:
std::string m_scheme;
diff --git a/tests/unit-tests/util/face-uri.t.cpp b/tests/unit-tests/util/face-uri.t.cpp
index 74c6784..0b9a61a 100644
--- a/tests/unit-tests/util/face-uri.t.cpp
+++ b/tests/unit-tests/util/face-uri.t.cpp
@@ -1,12 +1,12 @@
/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
/**
- * Copyright (c) 2014-2016, Regents of the University of California,
- * Arizona Board of Regents,
- * Colorado State University,
- * University Pierre & Marie Curie, Sorbonne University,
- * Washington University in St. Louis,
- * Beijing Institute of Technology,
- * The University of Memphis.
+ * Copyright (c) 2013-2017 Regents of the University of California,
+ * Arizona Board of Regents,
+ * Colorado State University,
+ * University Pierre & Marie Curie, Sorbonne University,
+ * Washington University in St. Louis,
+ * Beijing Institute of Technology,
+ * The University of Memphis.
*
* This file is part of ndn-cxx library (NDN C++ library with eXperimental eXtensions).
*
@@ -401,6 +401,7 @@
runTests();
}
+BOOST_AUTO_TEST_CASE_EXPECTED_FAILURES(ParseDev, 1)
BOOST_AUTO_TEST_CASE(ParseDev)
{
FaceUri uri;
@@ -411,9 +412,33 @@
BOOST_CHECK_EQUAL(uri.getPort(), "");
BOOST_CHECK_EQUAL(uri.getPath(), "");
+ BOOST_CHECK_EQUAL(uri.parse("dev://eth0:8888"), false); // Bug #3896
+
std::string ifname = "en1";
- BOOST_REQUIRE_NO_THROW(FaceUri::fromDev(ifname));
- BOOST_CHECK_EQUAL(FaceUri::fromDev(ifname).toString(), "dev://en1");
+ BOOST_REQUIRE_NO_THROW(uri = FaceUri::fromDev(ifname));
+ BOOST_CHECK_EQUAL(uri.toString(), "dev://en1");
+}
+
+BOOST_AUTO_TEST_CASE(IsCanonicalDev)
+{
+ BOOST_CHECK_EQUAL(FaceUri::canCanonize("dev"), true);
+
+ BOOST_CHECK_EQUAL(FaceUri("dev://eth0").isCanonical(), true);
+ BOOST_CHECK_EQUAL(FaceUri("dev://").isCanonical(), false);
+ BOOST_CHECK_EQUAL(FaceUri("dev://eth0:8888").isCanonical(), false);
+ BOOST_CHECK_EQUAL(FaceUri("dev://eth0/").isCanonical(), false);
+ BOOST_CHECK_EQUAL(FaceUri("dev://eth0/A").isCanonical(), false);
+}
+
+BOOST_FIXTURE_TEST_CASE(CanonizeDev, CanonizeFixture)
+{
+ addTest("dev://eth0", true, "dev://eth0");
+ addTest("dev://", false, "");
+ addTest("dev://eth0:8888", false, "");
+ addTest("dev://eth0/", true, "dev://eth0");
+ addTest("dev://eth0/A", false, "");
+
+ runTests();
}
BOOST_AUTO_TEST_CASE(ParseUdpDev)
@@ -496,19 +521,16 @@
BOOST_CHECK_EQUAL(FaceUri::canCanonize("null"), false);
BOOST_CHECK_EQUAL(FaceUri::canCanonize("unix"), false);
BOOST_CHECK_EQUAL(FaceUri::canCanonize("fd"), false);
- BOOST_CHECK_EQUAL(FaceUri::canCanonize("dev"), false);
BOOST_CHECK_EQUAL(FaceUri("internal://").isCanonical(), false);
BOOST_CHECK_EQUAL(FaceUri("null://").isCanonical(), false);
BOOST_CHECK_EQUAL(FaceUri("unix:///var/run/nfd.sock").isCanonical(), false);
BOOST_CHECK_EQUAL(FaceUri("fd://0").isCanonical(), false);
- BOOST_CHECK_EQUAL(FaceUri("dev://eth1").isCanonical(), false);
addTest("internal://", false, "");
addTest("null://", false, "");
addTest("unix:///var/run/nfd.sock", false, "");
addTest("fd://0", false, "");
- addTest("dev://eth1", false, "");
runTests();
}