blob: 1db5b8dd12dff0cd289e994cd0b380e6281b430a [file] [log] [blame]
Junxiao Shia60d9362014-11-12 09:38:21 -07001/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
2/**
Alexander Afanasyevaf99f462015-01-19 21:43:09 -08003 * Copyright (c) 2013-2015 Regents of the University of California.
Junxiao Shia60d9362014-11-12 09:38:21 -07004 *
5 * This file is part of ndn-cxx library (NDN C++ library with eXperimental eXtensions).
6 *
7 * ndn-cxx library is free software: you can redistribute it and/or modify it under the
8 * terms of the GNU Lesser General Public License as published by the Free Software
9 * Foundation, either version 3 of the License, or (at your option) any later version.
10 *
11 * ndn-cxx library is distributed in the hope that it will be useful, but WITHOUT ANY
12 * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A
13 * PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details.
14 *
15 * You should have received copies of the GNU General Public License and GNU Lesser
16 * General Public License along with ndn-cxx, e.g., in COPYING.md file. If not, see
17 * <http://www.gnu.org/licenses/>.
18 *
19 * See AUTHORS.md for complete list of ndn-cxx authors and contributors.
20 */
21
22#include "dummy-client-face.hpp"
23#include "../transport/transport.hpp"
24#include "../management/nfd-controller.hpp"
25#include "../management/nfd-control-response.hpp"
26
27namespace ndn {
28namespace util {
29
30const DummyClientFace::Options DummyClientFace::DEFAULT_OPTIONS { true, false };
31
32class DummyClientFace::Transport : public ndn::Transport
33{
34public:
35 void
Eric Newberry83872fd2015-08-06 17:01:24 -070036 receive(Block block)
Junxiao Shia60d9362014-11-12 09:38:21 -070037 {
Eric Newberry83872fd2015-08-06 17:01:24 -070038 block.encode();
39 if (static_cast<bool>(m_receiveCallback)) {
Junxiao Shia60d9362014-11-12 09:38:21 -070040 m_receiveCallback(block);
Eric Newberry83872fd2015-08-06 17:01:24 -070041 }
Junxiao Shia60d9362014-11-12 09:38:21 -070042 }
43
44 virtual void
45 close()
46 {
47 }
48
49 virtual void
50 pause()
51 {
52 }
53
54 virtual void
55 resume()
56 {
57 }
58
59 virtual void
60 send(const Block& wire)
61 {
Junxiao Shi27913b42014-12-23 14:49:38 -070062 onSendBlock(wire);
Junxiao Shia60d9362014-11-12 09:38:21 -070063 }
64
65 virtual void
66 send(const Block& header, const Block& payload)
67 {
Alexander Afanasyevea719672015-02-10 20:25:23 -080068 EncodingBuffer encoder(header.size() + payload.size(), header.size() + payload.size());
69 encoder.appendByteArray(header.wire(), header.size());
70 encoder.appendByteArray(payload.wire(), payload.size());
71
72 this->send(encoder.block());
Junxiao Shia60d9362014-11-12 09:38:21 -070073 }
74
75 boost::asio::io_service&
76 getIoService()
77 {
78 return *m_ioService;
79 }
80
Junxiao Shi27913b42014-12-23 14:49:38 -070081public:
82 Signal<Transport, Block> onSendBlock;
Junxiao Shia60d9362014-11-12 09:38:21 -070083};
84
Alexander Afanasyev3a6da362015-12-29 20:31:03 -080085DummyClientFace::DummyClientFace(const Options& options/* = DummyClientFace::DEFAULT_OPTIONS*/)
86 : Face(make_shared<DummyClientFace::Transport>())
87#ifdef NDN_UTIL_DUMMY_FACE_KEEP_DEPRECATED
88 , sentDatas(sentData)
89#endif // NDN_UTIL_DUMMY_FACE_KEEP_DEPRECATED
Junxiao Shia60d9362014-11-12 09:38:21 -070090{
91 this->construct(options);
92}
93
Alexander Afanasyev3a6da362015-12-29 20:31:03 -080094DummyClientFace::DummyClientFace(boost::asio::io_service& ioService,
95 const Options& options/* = DummyClientFace::DEFAULT_OPTIONS*/)
96 : Face(make_shared<DummyClientFace::Transport>(), ioService)
97#ifdef NDN_UTIL_DUMMY_FACE_KEEP_DEPRECATED
98 , sentDatas(sentData)
99#endif // NDN_UTIL_DUMMY_FACE_KEEP_DEPRECATED
Junxiao Shia60d9362014-11-12 09:38:21 -0700100{
101 this->construct(options);
102}
103
104void
105DummyClientFace::construct(const Options& options)
106{
Alexander Afanasyev3a6da362015-12-29 20:31:03 -0800107 static_pointer_cast<Transport>(getTransport())->onSendBlock.connect([this] (const Block& blockFromDaemon) {
Eric Newberrye3e25052015-11-28 20:37:08 -0700108 Block packet(blockFromDaemon);
109 packet.encode();
110 lp::Packet lpPacket(packet);
Alexander Afanasyevea719672015-02-10 20:25:23 -0800111
Eric Newberrye3e25052015-11-28 20:37:08 -0700112 Buffer::const_iterator begin, end;
113 std::tie(begin, end) = lpPacket.get<lp::FragmentField>();
114 Block block(&*begin, std::distance(begin, end));
Alexander Afanasyevea719672015-02-10 20:25:23 -0800115
Eric Newberrye3e25052015-11-28 20:37:08 -0700116 if (block.type() == tlv::Interest) {
117 shared_ptr<Interest> interest = make_shared<Interest>(block);
118 if (lpPacket.has<lp::NackField>()) {
119 shared_ptr<lp::Nack> nack = make_shared<lp::Nack>(std::move(*interest));
120 nack->setHeader(lpPacket.get<lp::NackField>());
121 if (lpPacket.has<lp::NextHopFaceIdField>()) {
Junxiao Shi4b469982015-12-03 18:20:19 +0000122 nack->setTag(make_shared<lp::NextHopFaceIdTag>(lpPacket.get<lp::NextHopFaceIdField>()));
Eric Newberry83872fd2015-08-06 17:01:24 -0700123 }
Eric Newberrye3e25052015-11-28 20:37:08 -0700124 onSendNack(*nack);
Eric Newberry83872fd2015-08-06 17:01:24 -0700125 }
Eric Newberrye3e25052015-11-28 20:37:08 -0700126 else {
127 if (lpPacket.has<lp::NextHopFaceIdField>()) {
Junxiao Shi4b469982015-12-03 18:20:19 +0000128 interest->setTag(make_shared<lp::NextHopFaceIdTag>(lpPacket.get<lp::NextHopFaceIdField>()));
Eric Newberry83872fd2015-08-06 17:01:24 -0700129 }
Eric Newberrye3e25052015-11-28 20:37:08 -0700130 onSendInterest(*interest);
Eric Newberry83872fd2015-08-06 17:01:24 -0700131 }
Junxiao Shi27913b42014-12-23 14:49:38 -0700132 }
Eric Newberrye3e25052015-11-28 20:37:08 -0700133 else if (block.type() == tlv::Data) {
134 shared_ptr<Data> data = make_shared<Data>(block);
135
136 if (lpPacket.has<lp::CachePolicyField>()) {
Junxiao Shi4b469982015-12-03 18:20:19 +0000137 data->setTag(make_shared<lp::CachePolicyTag>(lpPacket.get<lp::CachePolicyField>()));
Eric Newberrye3e25052015-11-28 20:37:08 -0700138 }
139
140 onSendData(*data);
Junxiao Shi27913b42014-12-23 14:49:38 -0700141 }
142 });
143
Junxiao Shia60d9362014-11-12 09:38:21 -0700144 if (options.enablePacketLogging)
145 this->enablePacketLogging();
146
147 if (options.enableRegistrationReply)
148 this->enableRegistrationReply();
149}
150
151void
152DummyClientFace::enablePacketLogging()
153{
Junxiao Shi27913b42014-12-23 14:49:38 -0700154 onSendInterest.connect([this] (const Interest& interest) {
155 this->sentInterests.push_back(interest);
156 });
157 onSendData.connect([this] (const Data& data) {
Alexander Afanasyev3a6da362015-12-29 20:31:03 -0800158 this->sentData.push_back(data);
Junxiao Shi27913b42014-12-23 14:49:38 -0700159 });
Eric Newberry83872fd2015-08-06 17:01:24 -0700160 onSendNack.connect([this] (const lp::Nack& nack) {
161 this->sentNacks.push_back(nack);
162 });
Junxiao Shia60d9362014-11-12 09:38:21 -0700163}
164
165void
166DummyClientFace::enableRegistrationReply()
167{
Junxiao Shi27913b42014-12-23 14:49:38 -0700168 onSendInterest.connect([this] (const Interest& interest) {
Junxiao Shia60d9362014-11-12 09:38:21 -0700169 static const Name localhostRegistration("/localhost/nfd/rib");
170 if (!localhostRegistration.isPrefixOf(interest.getName()))
171 return;
172
173 nfd::ControlParameters params(interest.getName().get(-5).blockFromValue());
174 params.setFaceId(1);
175 params.setOrigin(0);
176 if (interest.getName().get(3) == name::Component("register")) {
177 params.setCost(0);
178 }
179
180 nfd::ControlResponse resp;
181 resp.setCode(200);
182 resp.setBody(params.wireEncode());
183
184 shared_ptr<Data> data = make_shared<Data>(interest.getName());
185 data->setContent(resp.wireEncode());
186
187 KeyChain keyChain;
Yingdi Yu1b0311c2015-06-10 14:58:47 -0700188 keyChain.sign(*data, security::SigningInfo(security::SigningInfo::SIGNER_TYPE_SHA256));
Junxiao Shia60d9362014-11-12 09:38:21 -0700189
190 this->getIoService().post([this, data] { this->receive(*data); });
Junxiao Shi27913b42014-12-23 14:49:38 -0700191 });
Junxiao Shia60d9362014-11-12 09:38:21 -0700192}
193
194template<typename Packet>
195void
196DummyClientFace::receive(const Packet& packet)
197{
Eric Newberry83872fd2015-08-06 17:01:24 -0700198 lp::Packet lpPacket(packet.wireEncode());
Alexander Afanasyevea719672015-02-10 20:25:23 -0800199
Junxiao Shi4b469982015-12-03 18:20:19 +0000200 shared_ptr<lp::IncomingFaceIdTag> incomingFaceIdTag =
201 static_cast<const TagHost&>(packet).getTag<lp::IncomingFaceIdTag>();
202 if (incomingFaceIdTag != nullptr) {
203 lpPacket.add<lp::IncomingFaceIdField>(*incomingFaceIdTag);
Alexander Afanasyevea719672015-02-10 20:25:23 -0800204 }
Eric Newberry83872fd2015-08-06 17:01:24 -0700205
Junxiao Shi4b469982015-12-03 18:20:19 +0000206 shared_ptr<lp::NextHopFaceIdTag> nextHopFaceIdTag =
207 static_cast<const TagHost&>(packet).getTag<lp::NextHopFaceIdTag>();
208 if (nextHopFaceIdTag != nullptr) {
209 lpPacket.add<lp::NextHopFaceIdField>(*nextHopFaceIdTag);
Alexander Afanasyevea719672015-02-10 20:25:23 -0800210 }
Alexander Afanasyev3a6da362015-12-29 20:31:03 -0800211 static_pointer_cast<Transport>(getTransport())->receive(lpPacket.wireEncode());
Junxiao Shia60d9362014-11-12 09:38:21 -0700212}
213
214template void
215DummyClientFace::receive<Interest>(const Interest& packet);
216
217template void
218DummyClientFace::receive<Data>(const Data& packet);
219
Eric Newberry83872fd2015-08-06 17:01:24 -0700220template<>
221void
222DummyClientFace::receive<lp::Nack>(const lp::Nack& nack)
223{
224 lp::Packet lpPacket;
225 lpPacket.add<lp::NackField>(nack.getHeader());
226 Block interest = nack.getInterest().wireEncode();
227 lpPacket.add<lp::FragmentField>(make_pair(interest.begin(), interest.end()));
228
Junxiao Shi4b469982015-12-03 18:20:19 +0000229 shared_ptr<lp::IncomingFaceIdTag> incomingFaceIdTag = nack.getTag<lp::IncomingFaceIdTag>();
230 if (incomingFaceIdTag != nullptr) {
231 lpPacket.add<lp::IncomingFaceIdField>(*incomingFaceIdTag);
Eric Newberry83872fd2015-08-06 17:01:24 -0700232 }
233
Alexander Afanasyev3a6da362015-12-29 20:31:03 -0800234 static_pointer_cast<Transport>(getTransport())->receive(lpPacket.wireEncode());
Eric Newberry83872fd2015-08-06 17:01:24 -0700235}
Junxiao Shia60d9362014-11-12 09:38:21 -0700236
Alexander Afanasyev3a6da362015-12-29 20:31:03 -0800237#ifdef NDN_UTIL_DUMMY_FACE_KEEP_DEPRECATED
238
Junxiao Shia60d9362014-11-12 09:38:21 -0700239shared_ptr<DummyClientFace>
240makeDummyClientFace(const DummyClientFace::Options& options)
241{
Junxiao Shia1ea5062014-12-27 22:33:39 -0700242 // cannot use make_shared<DummyClientFace> because DummyClientFace constructor is private
Alexander Afanasyev3a6da362015-12-29 20:31:03 -0800243 return shared_ptr<DummyClientFace>(new DummyClientFace(options));
Junxiao Shia60d9362014-11-12 09:38:21 -0700244}
245
246shared_ptr<DummyClientFace>
247makeDummyClientFace(boost::asio::io_service& ioService,
248 const DummyClientFace::Options& options)
249{
Junxiao Shia1ea5062014-12-27 22:33:39 -0700250 // cannot use make_shared<DummyClientFace> because DummyClientFace constructor is private
Alexander Afanasyev3a6da362015-12-29 20:31:03 -0800251 return shared_ptr<DummyClientFace>(new DummyClientFace(ref(ioService), options));
Junxiao Shia60d9362014-11-12 09:38:21 -0700252}
253
Alexander Afanasyev3a6da362015-12-29 20:31:03 -0800254#endif // NDN_UTIL_DUMMY_FACE_KEEP_DEPRECATED
255
Junxiao Shia60d9362014-11-12 09:38:21 -0700256} // namespace util
257} // namespace ndn