blob: d92245c1021bcff6259f7f70f9561f2e7195b6a5 [file] [log] [blame]
Junxiao Shi70911652014-08-12 10:14:24 -07001/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
2/**
3 * Copyright (c) 2013-2014 Regents of the University of California.
4 *
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 "nfd-control-command.hpp"
Junxiao Shi5de006b2014-10-26 20:20:52 -070023#include "nfd-command-options.hpp" // only used in deprecated functions
Junxiao Shi70911652014-08-12 10:14:24 -070024
25namespace ndn {
26namespace nfd {
27
28ControlCommand::ControlCommand(const std::string& module, const std::string& verb)
Junxiao Shi5de006b2014-10-26 20:20:52 -070029 : m_module(module)
30 , m_verb(verb)
Junxiao Shi70911652014-08-12 10:14:24 -070031{
Junxiao Shi70911652014-08-12 10:14:24 -070032}
33
34void
35ControlCommand::validateRequest(const ControlParameters& parameters) const
36{
37 m_requestValidator.validate(parameters);
38}
39
40void
41ControlCommand::applyDefaultsToRequest(ControlParameters& parameters) const
42{
43}
44
45void
46ControlCommand::validateResponse(const ControlParameters& parameters) const
47{
48 m_responseValidator.validate(parameters);
49}
50
51void
52ControlCommand::applyDefaultsToResponse(ControlParameters& parameters) const
53{
54}
55
56Name
Junxiao Shi5de006b2014-10-26 20:20:52 -070057ControlCommand::getRequestName(const Name& commandPrefix,
58 const ControlParameters& parameters) const
Junxiao Shi70911652014-08-12 10:14:24 -070059{
60 this->validateRequest(parameters);
61
Junxiao Shi5de006b2014-10-26 20:20:52 -070062 Name name = commandPrefix;
63 name.append(m_module).append(m_verb);
Junxiao Shi70911652014-08-12 10:14:24 -070064 name.append(parameters.wireEncode());
65 return name;
66}
67
Junxiao Shi5de006b2014-10-26 20:20:52 -070068const Name&
69ControlCommand::getPrefix() const
70{
71 // m_prefix is needed because we can't return a local variable as a reference,
72 // and changing the "const Name&" return type to "Name" may cause incompatibility
73 if (m_prefix.empty()) {
74 m_prefix.append(CommandOptions::DEFAULT_PREFIX);
75 m_prefix.append(m_module).append(m_verb);
76 }
77 return m_prefix;
78}
79
80Name
81ControlCommand::getRequestName(const ControlParameters& parameters) const
82{
83 return this->getRequestName(CommandOptions::DEFAULT_PREFIX, parameters);
84}
85
Junxiao Shi70911652014-08-12 10:14:24 -070086ControlCommand::FieldValidator::FieldValidator()
87 : m_required(CONTROL_PARAMETER_UBOUND)
88 , m_optional(CONTROL_PARAMETER_UBOUND)
89{
90}
91
92void
93ControlCommand::FieldValidator::validate(const ControlParameters& parameters) const
94{
95 const std::vector<bool>& presentFields = parameters.getPresentFields();
96
97 for (size_t i = 0; i < CONTROL_PARAMETER_UBOUND; ++i) {
98 bool isPresent = presentFields[i];
99 if (m_required[i]) {
100 if (!isPresent) {
101 throw ArgumentError(CONTROL_PARAMETER_FIELD[i] + " is required but missing");
102 }
103 }
104 else if (isPresent && !m_optional[i]) {
105 throw ArgumentError(CONTROL_PARAMETER_FIELD[i] + " is forbidden but present");
106 }
107 }
108}
109
110FaceCreateCommand::FaceCreateCommand()
111 : ControlCommand("faces", "create")
112{
113 m_requestValidator
114 .required(CONTROL_PARAMETER_URI);
115 m_responseValidator
116 .required(CONTROL_PARAMETER_URI)
117 .required(CONTROL_PARAMETER_FACE_ID);
118}
119
120void
121FaceCreateCommand::validateResponse(const ControlParameters& parameters) const
122{
123 this->ControlCommand::validateResponse(parameters);
124
125 if (parameters.getFaceId() == 0) {
126 throw ArgumentError("FaceId must not be zero");
127 }
128}
129
130FaceDestroyCommand::FaceDestroyCommand()
131 : ControlCommand("faces", "destroy")
132{
133 m_requestValidator
134 .required(CONTROL_PARAMETER_FACE_ID);
135 m_responseValidator = m_requestValidator;
136}
137
138void
139FaceDestroyCommand::validateRequest(const ControlParameters& parameters) const
140{
141 this->ControlCommand::validateRequest(parameters);
142
143 if (parameters.getFaceId() == 0) {
144 throw ArgumentError("FaceId must not be zero");
145 }
146}
147
148void
149FaceDestroyCommand::validateResponse(const ControlParameters& parameters) const
150{
151 this->validateRequest(parameters);
152}
153
154FaceLocalControlCommand::FaceLocalControlCommand(const std::string& verb)
155 : ControlCommand("faces", verb)
156{
157 m_requestValidator
158 .required(CONTROL_PARAMETER_LOCAL_CONTROL_FEATURE);
159 m_responseValidator = m_requestValidator;
160}
161
162void
163FaceLocalControlCommand::validateRequest(const ControlParameters& parameters) const
164{
165 this->ControlCommand::validateRequest(parameters);
166
167 switch (parameters.getLocalControlFeature()) {
168 case LOCAL_CONTROL_FEATURE_INCOMING_FACE_ID:
169 case LOCAL_CONTROL_FEATURE_NEXT_HOP_FACE_ID:
170 break;
171 default:
172 throw ArgumentError("LocalControlFeature is invalid");
173 }
174}
175
176void
177FaceLocalControlCommand::validateResponse(const ControlParameters& parameters) const
178{
179 this->validateRequest(parameters);
180}
181
182FaceEnableLocalControlCommand::FaceEnableLocalControlCommand()
183 : FaceLocalControlCommand("enable-local-control")
184{
185}
186
187FaceDisableLocalControlCommand::FaceDisableLocalControlCommand()
188 : FaceLocalControlCommand("disable-local-control")
189{
190}
191
192FibAddNextHopCommand::FibAddNextHopCommand()
193 : ControlCommand("fib", "add-nexthop")
194{
195 m_requestValidator
196 .required(CONTROL_PARAMETER_NAME)
197 .optional(CONTROL_PARAMETER_FACE_ID)
198 .optional(CONTROL_PARAMETER_COST);
199 m_responseValidator
200 .required(CONTROL_PARAMETER_NAME)
201 .required(CONTROL_PARAMETER_FACE_ID)
202 .required(CONTROL_PARAMETER_COST);
203}
204
205void
206FibAddNextHopCommand::applyDefaultsToRequest(ControlParameters& parameters) const
207{
208 if (!parameters.hasFaceId()) {
209 parameters.setFaceId(0);
210 }
211 if (!parameters.hasCost()) {
212 parameters.setCost(0);
213 }
214}
215
216void
217FibAddNextHopCommand::validateResponse(const ControlParameters& parameters) const
218{
219 this->ControlCommand::validateResponse(parameters);
220
221 if (parameters.getFaceId() == 0) {
222 throw ArgumentError("FaceId must not be zero");
223 }
224}
225
226FibRemoveNextHopCommand::FibRemoveNextHopCommand()
227 : ControlCommand("fib", "remove-nexthop")
228{
229 m_requestValidator
230 .required(CONTROL_PARAMETER_NAME)
231 .optional(CONTROL_PARAMETER_FACE_ID);
232 m_responseValidator
233 .required(CONTROL_PARAMETER_NAME)
234 .required(CONTROL_PARAMETER_FACE_ID);
235}
236
237void
238FibRemoveNextHopCommand::applyDefaultsToRequest(ControlParameters& parameters) const
239{
240 if (!parameters.hasFaceId()) {
241 parameters.setFaceId(0);
242 }
243}
244
245void
246FibRemoveNextHopCommand::validateResponse(const ControlParameters& parameters) const
247{
248 this->ControlCommand::validateResponse(parameters);
249
250 if (parameters.getFaceId() == 0) {
251 throw ArgumentError("FaceId must not be zero");
252 }
253}
254
255StrategyChoiceSetCommand::StrategyChoiceSetCommand()
256 : ControlCommand("strategy-choice", "set")
257{
258 m_requestValidator
259 .required(CONTROL_PARAMETER_NAME)
260 .required(CONTROL_PARAMETER_STRATEGY);
261 m_responseValidator = m_requestValidator;
262}
263
264StrategyChoiceUnsetCommand::StrategyChoiceUnsetCommand()
265 : ControlCommand("strategy-choice", "unset")
266{
267 m_requestValidator
268 .required(CONTROL_PARAMETER_NAME);
269 m_responseValidator = m_requestValidator;
270}
271
272void
273StrategyChoiceUnsetCommand::validateRequest(const ControlParameters& parameters) const
274{
275 this->ControlCommand::validateRequest(parameters);
276
277 if (parameters.getName().size() == 0) {
278 throw ArgumentError("Name must not be ndn:/");
279 }
280}
281
282void
283StrategyChoiceUnsetCommand::validateResponse(const ControlParameters& parameters) const
284{
285 this->validateRequest(parameters);
286}
287
288RibRegisterCommand::RibRegisterCommand()
289 : ControlCommand("rib", "register")
290{
291 m_requestValidator
292 .required(CONTROL_PARAMETER_NAME)
293 .optional(CONTROL_PARAMETER_FACE_ID)
294 .optional(CONTROL_PARAMETER_ORIGIN)
295 .optional(CONTROL_PARAMETER_COST)
296 .optional(CONTROL_PARAMETER_FLAGS)
297 .optional(CONTROL_PARAMETER_EXPIRATION_PERIOD);
298 m_responseValidator
299 .required(CONTROL_PARAMETER_NAME)
300 .required(CONTROL_PARAMETER_FACE_ID)
301 .required(CONTROL_PARAMETER_ORIGIN)
302 .required(CONTROL_PARAMETER_COST)
303 .required(CONTROL_PARAMETER_FLAGS)
304 .optional(CONTROL_PARAMETER_EXPIRATION_PERIOD);
305}
306
307void
308RibRegisterCommand::applyDefaultsToRequest(ControlParameters& parameters) const
309{
310 if (!parameters.hasFaceId()) {
311 parameters.setFaceId(0);
312 }
313 if (!parameters.hasOrigin()) {
314 parameters.setOrigin(ROUTE_ORIGIN_APP);
315 }
316 if (!parameters.hasCost()) {
317 parameters.setCost(0);
318 }
319 if (!parameters.hasFlags()) {
320 parameters.setFlags(ROUTE_FLAG_CHILD_INHERIT);
321 }
322}
323
324void
325RibRegisterCommand::validateResponse(const ControlParameters& parameters) const
326{
327 this->ControlCommand::validateResponse(parameters);
328
329 if (parameters.getFaceId() == 0) {
330 throw ArgumentError("FaceId must not be zero");
331 }
332}
333
334RibUnregisterCommand::RibUnregisterCommand()
335 : ControlCommand("rib", "unregister")
336{
337 m_requestValidator
338 .required(CONTROL_PARAMETER_NAME)
339 .optional(CONTROL_PARAMETER_FACE_ID)
340 .optional(CONTROL_PARAMETER_ORIGIN);
341 m_responseValidator
342 .required(CONTROL_PARAMETER_NAME)
343 .required(CONTROL_PARAMETER_FACE_ID)
344 .required(CONTROL_PARAMETER_ORIGIN);
345}
346
347void
348RibUnregisterCommand::applyDefaultsToRequest(ControlParameters& parameters) const
349{
350 if (!parameters.hasFaceId()) {
351 parameters.setFaceId(0);
352 }
353 if (!parameters.hasOrigin()) {
354 parameters.setOrigin(ROUTE_ORIGIN_APP);
355 }
356}
357
358void
359RibUnregisterCommand::validateResponse(const ControlParameters& parameters) const
360{
361 this->ControlCommand::validateResponse(parameters);
362
363 if (parameters.getFaceId() == 0) {
364 throw ArgumentError("FaceId must not be zero");
365 }
366}
367
368} // namespace nfd
369} // namespace ndn