blob: 84d4529ad42be5cca0ec88432406d1d946d4f0c1 [file] [log] [blame]
Junxiao Shicde37ad2015-12-24 01:02:05 -07001/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
Junxiao Shi84d62cb2017-07-12 16:15:18 +00002/*
Junxiao Shi38b24c72017-01-05 02:59:31 +00003 * Copyright (c) 2014-2017, Regents of the University of California,
Junxiao Shicde37ad2015-12-24 01:02:05 -07004 * Arizona Board of Regents,
5 * Colorado State University,
6 * University Pierre & Marie Curie, Sorbonne University,
7 * Washington University in St. Louis,
8 * Beijing Institute of Technology,
9 * The University of Memphis.
10 *
11 * This file is part of NFD (Named Data Networking Forwarding Daemon).
12 * See AUTHORS.md for complete list of NFD authors and contributors.
13 *
14 * NFD is free software: you can redistribute it and/or modify it under the terms
15 * of the GNU General Public License as published by the Free Software Foundation,
16 * either version 3 of the License, or (at your option) any later version.
17 *
18 * NFD is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
19 * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
20 * PURPOSE. See the GNU General Public License for more details.
21 *
22 * You should have received a copy of the GNU General Public License along with
23 * NFD, e.g., in COPYING.md file. If not, see <http://www.gnu.org/licenses/>.
24 */
25
26#include "face/udp-factory.hpp"
27
Junxiao Shi64d99f22017-01-21 23:06:36 +000028#include "face-system-fixture.hpp"
Davide Pesaventob15276f2017-07-15 16:27:13 -040029#include "factory-test-common.hpp"
Davide Pesaventob15276f2017-07-15 16:27:13 -040030
Junxiao Shic31080d2017-01-24 15:10:12 +000031#include <boost/algorithm/string/replace.hpp>
Davide Pesaventob15276f2017-07-15 16:27:13 -040032#include <boost/range/algorithm/count_if.hpp>
Davide Pesavento4b89a6e2017-10-07 15:29:50 -040033#include <ndn-cxx/net/address-converter.hpp>
Junxiao Shicde37ad2015-12-24 01:02:05 -070034
35namespace nfd {
Junxiao Shi64d99f22017-01-21 23:06:36 +000036namespace face {
Junxiao Shicde37ad2015-12-24 01:02:05 -070037namespace tests {
38
Davide Pesavento4b89a6e2017-10-07 15:29:50 -040039class UdpFactoryFixture : public FaceSystemFactoryFixture<UdpFactory>
40{
41protected:
42 shared_ptr<UdpChannel>
Davide Pesaventobb734df2017-10-24 18:05:36 -040043 createChannel(const std::string& localIp, uint16_t localPort)
Davide Pesavento4b89a6e2017-10-07 15:29:50 -040044 {
Davide Pesaventobb734df2017-10-24 18:05:36 -040045 udp::Endpoint endpoint(ndn::ip::addressFromString(localIp), localPort);
Davide Pesavento4b89a6e2017-10-07 15:29:50 -040046 return factory.createChannel(endpoint, time::minutes(5));
47 }
48};
Junxiao Shi0ba6d642017-07-17 00:53:22 +000049
Davide Pesaventobb734df2017-10-24 18:05:36 -040050class UdpFactoryMcastFixture : public UdpFactoryFixture
51{
52protected:
53 UdpFactoryMcastFixture()
54 {
55 for (const auto& netif : collectNetworkInterfaces()) {
56 if (netif->isUp() && netif->canMulticast() &&
57 hasAddressFamily(*netif, ndn::net::AddressFamily::V4)) {
58 netifs.push_back(netif);
59 }
60 }
61
62 this->copyRealNetifsToNetmon();
63 }
64
65 shared_ptr<Face>
66 createMulticastFace(const std::string& localIp, const std::string& mcastIp, uint16_t mcastPort)
67 {
68 BOOST_ASSERT(!netifs.empty());
69 udp::Endpoint localEndpoint(ndn::ip::addressFromString(localIp), mcastPort);
70 udp::Endpoint mcastEndpoint(ndn::ip::addressFromString(mcastIp), mcastPort);
71 return factory.createMulticastFace(localEndpoint, mcastEndpoint, *netifs.front());
72 }
73
74 std::vector<const Face*>
75 listUdp4McastFaces(ndn::nfd::LinkType linkType = ndn::nfd::LINK_TYPE_MULTI_ACCESS) const
76 {
77 return this->listFacesByScheme("udp4", linkType);
78 }
79
80 /** \brief determine whether \p netif has at least one address of the given family
81 */
82 static bool
83 hasAddressFamily(const NetworkInterface& netif, ndn::net::AddressFamily af)
84 {
85 return std::any_of(netif.getNetworkAddresses().begin(), netif.getNetworkAddresses().end(),
86 [af] (const NetworkAddress& a) { return a.getFamily() == af; });
87 }
88
89 /** \brief determine whether a UDP multicast face is created on \p netif
90 */
91 static bool
92 isFaceOnNetif(const Face& face, const shared_ptr<const NetworkInterface>& netif)
93 {
94 auto ip = boost::asio::ip::address_v4::from_string(face.getLocalUri().getHost());
95 return std::any_of(netif->getNetworkAddresses().begin(), netif->getNetworkAddresses().end(),
96 [ip] (const NetworkAddress& a) { return a.getIp() == ip; });
97 }
98
99protected:
100 /** \brief MulticastUdpTransport-capable network interfaces
101 */
102 std::vector<shared_ptr<const NetworkInterface>> netifs;
103};
104
105#define SKIP_IF_UDP_MCAST_NETIF_COUNT_LT(n) \
106 do { \
107 if (this->netifs.size() < (n)) { \
108 BOOST_WARN_MESSAGE(false, "skipping assertions that require " #n \
109 " or more MulticastUdpTransport-capable network interfaces"); \
110 return; \
111 } \
112 } while (false)
113
Junxiao Shicde37ad2015-12-24 01:02:05 -0700114BOOST_AUTO_TEST_SUITE(Face)
Junxiao Shi0ba6d642017-07-17 00:53:22 +0000115BOOST_FIXTURE_TEST_SUITE(TestUdpFactory, UdpFactoryFixture)
Junxiao Shicde37ad2015-12-24 01:02:05 -0700116
117using nfd::Face;
118
Junxiao Shi0ba6d642017-07-17 00:53:22 +0000119BOOST_AUTO_TEST_SUITE(ProcessConfig)
Junxiao Shi64d99f22017-01-21 23:06:36 +0000120
121BOOST_AUTO_TEST_CASE(Channels)
122{
123 const std::string CONFIG = R"CONFIG(
124 face_system
125 {
126 udp
127 {
128 port 7001
129 enable_v4 yes
130 enable_v6 yes
131 idle_timeout 30
132 mcast no
133 }
134 }
135 )CONFIG";
136
137 parseConfig(CONFIG, true);
138 parseConfig(CONFIG, false);
139
Junxiao Shi64d99f22017-01-21 23:06:36 +0000140 checkChannelListEqual(factory, {"udp4://0.0.0.0:7001", "udp6://[::]:7001"});
141}
142
143BOOST_AUTO_TEST_CASE(ChannelV4)
144{
145 const std::string CONFIG = R"CONFIG(
146 face_system
147 {
148 udp
149 {
150 port 7001
151 enable_v4 yes
152 enable_v6 no
153 mcast no
154 }
155 }
156 )CONFIG";
157
158 parseConfig(CONFIG, true);
159 parseConfig(CONFIG, false);
160
Junxiao Shi64d99f22017-01-21 23:06:36 +0000161 checkChannelListEqual(factory, {"udp4://0.0.0.0:7001"});
162}
163
164BOOST_AUTO_TEST_CASE(ChannelV6)
165{
166 const std::string CONFIG = R"CONFIG(
167 face_system
168 {
169 udp
170 {
171 port 7001
172 enable_v4 no
173 enable_v6 yes
174 mcast no
175 }
176 }
177 )CONFIG";
178
179 parseConfig(CONFIG, true);
180 parseConfig(CONFIG, false);
181
Junxiao Shi64d99f22017-01-21 23:06:36 +0000182 checkChannelListEqual(factory, {"udp6://[::]:7001"});
183}
184
Davide Pesaventobb734df2017-10-24 18:05:36 -0400185BOOST_FIXTURE_TEST_CASE(EnableDisableMcast, UdpFactoryMcastFixture)
Junxiao Shi64d99f22017-01-21 23:06:36 +0000186{
187#ifdef __linux__
Junxiao Shibbace1d2017-08-06 20:03:37 +0000188 // need superuser privilege for creating multicast faces on Linux
Junxiao Shi64d99f22017-01-21 23:06:36 +0000189 SKIP_IF_NOT_SUPERUSER();
190#endif // __linux__
191
192 const std::string CONFIG_WITH_MCAST = R"CONFIG(
193 face_system
194 {
195 udp
196 {
197 mcast yes
198 }
199 }
200 )CONFIG";
201 const std::string CONFIG_WITHOUT_MCAST = R"CONFIG(
202 face_system
203 {
204 udp
205 {
206 mcast no
207 }
208 }
209 )CONFIG";
210
211 parseConfig(CONFIG_WITHOUT_MCAST, false);
Davide Pesaventobb734df2017-10-24 18:05:36 -0400212 BOOST_CHECK_EQUAL(this->listUdp4McastFaces().size(), 0);
Junxiao Shi64d99f22017-01-21 23:06:36 +0000213
214 SKIP_IF_UDP_MCAST_NETIF_COUNT_LT(1);
215
216 parseConfig(CONFIG_WITH_MCAST, false);
217 g_io.poll();
Davide Pesaventobb734df2017-10-24 18:05:36 -0400218 BOOST_CHECK_EQUAL(this->listUdp4McastFaces().size(), netifs.size());
Junxiao Shi64d99f22017-01-21 23:06:36 +0000219
220 parseConfig(CONFIG_WITHOUT_MCAST, false);
221 g_io.poll();
Davide Pesaventobb734df2017-10-24 18:05:36 -0400222 BOOST_CHECK_EQUAL(this->listUdp4McastFaces().size(), 0);
Junxiao Shi64d99f22017-01-21 23:06:36 +0000223}
224
Davide Pesaventobb734df2017-10-24 18:05:36 -0400225BOOST_FIXTURE_TEST_CASE(McastAdHoc, UdpFactoryMcastFixture)
Teng Liangfe4fce32017-03-29 04:49:38 +0000226{
227#ifdef __linux__
Junxiao Shibbace1d2017-08-06 20:03:37 +0000228 // need superuser privilege for creating multicast faces on Linux
Teng Liangfe4fce32017-03-29 04:49:38 +0000229 SKIP_IF_NOT_SUPERUSER();
230#endif // __linux__
231 SKIP_IF_UDP_MCAST_NETIF_COUNT_LT(1);
232
233 const std::string CONFIG = R"CONFIG(
234 face_system
235 {
236 udp
237 {
238 mcast_ad_hoc yes
239 }
240 }
241 )CONFIG";
242
243 parseConfig(CONFIG, false);
Davide Pesaventobb734df2017-10-24 18:05:36 -0400244 BOOST_CHECK_EQUAL(this->listUdp4McastFaces(ndn::nfd::LINK_TYPE_AD_HOC).size(), netifs.size());
Teng Liangfe4fce32017-03-29 04:49:38 +0000245}
246
Davide Pesaventobb734df2017-10-24 18:05:36 -0400247BOOST_FIXTURE_TEST_CASE(ChangeMcastEndpoint, UdpFactoryMcastFixture)
Junxiao Shi64d99f22017-01-21 23:06:36 +0000248{
249#ifdef __linux__
Junxiao Shibbace1d2017-08-06 20:03:37 +0000250 // need superuser privilege for creating multicast faces on Linux
Junxiao Shi64d99f22017-01-21 23:06:36 +0000251 SKIP_IF_NOT_SUPERUSER();
252#endif // __linux__
253 SKIP_IF_UDP_MCAST_NETIF_COUNT_LT(1);
254
255 const std::string CONFIG1 = R"CONFIG(
256 face_system
257 {
258 udp
259 {
260 mcast_group 239.66.30.1
261 mcast_port 7011
262 }
263 }
264 )CONFIG";
265 const std::string CONFIG2 = R"CONFIG(
266 face_system
267 {
268 udp
269 {
270 mcast_group 239.66.30.2
271 mcast_port 7012
272 }
273 }
274 )CONFIG";
275
276 parseConfig(CONFIG1, false);
Davide Pesaventobb734df2017-10-24 18:05:36 -0400277 auto udpMcastFaces = this->listUdp4McastFaces();
Junxiao Shi64d99f22017-01-21 23:06:36 +0000278 BOOST_REQUIRE_EQUAL(udpMcastFaces.size(), netifs.size());
279 BOOST_CHECK_EQUAL(udpMcastFaces.front()->getRemoteUri(),
280 FaceUri("udp4://239.66.30.1:7011"));
281
282 parseConfig(CONFIG2, false);
283 g_io.poll();
Davide Pesaventobb734df2017-10-24 18:05:36 -0400284 udpMcastFaces = this->listUdp4McastFaces();
Junxiao Shi64d99f22017-01-21 23:06:36 +0000285 BOOST_REQUIRE_EQUAL(udpMcastFaces.size(), netifs.size());
286 BOOST_CHECK_EQUAL(udpMcastFaces.front()->getRemoteUri(),
287 FaceUri("udp4://239.66.30.2:7012"));
288}
289
Davide Pesaventobb734df2017-10-24 18:05:36 -0400290BOOST_FIXTURE_TEST_CASE(Whitelist, UdpFactoryMcastFixture)
Junxiao Shic31080d2017-01-24 15:10:12 +0000291{
292#ifdef __linux__
Junxiao Shibbace1d2017-08-06 20:03:37 +0000293 // need superuser privilege for creating multicast faces on Linux
Junxiao Shic31080d2017-01-24 15:10:12 +0000294 SKIP_IF_NOT_SUPERUSER();
295#endif // __linux__
296 SKIP_IF_UDP_MCAST_NETIF_COUNT_LT(1);
297
298 std::string CONFIG = R"CONFIG(
299 face_system
300 {
301 udp
302 {
303 whitelist
304 {
305 ifname %ifname
306 }
307 }
308 }
309 )CONFIG";
Junxiao Shi84d62cb2017-07-12 16:15:18 +0000310 boost::replace_first(CONFIG, "%ifname", netifs.front()->getName());
Junxiao Shic31080d2017-01-24 15:10:12 +0000311
312 parseConfig(CONFIG, false);
Davide Pesaventobb734df2017-10-24 18:05:36 -0400313 auto udpMcastFaces = this->listUdp4McastFaces();
Junxiao Shic31080d2017-01-24 15:10:12 +0000314 BOOST_REQUIRE_EQUAL(udpMcastFaces.size(), 1);
315 BOOST_CHECK(isFaceOnNetif(*udpMcastFaces.front(), netifs.front()));
316}
317
Davide Pesaventobb734df2017-10-24 18:05:36 -0400318BOOST_FIXTURE_TEST_CASE(Blacklist, UdpFactoryMcastFixture)
Junxiao Shic31080d2017-01-24 15:10:12 +0000319{
320#ifdef __linux__
Junxiao Shibbace1d2017-08-06 20:03:37 +0000321 // need superuser privilege for creating multicast faces on Linux
Junxiao Shic31080d2017-01-24 15:10:12 +0000322 SKIP_IF_NOT_SUPERUSER();
323#endif // __linux__
324 SKIP_IF_UDP_MCAST_NETIF_COUNT_LT(1);
325
326 std::string CONFIG = R"CONFIG(
327 face_system
328 {
329 udp
330 {
331 blacklist
332 {
333 ifname %ifname
334 }
335 }
336 }
337 )CONFIG";
Junxiao Shi84d62cb2017-07-12 16:15:18 +0000338 boost::replace_first(CONFIG, "%ifname", netifs.front()->getName());
Junxiao Shic31080d2017-01-24 15:10:12 +0000339
340 parseConfig(CONFIG, false);
Davide Pesaventobb734df2017-10-24 18:05:36 -0400341 auto udpMcastFaces = this->listUdp4McastFaces();
Junxiao Shic31080d2017-01-24 15:10:12 +0000342 BOOST_CHECK_EQUAL(udpMcastFaces.size(), netifs.size() - 1);
Davide Pesaventob15276f2017-07-15 16:27:13 -0400343 BOOST_CHECK_EQUAL(boost::count_if(udpMcastFaces, [this] (const Face* face) {
Junxiao Shic31080d2017-01-24 15:10:12 +0000344 return isFaceOnNetif(*face, netifs.front());
345 }), 0);
346}
347
Davide Pesaventobb734df2017-10-24 18:05:36 -0400348BOOST_FIXTURE_TEST_CASE(ChangePredicate, UdpFactoryMcastFixture)
Junxiao Shic31080d2017-01-24 15:10:12 +0000349{
350#ifdef __linux__
Junxiao Shibbace1d2017-08-06 20:03:37 +0000351 // need superuser privilege for creating multicast faces on Linux
Junxiao Shic31080d2017-01-24 15:10:12 +0000352 SKIP_IF_NOT_SUPERUSER();
353#endif // __linux__
354 SKIP_IF_UDP_MCAST_NETIF_COUNT_LT(2);
355
356 std::string CONFIG1 = R"CONFIG(
357 face_system
358 {
359 udp
360 {
361 whitelist
362 {
363 ifname %ifname
364 }
365 }
366 }
367 )CONFIG";
368 std::string CONFIG2 = CONFIG1;
Junxiao Shi84d62cb2017-07-12 16:15:18 +0000369 boost::replace_first(CONFIG1, "%ifname", netifs.front()->getName());
370 boost::replace_first(CONFIG2, "%ifname", netifs.back()->getName());
Junxiao Shic31080d2017-01-24 15:10:12 +0000371
372 parseConfig(CONFIG1, false);
Davide Pesaventobb734df2017-10-24 18:05:36 -0400373 auto udpMcastFaces = this->listUdp4McastFaces();
Junxiao Shic31080d2017-01-24 15:10:12 +0000374 BOOST_REQUIRE_EQUAL(udpMcastFaces.size(), 1);
375 BOOST_CHECK(isFaceOnNetif(*udpMcastFaces.front(), netifs.front()));
376
377 parseConfig(CONFIG2, false);
378 g_io.poll();
Davide Pesaventobb734df2017-10-24 18:05:36 -0400379 udpMcastFaces = this->listUdp4McastFaces();
Junxiao Shic31080d2017-01-24 15:10:12 +0000380 BOOST_REQUIRE_EQUAL(udpMcastFaces.size(), 1);
381 BOOST_CHECK(isFaceOnNetif(*udpMcastFaces.front(), netifs.back()));
382}
383
Junxiao Shi64d99f22017-01-21 23:06:36 +0000384BOOST_AUTO_TEST_CASE(Omitted)
385{
386 const std::string CONFIG = R"CONFIG(
387 face_system
388 {
389 }
390 )CONFIG";
391
392 parseConfig(CONFIG, true);
393 parseConfig(CONFIG, false);
394
Junxiao Shi64d99f22017-01-21 23:06:36 +0000395 BOOST_CHECK_EQUAL(factory.getChannels().size(), 0);
396 BOOST_CHECK_EQUAL(this->listFacesByScheme("udp4", ndn::nfd::LINK_TYPE_MULTI_ACCESS).size(), 0);
397}
398
Davide Pesaventobb734df2017-10-24 18:05:36 -0400399BOOST_AUTO_TEST_CASE(AllDisabled)
400{
401 const std::string CONFIG = R"CONFIG(
402 face_system
403 {
404 udp
405 {
406 enable_v4 no
407 enable_v6 no
408 mcast no
409 }
410 }
411 )CONFIG";
412
413 BOOST_CHECK_THROW(parseConfig(CONFIG, true), ConfigFile::Error);
414 BOOST_CHECK_THROW(parseConfig(CONFIG, false), ConfigFile::Error);
415}
416
Junxiao Shi64d99f22017-01-21 23:06:36 +0000417BOOST_AUTO_TEST_CASE(BadIdleTimeout)
418{
419 const std::string CONFIG = R"CONFIG(
420 face_system
421 {
422 udp
423 {
424 idle_timeout hello
425 }
426 }
427 )CONFIG";
428
429 BOOST_CHECK_THROW(parseConfig(CONFIG, true), ConfigFile::Error);
430 BOOST_CHECK_THROW(parseConfig(CONFIG, false), ConfigFile::Error);
431}
432
433BOOST_AUTO_TEST_CASE(BadMcast)
434{
435 const std::string CONFIG = R"CONFIG(
436 face_system
437 {
438 udp
439 {
440 mcast hello
441 }
442 }
443 )CONFIG";
444
445 BOOST_CHECK_THROW(parseConfig(CONFIG, true), ConfigFile::Error);
446 BOOST_CHECK_THROW(parseConfig(CONFIG, false), ConfigFile::Error);
447}
448
449BOOST_AUTO_TEST_CASE(BadMcastGroup)
450{
Davide Pesaventobb734df2017-10-24 18:05:36 -0400451 // not an address
452 const std::string CONFIG1 = R"CONFIG(
Junxiao Shi64d99f22017-01-21 23:06:36 +0000453 face_system
454 {
455 udp
456 {
457 mcast_group hello
458 }
459 }
460 )CONFIG";
461
Davide Pesaventobb734df2017-10-24 18:05:36 -0400462 BOOST_CHECK_THROW(parseConfig(CONFIG1, true), ConfigFile::Error);
463 BOOST_CHECK_THROW(parseConfig(CONFIG1, false), ConfigFile::Error);
Junxiao Shi64d99f22017-01-21 23:06:36 +0000464
Davide Pesaventobb734df2017-10-24 18:05:36 -0400465 // non-multicast address
466 const std::string CONFIG2 = R"CONFIG(
Junxiao Shi64d99f22017-01-21 23:06:36 +0000467 face_system
468 {
469 udp
470 {
471 mcast_group 10.0.0.1
472 }
473 }
474 )CONFIG";
475
Davide Pesaventobb734df2017-10-24 18:05:36 -0400476 BOOST_CHECK_THROW(parseConfig(CONFIG2, true), ConfigFile::Error);
477 BOOST_CHECK_THROW(parseConfig(CONFIG2, false), ConfigFile::Error);
Junxiao Shi64d99f22017-01-21 23:06:36 +0000478
Davide Pesaventobb734df2017-10-24 18:05:36 -0400479 // wrong address family
480 const std::string CONFIG3 = R"CONFIG(
Junxiao Shi64d99f22017-01-21 23:06:36 +0000481 face_system
482 {
483 udp
484 {
Davide Pesaventobb734df2017-10-24 18:05:36 -0400485 mcast_group ff02::1234
Junxiao Shi64d99f22017-01-21 23:06:36 +0000486 }
487 }
488 )CONFIG";
489
Davide Pesaventobb734df2017-10-24 18:05:36 -0400490 BOOST_CHECK_THROW(parseConfig(CONFIG3, true), ConfigFile::Error);
491 BOOST_CHECK_THROW(parseConfig(CONFIG3, false), ConfigFile::Error);
Junxiao Shi64d99f22017-01-21 23:06:36 +0000492}
493
Davide Pesaventobb734df2017-10-24 18:05:36 -0400494BOOST_AUTO_TEST_CASE(BadMcastPort)
Junxiao Shi64d99f22017-01-21 23:06:36 +0000495{
Davide Pesaventobb734df2017-10-24 18:05:36 -0400496 const std::string CONFIG1 = R"CONFIG(
Junxiao Shi64d99f22017-01-21 23:06:36 +0000497 face_system
498 {
499 udp
500 {
Davide Pesaventobb734df2017-10-24 18:05:36 -0400501 mcast_port hey
Junxiao Shi64d99f22017-01-21 23:06:36 +0000502 }
503 }
504 )CONFIG";
505
Davide Pesaventobb734df2017-10-24 18:05:36 -0400506 BOOST_CHECK_THROW(parseConfig(CONFIG1, true), ConfigFile::Error);
507 BOOST_CHECK_THROW(parseConfig(CONFIG1, false), ConfigFile::Error);
508
509 const std::string CONFIG2 = R"CONFIG(
510 face_system
511 {
512 udp
513 {
514 mcast_port 99999
515 }
516 }
517 )CONFIG";
518
519 BOOST_CHECK_THROW(parseConfig(CONFIG2, true), ConfigFile::Error);
520 BOOST_CHECK_THROW(parseConfig(CONFIG2, false), ConfigFile::Error);
Junxiao Shi64d99f22017-01-21 23:06:36 +0000521}
522
523BOOST_AUTO_TEST_CASE(UnknownOption)
524{
525 const std::string CONFIG = R"CONFIG(
526 face_system
527 {
528 udp
529 {
530 hello
531 }
532 }
533 )CONFIG";
534
535 BOOST_CHECK_THROW(parseConfig(CONFIG, true), ConfigFile::Error);
536 BOOST_CHECK_THROW(parseConfig(CONFIG, false), ConfigFile::Error);
537}
538
539BOOST_AUTO_TEST_SUITE_END() // ProcessConfig
540
Junxiao Shicde37ad2015-12-24 01:02:05 -0700541BOOST_AUTO_TEST_CASE(GetChannels)
542{
Davide Pesaventob15276f2017-07-15 16:27:13 -0400543 BOOST_CHECK_EQUAL(factory.getChannels().empty(), true);
Junxiao Shicde37ad2015-12-24 01:02:05 -0700544
Davide Pesaventob15276f2017-07-15 16:27:13 -0400545 std::set<std::string> expected;
Davide Pesaventobb734df2017-10-24 18:05:36 -0400546 expected.insert(createChannel("127.0.0.1", 20070)->getUri().toString());
547 expected.insert(createChannel("127.0.0.1", 20071)->getUri().toString());
548 expected.insert(createChannel("::1", 20071)->getUri().toString());
Davide Pesaventob15276f2017-07-15 16:27:13 -0400549 checkChannelListEqual(factory, expected);
Junxiao Shicde37ad2015-12-24 01:02:05 -0700550}
551
Davide Pesaventobb734df2017-10-24 18:05:36 -0400552BOOST_FIXTURE_TEST_CASE(CreateChannel, UdpFactoryMcastFixture)
Junxiao Shicde37ad2015-12-24 01:02:05 -0700553{
Davide Pesaventobb734df2017-10-24 18:05:36 -0400554 auto channel1 = createChannel("127.0.0.1", 20070);
555 auto channel1a = createChannel("127.0.0.1", 20070);
Junxiao Shicde37ad2015-12-24 01:02:05 -0700556 BOOST_CHECK_EQUAL(channel1, channel1a);
557 BOOST_CHECK_EQUAL(channel1->getUri().toString(), "udp4://127.0.0.1:20070");
558
Davide Pesaventobb734df2017-10-24 18:05:36 -0400559 auto channel2 = createChannel("127.0.0.1", 20071);
Junxiao Shicde37ad2015-12-24 01:02:05 -0700560 BOOST_CHECK_NE(channel1, channel2);
561
Davide Pesaventobb734df2017-10-24 18:05:36 -0400562 auto channel3 = createChannel("::1", 20071);
Weiwei Liu72cee942016-02-04 16:49:19 -0700563 BOOST_CHECK_NE(channel2, channel3);
564 BOOST_CHECK_EQUAL(channel3->getUri().toString(), "udp6://[::1]:20071");
Junxiao Shicde37ad2015-12-24 01:02:05 -0700565
Weiwei Liu72cee942016-02-04 16:49:19 -0700566 // createChannel with multicast address
Davide Pesaventobb734df2017-10-24 18:05:36 -0400567 BOOST_CHECK_EXCEPTION(createChannel("224.0.0.1", 20070), UdpFactory::Error,
Weiwei Liu72cee942016-02-04 16:49:19 -0700568 [] (const UdpFactory::Error& e) {
569 return strcmp(e.what(),
570 "createChannel is only for unicast channels. The provided endpoint "
571 "is multicast. Use createMulticastFace to create a multicast face") == 0;
572 });
Junxiao Shicde37ad2015-12-24 01:02:05 -0700573
Davide Pesaventobb734df2017-10-24 18:05:36 -0400574#ifdef __linux__
575 // need superuser privilege for creating multicast faces on Linux
576 SKIP_IF_NOT_SUPERUSER();
577#endif // __linux__
578 SKIP_IF_UDP_MCAST_NETIF_COUNT_LT(1);
579
Weiwei Liu72cee942016-02-04 16:49:19 -0700580 // createChannel with a local endpoint that has already been allocated for a UDP multicast face
Davide Pesaventobb734df2017-10-24 18:05:36 -0400581 auto multicastFace = createMulticastFace("127.0.0.1", "224.0.0.1", 20072);
582 BOOST_CHECK_EXCEPTION(createChannel("127.0.0.1", 20072), UdpFactory::Error,
Weiwei Liu72cee942016-02-04 16:49:19 -0700583 [] (const UdpFactory::Error& e) {
584 return strcmp(e.what(),
585 "Cannot create the requested UDP unicast channel, local "
586 "endpoint is already allocated for a UDP multicast face") == 0;
587 });
588}
Junxiao Shicde37ad2015-12-24 01:02:05 -0700589
Davide Pesaventobb734df2017-10-24 18:05:36 -0400590BOOST_FIXTURE_TEST_CASE(CreateMulticastFace, UdpFactoryMcastFixture)
Weiwei Liu72cee942016-02-04 16:49:19 -0700591{
Davide Pesaventobb734df2017-10-24 18:05:36 -0400592#ifdef __linux__
593 // need superuser privilege for creating multicast faces on Linux
594 SKIP_IF_NOT_SUPERUSER();
595#endif // __linux__
596 SKIP_IF_UDP_MCAST_NETIF_COUNT_LT(1);
597
598 auto multicastFace1 = createMulticastFace("127.0.0.1", "224.0.0.1", 20070);
599 auto multicastFace1a = createMulticastFace("127.0.0.1", "224.0.0.1", 20070);
Junxiao Shicde37ad2015-12-24 01:02:05 -0700600 BOOST_CHECK_EQUAL(multicastFace1, multicastFace1a);
601
Davide Pesaventobb734df2017-10-24 18:05:36 -0400602 // createMulticastFace with an IPv4 local endpoint already used by a channel
603 auto channel = createChannel("127.0.0.1", 20071);
604 BOOST_CHECK_EXCEPTION(createMulticastFace("127.0.0.1", "224.0.0.1", 20071), UdpFactory::Error,
Weiwei Liu72cee942016-02-04 16:49:19 -0700605 [] (const UdpFactory::Error& e) {
606 return strcmp(e.what(),
607 "Cannot create the requested UDP multicast face, local "
608 "endpoint is already allocated for a UDP unicast channel") == 0;
609 });
Junxiao Shicde37ad2015-12-24 01:02:05 -0700610
Davide Pesaventobb734df2017-10-24 18:05:36 -0400611 // createMulticastFace with an IPv4 local endpoint already
Davide Pesaventoeee53aa2016-04-11 17:20:21 +0200612 // used by a multicast face on a different multicast group
Davide Pesaventobb734df2017-10-24 18:05:36 -0400613 BOOST_CHECK_EXCEPTION(createMulticastFace("127.0.0.1", "224.0.0.42", 20070), UdpFactory::Error,
Weiwei Liu72cee942016-02-04 16:49:19 -0700614 [] (const UdpFactory::Error& e) {
615 return strcmp(e.what(),
616 "Cannot create the requested UDP multicast face, local "
617 "endpoint is already allocated for a UDP multicast face "
618 "on a different multicast group") == 0;
619 });
Junxiao Shicde37ad2015-12-24 01:02:05 -0700620
Weiwei Liu72cee942016-02-04 16:49:19 -0700621 // createMulticastFace with an IPv6 multicast address
Davide Pesaventobb734df2017-10-24 18:05:36 -0400622 BOOST_CHECK_EXCEPTION(createMulticastFace("::1", "ff01::114", 20073), UdpFactory::Error,
Weiwei Liu72cee942016-02-04 16:49:19 -0700623 [] (const UdpFactory::Error& e) {
624 return strcmp(e.what(),
625 "IPv6 multicast is not supported yet. Please provide an IPv4 "
626 "address") == 0;
627 });
Junxiao Shicde37ad2015-12-24 01:02:05 -0700628}
629
Davide Pesaventob15276f2017-07-15 16:27:13 -0400630BOOST_AUTO_TEST_CASE(CreateFace)
Junxiao Shicde37ad2015-12-24 01:02:05 -0700631{
Eric Newberry42602412016-08-27 09:33:18 -0700632 createFace(factory,
633 FaceUri("udp4://127.0.0.1:6363"),
Eric Newberry78e32b02017-04-01 14:34:44 +0000634 {},
Eric Newberry42602412016-08-27 09:33:18 -0700635 ndn::nfd::FACE_PERSISTENCY_PERSISTENT,
Eric Newberryf40551a2016-09-05 15:41:16 -0700636 false,
Eric Newberry2642cd22017-07-13 21:34:53 -0400637 false,
Eric Newberry42602412016-08-27 09:33:18 -0700638 {CreateFaceExpectedResult::FAILURE, 504, "No channels available to connect"});
Junxiao Shicde37ad2015-12-24 01:02:05 -0700639
Davide Pesaventobb734df2017-10-24 18:05:36 -0400640 createChannel("127.0.0.1", 20071);
Junxiao Shicde37ad2015-12-24 01:02:05 -0700641
Eric Newberry42602412016-08-27 09:33:18 -0700642 createFace(factory,
Davide Pesaventoa3c9ddb2017-04-10 22:15:24 -0400643 FaceUri("udp4://127.0.0.1:6363"),
Eric Newberry78e32b02017-04-01 14:34:44 +0000644 {},
Eric Newberry42602412016-08-27 09:33:18 -0700645 ndn::nfd::FACE_PERSISTENCY_PERSISTENT,
Eric Newberryf40551a2016-09-05 15:41:16 -0700646 false,
Eric Newberry2642cd22017-07-13 21:34:53 -0400647 false,
Eric Newberry42602412016-08-27 09:33:18 -0700648 {CreateFaceExpectedResult::SUCCESS, 0, ""});
Eric Newberry78e32b02017-04-01 14:34:44 +0000649
Eric Newberry42602412016-08-27 09:33:18 -0700650 createFace(factory,
Davide Pesaventoa3c9ddb2017-04-10 22:15:24 -0400651 FaceUri("udp4://127.0.0.1:6363"),
Eric Newberry78e32b02017-04-01 14:34:44 +0000652 {},
Eric Newberry42602412016-08-27 09:33:18 -0700653 ndn::nfd::FACE_PERSISTENCY_PERMANENT,
Eric Newberryf40551a2016-09-05 15:41:16 -0700654 false,
Eric Newberry2642cd22017-07-13 21:34:53 -0400655 false,
Eric Newberry42602412016-08-27 09:33:18 -0700656 {CreateFaceExpectedResult::SUCCESS, 0, ""});
Junxiao Shicde37ad2015-12-24 01:02:05 -0700657
Eric Newberry42602412016-08-27 09:33:18 -0700658 createFace(factory,
659 FaceUri("udp4://127.0.0.1:20072"),
Eric Newberry78e32b02017-04-01 14:34:44 +0000660 {},
Eric Newberry42602412016-08-27 09:33:18 -0700661 ndn::nfd::FACE_PERSISTENCY_PERMANENT,
Eric Newberryf40551a2016-09-05 15:41:16 -0700662 false,
Eric Newberry2642cd22017-07-13 21:34:53 -0400663 false,
664 {CreateFaceExpectedResult::SUCCESS, 0, ""});
665
Eric Newberry2642cd22017-07-13 21:34:53 -0400666 createFace(factory,
667 FaceUri("udp4://127.0.0.1:20073"),
668 {},
669 ndn::nfd::FACE_PERSISTENCY_PERMANENT,
670 false,
671 true,
Eric Newberry42602412016-08-27 09:33:18 -0700672 {CreateFaceExpectedResult::SUCCESS, 0, ""});
Junxiao Shicde37ad2015-12-24 01:02:05 -0700673}
674
Davide Pesaventob15276f2017-07-15 16:27:13 -0400675BOOST_AUTO_TEST_CASE(UnsupportedCreateFace)
Junxiao Shicde37ad2015-12-24 01:02:05 -0700676{
Davide Pesaventobb734df2017-10-24 18:05:36 -0400677 createChannel("127.0.0.1", 20071);
Junxiao Shicde37ad2015-12-24 01:02:05 -0700678
Eric Newberry42602412016-08-27 09:33:18 -0700679 createFace(factory,
Davide Pesavento46afec42017-05-28 14:28:47 -0400680 FaceUri("udp4://127.0.0.1:20072"),
Davide Pesaventoa3c9ddb2017-04-10 22:15:24 -0400681 FaceUri("udp4://127.0.0.1:20071"),
Davide Pesavento46afec42017-05-28 14:28:47 -0400682 ndn::nfd::FACE_PERSISTENCY_PERSISTENT,
683 false,
Eric Newberry2642cd22017-07-13 21:34:53 -0400684 false,
Davide Pesavento46afec42017-05-28 14:28:47 -0400685 {CreateFaceExpectedResult::FAILURE, 406,
686 "Unicast UDP faces cannot be created with a LocalUri"});
687
688 createFace(factory,
689 FaceUri("udp4://127.0.0.1:20072"),
Eric Newberry78e32b02017-04-01 14:34:44 +0000690 {},
Eric Newberry42602412016-08-27 09:33:18 -0700691 ndn::nfd::FACE_PERSISTENCY_ON_DEMAND,
Eric Newberryf40551a2016-09-05 15:41:16 -0700692 false,
Eric Newberry2642cd22017-07-13 21:34:53 -0400693 false,
Eric Newberry42602412016-08-27 09:33:18 -0700694 {CreateFaceExpectedResult::FAILURE, 406,
Davide Pesavento46afec42017-05-28 14:28:47 -0400695 "Outgoing UDP faces do not support on-demand persistency"});
Eric Newberry78e32b02017-04-01 14:34:44 +0000696
697 createFace(factory,
Davide Pesavento46afec42017-05-28 14:28:47 -0400698 FaceUri("udp4://233.252.0.1:23252"),
699 {},
Eric Newberry78e32b02017-04-01 14:34:44 +0000700 ndn::nfd::FACE_PERSISTENCY_PERSISTENT,
701 false,
Eric Newberry2642cd22017-07-13 21:34:53 -0400702 false,
Eric Newberry78e32b02017-04-01 14:34:44 +0000703 {CreateFaceExpectedResult::FAILURE, 406,
Davide Pesavento46afec42017-05-28 14:28:47 -0400704 "Cannot create multicast UDP faces"});
705
706 createFace(factory,
Davide Pesavento46afec42017-05-28 14:28:47 -0400707 FaceUri("udp4://127.0.0.1:20072"),
708 {},
709 ndn::nfd::FACE_PERSISTENCY_PERSISTENT,
710 true,
Eric Newberry2642cd22017-07-13 21:34:53 -0400711 false,
Davide Pesavento46afec42017-05-28 14:28:47 -0400712 {CreateFaceExpectedResult::FAILURE, 406,
713 "Local fields can only be enabled on faces with local scope"});
Junxiao Shicde37ad2015-12-24 01:02:05 -0700714}
715
Junxiao Shicde37ad2015-12-24 01:02:05 -0700716BOOST_AUTO_TEST_SUITE_END() // TestUdpFactory
717BOOST_AUTO_TEST_SUITE_END() // Face
718
719} // namespace tests
Junxiao Shi64d99f22017-01-21 23:06:36 +0000720} // namespace face
Junxiao Shicde37ad2015-12-24 01:02:05 -0700721} // namespace nfd