]> git.proxmox.com Git - mirror_frr.git/blame - ripd/rip_cli.c
Merge pull request #3287 from donaldsharp/v6_access_list
[mirror_frr.git] / ripd / rip_cli.c
CommitLineData
707656ec
RW
1/*
2 * Copyright (C) 1997, 1998, 1999 Kunihiro Ishiguro <kunihiro@zebra.org>
3 * Copyright (C) 2018 NetDEF, Inc.
4 * Renato Westphal
5 *
6 * This program is free software; you can redistribute it and/or modify it
7 * under the terms of the GNU General Public License as published by the Free
8 * Software Foundation; either version 2 of the License, or (at your option)
9 * any later version.
10 *
11 * This program is distributed in the hope that it will be useful, but WITHOUT
12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
14 * more details.
15 *
16 * You should have received a copy of the GNU General Public License along
17 * with this program; see the file COPYING; if not, write to the Free Software
18 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
19 */
20
21#include <zebra.h>
22
23#include "if.h"
24#include "vrf.h"
25#include "log.h"
26#include "prefix.h"
27#include "command.h"
28#include "northbound_cli.h"
29#include "libfrr.h"
30
31#include "ripd/ripd.h"
32#include "ripd/rip_cli.h"
33#ifndef VTYSH_EXTRACT_PL
34#include "ripd/rip_cli_clippy.c"
35#endif
36
8c9226c2
RW
37/*
38 * XPath: /frr-ripd:ripd/instance
39 */
40DEFPY_NOSH (router_rip,
41 router_rip_cmd,
42 "router rip",
43 "Enable a routing process\n"
44 "Routing Information Protocol (RIP)\n")
45{
46 int ret;
47
48 struct cli_config_change changes[] = {
49 {
50 .xpath = "/frr-ripd:ripd/instance",
51 .operation = NB_OP_CREATE,
52 .value = NULL,
53 },
54 };
55
56 ret = nb_cli_cfg_change(vty, NULL, changes, array_size(changes));
57 if (ret == CMD_SUCCESS)
58 VTY_PUSH_XPATH(RIP_NODE, changes[0].xpath);
59
60 return ret;
61}
62
63DEFPY (no_router_rip,
64 no_router_rip_cmd,
65 "no router rip",
66 NO_STR
67 "Enable a routing process\n"
68 "Routing Information Protocol (RIP)\n")
69{
70 struct cli_config_change changes[] = {
71 {
72 .xpath = "/frr-ripd:ripd/instance",
73 .operation = NB_OP_DELETE,
74 .value = NULL,
75 },
76 };
77
78 return nb_cli_cfg_change(vty, NULL, changes, array_size(changes));
79}
80
81void cli_show_router_rip(struct vty *vty, struct lyd_node *dnode,
82 bool show_defaults)
83{
84 vty_out(vty, "!\n");
85 vty_out(vty, "router rip\n");
86}
87
edbf59d2
RW
88/*
89 * XPath: /frr-ripd:ripd/instance/allow-ecmp
90 */
91DEFPY (rip_allow_ecmp,
92 rip_allow_ecmp_cmd,
93 "[no] allow-ecmp",
94 NO_STR
95 "Allow Equal Cost MultiPath\n")
96{
97 struct cli_config_change changes[] = {
98 {
99 .xpath = "./allow-ecmp",
100 .operation = NB_OP_MODIFY,
101 .value = no ? "false" : "true",
102 },
103 };
104
105 return nb_cli_cfg_change(vty, NULL, changes, array_size(changes));
106}
107
108void cli_show_rip_allow_ecmp(struct vty *vty, struct lyd_node *dnode,
109 bool show_defaults)
110{
111 if (!yang_dnode_get_bool(dnode, NULL))
112 vty_out(vty, " no");
113
114 vty_out(vty, " allow-ecmp\n");
115}
116
0b0609ba
RW
117/*
118 * XPath: /frr-ripd:ripd/instance/default-information-originate
119 */
120DEFPY (rip_default_information_originate,
121 rip_default_information_originate_cmd,
122 "[no] default-information originate",
123 NO_STR
124 "Control distribution of default route\n"
125 "Distribute a default route\n")
126{
127 struct cli_config_change changes[] = {
128 {
129 .xpath = "./default-information-originate",
130 .operation = NB_OP_MODIFY,
131 .value = no ? "false" : "true",
132 },
133 };
134
135 return nb_cli_cfg_change(vty, NULL, changes, array_size(changes));
136}
137
138void cli_show_rip_default_information_originate(struct vty *vty,
139 struct lyd_node *dnode,
140 bool show_defaults)
141{
142 if (!yang_dnode_get_bool(dnode, NULL))
143 vty_out(vty, " no");
144
145 vty_out(vty, " default-information originate\n");
146}
147
282ae30c
RW
148/*
149 * XPath: /frr-ripd:ripd/instance/default-metric
150 */
151DEFPY (rip_default_metric,
152 rip_default_metric_cmd,
153 "default-metric (1-16)",
154 "Set a metric of redistribute routes\n"
155 "Default metric\n")
156{
157 struct cli_config_change changes[] = {
158 {
159 .xpath = "./default-metric",
160 .operation = NB_OP_MODIFY,
161 .value = default_metric_str,
162 },
163 };
164
165 return nb_cli_cfg_change(vty, NULL, changes, array_size(changes));
166}
167
168DEFPY (no_rip_default_metric,
169 no_rip_default_metric_cmd,
170 "no default-metric [(1-16)]",
171 NO_STR
172 "Set a metric of redistribute routes\n"
173 "Default metric\n")
174{
175 struct cli_config_change changes[] = {
176 {
177 .xpath = "./default-metric",
178 .operation = NB_OP_MODIFY,
179 .value = NULL,
180 },
181 };
182
183 return nb_cli_cfg_change(vty, NULL, changes, array_size(changes));
184}
185
186void cli_show_rip_default_metric(struct vty *vty, struct lyd_node *dnode,
187 bool show_defaults)
188{
189 vty_out(vty, " default-metric %s\n",
190 yang_dnode_get_string(dnode, NULL));
191}
192
7f8a9cba
RW
193/*
194 * XPath: /frr-ripd:ripd/instance/distance/default
195 */
196DEFPY (rip_distance,
197 rip_distance_cmd,
198 "distance (1-255)",
199 "Administrative distance\n"
200 "Distance value\n")
201{
202 struct cli_config_change changes[] = {
203 {
204 .xpath = "./distance/default",
205 .operation = NB_OP_MODIFY,
206 .value = distance_str,
207 },
208 };
209
210 return nb_cli_cfg_change(vty, NULL, changes, array_size(changes));
211}
212
213DEFPY (no_rip_distance,
214 no_rip_distance_cmd,
215 "no distance [(1-255)]",
216 NO_STR
217 "Administrative distance\n"
218 "Distance value\n")
219{
220 struct cli_config_change changes[] = {
221 {
222 .xpath = "./distance/default",
223 .operation = NB_OP_MODIFY,
224 .value = NULL,
225 },
226 };
227
228 return nb_cli_cfg_change(vty, NULL, changes, array_size(changes));
229}
230
231void cli_show_rip_distance(struct vty *vty, struct lyd_node *dnode,
232 bool show_defaults)
233{
234 vty_out(vty, " distance %s\n", yang_dnode_get_string(dnode, NULL));
235}
236
23b23d8c
RW
237/*
238 * XPath: /frr-ripd:ripd/instance/distance/source
239 */
240DEFPY (rip_distance_source,
241 rip_distance_source_cmd,
242 "distance (1-255) A.B.C.D/M$prefix [WORD$acl]",
243 "Administrative distance\n"
244 "Distance value\n"
245 "IP source prefix\n"
246 "Access list name\n")
247{
248 char xpath_list[XPATH_MAXLEN];
249 struct cli_config_change changes[] = {
250 {
251 .xpath = ".",
252 .operation = NB_OP_CREATE,
253 },
254 {
255 .xpath = "./distance",
256 .operation = NB_OP_MODIFY,
257 .value = distance_str,
258 },
259 {
260 .xpath = "./access-list",
261 .operation = acl ? NB_OP_MODIFY : NB_OP_DELETE,
262 .value = acl,
263 },
264 };
265
266 snprintf(xpath_list, sizeof(xpath_list),
267 "./distance/source[prefix='%s']", prefix_str);
268
269 return nb_cli_cfg_change(vty, xpath_list, changes, array_size(changes));
270}
271
272DEFPY (no_rip_distance_source,
273 no_rip_distance_source_cmd,
274 "no distance (1-255) A.B.C.D/M$prefix [WORD$acl]",
275 NO_STR
276 "Administrative distance\n"
277 "Distance value\n"
278 "IP source prefix\n"
279 "Access list name\n")
280{
281 char xpath_list[XPATH_MAXLEN];
282 struct cli_config_change changes[] = {
283 {
284 .xpath = ".",
285 .operation = NB_OP_DELETE,
286 },
287 };
288
289 snprintf(xpath_list, sizeof(xpath_list),
290 "./distance/source[prefix='%s']", prefix_str);
291
292 return nb_cli_cfg_change(vty, xpath_list, changes, 1);
293}
294
295void cli_show_rip_distance_source(struct vty *vty, struct lyd_node *dnode,
296 bool show_defaults)
297{
298 vty_out(vty, " distance %s %s",
299 yang_dnode_get_string(dnode, "./distance"),
300 yang_dnode_get_string(dnode, "./prefix"));
301 if (yang_dnode_exists(dnode, "./access-list"))
302 vty_out(vty, " %s",
303 yang_dnode_get_string(dnode, "./access-list"));
304 vty_out(vty, "\n");
305}
306
f0ab22fb
RW
307/*
308 * XPath: /frr-ripd:ripd/instance/explicit-neighbor
309 */
310DEFPY (rip_neighbor,
311 rip_neighbor_cmd,
312 "[no] neighbor A.B.C.D",
313 NO_STR
314 "Specify a neighbor router\n"
315 "Neighbor address\n")
316{
317 struct cli_config_change changes[] = {
318 {
319 .xpath = "./explicit-neighbor",
320 .operation = no ? NB_OP_DELETE : NB_OP_CREATE,
321 .value = neighbor_str,
322 },
323 };
324
325 return nb_cli_cfg_change(vty, NULL, changes, array_size(changes));
326}
327
328void cli_show_rip_neighbor(struct vty *vty, struct lyd_node *dnode,
329 bool show_defaults)
330{
331 vty_out(vty, " neighbor %s\n", yang_dnode_get_string(dnode, NULL));
332}
333
3d7a1be8
RW
334/*
335 * XPath: /frr-ripd:ripd/instance/network
336 */
337DEFPY (rip_network_prefix,
338 rip_network_prefix_cmd,
339 "[no] network A.B.C.D/M",
340 NO_STR
341 "Enable routing on an IP network\n"
342 "IP prefix <network>/<length>, e.g., 35.0.0.0/8\n")
343{
344 struct cli_config_change changes[] = {
345 {
346 .xpath = "./network",
347 .operation = no ? NB_OP_DELETE : NB_OP_CREATE,
348 .value = network_str,
349 },
350 };
351
352 return nb_cli_cfg_change(vty, NULL, changes, array_size(changes));
353}
354
355void cli_show_rip_network_prefix(struct vty *vty, struct lyd_node *dnode,
356 bool show_defaults)
357{
358 vty_out(vty, " network %s\n", yang_dnode_get_string(dnode, NULL));
359}
360
361/*
362 * XPath: /frr-ripd:ripd/instance/interface
363 */
364DEFPY (rip_network_if,
365 rip_network_if_cmd,
366 "[no] network WORD",
367 NO_STR
368 "Enable routing on an IP network\n"
369 "Interface name\n")
370{
371 struct cli_config_change changes[] = {
372 {
373 .xpath = "./interface",
374 .operation = no ? NB_OP_DELETE : NB_OP_CREATE,
375 .value = network,
376 },
377 };
378
379 return nb_cli_cfg_change(vty, NULL, changes, array_size(changes));
380}
381
382void cli_show_rip_network_interface(struct vty *vty, struct lyd_node *dnode,
383 bool show_defaults)
384{
385 vty_out(vty, " network %s\n", yang_dnode_get_string(dnode, NULL));
386}
387
8c942f65
RW
388/*
389 * XPath: /frr-ripd:ripd/instance/offset-list
390 */
391DEFPY (rip_offset_list,
392 rip_offset_list_cmd,
393 "offset-list WORD$acl <in|out>$direction (0-16)$metric [IFNAME]",
394 "Modify RIP metric\n"
395 "Access-list name\n"
396 "For incoming updates\n"
397 "For outgoing updates\n"
398 "Metric value\n"
399 "Interface to match\n")
400{
401 char xpath_list[XPATH_MAXLEN];
402 struct cli_config_change changes[] = {
403 {
404 .xpath = ".",
405 .operation = NB_OP_CREATE,
406 },
407 {
408 .xpath = "./access-list",
409 .operation = NB_OP_MODIFY,
410 .value = acl,
411 },
412 {
413 .xpath = "./metric",
414 .operation = NB_OP_MODIFY,
415 .value = metric_str,
416 },
417 };
418
419 snprintf(xpath_list, sizeof(xpath_list),
420 "./offset-list[interface='%s'][direction='%s']",
421 ifname ? ifname : "*", direction);
422
423 return nb_cli_cfg_change(vty, xpath_list, changes, array_size(changes));
424}
425
426DEFPY (no_rip_offset_list,
427 no_rip_offset_list_cmd,
428 "no offset-list WORD$acl <in|out>$direction (0-16)$metric [IFNAME]",
429 NO_STR
430 "Modify RIP metric\n"
431 "Access-list name\n"
432 "For incoming updates\n"
433 "For outgoing updates\n"
434 "Metric value\n"
435 "Interface to match\n")
436{
437 char xpath_list[XPATH_MAXLEN];
438 struct cli_config_change changes[] = {
439 {
440 .xpath = ".",
441 .operation = NB_OP_DELETE,
442 },
443 };
444
445 snprintf(xpath_list, sizeof(xpath_list),
446 "./offset-list[interface='%s'][direction='%s']",
447 ifname ? ifname : "*", direction);
448
449 return nb_cli_cfg_change(vty, xpath_list, changes, array_size(changes));
450}
451
452void cli_show_rip_offset_list(struct vty *vty, struct lyd_node *dnode,
453 bool show_defaults)
454{
455 const char *interface;
456
457 interface = yang_dnode_get_string(dnode, "./interface");
458
459 vty_out(vty, " offset-list %s %s %s",
460 yang_dnode_get_string(dnode, "./access-list"),
461 yang_dnode_get_string(dnode, "./direction"),
462 yang_dnode_get_string(dnode, "./metric"));
463 if (!strmatch(interface, "*"))
464 vty_out(vty, " %s", interface);
465 vty_out(vty, "\n");
466}
467
44f2f852
RW
468/*
469 * XPath: /frr-ripd:ripd/instance/passive-default
470 */
471DEFPY (rip_passive_default,
472 rip_passive_default_cmd,
473 "[no] passive-interface default",
474 NO_STR
475 "Suppress routing updates on an interface\n"
476 "default for all interfaces\n")
477{
478 struct cli_config_change changes[] = {
479 {
480 .xpath = "./passive-default",
481 .operation = NB_OP_MODIFY,
482 .value = no ? "false" : "true",
483 },
484 };
485
486 return nb_cli_cfg_change(vty, NULL, changes, array_size(changes));
487}
488
489void cli_show_rip_passive_default(struct vty *vty, struct lyd_node *dnode,
490 bool show_defaults)
491{
492 if (!yang_dnode_get_bool(dnode, NULL))
493 vty_out(vty, " no");
494
495 vty_out(vty, " passive-interface default\n");
496}
497
498/*
499 * XPath: /frr-ripd:ripd/instance/passive-interface
500 * /frr-ripd:ripd/instance/non-passive-interface
501 */
502DEFPY (rip_passive_interface,
503 rip_passive_interface_cmd,
504 "[no] passive-interface IFNAME",
505 NO_STR
506 "Suppress routing updates on an interface\n"
507 "Interface name\n")
508{
509 struct cli_config_change changes[] = {
510 {
511 .xpath = "./passive-interface",
512 .operation = no ? NB_OP_DELETE : NB_OP_CREATE,
513 .value = ifname,
514 },
515 {
516 .xpath = "./non-passive-interface",
517 .operation = no ? NB_OP_CREATE : NB_OP_DELETE,
518 .value = ifname,
519 },
520 };
521
522 return nb_cli_cfg_change(vty, NULL, changes, array_size(changes));
523}
524
525void cli_show_rip_passive_interface(struct vty *vty, struct lyd_node *dnode,
526 bool show_defaults)
527{
528 vty_out(vty, " passive-interface %s\n",
529 yang_dnode_get_string(dnode, NULL));
530}
531
532void cli_show_rip_non_passive_interface(struct vty *vty, struct lyd_node *dnode,
533 bool show_defaults)
534{
535 vty_out(vty, " no passive-interface %s\n",
536 yang_dnode_get_string(dnode, NULL));
537}
538
908f0020
RW
539/*
540 * XPath: /frr-ripd:ripd/instance/redistribute
541 */
542DEFPY (rip_redistribute,
543 rip_redistribute_cmd,
544 "redistribute " FRR_REDIST_STR_RIPD "$protocol [{metric (0-16)|route-map WORD}]",
545 REDIST_STR
546 FRR_REDIST_HELP_STR_RIPD
547 "Metric\n"
548 "Metric value\n"
549 "Route map reference\n"
550 "Pointer to route-map entries\n")
551{
552 char xpath_list[XPATH_MAXLEN];
553 struct cli_config_change changes[] = {
554 {
555 .xpath = ".",
556 .operation = NB_OP_CREATE,
557 },
558 {
559 .xpath = "./route-map",
560 .operation = route_map ? NB_OP_MODIFY : NB_OP_DELETE,
561 .value = route_map,
562 },
563 {
564 .xpath = "./metric",
565 .operation = metric_str ? NB_OP_MODIFY : NB_OP_DELETE,
566 .value = metric_str,
567 },
568 };
569
570 snprintf(xpath_list, sizeof(xpath_list),
571 "./redistribute[protocol='%s']", protocol);
572
573 return nb_cli_cfg_change(vty, xpath_list, changes, array_size(changes));
574}
575
576DEFPY (no_rip_redistribute,
577 no_rip_redistribute_cmd,
578 "no redistribute " FRR_REDIST_STR_RIPD "$protocol [{metric (0-16)|route-map WORD}]",
579 NO_STR
580 REDIST_STR
581 FRR_REDIST_HELP_STR_RIPD
582 "Metric\n"
583 "Metric value\n"
584 "Route map reference\n"
585 "Pointer to route-map entries\n")
586{
587 char xpath_list[XPATH_MAXLEN];
588 struct cli_config_change changes[] = {
589 {
590 .xpath = ".",
591 .operation = NB_OP_DELETE,
592 },
593 };
594
595 snprintf(xpath_list, sizeof(xpath_list),
596 "./redistribute[protocol='%s']", protocol);
597
598 return nb_cli_cfg_change(vty, xpath_list, changes, array_size(changes));
599}
600
601void cli_show_rip_redistribute(struct vty *vty, struct lyd_node *dnode,
602 bool show_defaults)
603{
604 vty_out(vty, " redistribute %s",
605 yang_dnode_get_string(dnode, "./protocol"));
606 if (yang_dnode_exists(dnode, "./metric"))
607 vty_out(vty, " metric %s",
608 yang_dnode_get_string(dnode, "./metric"));
609 if (yang_dnode_exists(dnode, "./route-map"))
610 vty_out(vty, " route-map %s",
611 yang_dnode_get_string(dnode, "./route-map"));
612 vty_out(vty, "\n");
613}
614
40687878
RW
615/*
616 * XPath: /frr-ripd:ripd/instance/static-route
617 */
618DEFPY (rip_route,
619 rip_route_cmd,
620 "[no] route A.B.C.D/M",
621 NO_STR
622 "RIP static route configuration\n"
623 "IP prefix <network>/<length>\n")
624{
625 struct cli_config_change changes[] = {
626 {
627 .xpath = "./static-route",
628 .operation = no ? NB_OP_DELETE : NB_OP_CREATE,
629 .value = route_str,
630 },
631 };
632
633 return nb_cli_cfg_change(vty, NULL, changes, array_size(changes));
634}
635
636void cli_show_rip_route(struct vty *vty, struct lyd_node *dnode,
637 bool show_defaults)
638{
639 vty_out(vty, " route %s\n", yang_dnode_get_string(dnode, NULL));
640}
641
b745780b
RW
642/*
643 * XPath: /frr-ripd:ripd/instance/timers
644 */
645DEFPY (rip_timers,
646 rip_timers_cmd,
647 "timers basic (5-2147483647)$update (5-2147483647)$timeout (5-2147483647)$garbage",
648 "Adjust routing timers\n"
649 "Basic routing protocol update timers\n"
650 "Routing table update timer value in second. Default is 30.\n"
651 "Routing information timeout timer. Default is 180.\n"
652 "Garbage collection timer. Default is 120.\n")
653{
654 struct cli_config_change changes[] = {
655 {
656 .xpath = "./timers/update-interval",
657 .operation = NB_OP_MODIFY,
658 .value = update_str,
659 },
660 {
661 .xpath = "./timers/holddown-interval",
662 .operation = NB_OP_MODIFY,
663 .value = timeout_str,
664 },
665 {
666 .xpath = "./timers/flush-interval",
667 .operation = NB_OP_MODIFY,
668 .value = garbage_str,
669 },
670 };
671
672 return nb_cli_cfg_change(vty, NULL, changes, array_size(changes));
673}
674
675DEFPY (no_rip_timers,
676 no_rip_timers_cmd,
677 "no timers basic [(5-2147483647) (5-2147483647) (5-2147483647)]",
678 NO_STR
679 "Adjust routing timers\n"
680 "Basic routing protocol update timers\n"
681 "Routing table update timer value in second. Default is 30.\n"
682 "Routing information timeout timer. Default is 180.\n"
683 "Garbage collection timer. Default is 120.\n")
684{
685 struct cli_config_change changes[] = {
686 {
687 .xpath = "./timers/update-interval",
688 .operation = NB_OP_MODIFY,
689 .value = NULL,
690 },
691 {
692 .xpath = "./timers/holddown-interval",
693 .operation = NB_OP_MODIFY,
694 .value = NULL,
695 },
696 {
697 .xpath = "./timers/flush-interval",
698 .operation = NB_OP_MODIFY,
699 .value = NULL,
700 },
701 };
702
703 return nb_cli_cfg_change(vty, NULL, changes, array_size(changes));
704}
705
706void cli_show_rip_timers(struct vty *vty, struct lyd_node *dnode,
707 bool show_defaults)
708{
709 vty_out(vty, " timers basic %s %s %s\n",
710 yang_dnode_get_string(dnode, "./update-interval"),
711 yang_dnode_get_string(dnode, "./holddown-interval"),
712 yang_dnode_get_string(dnode, "./flush-interval"));
713}
714
90eff9da
RW
715/*
716 * XPath: /frr-ripd:ripd/instance/version
717 */
718DEFPY (rip_version,
719 rip_version_cmd,
720 "version (1-2)",
721 "Set routing protocol version\n"
722 "version\n")
723{
724 struct cli_config_change changes[] = {
725 {
726 .xpath = "./version/receive",
727 .operation = NB_OP_MODIFY,
728 .value = version_str,
729 },
730 {
731 .xpath = "./version/send",
732 .operation = NB_OP_MODIFY,
733 .value = version_str,
734 },
735 };
736
737 return nb_cli_cfg_change(vty, NULL, changes, array_size(changes));
738}
739
740DEFPY (no_rip_version,
741 no_rip_version_cmd,
742 "no version [(1-2)]",
743 NO_STR
744 "Set routing protocol version\n"
745 "version\n")
746{
747 struct cli_config_change changes[] = {
748 {
749 .xpath = "./version/receive",
750 .operation = NB_OP_MODIFY,
751 },
752 {
753 .xpath = "./version/send",
754 .operation = NB_OP_MODIFY,
755 },
756 };
757
758 return nb_cli_cfg_change(vty, NULL, changes, array_size(changes));
759}
760
761void cli_show_rip_version(struct vty *vty, struct lyd_node *dnode,
762 bool show_defaults)
763{
764 /*
765 * We have only one "version" command and three possible combinations of
766 * send/receive values.
767 */
768 switch (yang_dnode_get_enum(dnode, "./receive")) {
769 case RI_RIP_VERSION_1:
770 vty_out(vty, " version 1\n");
771 break;
772 case RI_RIP_VERSION_2:
773 vty_out(vty, " version 2\n");
774 break;
775 case RI_RIP_VERSION_1_AND_2:
776 vty_out(vty, " no version\n");
777 break;
778 }
779}
780
94b117b2
RW
781/*
782 * XPath: /frr-interface:lib/interface/frr-ripd:rip/split-horizon
783 */
784DEFPY (ip_rip_split_horizon,
785 ip_rip_split_horizon_cmd,
786 "[no] ip rip split-horizon [poisoned-reverse$poisoned_reverse]",
787 NO_STR
788 IP_STR
789 "Routing Information Protocol\n"
790 "Perform split horizon\n"
791 "With poisoned-reverse\n")
792{
793 struct cli_config_change changes[] = {
794 {
795 .xpath = "./frr-ripd:rip/split-horizon",
796 .operation = NB_OP_MODIFY,
797 },
798 };
799
800 if (no)
801 changes[0].value = "disabled";
802 else if (poisoned_reverse)
803 changes[0].value = "poison-reverse";
804 else
805 changes[0].value = "simple";
806
807 return nb_cli_cfg_change(vty, NULL, changes, array_size(changes));
808}
809
810void cli_show_ip_rip_split_horizon(struct vty *vty, struct lyd_node *dnode,
811 bool show_defaults)
812{
813 int value;
814
815 value = yang_dnode_get_enum(dnode, NULL);
816 switch (value) {
817 case RIP_NO_SPLIT_HORIZON:
818 vty_out(vty, " no ip rip split-horizon\n");
819 break;
820 case RIP_SPLIT_HORIZON:
821 vty_out(vty, " ip rip split-horizon\n");
822 break;
823 case RIP_SPLIT_HORIZON_POISONED_REVERSE:
824 vty_out(vty, " ip rip split-horizon poisoned-reverse\n");
825 break;
826 }
827}
828
829/*
830 * XPath: /frr-interface:lib/interface/frr-ripd:rip/v2-broadcast
831 */
832DEFPY (ip_rip_v2_broadcast,
833 ip_rip_v2_broadcast_cmd,
834 "[no] ip rip v2-broadcast",
835 NO_STR
836 IP_STR
837 "Routing Information Protocol\n"
838 "Send ip broadcast v2 update\n")
839{
840 struct cli_config_change changes[] = {
841 {
842 .xpath = "./frr-ripd:rip/v2-broadcast",
843 .operation = NB_OP_MODIFY,
844 .value = no ? "false" : "true",
845 },
846 };
847
848 return nb_cli_cfg_change(vty, NULL, changes, array_size(changes));
849}
850
851void cli_show_ip_rip_v2_broadcast(struct vty *vty, struct lyd_node *dnode,
852 bool show_defaults)
853{
854 if (!yang_dnode_get_bool(dnode, NULL))
855 vty_out(vty, " no");
856
857 vty_out(vty, " ip rip v2-broadcast\n");
858}
859
860/*
861 * XPath: /frr-interface:lib/interface/frr-ripd:rip/version-receive
862 */
863DEFPY (ip_rip_receive_version,
864 ip_rip_receive_version_cmd,
865 "ip rip receive version <{1$v1|2$v2}|none>",
866 IP_STR
867 "Routing Information Protocol\n"
868 "Advertisement reception\n"
869 "Version control\n"
870 "RIP version 1\n"
871 "RIP version 2\n"
872 "None\n")
873{
874 struct cli_config_change changes[] = {
875 {
876 .xpath = "./frr-ripd:rip/version-receive",
877 .operation = NB_OP_MODIFY,
878 },
879 };
880
881 if (v1 && v2)
882 changes[0].value = "both";
883 else if (v1)
884 changes[0].value = "1";
885 else if (v2)
886 changes[0].value = "2";
887 else
888 changes[0].value = "none";
889
890 return nb_cli_cfg_change(vty, NULL, changes, array_size(changes));
891}
892
893DEFPY (no_ip_rip_receive_version,
894 no_ip_rip_receive_version_cmd,
895 "no ip rip receive version [<{1|2}|none>]",
896 NO_STR
897 IP_STR
898 "Routing Information Protocol\n"
899 "Advertisement reception\n"
900 "Version control\n"
901 "RIP version 1\n"
902 "RIP version 2\n"
903 "None\n")
904{
905 struct cli_config_change changes[] = {
906 {
907 .xpath = "./frr-ripd:rip/version-receive",
908 .operation = NB_OP_MODIFY,
909 .value = NULL,
910 },
911 };
912
913 return nb_cli_cfg_change(vty, NULL, changes, array_size(changes));
914}
915
916void cli_show_ip_rip_receive_version(struct vty *vty, struct lyd_node *dnode,
917 bool show_defaults)
918{
919 switch (yang_dnode_get_enum(dnode, NULL)) {
920 case RI_RIP_UNSPEC:
921 vty_out(vty, " no ip rip receive version\n");
922 break;
923 case RI_RIP_VERSION_1:
924 vty_out(vty, " ip rip receive version 1\n");
925 break;
926 case RI_RIP_VERSION_2:
927 vty_out(vty, " ip rip receive version 2\n");
928 break;
929 case RI_RIP_VERSION_1_AND_2:
930 vty_out(vty, " ip rip receive version 1 2\n");
931 break;
932 case RI_RIP_VERSION_NONE:
933 vty_out(vty, " ip rip receive version none\n");
934 break;
935 }
936}
937
938/*
939 * XPath: /frr-interface:lib/interface/frr-ripd:rip/version-send
940 */
941DEFPY (ip_rip_send_version,
942 ip_rip_send_version_cmd,
943 "ip rip send version <{1$v1|2$v2}|none>",
944 IP_STR
945 "Routing Information Protocol\n"
946 "Advertisement transmission\n"
947 "Version control\n"
948 "RIP version 1\n"
949 "RIP version 2\n"
950 "None\n")
951{
952 struct cli_config_change changes[] = {
953 {
954 .xpath = "./frr-ripd:rip/version-send",
955 .operation = NB_OP_MODIFY,
956 },
957 };
958
959 if (v1 && v2)
960 changes[0].value = "both";
961 else if (v1)
962 changes[0].value = "1";
963 else if (v2)
964 changes[0].value = "2";
965 else
966 changes[0].value = "none";
967
968 return nb_cli_cfg_change(vty, NULL, changes, array_size(changes));
969}
970
971DEFPY (no_ip_rip_send_version,
972 no_ip_rip_send_version_cmd,
973 "no ip rip send version [<{1|2}|none>]",
974 NO_STR
975 IP_STR
976 "Routing Information Protocol\n"
977 "Advertisement transmission\n"
978 "Version control\n"
979 "RIP version 1\n"
980 "RIP version 2\n"
981 "None\n")
982{
983 struct cli_config_change changes[] = {
984 {
985 .xpath = "./frr-ripd:rip/version-send",
986 .operation = NB_OP_MODIFY,
987 .value = NULL,
988 },
989 };
990
991 return nb_cli_cfg_change(vty, NULL, changes, array_size(changes));
992}
993
994void cli_show_ip_rip_send_version(struct vty *vty, struct lyd_node *dnode,
995 bool show_defaults)
996{
997 switch (yang_dnode_get_enum(dnode, NULL)) {
998 case RI_RIP_UNSPEC:
999 vty_out(vty, " no ip rip send version\n");
1000 break;
1001 case RI_RIP_VERSION_1:
1002 vty_out(vty, " ip rip send version 1\n");
1003 break;
1004 case RI_RIP_VERSION_2:
1005 vty_out(vty, " ip rip send version 2\n");
1006 break;
1007 case RI_RIP_VERSION_1_AND_2:
1008 vty_out(vty, " ip rip send version 1 2\n");
1009 break;
1010 case RI_RIP_VERSION_NONE:
1011 vty_out(vty, " ip rip send version none\n");
1012 break;
1013 }
1014}
1015
1016/*
1017 * XPath: /frr-interface:lib/interface/frr-ripd:rip/authentication-scheme
1018 */
1019DEFPY (ip_rip_authentication_mode,
1020 ip_rip_authentication_mode_cmd,
1021 "ip rip authentication mode <md5$mode [auth-length <rfc|old-ripd>$auth_length]|text$mode>",
1022 IP_STR
1023 "Routing Information Protocol\n"
1024 "Authentication control\n"
1025 "Authentication mode\n"
1026 "Keyed message digest\n"
1027 "MD5 authentication data length\n"
1028 "RFC compatible\n"
1029 "Old ripd compatible\n"
1030 "Clear text authentication\n")
1031{
1032 struct cli_config_change changes[] = {
1033 {
1034 .xpath = "./frr-ripd:rip/authentication-scheme/mode",
1035 .operation = NB_OP_MODIFY,
1036 .value = strmatch(mode, "md5") ? "md5" : "plain-text",
1037 },
1038 {
1039 .xpath = "./frr-ripd:rip/authentication-scheme/md5-auth-length",
1040 .operation = NB_OP_MODIFY,
1041 },
1042 };
1043
1044 if (auth_length) {
1045 if (strmatch(auth_length, "rfc"))
1046 changes[1].value = "16";
1047 else
1048 changes[1].value = "20";
1049 }
1050
1051 return nb_cli_cfg_change(vty, NULL, changes, array_size(changes));
1052}
1053
1054DEFPY (no_ip_rip_authentication_mode,
1055 no_ip_rip_authentication_mode_cmd,
1056 "no ip rip authentication mode [<md5 [auth-length <rfc|old-ripd>]|text>]",
1057 NO_STR
1058 IP_STR
1059 "Routing Information Protocol\n"
1060 "Authentication control\n"
1061 "Authentication mode\n"
1062 "Keyed message digest\n"
1063 "MD5 authentication data length\n"
1064 "RFC compatible\n"
1065 "Old ripd compatible\n"
1066 "Clear text authentication\n")
1067{
1068 struct cli_config_change changes[] = {
1069 {
1070 .xpath = "./frr-ripd:rip/authentication-scheme/mode",
1071 .operation = NB_OP_MODIFY,
1072 },
1073 {
1074 .xpath = "./frr-ripd:rip/authentication-scheme/md5-auth-length",
1075 .operation = NB_OP_MODIFY,
1076 },
1077 };
1078
1079 return nb_cli_cfg_change(vty, NULL, changes, array_size(changes));
1080}
1081
1082void cli_show_ip_rip_authentication_scheme(struct vty *vty,
1083 struct lyd_node *dnode,
1084 bool show_defaults)
1085{
1086 switch (yang_dnode_get_enum(dnode, "./mode")) {
1087 case RIP_NO_AUTH:
1088 vty_out(vty, " no ip rip authentication mode\n");
1089 break;
1090 case RIP_AUTH_SIMPLE_PASSWORD:
1091 vty_out(vty, " ip rip authentication mode text\n");
1092 break;
1093 case RIP_AUTH_MD5:
1094 vty_out(vty, " ip rip authentication mode md5");
1095 if (show_defaults
1096 || !yang_dnode_is_default(dnode, "./md5-auth-length")) {
1097 if (yang_dnode_get_enum(dnode, "./md5-auth-length")
1098 == RIP_AUTH_MD5_SIZE)
1099 vty_out(vty, " auth-length rfc");
1100 else
1101 vty_out(vty, " auth-length old-ripd");
1102 }
1103 vty_out(vty, "\n");
1104 break;
1105 }
1106}
1107
1108/*
1109 * XPath: /frr-interface:lib/interface/frr-ripd:rip/authentication-password
1110 */
1111DEFPY (ip_rip_authentication_string,
1112 ip_rip_authentication_string_cmd,
1113 "ip rip authentication string LINE$password",
1114 IP_STR
1115 "Routing Information Protocol\n"
1116 "Authentication control\n"
1117 "Authentication string\n"
1118 "Authentication string\n")
1119{
1120 struct cli_config_change changes[] = {
1121 {
1122 .xpath = "./frr-ripd:rip/authentication-password",
1123 .operation = NB_OP_MODIFY,
1124 .value = password,
1125 },
1126 };
1127
1128 if (strlen(password) > 16) {
1129 vty_out(vty,
1130 "%% RIPv2 authentication string must be shorter than 16\n");
1131 return CMD_WARNING_CONFIG_FAILED;
1132 }
1133
1134 if (yang_dnode_exists(vty->candidate_config->dnode, "%s%s",
1135 VTY_CURR_XPATH,
1136 "/frr-ripd:rip/authentication-key-chain")) {
1137 vty_out(vty, "%% key-chain configuration exists\n");
1138 return CMD_WARNING_CONFIG_FAILED;
1139 }
1140
1141 return nb_cli_cfg_change(vty, NULL, changes, array_size(changes));
1142}
1143
1144DEFPY (no_ip_rip_authentication_string,
1145 no_ip_rip_authentication_string_cmd,
1146 "no ip rip authentication string [LINE]",
1147 NO_STR
1148 IP_STR
1149 "Routing Information Protocol\n"
1150 "Authentication control\n"
1151 "Authentication string\n"
1152 "Authentication string\n")
1153{
1154 struct cli_config_change changes[] = {
1155 {
1156 .xpath = "./frr-ripd:rip/authentication-password",
1157 .operation = NB_OP_DELETE,
1158 },
1159 };
1160
1161 return nb_cli_cfg_change(vty, NULL, changes, array_size(changes));
1162}
1163
1164void cli_show_ip_rip_authentication_string(struct vty *vty,
1165 struct lyd_node *dnode,
1166 bool show_defaults)
1167{
1168 vty_out(vty, " ip rip authentication string %s\n",
1169 yang_dnode_get_string(dnode, NULL));
1170}
1171
1172/*
1173 * XPath: /frr-interface:lib/interface/frr-ripd:rip/authentication-key-chain
1174 */
1175DEFPY (ip_rip_authentication_key_chain,
1176 ip_rip_authentication_key_chain_cmd,
1177 "ip rip authentication key-chain LINE$keychain",
1178 IP_STR
1179 "Routing Information Protocol\n"
1180 "Authentication control\n"
1181 "Authentication key-chain\n"
1182 "name of key-chain\n")
1183{
1184 struct cli_config_change changes[] = {
1185 {
1186 .xpath = "./frr-ripd:rip/authentication-key-chain",
1187 .operation = NB_OP_MODIFY,
1188 .value = keychain,
1189 },
1190 };
1191
1192 if (yang_dnode_exists(vty->candidate_config->dnode, "%s%s",
1193 VTY_CURR_XPATH,
1194 "/frr-ripd:rip/authentication-password")) {
1195 vty_out(vty, "%% authentication string configuration exists\n");
1196 return CMD_WARNING_CONFIG_FAILED;
1197 }
1198
1199 return nb_cli_cfg_change(vty, NULL, changes, array_size(changes));
1200}
1201
1202DEFPY (no_ip_rip_authentication_key_chain,
1203 no_ip_rip_authentication_key_chain_cmd,
1204 "no ip rip authentication key-chain [LINE]",
1205 NO_STR
1206 IP_STR
1207 "Routing Information Protocol\n"
1208 "Authentication control\n"
1209 "Authentication key-chain\n"
1210 "name of key-chain\n")
1211{
1212 struct cli_config_change changes[] = {
1213 {
1214 .xpath = "./frr-ripd:rip/authentication-key-chain",
1215 .operation = NB_OP_DELETE,
1216 },
1217 };
1218
1219 return nb_cli_cfg_change(vty, NULL, changes, array_size(changes));
1220}
1221
1222void cli_show_ip_rip_authentication_key_chain(struct vty *vty,
1223 struct lyd_node *dnode,
1224 bool show_defaults)
1225{
1226 vty_out(vty, " ip rip authentication key-chain %s\n",
1227 yang_dnode_get_string(dnode, NULL));
1228}
1229
1137aef4
RW
1230/*
1231 * XPath: /frr-ripd:clear-rip-route
1232 */
1233DEFPY (clear_ip_rip,
1234 clear_ip_rip_cmd,
1235 "clear ip rip",
1236 CLEAR_STR
1237 IP_STR
1238 "Clear IP RIP database\n")
1239{
1240 return nb_cli_rpc("/frr-ripd:clear-rip-route", NULL, NULL);
1241}
1242
707656ec
RW
1243void rip_cli_init(void)
1244{
8c9226c2
RW
1245 install_element(CONFIG_NODE, &router_rip_cmd);
1246 install_element(CONFIG_NODE, &no_router_rip_cmd);
edbf59d2
RW
1247
1248 install_element(RIP_NODE, &rip_allow_ecmp_cmd);
0b0609ba 1249 install_element(RIP_NODE, &rip_default_information_originate_cmd);
282ae30c
RW
1250 install_element(RIP_NODE, &rip_default_metric_cmd);
1251 install_element(RIP_NODE, &no_rip_default_metric_cmd);
7f8a9cba
RW
1252 install_element(RIP_NODE, &rip_distance_cmd);
1253 install_element(RIP_NODE, &no_rip_distance_cmd);
23b23d8c
RW
1254 install_element(RIP_NODE, &rip_distance_source_cmd);
1255 install_element(RIP_NODE, &no_rip_distance_source_cmd);
f0ab22fb 1256 install_element(RIP_NODE, &rip_neighbor_cmd);
3d7a1be8
RW
1257 install_element(RIP_NODE, &rip_network_prefix_cmd);
1258 install_element(RIP_NODE, &rip_network_if_cmd);
8c942f65
RW
1259 install_element(RIP_NODE, &rip_offset_list_cmd);
1260 install_element(RIP_NODE, &no_rip_offset_list_cmd);
44f2f852
RW
1261 install_element(RIP_NODE, &rip_passive_default_cmd);
1262 install_element(RIP_NODE, &rip_passive_interface_cmd);
908f0020
RW
1263 install_element(RIP_NODE, &rip_redistribute_cmd);
1264 install_element(RIP_NODE, &no_rip_redistribute_cmd);
40687878 1265 install_element(RIP_NODE, &rip_route_cmd);
b745780b
RW
1266 install_element(RIP_NODE, &rip_timers_cmd);
1267 install_element(RIP_NODE, &no_rip_timers_cmd);
90eff9da
RW
1268 install_element(RIP_NODE, &rip_version_cmd);
1269 install_element(RIP_NODE, &no_rip_version_cmd);
94b117b2
RW
1270
1271 install_element(INTERFACE_NODE, &ip_rip_split_horizon_cmd);
1272 install_element(INTERFACE_NODE, &ip_rip_v2_broadcast_cmd);
1273 install_element(INTERFACE_NODE, &ip_rip_receive_version_cmd);
1274 install_element(INTERFACE_NODE, &no_ip_rip_receive_version_cmd);
1275 install_element(INTERFACE_NODE, &ip_rip_send_version_cmd);
1276 install_element(INTERFACE_NODE, &no_ip_rip_send_version_cmd);
1277 install_element(INTERFACE_NODE, &ip_rip_authentication_mode_cmd);
1278 install_element(INTERFACE_NODE, &no_ip_rip_authentication_mode_cmd);
1279 install_element(INTERFACE_NODE, &ip_rip_authentication_string_cmd);
1280 install_element(INTERFACE_NODE, &no_ip_rip_authentication_string_cmd);
1281 install_element(INTERFACE_NODE, &ip_rip_authentication_key_chain_cmd);
1282 install_element(INTERFACE_NODE,
1283 &no_ip_rip_authentication_key_chain_cmd);
1284
1137aef4 1285 install_element(ENABLE_NODE, &clear_ip_rip_cmd);
707656ec 1286}