]> git.proxmox.com Git - mirror_frr.git/blob - zebra/zebra_vty.c
Merge pull request #2122 from donaldsharp/zebra_nhs
[mirror_frr.git] / zebra / zebra_vty.c
1 /* Zebra VTY functions
2 * Copyright (C) 2002 Kunihiro Ishiguro
3 *
4 * This file is part of GNU Zebra.
5 *
6 * GNU Zebra 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
8 * Free Software Foundation; either version 2, or (at your option) any
9 * later version.
10 *
11 * GNU Zebra is distributed in the hope that it will be useful, but
12 * WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * General Public License for 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 "memory.h"
24 #include "zebra_memory.h"
25 #include "if.h"
26 #include "prefix.h"
27 #include "command.h"
28 #include "table.h"
29 #include "rib.h"
30 #include "nexthop.h"
31 #include "vrf.h"
32 #include "linklist.h"
33 #include "mpls.h"
34 #include "routemap.h"
35 #include "srcdest_table.h"
36 #include "vxlan.h"
37
38 #include "zebra/zserv.h"
39 #include "zebra/zebra_vrf.h"
40 #include "zebra/zebra_mpls.h"
41 #include "zebra/zebra_rnh.h"
42 #include "zebra/redistribute.h"
43 #include "zebra/zebra_routemap.h"
44 #include "lib/json.h"
45 #include "zebra/zebra_vxlan.h"
46 #ifndef VTYSH_EXTRACT_PL
47 #include "zebra/zebra_vty_clippy.c"
48 #endif
49 #include "zebra/zserv.h"
50 #include "zebra/router-id.h"
51 #include "zebra/ipforward.h"
52 #include "zebra/zebra_vxlan_private.h"
53 #include "zebra/zebra_pbr.h"
54
55 extern int allow_delete;
56
57 static int do_show_ip_route(struct vty *vty, const char *vrf_name, afi_t afi,
58 safi_t safi, bool use_fib, uint8_t use_json,
59 route_tag_t tag,
60 const struct prefix *longer_prefix_p,
61 bool supernets_only, int type,
62 unsigned short ospf_instance_id);
63 static void vty_show_ip_route_detail(struct vty *vty, struct route_node *rn,
64 int mcast);
65 static void vty_show_ip_route_summary(struct vty *vty,
66 struct route_table *table);
67 static void vty_show_ip_route_summary_prefix(struct vty *vty,
68 struct route_table *table);
69
70 /*
71 * special macro to allow us to get the correct zebra_vrf
72 */
73 #define ZEBRA_DECLVAR_CONTEXT(A, B) \
74 struct vrf *A = VTY_GET_CONTEXT(vrf); \
75 struct zebra_vrf *B = (vrf) ? vrf->info : NULL;
76
77 /* VNI range as per RFC 7432 */
78 #define CMD_VNI_RANGE "(1-16777215)"
79
80 DEFUN (ip_multicast_mode,
81 ip_multicast_mode_cmd,
82 "ip multicast rpf-lookup-mode <urib-only|mrib-only|mrib-then-urib|lower-distance|longer-prefix>",
83 IP_STR
84 "Multicast options\n"
85 "RPF lookup behavior\n"
86 "Lookup in unicast RIB only\n"
87 "Lookup in multicast RIB only\n"
88 "Try multicast RIB first, fall back to unicast RIB\n"
89 "Lookup both, use entry with lower distance\n"
90 "Lookup both, use entry with longer prefix\n")
91 {
92 char *mode = argv[3]->text;
93
94 if (strmatch(mode, "urib-only"))
95 multicast_mode_ipv4_set(MCAST_URIB_ONLY);
96 else if (strmatch(mode, "mrib-only"))
97 multicast_mode_ipv4_set(MCAST_MRIB_ONLY);
98 else if (strmatch(mode, "mrib-then-urib"))
99 multicast_mode_ipv4_set(MCAST_MIX_MRIB_FIRST);
100 else if (strmatch(mode, "lower-distance"))
101 multicast_mode_ipv4_set(MCAST_MIX_DISTANCE);
102 else if (strmatch(mode, "longer-prefix"))
103 multicast_mode_ipv4_set(MCAST_MIX_PFXLEN);
104 else {
105 vty_out(vty, "Invalid mode specified\n");
106 return CMD_WARNING_CONFIG_FAILED;
107 }
108
109 return CMD_SUCCESS;
110 }
111
112 DEFUN (no_ip_multicast_mode,
113 no_ip_multicast_mode_cmd,
114 "no ip multicast rpf-lookup-mode [<urib-only|mrib-only|mrib-then-urib|lower-distance|longer-prefix>]",
115 NO_STR
116 IP_STR
117 "Multicast options\n"
118 "RPF lookup behavior\n"
119 "Lookup in unicast RIB only\n"
120 "Lookup in multicast RIB only\n"
121 "Try multicast RIB first, fall back to unicast RIB\n"
122 "Lookup both, use entry with lower distance\n"
123 "Lookup both, use entry with longer prefix\n")
124 {
125 multicast_mode_ipv4_set(MCAST_NO_CONFIG);
126 return CMD_SUCCESS;
127 }
128
129
130 DEFUN (show_ip_rpf,
131 show_ip_rpf_cmd,
132 "show ip rpf [json]",
133 SHOW_STR
134 IP_STR
135 "Display RPF information for multicast source\n"
136 JSON_STR)
137 {
138 int uj = use_json(argc, argv);
139 return do_show_ip_route(vty, VRF_DEFAULT_NAME, AFI_IP, SAFI_MULTICAST,
140 false, uj, 0, NULL, false, 0, 0);
141 }
142
143 DEFUN (show_ip_rpf_addr,
144 show_ip_rpf_addr_cmd,
145 "show ip rpf A.B.C.D",
146 SHOW_STR
147 IP_STR
148 "Display RPF information for multicast source\n"
149 "IP multicast source address (e.g. 10.0.0.0)\n")
150 {
151 int idx_ipv4 = 3;
152 struct in_addr addr;
153 struct route_node *rn;
154 struct route_entry *re;
155 int ret;
156
157 ret = inet_aton(argv[idx_ipv4]->arg, &addr);
158 if (ret == 0) {
159 vty_out(vty, "%% Malformed address\n");
160 return CMD_WARNING;
161 }
162
163 re = rib_match_ipv4_multicast(VRF_DEFAULT, addr, &rn);
164
165 if (re)
166 vty_show_ip_route_detail(vty, rn, 1);
167 else
168 vty_out(vty, "%% No match for RPF lookup\n");
169
170 return CMD_SUCCESS;
171 }
172
173 /* New RIB. Detailed information for IPv4 route. */
174 static void vty_show_ip_route_detail(struct vty *vty, struct route_node *rn,
175 int mcast)
176 {
177 struct route_entry *re;
178 struct nexthop *nexthop;
179 char buf[SRCDEST2STR_BUFFER];
180 struct zebra_vrf *zvrf;
181
182 RNODE_FOREACH_RE (rn, re) {
183 const char *mcast_info = "";
184 if (mcast) {
185 rib_table_info_t *info = srcdest_rnode_table_info(rn);
186 mcast_info = (info->safi == SAFI_MULTICAST)
187 ? " using Multicast RIB"
188 : " using Unicast RIB";
189 }
190
191 vty_out(vty, "Routing entry for %s%s\n",
192 srcdest_rnode2str(rn, buf, sizeof(buf)), mcast_info);
193 vty_out(vty, " Known via \"%s", zebra_route_string(re->type));
194 if (re->instance)
195 vty_out(vty, "[%d]", re->instance);
196 vty_out(vty, "\"");
197 vty_out(vty, ", distance %u, metric %u", re->distance,
198 re->metric);
199 if (re->tag) {
200 vty_out(vty, ", tag %u", re->tag);
201 #if defined(SUPPORT_REALMS)
202 if (re->tag > 0 && re->tag <= 255)
203 vty_out(vty, "(realm)");
204 #endif
205 }
206 if (re->mtu)
207 vty_out(vty, ", mtu %u", re->mtu);
208 if (re->vrf_id != VRF_DEFAULT) {
209 zvrf = vrf_info_lookup(re->vrf_id);
210 vty_out(vty, ", vrf %s", zvrf_name(zvrf));
211 }
212 if (CHECK_FLAG(re->flags, ZEBRA_FLAG_SELECTED))
213 vty_out(vty, ", best");
214 vty_out(vty, "\n");
215
216 time_t uptime;
217 struct tm *tm;
218
219 uptime = time(NULL);
220 uptime -= re->uptime;
221 tm = gmtime(&uptime);
222
223 vty_out(vty, " Last update ");
224
225 if (uptime < ONE_DAY_SECOND)
226 vty_out(vty, "%02d:%02d:%02d", tm->tm_hour, tm->tm_min,
227 tm->tm_sec);
228 else if (uptime < ONE_WEEK_SECOND)
229 vty_out(vty, "%dd%02dh%02dm", tm->tm_yday, tm->tm_hour,
230 tm->tm_min);
231 else
232 vty_out(vty, "%02dw%dd%02dh", tm->tm_yday / 7,
233 tm->tm_yday - ((tm->tm_yday / 7) * 7),
234 tm->tm_hour);
235 vty_out(vty, " ago\n");
236
237 for (ALL_NEXTHOPS(re->ng, nexthop)) {
238 char addrstr[32];
239
240 vty_out(vty, " %c%s",
241 CHECK_FLAG(nexthop->flags, NEXTHOP_FLAG_FIB)
242 ? CHECK_FLAG(nexthop->flags,
243 NEXTHOP_FLAG_DUPLICATE)
244 ? ' '
245 : '*'
246 : ' ',
247 nexthop->rparent ? " " : "");
248
249 switch (nexthop->type) {
250 case NEXTHOP_TYPE_IPV4:
251 case NEXTHOP_TYPE_IPV4_IFINDEX:
252 vty_out(vty, " %s",
253 inet_ntoa(nexthop->gate.ipv4));
254 if (nexthop->ifindex)
255 vty_out(vty, ", via %s",
256 ifindex2ifname(
257 nexthop->ifindex,
258 nexthop->vrf_id));
259 break;
260 case NEXTHOP_TYPE_IPV6:
261 case NEXTHOP_TYPE_IPV6_IFINDEX:
262 vty_out(vty, " %s",
263 inet_ntop(AF_INET6, &nexthop->gate.ipv6,
264 buf, sizeof buf));
265 if (nexthop->ifindex)
266 vty_out(vty, ", via %s",
267 ifindex2ifname(
268 nexthop->ifindex,
269 nexthop->vrf_id));
270 break;
271 case NEXTHOP_TYPE_IFINDEX:
272 vty_out(vty, " directly connected, %s",
273 ifindex2ifname(nexthop->ifindex,
274 nexthop->vrf_id));
275 break;
276 case NEXTHOP_TYPE_BLACKHOLE:
277 vty_out(vty, " unreachable");
278 switch (nexthop->bh_type) {
279 case BLACKHOLE_REJECT:
280 vty_out(vty, " (ICMP unreachable)");
281 break;
282 case BLACKHOLE_ADMINPROHIB:
283 vty_out(vty,
284 " (ICMP admin-prohibited)");
285 break;
286 case BLACKHOLE_NULL:
287 vty_out(vty, " (blackhole)");
288 break;
289 case BLACKHOLE_UNSPEC:
290 break;
291 }
292 break;
293 default:
294 break;
295 }
296
297 if ((re->vrf_id != nexthop->vrf_id)
298 && (nexthop->type != NEXTHOP_TYPE_BLACKHOLE)) {
299 struct vrf *vrf =
300 vrf_lookup_by_id(nexthop->vrf_id);
301
302 if (vrf)
303 vty_out(vty, "(vrf %s)", vrf->name);
304 else
305 vty_out(vty, "(vrf UKNOWN)");
306 }
307
308 if (CHECK_FLAG(nexthop->flags, NEXTHOP_FLAG_DUPLICATE))
309 vty_out(vty, " (duplicate nexthop removed)");
310
311 if (!CHECK_FLAG(nexthop->flags, NEXTHOP_FLAG_ACTIVE))
312 vty_out(vty, " inactive");
313
314 if (CHECK_FLAG(nexthop->flags, NEXTHOP_FLAG_ONLINK))
315 vty_out(vty, " onlink");
316
317 if (CHECK_FLAG(nexthop->flags, NEXTHOP_FLAG_RECURSIVE))
318 vty_out(vty, " (recursive)");
319
320 switch (nexthop->type) {
321 case NEXTHOP_TYPE_IPV4:
322 case NEXTHOP_TYPE_IPV4_IFINDEX:
323 if (nexthop->src.ipv4.s_addr) {
324 if (inet_ntop(AF_INET,
325 &nexthop->src.ipv4,
326 addrstr, sizeof addrstr))
327 vty_out(vty, ", src %s",
328 addrstr);
329 }
330 break;
331 case NEXTHOP_TYPE_IPV6:
332 case NEXTHOP_TYPE_IPV6_IFINDEX:
333 if (!IPV6_ADDR_SAME(&nexthop->src.ipv6,
334 &in6addr_any)) {
335 if (inet_ntop(AF_INET6,
336 &nexthop->src.ipv6,
337 addrstr, sizeof addrstr))
338 vty_out(vty, ", src %s",
339 addrstr);
340 }
341 break;
342 default:
343 break;
344 }
345
346 if (re->nexthop_mtu)
347 vty_out(vty, ", mtu %u", re->nexthop_mtu);
348
349 /* Label information */
350 if (nexthop->nh_label
351 && nexthop->nh_label->num_labels) {
352 vty_out(vty, ", label %s",
353 mpls_label2str(
354 nexthop->nh_label->num_labels,
355 nexthop->nh_label->label, buf,
356 sizeof buf, 1));
357 }
358
359 vty_out(vty, "\n");
360 }
361 vty_out(vty, "\n");
362 }
363 }
364
365 static void vty_show_ip_route(struct vty *vty, struct route_node *rn,
366 struct route_entry *re, json_object *json)
367 {
368 struct nexthop *nexthop;
369 int len = 0;
370 char buf[SRCDEST2STR_BUFFER];
371 json_object *json_nexthops = NULL;
372 json_object *json_nexthop = NULL;
373 json_object *json_route = NULL;
374 json_object *json_labels = NULL;
375 time_t uptime;
376 struct tm *tm;
377
378 uptime = time(NULL);
379 uptime -= re->uptime;
380 tm = gmtime(&uptime);
381
382 if (json) {
383 json_route = json_object_new_object();
384 json_nexthops = json_object_new_array();
385
386 json_object_string_add(json_route, "prefix",
387 srcdest_rnode2str(rn, buf, sizeof buf));
388 json_object_string_add(json_route, "protocol",
389 zebra_route_string(re->type));
390
391 if (re->instance)
392 json_object_int_add(json_route, "instance",
393 re->instance);
394
395 if (re->vrf_id)
396 json_object_int_add(json_route, "vrfId", re->vrf_id);
397
398 if (CHECK_FLAG(re->flags, ZEBRA_FLAG_SELECTED))
399 json_object_boolean_true_add(json_route, "selected");
400
401 if (re->type != ZEBRA_ROUTE_CONNECT) {
402 json_object_int_add(json_route, "distance",
403 re->distance);
404 json_object_int_add(json_route, "metric", re->metric);
405 }
406
407 json_object_int_add(json_route, "internalStatus",
408 re->status);
409 json_object_int_add(json_route, "internalFlags",
410 re->flags);
411 if (uptime < ONE_DAY_SECOND)
412 sprintf(buf, "%02d:%02d:%02d", tm->tm_hour, tm->tm_min,
413 tm->tm_sec);
414 else if (uptime < ONE_WEEK_SECOND)
415 sprintf(buf, "%dd%02dh%02dm", tm->tm_yday, tm->tm_hour,
416 tm->tm_min);
417 else
418 sprintf(buf, "%02dw%dd%02dh", tm->tm_yday / 7,
419 tm->tm_yday - ((tm->tm_yday / 7) * 7),
420 tm->tm_hour);
421
422 json_object_string_add(json_route, "uptime", buf);
423
424 for (ALL_NEXTHOPS(re->ng, nexthop)) {
425 json_nexthop = json_object_new_object();
426
427 json_object_int_add(json_nexthop, "flags",
428 nexthop->flags);
429
430 if (CHECK_FLAG(nexthop->flags, NEXTHOP_FLAG_DUPLICATE))
431 json_object_boolean_true_add(json_nexthop,
432 "duplicate");
433
434 if (CHECK_FLAG(nexthop->flags, NEXTHOP_FLAG_FIB))
435 json_object_boolean_true_add(json_nexthop,
436 "fib");
437
438 switch (nexthop->type) {
439 case NEXTHOP_TYPE_IPV4:
440 case NEXTHOP_TYPE_IPV4_IFINDEX:
441 json_object_string_add(
442 json_nexthop, "ip",
443 inet_ntoa(nexthop->gate.ipv4));
444 json_object_string_add(json_nexthop, "afi",
445 "ipv4");
446
447 if (nexthop->ifindex) {
448 json_object_int_add(json_nexthop,
449 "interfaceIndex",
450 nexthop->ifindex);
451 json_object_string_add(
452 json_nexthop, "interfaceName",
453 ifindex2ifname(
454 nexthop->ifindex,
455 nexthop->vrf_id));
456 }
457 break;
458 case NEXTHOP_TYPE_IPV6:
459 case NEXTHOP_TYPE_IPV6_IFINDEX:
460 json_object_string_add(
461 json_nexthop, "ip",
462 inet_ntop(AF_INET6, &nexthop->gate.ipv6,
463 buf, sizeof buf));
464 json_object_string_add(json_nexthop, "afi",
465 "ipv6");
466
467 if (nexthop->ifindex) {
468 json_object_int_add(json_nexthop,
469 "interfaceIndex",
470 nexthop->ifindex);
471 json_object_string_add(
472 json_nexthop, "interfaceName",
473 ifindex2ifname(
474 nexthop->ifindex,
475 nexthop->vrf_id));
476 }
477 break;
478
479 case NEXTHOP_TYPE_IFINDEX:
480 json_object_boolean_true_add(
481 json_nexthop, "directlyConnected");
482 json_object_int_add(json_nexthop,
483 "interfaceIndex",
484 nexthop->ifindex);
485 json_object_string_add(
486 json_nexthop, "interfaceName",
487 ifindex2ifname(nexthop->ifindex,
488 nexthop->vrf_id));
489 break;
490 case NEXTHOP_TYPE_BLACKHOLE:
491 json_object_boolean_true_add(json_nexthop,
492 "unreachable");
493 switch (nexthop->bh_type) {
494 case BLACKHOLE_REJECT:
495 json_object_boolean_true_add(
496 json_nexthop, "reject");
497 break;
498 case BLACKHOLE_ADMINPROHIB:
499 json_object_boolean_true_add(
500 json_nexthop,
501 "admin-prohibited");
502 break;
503 case BLACKHOLE_NULL:
504 json_object_boolean_true_add(
505 json_nexthop, "blackhole");
506 break;
507 case BLACKHOLE_UNSPEC:
508 break;
509 }
510 break;
511 default:
512 break;
513 }
514
515 if ((nexthop->vrf_id != re->vrf_id)
516 && (nexthop->type != NEXTHOP_TYPE_BLACKHOLE)) {
517 struct vrf *vrf =
518 vrf_lookup_by_id(nexthop->vrf_id);
519
520 json_object_string_add(json_nexthop, "vrf",
521 vrf->name);
522 }
523 if (CHECK_FLAG(nexthop->flags, NEXTHOP_FLAG_DUPLICATE))
524 json_object_boolean_true_add(json_nexthop,
525 "duplicate");
526
527 if (CHECK_FLAG(nexthop->flags, NEXTHOP_FLAG_ACTIVE))
528 json_object_boolean_true_add(json_nexthop,
529 "active");
530
531 if (CHECK_FLAG(nexthop->flags, NEXTHOP_FLAG_ONLINK))
532 json_object_boolean_true_add(json_nexthop,
533 "onLink");
534
535 if (CHECK_FLAG(nexthop->flags, NEXTHOP_FLAG_RECURSIVE))
536 json_object_boolean_true_add(json_nexthop,
537 "recursive");
538
539 switch (nexthop->type) {
540 case NEXTHOP_TYPE_IPV4:
541 case NEXTHOP_TYPE_IPV4_IFINDEX:
542 if (nexthop->src.ipv4.s_addr) {
543 if (inet_ntop(AF_INET,
544 &nexthop->src.ipv4, buf,
545 sizeof buf))
546 json_object_string_add(
547 json_nexthop, "source",
548 buf);
549 }
550 break;
551 case NEXTHOP_TYPE_IPV6:
552 case NEXTHOP_TYPE_IPV6_IFINDEX:
553 if (!IPV6_ADDR_SAME(&nexthop->src.ipv6,
554 &in6addr_any)) {
555 if (inet_ntop(AF_INET6,
556 &nexthop->src.ipv6, buf,
557 sizeof buf))
558 json_object_string_add(
559 json_nexthop, "source",
560 buf);
561 }
562 break;
563 default:
564 break;
565 }
566
567 if (nexthop->nh_label
568 && nexthop->nh_label->num_labels) {
569 json_labels = json_object_new_array();
570
571 for (int label_index = 0;
572 label_index
573 < nexthop->nh_label->num_labels;
574 label_index++)
575 json_object_array_add(
576 json_labels,
577 json_object_new_int(
578 nexthop->nh_label->label
579 [label_index]));
580
581 json_object_object_add(json_nexthop, "labels",
582 json_labels);
583 }
584
585 json_object_array_add(json_nexthops, json_nexthop);
586 }
587
588 json_object_object_add(json_route, "nexthops", json_nexthops);
589 json_object_array_add(json, json_route);
590 return;
591 }
592
593 /* Nexthop information. */
594 for (ALL_NEXTHOPS(re->ng, nexthop)) {
595 if (nexthop == re->ng.nexthop) {
596 /* Prefix information. */
597 len = vty_out(vty, "%c", zebra_route_char(re->type));
598 if (re->instance)
599 len += vty_out(vty, "[%d]", re->instance);
600 len += vty_out(
601 vty, "%c%c %s",
602 CHECK_FLAG(re->flags, ZEBRA_FLAG_SELECTED)
603 ? '>'
604 : ' ',
605 CHECK_FLAG(nexthop->flags, NEXTHOP_FLAG_FIB)
606 ? '*'
607 : ' ',
608 srcdest_rnode2str(rn, buf, sizeof buf));
609
610 /* Distance and metric display. */
611 if (re->type != ZEBRA_ROUTE_CONNECT)
612 len += vty_out(vty, " [%u/%u]", re->distance,
613 re->metric);
614 } else {
615 vty_out(vty, " %c%*c",
616 CHECK_FLAG(nexthop->flags, NEXTHOP_FLAG_FIB)
617 ? CHECK_FLAG(nexthop->flags,
618 NEXTHOP_FLAG_DUPLICATE)
619 ? ' '
620 : '*'
621 : ' ',
622 len - 3 + (2 * nexthop_level(nexthop)), ' ');
623 }
624
625 switch (nexthop->type) {
626 case NEXTHOP_TYPE_IPV4:
627 case NEXTHOP_TYPE_IPV4_IFINDEX:
628 vty_out(vty, " via %s", inet_ntoa(nexthop->gate.ipv4));
629 if (nexthop->ifindex)
630 vty_out(vty, ", %s",
631 ifindex2ifname(nexthop->ifindex,
632 nexthop->vrf_id));
633 break;
634 case NEXTHOP_TYPE_IPV6:
635 case NEXTHOP_TYPE_IPV6_IFINDEX:
636 vty_out(vty, " via %s",
637 inet_ntop(AF_INET6, &nexthop->gate.ipv6, buf,
638 sizeof buf));
639 if (nexthop->ifindex)
640 vty_out(vty, ", %s",
641 ifindex2ifname(nexthop->ifindex,
642 nexthop->vrf_id));
643 break;
644
645 case NEXTHOP_TYPE_IFINDEX:
646 vty_out(vty, " is directly connected, %s",
647 ifindex2ifname(nexthop->ifindex,
648 nexthop->vrf_id));
649 break;
650 case NEXTHOP_TYPE_BLACKHOLE:
651 vty_out(vty, " unreachable");
652 switch (nexthop->bh_type) {
653 case BLACKHOLE_REJECT:
654 vty_out(vty, " (ICMP unreachable)");
655 break;
656 case BLACKHOLE_ADMINPROHIB:
657 vty_out(vty, " (ICMP admin-prohibited)");
658 break;
659 case BLACKHOLE_NULL:
660 vty_out(vty, " (blackhole)");
661 break;
662 case BLACKHOLE_UNSPEC:
663 break;
664 }
665 break;
666 default:
667 break;
668 }
669
670 if ((nexthop->vrf_id != re->vrf_id)
671 && (nexthop->type != NEXTHOP_TYPE_BLACKHOLE)) {
672 struct vrf *vrf = vrf_lookup_by_id(nexthop->vrf_id);
673
674 if (vrf)
675 vty_out(vty, "(vrf %s)", vrf->name);
676 else
677 vty_out(vty, "(vrf UKNOWN)");
678 }
679
680 if (!CHECK_FLAG(nexthop->flags, NEXTHOP_FLAG_ACTIVE))
681 vty_out(vty, " inactive");
682
683 if (CHECK_FLAG(nexthop->flags, NEXTHOP_FLAG_ONLINK))
684 vty_out(vty, " onlink");
685
686 if (CHECK_FLAG(nexthop->flags, NEXTHOP_FLAG_RECURSIVE))
687 vty_out(vty, " (recursive)");
688
689 switch (nexthop->type) {
690 case NEXTHOP_TYPE_IPV4:
691 case NEXTHOP_TYPE_IPV4_IFINDEX:
692 if (nexthop->src.ipv4.s_addr) {
693 if (inet_ntop(AF_INET, &nexthop->src.ipv4, buf,
694 sizeof buf))
695 vty_out(vty, ", src %s", buf);
696 }
697 break;
698 case NEXTHOP_TYPE_IPV6:
699 case NEXTHOP_TYPE_IPV6_IFINDEX:
700 if (!IPV6_ADDR_SAME(&nexthop->src.ipv6, &in6addr_any)) {
701 if (inet_ntop(AF_INET6, &nexthop->src.ipv6, buf,
702 sizeof buf))
703 vty_out(vty, ", src %s", buf);
704 }
705 break;
706 default:
707 break;
708 }
709
710 /* Label information */
711 if (nexthop->nh_label && nexthop->nh_label->num_labels) {
712 vty_out(vty, ", label %s",
713 mpls_label2str(nexthop->nh_label->num_labels,
714 nexthop->nh_label->label, buf,
715 sizeof buf, 1));
716 }
717
718 if (uptime < ONE_DAY_SECOND)
719 vty_out(vty, ", %02d:%02d:%02d", tm->tm_hour,
720 tm->tm_min, tm->tm_sec);
721 else if (uptime < ONE_WEEK_SECOND)
722 vty_out(vty, ", %dd%02dh%02dm", tm->tm_yday,
723 tm->tm_hour, tm->tm_min);
724 else
725 vty_out(vty, ", %02dw%dd%02dh", tm->tm_yday / 7,
726 tm->tm_yday - ((tm->tm_yday / 7) * 7),
727 tm->tm_hour);
728 vty_out(vty, "\n");
729 }
730 }
731
732 static void do_show_route_helper(struct vty *vty, struct zebra_vrf *zvrf,
733 struct route_table *table, afi_t afi,
734 bool use_fib, route_tag_t tag,
735 const struct prefix *longer_prefix_p,
736 bool supernets_only, int type,
737 unsigned short ospf_instance_id,
738 uint8_t use_json)
739 {
740 struct route_node *rn;
741 struct route_entry *re;
742 int first = 1;
743 rib_dest_t *dest;
744 json_object *json = NULL;
745 json_object *json_prefix = NULL;
746 uint32_t addr;
747 char buf[BUFSIZ];
748
749 if (use_json)
750 json = json_object_new_object();
751
752 /* Show all routes. */
753 for (rn = route_top(table); rn; rn = srcdest_route_next(rn)) {
754 dest = rib_dest_from_rnode(rn);
755
756 RNODE_FOREACH_RE (rn, re) {
757 if (use_fib && re != dest->selected_fib)
758 continue;
759
760 if (tag && re->tag != tag)
761 continue;
762
763 if (longer_prefix_p
764 && !prefix_match(longer_prefix_p, &rn->p))
765 continue;
766
767 /* This can only be true when the afi is IPv4 */
768 if (supernets_only) {
769 addr = ntohl(rn->p.u.prefix4.s_addr);
770
771 if (IN_CLASSC(addr) && rn->p.prefixlen >= 24)
772 continue;
773
774 if (IN_CLASSB(addr) && rn->p.prefixlen >= 16)
775 continue;
776
777 if (IN_CLASSA(addr) && rn->p.prefixlen >= 8)
778 continue;
779 }
780
781 if (type && re->type != type)
782 continue;
783
784 if (ospf_instance_id
785 && (re->type != ZEBRA_ROUTE_OSPF
786 || re->instance != ospf_instance_id))
787 continue;
788
789 if (use_json) {
790 if (!json_prefix)
791 json_prefix = json_object_new_array();
792 } else {
793 if (first) {
794 if (afi == AFI_IP)
795 vty_out(vty,
796 SHOW_ROUTE_V4_HEADER);
797 else
798 vty_out(vty,
799 SHOW_ROUTE_V6_HEADER);
800
801 if (zvrf_id(zvrf) != VRF_DEFAULT)
802 vty_out(vty, "\nVRF %s:\n",
803 zvrf_name(zvrf));
804
805 first = 0;
806 }
807 }
808
809 vty_show_ip_route(vty, rn, re, json_prefix);
810 }
811
812 if (json_prefix) {
813 prefix2str(&rn->p, buf, sizeof buf);
814 json_object_object_add(json, buf, json_prefix);
815 json_prefix = NULL;
816 }
817 }
818
819 if (use_json) {
820 vty_out(vty, "%s\n", json_object_to_json_string_ext(
821 json, JSON_C_TO_STRING_PRETTY));
822 json_object_free(json);
823 }
824 }
825
826 static int do_show_ip_route(struct vty *vty, const char *vrf_name, afi_t afi,
827 safi_t safi, bool use_fib, uint8_t use_json,
828 route_tag_t tag,
829 const struct prefix *longer_prefix_p,
830 bool supernets_only, int type,
831 unsigned short ospf_instance_id)
832 {
833 struct route_table *table;
834 struct zebra_vrf *zvrf = NULL;
835
836 if (!(zvrf = zebra_vrf_lookup_by_name(vrf_name))) {
837 if (use_json)
838 vty_out(vty, "{}\n");
839 else
840 vty_out(vty, "vrf %s not defined\n", vrf_name);
841 return CMD_SUCCESS;
842 }
843
844 if (zvrf_id(zvrf) == VRF_UNKNOWN) {
845 if (use_json)
846 vty_out(vty, "{}\n");
847 else
848 vty_out(vty, "vrf %s inactive\n", vrf_name);
849 return CMD_SUCCESS;
850 }
851
852 table = zebra_vrf_table(afi, safi, zvrf_id(zvrf));
853 if (!table) {
854 if (use_json)
855 vty_out(vty, "{}\n");
856 return CMD_SUCCESS;
857 }
858
859 do_show_route_helper(vty, zvrf, table, afi, use_fib, tag,
860 longer_prefix_p, supernets_only, type,
861 ospf_instance_id, use_json);
862
863 return CMD_SUCCESS;
864 }
865
866 DEFPY (show_route_table,
867 show_route_table_cmd,
868 "show <ip$ipv4|ipv6$ipv6> route table (1-4294967295)$table [json$json]",
869 SHOW_STR
870 IP_STR
871 IP6_STR
872 "IP routing table\n"
873 "Table to display\n"
874 "The table number to display, if available\n"
875 JSON_STR)
876 {
877 afi_t afi = ipv4 ? AFI_IP : AFI_IP6;
878 struct zebra_vrf *zvrf = zebra_vrf_lookup_by_id(VRF_DEFAULT);
879 struct route_table *t;
880
881 t = zebra_ns_find_table(zvrf->zns, table, afi);
882 if (t)
883 do_show_route_helper(vty, zvrf, t, afi, false, 0, false, false,
884 0, 0, !!json);
885
886 return CMD_SUCCESS;
887 }
888
889 DEFPY (show_route_table_vrf,
890 show_route_table_vrf_cmd,
891 "show <ip$ipv4|ipv6$ipv6> route table (1-4294967295)$table vrf NAME$vrf_name [json$json]",
892 SHOW_STR
893 IP_STR
894 IP6_STR
895 "IP routing table\n"
896 "Table to display\n"
897 "The table number to display, if available\n"
898 VRF_CMD_HELP_STR
899 JSON_STR)
900 {
901 afi_t afi = ipv4 ? AFI_IP : AFI_IP6;
902 struct zebra_vrf *zvrf;
903 struct route_table *t;
904 vrf_id_t vrf_id = VRF_DEFAULT;
905
906 if (vrf_name)
907 VRF_GET_ID(vrf_id, vrf_name, !!json);
908 zvrf = zebra_vrf_lookup_by_id(vrf_id);
909
910 t = zebra_ns_find_table(zvrf->zns, table, afi);
911 if (t)
912 do_show_route_helper(vty, zvrf, t, afi, false, 0, false, false,
913 0, 0, !!json);
914
915 return CMD_SUCCESS;
916 }
917
918 DEFUN (show_ip_nht,
919 show_ip_nht_cmd,
920 "show ip nht [vrf NAME]",
921 SHOW_STR
922 IP_STR
923 "IP nexthop tracking table\n"
924 VRF_CMD_HELP_STR)
925 {
926 int idx_vrf = 4;
927 vrf_id_t vrf_id = VRF_DEFAULT;
928
929 if (argc == 5)
930 VRF_GET_ID(vrf_id, argv[idx_vrf]->arg, false);
931
932 zebra_print_rnh_table(vrf_id, AF_INET, vty, RNH_NEXTHOP_TYPE);
933 return CMD_SUCCESS;
934 }
935
936
937 DEFUN (show_ip_nht_vrf_all,
938 show_ip_nht_vrf_all_cmd,
939 "show ip nht vrf all",
940 SHOW_STR
941 IP_STR
942 "IP nexthop tracking table\n"
943 VRF_ALL_CMD_HELP_STR)
944 {
945 struct vrf *vrf;
946 struct zebra_vrf *zvrf;
947
948 RB_FOREACH (vrf, vrf_name_head, &vrfs_by_name)
949 if ((zvrf = vrf->info) != NULL) {
950 vty_out(vty, "\nVRF %s:\n", zvrf_name(zvrf));
951 zebra_print_rnh_table(zvrf_id(zvrf), AF_INET, vty,
952 RNH_NEXTHOP_TYPE);
953 }
954
955 return CMD_SUCCESS;
956 }
957
958 DEFUN (show_ipv6_nht,
959 show_ipv6_nht_cmd,
960 "show ipv6 nht [vrf NAME]",
961 SHOW_STR
962 IPV6_STR
963 "IPv6 nexthop tracking table\n"
964 VRF_CMD_HELP_STR)
965 {
966 int idx_vrf = 4;
967 vrf_id_t vrf_id = VRF_DEFAULT;
968
969 if (argc == 5)
970 VRF_GET_ID(vrf_id, argv[idx_vrf]->arg, false);
971
972 zebra_print_rnh_table(vrf_id, AF_INET6, vty, RNH_NEXTHOP_TYPE);
973 return CMD_SUCCESS;
974 }
975
976
977 DEFUN (show_ipv6_nht_vrf_all,
978 show_ipv6_nht_vrf_all_cmd,
979 "show ipv6 nht vrf all",
980 SHOW_STR
981 IP_STR
982 "IPv6 nexthop tracking table\n"
983 VRF_ALL_CMD_HELP_STR)
984 {
985 struct vrf *vrf;
986 struct zebra_vrf *zvrf;
987
988 RB_FOREACH (vrf, vrf_name_head, &vrfs_by_name)
989 if ((zvrf = vrf->info) != NULL) {
990 vty_out(vty, "\nVRF %s:\n", zvrf_name(zvrf));
991 zebra_print_rnh_table(zvrf_id(zvrf), AF_INET6, vty,
992 RNH_NEXTHOP_TYPE);
993 }
994
995 return CMD_SUCCESS;
996 }
997
998 DEFUN (ip_nht_default_route,
999 ip_nht_default_route_cmd,
1000 "ip nht resolve-via-default",
1001 IP_STR
1002 "Filter Next Hop tracking route resolution\n"
1003 "Resolve via default route\n")
1004 {
1005 if (zebra_rnh_ip_default_route)
1006 return CMD_SUCCESS;
1007
1008 zebra_rnh_ip_default_route = 1;
1009 zebra_evaluate_rnh(VRF_DEFAULT, AF_INET, 1, RNH_NEXTHOP_TYPE, NULL);
1010 return CMD_SUCCESS;
1011 }
1012
1013 DEFUN (no_ip_nht_default_route,
1014 no_ip_nht_default_route_cmd,
1015 "no ip nht resolve-via-default",
1016 NO_STR
1017 IP_STR
1018 "Filter Next Hop tracking route resolution\n"
1019 "Resolve via default route\n")
1020 {
1021 if (!zebra_rnh_ip_default_route)
1022 return CMD_SUCCESS;
1023
1024 zebra_rnh_ip_default_route = 0;
1025 zebra_evaluate_rnh(VRF_DEFAULT, AF_INET, 1, RNH_NEXTHOP_TYPE, NULL);
1026 return CMD_SUCCESS;
1027 }
1028
1029 DEFUN (ipv6_nht_default_route,
1030 ipv6_nht_default_route_cmd,
1031 "ipv6 nht resolve-via-default",
1032 IP6_STR
1033 "Filter Next Hop tracking route resolution\n"
1034 "Resolve via default route\n")
1035 {
1036 if (zebra_rnh_ipv6_default_route)
1037 return CMD_SUCCESS;
1038
1039 zebra_rnh_ipv6_default_route = 1;
1040 zebra_evaluate_rnh(VRF_DEFAULT, AF_INET6, 1, RNH_NEXTHOP_TYPE, NULL);
1041 return CMD_SUCCESS;
1042 }
1043
1044 DEFUN (no_ipv6_nht_default_route,
1045 no_ipv6_nht_default_route_cmd,
1046 "no ipv6 nht resolve-via-default",
1047 NO_STR
1048 IP6_STR
1049 "Filter Next Hop tracking route resolution\n"
1050 "Resolve via default route\n")
1051 {
1052 if (!zebra_rnh_ipv6_default_route)
1053 return CMD_SUCCESS;
1054
1055 zebra_rnh_ipv6_default_route = 0;
1056 zebra_evaluate_rnh(VRF_DEFAULT, AF_INET6, 1, RNH_NEXTHOP_TYPE, NULL);
1057 return CMD_SUCCESS;
1058 }
1059
1060 DEFPY (show_route,
1061 show_route_cmd,
1062 "show\
1063 <\
1064 ip$ipv4 <fib$fib|route> [vrf <NAME$vrf_name|all$vrf_all>]\
1065 [{\
1066 tag (1-4294967295)\
1067 |A.B.C.D/M$prefix longer-prefixes\
1068 |supernets-only$supernets_only\
1069 }]\
1070 [<\
1071 " FRR_IP_REDIST_STR_ZEBRA "$type_str\
1072 |ospf$type_str (1-65535)$ospf_instance_id\
1073 >]\
1074 |ipv6$ipv6 <fib$fib|route> [vrf <NAME$vrf_name|all$vrf_all>]\
1075 [{\
1076 tag (1-4294967295)\
1077 |X:X::X:X/M$prefix longer-prefixes\
1078 }]\
1079 [" FRR_IP6_REDIST_STR_ZEBRA "$type_str]\
1080 >\
1081 [json$json]",
1082 SHOW_STR
1083 IP_STR
1084 "IP forwarding table\n"
1085 "IP routing table\n"
1086 VRF_FULL_CMD_HELP_STR
1087 "Show only routes with tag\n"
1088 "Tag value\n"
1089 "IP prefix <network>/<length>, e.g., 35.0.0.0/8\n"
1090 "Show route matching the specified Network/Mask pair only\n"
1091 "Show supernet entries only\n"
1092 FRR_IP_REDIST_HELP_STR_ZEBRA
1093 "Open Shortest Path First (OSPFv2)\n"
1094 "Instance ID\n"
1095 IPV6_STR
1096 "IP forwarding table\n"
1097 "IP routing table\n"
1098 VRF_FULL_CMD_HELP_STR
1099 "Show only routes with tag\n"
1100 "Tag value\n"
1101 "IPv6 prefix\n"
1102 "Show route matching the specified Network/Mask pair only\n"
1103 FRR_IP6_REDIST_HELP_STR_ZEBRA
1104 JSON_STR)
1105 {
1106 afi_t afi = ipv4 ? AFI_IP : AFI_IP6;
1107 struct vrf *vrf;
1108 int type = 0;
1109
1110 if (type_str) {
1111 type = proto_redistnum(afi, type_str);
1112 if (type < 0) {
1113 vty_out(vty, "Unknown route type\n");
1114 return CMD_WARNING;
1115 }
1116 }
1117
1118 if (vrf_all) {
1119 RB_FOREACH (vrf, vrf_name_head, &vrfs_by_name) {
1120 struct zebra_vrf *zvrf;
1121 struct route_table *table;
1122
1123 if ((zvrf = vrf->info) == NULL
1124 || (table = zvrf->table[afi][SAFI_UNICAST]) == NULL)
1125 continue;
1126
1127 do_show_ip_route(
1128 vty, zvrf_name(zvrf), afi, SAFI_UNICAST, !!fib,
1129 !!json, tag, prefix_str ? prefix : NULL,
1130 !!supernets_only, type, ospf_instance_id);
1131 }
1132 } else {
1133 vrf_id_t vrf_id = VRF_DEFAULT;
1134
1135 if (vrf_name)
1136 VRF_GET_ID(vrf_id, vrf_name, !!json);
1137 vrf = vrf_lookup_by_id(vrf_id);
1138 do_show_ip_route(vty, vrf->name, afi, SAFI_UNICAST, !!fib,
1139 !!json, tag, prefix_str ? prefix : NULL,
1140 !!supernets_only, type, ospf_instance_id);
1141 }
1142
1143 return CMD_SUCCESS;
1144 }
1145
1146 DEFPY (show_route_detail,
1147 show_route_detail_cmd,
1148 "show\
1149 <\
1150 ip$ipv4 route [vrf <NAME$vrf_name|all$vrf_all>]\
1151 <\
1152 A.B.C.D$address\
1153 |A.B.C.D/M$prefix\
1154 >\
1155 |ipv6$ipv6 route [vrf <NAME$vrf_name|all$vrf_all>]\
1156 <\
1157 X:X::X:X$address\
1158 |X:X::X:X/M$prefix\
1159 >\
1160 >",
1161 SHOW_STR
1162 IP_STR
1163 "IP routing table\n"
1164 VRF_FULL_CMD_HELP_STR
1165 "Network in the IP routing table to display\n"
1166 "IP prefix <network>/<length>, e.g., 35.0.0.0/8\n"
1167 IP6_STR
1168 "IP routing table\n"
1169 VRF_FULL_CMD_HELP_STR
1170 "IPv6 Address\n"
1171 "IPv6 prefix\n")
1172 {
1173 afi_t afi = ipv4 ? AFI_IP : AFI_IP6;
1174 struct route_table *table;
1175 struct prefix p;
1176 struct route_node *rn;
1177
1178 if (address_str)
1179 prefix_str = address_str;
1180 if (str2prefix(prefix_str, &p) < 0) {
1181 vty_out(vty, "%% Malformed address\n");
1182 return CMD_WARNING;
1183 }
1184
1185 if (vrf_all) {
1186 struct vrf *vrf;
1187 struct zebra_vrf *zvrf;
1188
1189 RB_FOREACH (vrf, vrf_name_head, &vrfs_by_name) {
1190 if ((zvrf = vrf->info) == NULL
1191 || (table = zvrf->table[afi][SAFI_UNICAST]) == NULL)
1192 continue;
1193
1194 rn = route_node_match(table, &p);
1195 if (!rn)
1196 continue;
1197 if (!address_str && rn->p.prefixlen != p.prefixlen) {
1198 route_unlock_node(rn);
1199 continue;
1200 }
1201
1202 vty_show_ip_route_detail(vty, rn, 0);
1203
1204 route_unlock_node(rn);
1205 }
1206 } else {
1207 vrf_id_t vrf_id = VRF_DEFAULT;
1208
1209 if (vrf_name)
1210 VRF_GET_ID(vrf_id, vrf_name, false);
1211
1212 table = zebra_vrf_table(afi, SAFI_UNICAST, vrf_id);
1213 if (!table)
1214 return CMD_SUCCESS;
1215
1216 rn = route_node_match(table, &p);
1217 if (!rn) {
1218 vty_out(vty, "%% Network not in table\n");
1219 return CMD_WARNING;
1220 }
1221 if (!address_str && rn->p.prefixlen != p.prefixlen) {
1222 vty_out(vty, "%% Network not in table\n");
1223 route_unlock_node(rn);
1224 return CMD_WARNING;
1225 }
1226
1227 vty_show_ip_route_detail(vty, rn, 0);
1228
1229 route_unlock_node(rn);
1230 }
1231
1232 return CMD_SUCCESS;
1233 }
1234
1235 DEFPY (show_route_summary,
1236 show_route_summary_cmd,
1237 "show\
1238 <\
1239 ip$ipv4 route [vrf <NAME$vrf_name|all$vrf_all>]\
1240 summary [prefix$prefix]\
1241 |ipv6$ipv6 route [vrf <NAME$vrf_name|all$vrf_all>]\
1242 summary [prefix$prefix]\
1243 >",
1244 SHOW_STR
1245 IP_STR
1246 "IP routing table\n"
1247 VRF_FULL_CMD_HELP_STR
1248 "Summary of all routes\n"
1249 "Prefix routes\n"
1250 IP6_STR
1251 "IP routing table\n"
1252 VRF_FULL_CMD_HELP_STR
1253 "Summary of all routes\n"
1254 "Prefix routes\n")
1255 {
1256 afi_t afi = ipv4 ? AFI_IP : AFI_IP6;
1257 struct route_table *table;
1258
1259 if (vrf_all) {
1260 struct vrf *vrf;
1261 struct zebra_vrf *zvrf;
1262
1263 RB_FOREACH (vrf, vrf_name_head, &vrfs_by_name) {
1264 if ((zvrf = vrf->info) == NULL
1265 || (table = zvrf->table[afi][SAFI_UNICAST]) == NULL)
1266 continue;
1267
1268 if (prefix)
1269 vty_show_ip_route_summary_prefix(vty, table);
1270 else
1271 vty_show_ip_route_summary(vty, table);
1272 }
1273 } else {
1274 vrf_id_t vrf_id = VRF_DEFAULT;
1275
1276 if (vrf_name)
1277 VRF_GET_ID(vrf_id, vrf_name, false);
1278
1279 table = zebra_vrf_table(afi, SAFI_UNICAST, vrf_id);
1280 if (!table)
1281 return CMD_SUCCESS;
1282
1283 if (prefix)
1284 vty_show_ip_route_summary_prefix(vty, table);
1285 else
1286 vty_show_ip_route_summary(vty, table);
1287 }
1288
1289 return CMD_SUCCESS;
1290 }
1291
1292 static void vty_show_ip_route_summary(struct vty *vty,
1293 struct route_table *table)
1294 {
1295 struct route_node *rn;
1296 struct route_entry *re;
1297 #define ZEBRA_ROUTE_IBGP ZEBRA_ROUTE_MAX
1298 #define ZEBRA_ROUTE_TOTAL (ZEBRA_ROUTE_IBGP + 1)
1299 uint32_t rib_cnt[ZEBRA_ROUTE_TOTAL + 1];
1300 uint32_t fib_cnt[ZEBRA_ROUTE_TOTAL + 1];
1301 uint32_t i;
1302 uint32_t is_ibgp;
1303
1304 memset(&rib_cnt, 0, sizeof(rib_cnt));
1305 memset(&fib_cnt, 0, sizeof(fib_cnt));
1306 for (rn = route_top(table); rn; rn = srcdest_route_next(rn))
1307 RNODE_FOREACH_RE (rn, re) {
1308 is_ibgp = (re->type == ZEBRA_ROUTE_BGP
1309 && CHECK_FLAG(re->flags, ZEBRA_FLAG_IBGP));
1310
1311 rib_cnt[ZEBRA_ROUTE_TOTAL]++;
1312 if (is_ibgp)
1313 rib_cnt[ZEBRA_ROUTE_IBGP]++;
1314 else
1315 rib_cnt[re->type]++;
1316
1317 if (CHECK_FLAG(re->flags, ZEBRA_FLAG_SELECTED)) {
1318 fib_cnt[ZEBRA_ROUTE_TOTAL]++;
1319
1320 if (is_ibgp)
1321 fib_cnt[ZEBRA_ROUTE_IBGP]++;
1322 else
1323 fib_cnt[re->type]++;
1324 }
1325 }
1326
1327 vty_out(vty, "%-20s %-20s %s (vrf %s)\n", "Route Source", "Routes",
1328 "FIB", zvrf_name(((rib_table_info_t *)table->info)->zvrf));
1329
1330 for (i = 0; i < ZEBRA_ROUTE_MAX; i++) {
1331 if ((rib_cnt[i] > 0) || (i == ZEBRA_ROUTE_BGP
1332 && rib_cnt[ZEBRA_ROUTE_IBGP] > 0)) {
1333 if (i == ZEBRA_ROUTE_BGP) {
1334 vty_out(vty, "%-20s %-20d %-20d \n", "ebgp",
1335 rib_cnt[ZEBRA_ROUTE_BGP],
1336 fib_cnt[ZEBRA_ROUTE_BGP]);
1337 vty_out(vty, "%-20s %-20d %-20d \n", "ibgp",
1338 rib_cnt[ZEBRA_ROUTE_IBGP],
1339 fib_cnt[ZEBRA_ROUTE_IBGP]);
1340 } else
1341 vty_out(vty, "%-20s %-20d %-20d \n",
1342 zebra_route_string(i), rib_cnt[i],
1343 fib_cnt[i]);
1344 }
1345 }
1346
1347 vty_out(vty, "------\n");
1348 vty_out(vty, "%-20s %-20d %-20d \n", "Totals",
1349 rib_cnt[ZEBRA_ROUTE_TOTAL], fib_cnt[ZEBRA_ROUTE_TOTAL]);
1350 vty_out(vty, "\n");
1351 }
1352
1353 /*
1354 * Implementation of the ip route summary prefix command.
1355 *
1356 * This command prints the primary prefixes that have been installed by various
1357 * protocols on the box.
1358 *
1359 */
1360 static void vty_show_ip_route_summary_prefix(struct vty *vty,
1361 struct route_table *table)
1362 {
1363 struct route_node *rn;
1364 struct route_entry *re;
1365 struct nexthop *nexthop;
1366 #define ZEBRA_ROUTE_IBGP ZEBRA_ROUTE_MAX
1367 #define ZEBRA_ROUTE_TOTAL (ZEBRA_ROUTE_IBGP + 1)
1368 uint32_t rib_cnt[ZEBRA_ROUTE_TOTAL + 1];
1369 uint32_t fib_cnt[ZEBRA_ROUTE_TOTAL + 1];
1370 uint32_t i;
1371 int cnt;
1372
1373 memset(&rib_cnt, 0, sizeof(rib_cnt));
1374 memset(&fib_cnt, 0, sizeof(fib_cnt));
1375 for (rn = route_top(table); rn; rn = srcdest_route_next(rn))
1376 RNODE_FOREACH_RE (rn, re) {
1377
1378 /*
1379 * In case of ECMP, count only once.
1380 */
1381 cnt = 0;
1382 for (nexthop = re->ng.nexthop; (!cnt && nexthop);
1383 nexthop = nexthop->next) {
1384 cnt++;
1385 rib_cnt[ZEBRA_ROUTE_TOTAL]++;
1386 rib_cnt[re->type]++;
1387 if (CHECK_FLAG(nexthop->flags,
1388 NEXTHOP_FLAG_FIB)) {
1389 fib_cnt[ZEBRA_ROUTE_TOTAL]++;
1390 fib_cnt[re->type]++;
1391 }
1392 if (re->type == ZEBRA_ROUTE_BGP
1393 && CHECK_FLAG(re->flags, ZEBRA_FLAG_IBGP)) {
1394 rib_cnt[ZEBRA_ROUTE_IBGP]++;
1395 if (CHECK_FLAG(nexthop->flags,
1396 NEXTHOP_FLAG_FIB))
1397 fib_cnt[ZEBRA_ROUTE_IBGP]++;
1398 }
1399 }
1400 }
1401
1402 vty_out(vty, "%-20s %-20s %s (vrf %s)\n", "Route Source",
1403 "Prefix Routes", "FIB",
1404 zvrf_name(((rib_table_info_t *)table->info)->zvrf));
1405
1406 for (i = 0; i < ZEBRA_ROUTE_MAX; i++) {
1407 if (rib_cnt[i] > 0) {
1408 if (i == ZEBRA_ROUTE_BGP) {
1409 vty_out(vty, "%-20s %-20d %-20d \n", "ebgp",
1410 rib_cnt[ZEBRA_ROUTE_BGP]
1411 - rib_cnt[ZEBRA_ROUTE_IBGP],
1412 fib_cnt[ZEBRA_ROUTE_BGP]
1413 - fib_cnt[ZEBRA_ROUTE_IBGP]);
1414 vty_out(vty, "%-20s %-20d %-20d \n", "ibgp",
1415 rib_cnt[ZEBRA_ROUTE_IBGP],
1416 fib_cnt[ZEBRA_ROUTE_IBGP]);
1417 } else
1418 vty_out(vty, "%-20s %-20d %-20d \n",
1419 zebra_route_string(i), rib_cnt[i],
1420 fib_cnt[i]);
1421 }
1422 }
1423
1424 vty_out(vty, "------\n");
1425 vty_out(vty, "%-20s %-20d %-20d \n", "Totals",
1426 rib_cnt[ZEBRA_ROUTE_TOTAL], fib_cnt[ZEBRA_ROUTE_TOTAL]);
1427 vty_out(vty, "\n");
1428 }
1429
1430 /*
1431 * Show IPv6 mroute command.Used to dump
1432 * the Multicast routing table.
1433 */
1434 DEFUN (show_ipv6_mroute,
1435 show_ipv6_mroute_cmd,
1436 "show ipv6 mroute [vrf NAME]",
1437 SHOW_STR
1438 IP_STR
1439 "IPv6 Multicast routing table\n"
1440 VRF_CMD_HELP_STR)
1441 {
1442 struct route_table *table;
1443 struct route_node *rn;
1444 struct route_entry *re;
1445 int first = 1;
1446 vrf_id_t vrf_id = VRF_DEFAULT;
1447
1448 if (argc == 5)
1449 VRF_GET_ID(vrf_id, argv[4]->arg, false);
1450
1451 table = zebra_vrf_table(AFI_IP6, SAFI_MULTICAST, vrf_id);
1452 if (!table)
1453 return CMD_SUCCESS;
1454
1455 /* Show all IPv6 route. */
1456 for (rn = route_top(table); rn; rn = srcdest_route_next(rn))
1457 RNODE_FOREACH_RE (rn, re) {
1458 if (first) {
1459 vty_out(vty, SHOW_ROUTE_V6_HEADER);
1460 first = 0;
1461 }
1462 vty_show_ip_route(vty, rn, re, NULL);
1463 }
1464 return CMD_SUCCESS;
1465 }
1466
1467 DEFUN (show_ipv6_mroute_vrf_all,
1468 show_ipv6_mroute_vrf_all_cmd,
1469 "show ipv6 mroute vrf all",
1470 SHOW_STR
1471 IP_STR
1472 "IPv6 Multicast routing table\n"
1473 VRF_ALL_CMD_HELP_STR)
1474 {
1475 struct route_table *table;
1476 struct route_node *rn;
1477 struct route_entry *re;
1478 struct vrf *vrf;
1479 struct zebra_vrf *zvrf;
1480 int first = 1;
1481
1482 RB_FOREACH (vrf, vrf_name_head, &vrfs_by_name) {
1483 if ((zvrf = vrf->info) == NULL
1484 || (table = zvrf->table[AFI_IP6][SAFI_MULTICAST]) == NULL)
1485 continue;
1486
1487 /* Show all IPv6 route. */
1488 for (rn = route_top(table); rn; rn = srcdest_route_next(rn))
1489 RNODE_FOREACH_RE (rn, re) {
1490 if (first) {
1491 vty_out(vty, SHOW_ROUTE_V6_HEADER);
1492 first = 0;
1493 }
1494 vty_show_ip_route(vty, rn, re, NULL);
1495 }
1496 }
1497 return CMD_SUCCESS;
1498 }
1499
1500 DEFUN (allow_external_route_update,
1501 allow_external_route_update_cmd,
1502 "allow-external-route-update",
1503 "Allow FRR routes to be overwritten by external processes\n")
1504 {
1505 allow_delete = 1;
1506
1507 return CMD_SUCCESS;
1508 }
1509
1510 DEFUN (no_allow_external_route_update,
1511 no_allow_external_route_update_cmd,
1512 "no allow-external-route-update",
1513 NO_STR
1514 "Allow FRR routes to be overwritten by external processes\n")
1515 {
1516 allow_delete = 0;
1517
1518 return CMD_SUCCESS;
1519 }
1520
1521 /* show vrf */
1522 DEFUN (show_vrf,
1523 show_vrf_cmd,
1524 "show vrf",
1525 SHOW_STR
1526 "VRF\n")
1527 {
1528 struct vrf *vrf;
1529 struct zebra_vrf *zvrf;
1530
1531 if (vrf_is_backend_netns())
1532 vty_out(vty, "netns-based vrfs\n");
1533
1534 RB_FOREACH (vrf, vrf_name_head, &vrfs_by_name) {
1535 if (!(zvrf = vrf->info))
1536 continue;
1537 if (zvrf_id(zvrf) == VRF_DEFAULT)
1538 continue;
1539
1540 vty_out(vty, "vrf %s ", zvrf_name(zvrf));
1541 if (zvrf_id(zvrf) == VRF_UNKNOWN || !zvrf_is_active(zvrf))
1542 vty_out(vty, "inactive");
1543 else if (zvrf_ns_name(zvrf))
1544 vty_out(vty, "id %u netns %s", zvrf_id(zvrf),
1545 zvrf_ns_name(zvrf));
1546 else
1547 vty_out(vty, "id %u table %u", zvrf_id(zvrf),
1548 zvrf->table_id);
1549 if (vrf_is_user_cfged(vrf))
1550 vty_out(vty, " (configured)");
1551 vty_out(vty, "\n");
1552 }
1553
1554 return CMD_SUCCESS;
1555 }
1556
1557 DEFUN_HIDDEN (default_vrf_vni_mapping,
1558 default_vrf_vni_mapping_cmd,
1559 "vni " CMD_VNI_RANGE "[prefix-routes-only]",
1560 "VNI corresponding to the DEFAULT VRF\n"
1561 "VNI-ID\n"
1562 "Prefix routes only \n")
1563 {
1564 int ret = 0;
1565 char err[ERR_STR_SZ];
1566 struct zebra_vrf *zvrf = NULL;
1567 vni_t vni = strtoul(argv[1]->arg, NULL, 10);
1568 int filter = 0;
1569
1570 zvrf = vrf_info_lookup(VRF_DEFAULT);
1571 if (!zvrf)
1572 return CMD_WARNING;
1573
1574 if (argc == 3)
1575 filter = 1;
1576
1577 ret = zebra_vxlan_process_vrf_vni_cmd(zvrf, vni, err, ERR_STR_SZ,
1578 filter, 1);
1579 if (ret != 0) {
1580 vty_out(vty, "%s\n", err);
1581 return CMD_WARNING;
1582 }
1583
1584 return CMD_SUCCESS;
1585 }
1586
1587 DEFUN_HIDDEN (no_default_vrf_vni_mapping,
1588 no_default_vrf_vni_mapping_cmd,
1589 "no vni " CMD_VNI_RANGE,
1590 NO_STR
1591 "VNI corresponding to DEFAULT VRF\n"
1592 "VNI-ID")
1593 {
1594 int ret = 0;
1595 char err[ERR_STR_SZ];
1596 vni_t vni = strtoul(argv[2]->arg, NULL, 10);
1597 struct zebra_vrf *zvrf = NULL;
1598
1599 zvrf = vrf_info_lookup(VRF_DEFAULT);
1600 if (!zvrf)
1601 return CMD_WARNING;
1602
1603 ret = zebra_vxlan_process_vrf_vni_cmd(zvrf, vni, err, ERR_STR_SZ, 0, 0);
1604 if (ret != 0) {
1605 vty_out(vty, "%s\n", err);
1606 return CMD_WARNING;
1607 }
1608
1609 return CMD_SUCCESS;
1610 }
1611
1612 DEFUN (vrf_vni_mapping,
1613 vrf_vni_mapping_cmd,
1614 "vni " CMD_VNI_RANGE "[prefix-routes-only]",
1615 "VNI corresponding to tenant VRF\n"
1616 "VNI-ID\n"
1617 "prefix-routes-only\n")
1618 {
1619 int ret = 0;
1620 int filter = 0;
1621
1622 ZEBRA_DECLVAR_CONTEXT(vrf, zvrf);
1623 vni_t vni = strtoul(argv[1]->arg, NULL, 10);
1624 char err[ERR_STR_SZ];
1625
1626 assert(vrf);
1627 assert(zvrf);
1628
1629 if (argc == 3)
1630 filter = 1;
1631
1632 /* Mark as having FRR configuration */
1633 vrf_set_user_cfged(vrf);
1634 ret = zebra_vxlan_process_vrf_vni_cmd(zvrf, vni, err, ERR_STR_SZ,
1635 filter, 1);
1636 if (ret != 0) {
1637 vty_out(vty, "%s\n", err);
1638 return CMD_WARNING;
1639 }
1640
1641 return CMD_SUCCESS;
1642 }
1643
1644 DEFUN (no_vrf_vni_mapping,
1645 no_vrf_vni_mapping_cmd,
1646 "no vni " CMD_VNI_RANGE "[prefix-routes-only]",
1647 NO_STR
1648 "VNI corresponding to tenant VRF\n"
1649 "VNI-ID\n"
1650 "prefix-routes-only\n")
1651 {
1652 int ret = 0;
1653 int filter = 0;
1654 char err[ERR_STR_SZ];
1655 vni_t vni = strtoul(argv[2]->arg, NULL, 10);
1656
1657 ZEBRA_DECLVAR_CONTEXT(vrf, zvrf);
1658
1659 assert(vrf);
1660 assert(zvrf);
1661
1662 if (argc == 4)
1663 filter = 1;
1664
1665 ret = zebra_vxlan_process_vrf_vni_cmd(zvrf, vni, err,
1666 ERR_STR_SZ, filter, 0);
1667 if (ret != 0) {
1668 vty_out(vty, "%s\n", err);
1669 return CMD_WARNING;
1670 }
1671
1672 /* If no other FRR config for this VRF, mark accordingly. */
1673 if (!zebra_vrf_has_config(zvrf))
1674 vrf_reset_user_cfged(vrf);
1675
1676 return CMD_SUCCESS;
1677 }
1678
1679 /* show vrf */
1680 DEFUN (show_vrf_vni,
1681 show_vrf_vni_cmd,
1682 "show vrf vni [json]",
1683 SHOW_STR
1684 "VRF\n"
1685 "VNI\n"
1686 JSON_STR)
1687 {
1688 struct vrf *vrf;
1689 struct zebra_vrf *zvrf;
1690 json_object *json = NULL;
1691 json_object *json_vrfs = NULL;
1692 uint8_t uj = use_json(argc, argv);
1693
1694 if (uj) {
1695 json = json_object_new_object();
1696 json_vrfs = json_object_new_array();
1697 }
1698
1699 if (!uj)
1700 vty_out(vty, "%-37s %-10s %-20s %-20s %-5s %-18s\n", "VRF",
1701 "VNI", "VxLAN IF", "L3-SVI", "State", "Rmac");
1702
1703 RB_FOREACH (vrf, vrf_name_head, &vrfs_by_name) {
1704 zvrf = vrf->info;
1705 if (!zvrf)
1706 continue;
1707
1708 zebra_vxlan_print_vrf_vni(vty, zvrf, json_vrfs);
1709 }
1710
1711 if (uj) {
1712 json_object_object_add(json, "vrfs", json_vrfs);
1713 vty_out(vty, "%s\n", json_object_to_json_string_ext(
1714 json, JSON_C_TO_STRING_PRETTY));
1715 json_object_free(json);
1716 }
1717
1718 return CMD_SUCCESS;
1719 }
1720
1721 DEFUN (show_evpn_global,
1722 show_evpn_global_cmd,
1723 "show evpn [json]",
1724 SHOW_STR
1725 "EVPN\n"
1726 JSON_STR)
1727 {
1728 uint8_t uj = use_json(argc, argv);
1729
1730 zebra_vxlan_print_evpn(vty, uj);
1731 return CMD_SUCCESS;
1732 }
1733
1734 DEFUN (show_evpn_vni,
1735 show_evpn_vni_cmd,
1736 "show evpn vni [json]",
1737 SHOW_STR
1738 "EVPN\n"
1739 "VxLAN information\n"
1740 JSON_STR)
1741 {
1742 struct zebra_vrf *zvrf;
1743 uint8_t uj = use_json(argc, argv);
1744
1745 zvrf = vrf_info_lookup(VRF_DEFAULT);
1746 zebra_vxlan_print_vnis(vty, zvrf, uj);
1747 return CMD_SUCCESS;
1748 }
1749
1750 DEFUN (show_evpn_vni_vni,
1751 show_evpn_vni_vni_cmd,
1752 "show evpn vni " CMD_VNI_RANGE "[json]",
1753 SHOW_STR
1754 "EVPN\n"
1755 "VxLAN Network Identifier\n"
1756 "VNI number\n"
1757 JSON_STR)
1758 {
1759 struct zebra_vrf *zvrf;
1760 vni_t vni;
1761 uint8_t uj = use_json(argc, argv);
1762
1763 vni = strtoul(argv[3]->arg, NULL, 10);
1764 zvrf = vrf_info_lookup(VRF_DEFAULT);
1765 zebra_vxlan_print_vni(vty, zvrf, vni, uj);
1766 return CMD_SUCCESS;
1767 }
1768
1769 DEFUN (show_evpn_rmac_vni_mac,
1770 show_evpn_rmac_vni_mac_cmd,
1771 "show evpn rmac vni " CMD_VNI_RANGE " mac WORD [json]",
1772 SHOW_STR
1773 "EVPN\n"
1774 "RMAC\n"
1775 "L3 VNI\n"
1776 "VNI number\n"
1777 "MAC\n"
1778 "mac-address (e.g. 0a:0a:0a:0a:0a:0a)\n"
1779 JSON_STR)
1780 {
1781 vni_t l3vni = 0;
1782 struct ethaddr mac;
1783 uint8_t uj = use_json(argc, argv);
1784
1785 l3vni = strtoul(argv[4]->arg, NULL, 10);
1786 if (!prefix_str2mac(argv[6]->arg, &mac)) {
1787 vty_out(vty, "%% Malformed MAC address\n");
1788 return CMD_WARNING;
1789 }
1790 zebra_vxlan_print_specific_rmac_l3vni(vty, l3vni, &mac, uj);
1791 return CMD_SUCCESS;
1792 }
1793
1794 DEFUN (show_evpn_rmac_vni,
1795 show_evpn_rmac_vni_cmd,
1796 "show evpn rmac vni " CMD_VNI_RANGE "[json]",
1797 SHOW_STR
1798 "EVPN\n"
1799 "RMAC\n"
1800 "L3 VNI\n"
1801 "VNI number\n"
1802 JSON_STR)
1803 {
1804 vni_t l3vni = 0;
1805 uint8_t uj = use_json(argc, argv);
1806
1807 l3vni = strtoul(argv[4]->arg, NULL, 10);
1808 zebra_vxlan_print_rmacs_l3vni(vty, l3vni, uj);
1809
1810 return CMD_SUCCESS;
1811 }
1812
1813 DEFUN (show_evpn_rmac_vni_all,
1814 show_evpn_rmac_vni_all_cmd,
1815 "show evpn rmac vni all [json]",
1816 SHOW_STR
1817 "EVPN\n"
1818 "RMAC addresses\n"
1819 "L3 VNI\n"
1820 "All VNIs\n"
1821 JSON_STR)
1822 {
1823 uint8_t uj = use_json(argc, argv);
1824
1825 zebra_vxlan_print_rmacs_all_l3vni(vty, uj);
1826
1827 return CMD_SUCCESS;
1828 }
1829
1830 DEFUN (show_evpn_nh_vni_ip,
1831 show_evpn_nh_vni_ip_cmd,
1832 "show evpn next-hops vni " CMD_VNI_RANGE " ip WORD [json]",
1833 SHOW_STR
1834 "EVPN\n"
1835 "Remote Vteps\n"
1836 "L3 VNI\n"
1837 "VNI number\n"
1838 "Ip address\n"
1839 "Host address (ipv4 or ipv6)\n"
1840 JSON_STR)
1841 {
1842 vni_t l3vni;
1843 struct ipaddr ip;
1844 uint8_t uj = use_json(argc, argv);
1845
1846 l3vni = strtoul(argv[4]->arg, NULL, 10);
1847 if (str2ipaddr(argv[6]->arg, &ip) != 0) {
1848 if (!uj)
1849 vty_out(vty, "%% Malformed Neighbor address\n");
1850 return CMD_WARNING;
1851 }
1852 zebra_vxlan_print_specific_nh_l3vni(vty, l3vni, &ip, uj);
1853
1854 return CMD_SUCCESS;
1855 }
1856
1857 DEFUN (show_evpn_nh_vni,
1858 show_evpn_nh_vni_cmd,
1859 "show evpn next-hops vni " CMD_VNI_RANGE "[json]",
1860 SHOW_STR
1861 "EVPN\n"
1862 "Remote Vteps\n"
1863 "L3 VNI\n"
1864 "VNI number\n"
1865 JSON_STR)
1866 {
1867 vni_t l3vni;
1868 uint8_t uj = use_json(argc, argv);
1869
1870 l3vni = strtoul(argv[4]->arg, NULL, 10);
1871 zebra_vxlan_print_nh_l3vni(vty, l3vni, uj);
1872
1873 return CMD_SUCCESS;
1874 }
1875
1876 DEFUN (show_evpn_nh_vni_all,
1877 show_evpn_nh_vni_all_cmd,
1878 "show evpn next-hops vni all [json]",
1879 SHOW_STR
1880 "EVPN\n"
1881 "Remote VTEPs\n"
1882 "L3 VNI\n"
1883 "All VNIs\n"
1884 JSON_STR)
1885 {
1886 uint8_t uj = use_json(argc, argv);
1887
1888 zebra_vxlan_print_nh_all_l3vni(vty, uj);
1889
1890 return CMD_SUCCESS;
1891 }
1892
1893 DEFUN (show_evpn_mac_vni,
1894 show_evpn_mac_vni_cmd,
1895 "show evpn mac vni " CMD_VNI_RANGE "[json]",
1896 SHOW_STR
1897 "EVPN\n"
1898 "MAC addresses\n"
1899 "VxLAN Network Identifier\n"
1900 "VNI number\n"
1901 JSON_STR)
1902 {
1903 struct zebra_vrf *zvrf;
1904 vni_t vni;
1905 uint8_t uj = use_json(argc, argv);
1906
1907 vni = strtoul(argv[4]->arg, NULL, 10);
1908 zvrf = vrf_info_lookup(VRF_DEFAULT);
1909 zebra_vxlan_print_macs_vni(vty, zvrf, vni, uj);
1910 return CMD_SUCCESS;
1911 }
1912
1913 DEFUN (show_evpn_mac_vni_all,
1914 show_evpn_mac_vni_all_cmd,
1915 "show evpn mac vni all [json]",
1916 SHOW_STR
1917 "EVPN\n"
1918 "MAC addresses\n"
1919 "VxLAN Network Identifier\n"
1920 "All VNIs\n"
1921 JSON_STR)
1922 {
1923 struct zebra_vrf *zvrf;
1924 uint8_t uj = use_json(argc, argv);
1925
1926 zvrf = vrf_info_lookup(VRF_DEFAULT);
1927 zebra_vxlan_print_macs_all_vni(vty, zvrf, uj);
1928 return CMD_SUCCESS;
1929 }
1930
1931 DEFUN (show_evpn_mac_vni_all_vtep,
1932 show_evpn_mac_vni_all_vtep_cmd,
1933 "show evpn mac vni all vtep A.B.C.D [json]",
1934 SHOW_STR
1935 "EVPN\n"
1936 "MAC addresses\n"
1937 "VxLAN Network Identifier\n"
1938 "All VNIs\n"
1939 "Remote VTEP\n"
1940 "Remote VTEP IP address\n"
1941 JSON_STR)
1942 {
1943 struct zebra_vrf *zvrf;
1944 struct in_addr vtep_ip;
1945 uint8_t uj = use_json(argc, argv);
1946
1947 if (!inet_aton(argv[6]->arg, &vtep_ip)) {
1948 if (!uj)
1949 vty_out(vty, "%% Malformed VTEP IP address\n");
1950 return CMD_WARNING;
1951 }
1952 zvrf = vrf_info_lookup(VRF_DEFAULT);
1953 zebra_vxlan_print_macs_all_vni_vtep(vty, zvrf, vtep_ip, uj);
1954
1955 return CMD_SUCCESS;
1956 }
1957
1958
1959 DEFUN (show_evpn_mac_vni_mac,
1960 show_evpn_mac_vni_mac_cmd,
1961 "show evpn mac vni " CMD_VNI_RANGE " mac WORD",
1962 SHOW_STR
1963 "EVPN\n"
1964 "MAC addresses\n"
1965 "VxLAN Network Identifier\n"
1966 "VNI number\n"
1967 "MAC\n"
1968 "MAC address (e.g., 00:e0:ec:20:12:62)\n")
1969 {
1970 struct zebra_vrf *zvrf;
1971 vni_t vni;
1972 struct ethaddr mac;
1973
1974 vni = strtoul(argv[4]->arg, NULL, 10);
1975 if (!prefix_str2mac(argv[6]->arg, &mac)) {
1976 vty_out(vty, "%% Malformed MAC address");
1977 return CMD_WARNING;
1978 }
1979 zvrf = vrf_info_lookup(VRF_DEFAULT);
1980 zebra_vxlan_print_specific_mac_vni(vty, zvrf, vni, &mac);
1981 return CMD_SUCCESS;
1982 }
1983
1984 DEFUN (show_evpn_mac_vni_vtep,
1985 show_evpn_mac_vni_vtep_cmd,
1986 "show evpn mac vni " CMD_VNI_RANGE " vtep A.B.C.D" "[json]",
1987 SHOW_STR
1988 "EVPN\n"
1989 "MAC addresses\n"
1990 "VxLAN Network Identifier\n"
1991 "VNI number\n"
1992 "Remote VTEP\n"
1993 "Remote VTEP IP address\n"
1994 JSON_STR)
1995 {
1996 struct zebra_vrf *zvrf;
1997 vni_t vni;
1998 struct in_addr vtep_ip;
1999 uint8_t uj = use_json(argc, argv);
2000
2001 vni = strtoul(argv[4]->arg, NULL, 10);
2002 if (!inet_aton(argv[6]->arg, &vtep_ip)) {
2003 if (!uj)
2004 vty_out(vty, "%% Malformed VTEP IP address\n");
2005 return CMD_WARNING;
2006 }
2007
2008 zvrf = vrf_info_lookup(VRF_DEFAULT);
2009 zebra_vxlan_print_macs_vni_vtep(vty, zvrf, vni, vtep_ip, uj);
2010 return CMD_SUCCESS;
2011 }
2012
2013 DEFUN (show_evpn_neigh_vni,
2014 show_evpn_neigh_vni_cmd,
2015 "show evpn arp-cache vni " CMD_VNI_RANGE "[json]",
2016 SHOW_STR
2017 "EVPN\n"
2018 "ARP and ND cache\n"
2019 "VxLAN Network Identifier\n"
2020 "VNI number\n"
2021 JSON_STR)
2022 {
2023 struct zebra_vrf *zvrf;
2024 vni_t vni;
2025 uint8_t uj = use_json(argc, argv);
2026
2027 vni = strtoul(argv[4]->arg, NULL, 10);
2028 zvrf = vrf_info_lookup(VRF_DEFAULT);
2029 zebra_vxlan_print_neigh_vni(vty, zvrf, vni, uj);
2030 return CMD_SUCCESS;
2031 }
2032
2033 DEFUN (show_evpn_neigh_vni_all,
2034 show_evpn_neigh_vni_all_cmd,
2035 "show evpn arp-cache vni all [json]",
2036 SHOW_STR
2037 "EVPN\n"
2038 "ARP and ND cache\n"
2039 "VxLAN Network Identifier\n"
2040 "All VNIs\n"
2041 JSON_STR)
2042 {
2043 struct zebra_vrf *zvrf;
2044 uint8_t uj = use_json(argc, argv);
2045
2046 zvrf = vrf_info_lookup(VRF_DEFAULT);
2047 zebra_vxlan_print_neigh_all_vni(vty, zvrf, uj);
2048 return CMD_SUCCESS;
2049 }
2050
2051 DEFUN (show_evpn_neigh_vni_neigh,
2052 show_evpn_neigh_vni_neigh_cmd,
2053 "show evpn arp-cache vni " CMD_VNI_RANGE " ip WORD [json]",
2054 SHOW_STR
2055 "EVPN\n"
2056 "ARP and ND cache\n"
2057 "VxLAN Network Identifier\n"
2058 "VNI number\n"
2059 "Neighbor\n"
2060 "Neighbor address (IPv4 or IPv6 address)\n"
2061 JSON_STR)
2062 {
2063 struct zebra_vrf *zvrf;
2064 vni_t vni;
2065 struct ipaddr ip;
2066 uint8_t uj = use_json(argc, argv);
2067
2068 vni = strtoul(argv[4]->arg, NULL, 10);
2069 if (str2ipaddr(argv[6]->arg, &ip) != 0) {
2070 if (!uj)
2071 vty_out(vty, "%% Malformed Neighbor address\n");
2072 return CMD_WARNING;
2073 }
2074 zvrf = vrf_info_lookup(VRF_DEFAULT);
2075 zebra_vxlan_print_specific_neigh_vni(vty, zvrf, vni, &ip, uj);
2076 return CMD_SUCCESS;
2077 }
2078
2079 DEFUN (show_evpn_neigh_vni_vtep,
2080 show_evpn_neigh_vni_vtep_cmd,
2081 "show evpn arp-cache vni " CMD_VNI_RANGE " vtep A.B.C.D [json]",
2082 SHOW_STR
2083 "EVPN\n"
2084 "ARP and ND cache\n"
2085 "VxLAN Network Identifier\n"
2086 "VNI number\n"
2087 "Remote VTEP\n"
2088 "Remote VTEP IP address\n"
2089 JSON_STR)
2090 {
2091 struct zebra_vrf *zvrf;
2092 vni_t vni;
2093 struct in_addr vtep_ip;
2094 uint8_t uj = use_json(argc, argv);
2095
2096 vni = strtoul(argv[4]->arg, NULL, 10);
2097 if (!inet_aton(argv[6]->arg, &vtep_ip)) {
2098 if (!uj)
2099 vty_out(vty, "%% Malformed VTEP IP address\n");
2100 return CMD_WARNING;
2101 }
2102
2103 zvrf = vrf_info_lookup(VRF_DEFAULT);
2104 zebra_vxlan_print_neigh_vni_vtep(vty, zvrf, vni, vtep_ip, uj);
2105 return CMD_SUCCESS;
2106 }
2107
2108 /* policy routing contexts */
2109 DEFUN (show_pbr_ipset,
2110 show_pbr_ipset_cmd,
2111 "show pbr ipset [WORD]",
2112 SHOW_STR
2113 "Policy-Based Routing\n"
2114 "IPset Context information\n"
2115 "IPset Name information\n")
2116 {
2117 int idx = 0;
2118 int found = 0;
2119 found = argv_find(argv, argc, "WORD", &idx);
2120 if (!found)
2121 zebra_pbr_show_ipset_list(vty, NULL);
2122 else
2123 zebra_pbr_show_ipset_list(vty, argv[idx]->arg);
2124 return CMD_SUCCESS;
2125 }
2126
2127 /* policy routing contexts */
2128 DEFUN (show_pbr_iptable,
2129 show_pbr_iptable_cmd,
2130 "show pbr iptable [WORD]",
2131 SHOW_STR
2132 "Policy-Based Routing\n"
2133 "IPtable Context information\n"
2134 "IPtable Name information\n")
2135 {
2136 int idx = 0;
2137 int found = 0;
2138
2139 found = argv_find(argv, argc, "WORD", &idx);
2140 if (!found)
2141 zebra_pbr_show_iptable(vty, NULL);
2142 else
2143 zebra_pbr_show_iptable(vty, argv[idx]->arg);
2144 return CMD_SUCCESS;
2145 }
2146
2147 /* Static ip route configuration write function. */
2148 static int zebra_ip_config(struct vty *vty)
2149 {
2150 int write = 0;
2151
2152 write += zebra_import_table_config(vty);
2153
2154 return write;
2155 }
2156
2157 DEFUN (ip_zebra_import_table_distance,
2158 ip_zebra_import_table_distance_cmd,
2159 "ip import-table (1-252) [distance (1-255)] [route-map WORD]",
2160 IP_STR
2161 "import routes from non-main kernel table\n"
2162 "kernel routing table id\n"
2163 "Distance for imported routes\n"
2164 "Default distance value\n"
2165 "route-map for filtering\n"
2166 "route-map name\n")
2167 {
2168 uint32_t table_id = 0;
2169
2170 table_id = strtoul(argv[2]->arg, NULL, 10);
2171 int distance = ZEBRA_TABLE_DISTANCE_DEFAULT;
2172 char *rmap =
2173 strmatch(argv[argc - 2]->text, "route-map")
2174 ? XSTRDUP(MTYPE_ROUTE_MAP_NAME, argv[argc - 1]->arg)
2175 : NULL;
2176 int ret;
2177
2178 if (argc == 7 || (argc == 5 && !rmap))
2179 distance = strtoul(argv[4]->arg, NULL, 10);
2180
2181 if (!is_zebra_valid_kernel_table(table_id)) {
2182 vty_out(vty,
2183 "Invalid routing table ID, %d. Must be in range 1-252\n",
2184 table_id);
2185 if (rmap)
2186 XFREE(MTYPE_ROUTE_MAP_NAME, rmap);
2187 return CMD_WARNING;
2188 }
2189
2190 if (is_zebra_main_routing_table(table_id)) {
2191 vty_out(vty,
2192 "Invalid routing table ID, %d. Must be non-default table\n",
2193 table_id);
2194 if (rmap)
2195 XFREE(MTYPE_ROUTE_MAP_NAME, rmap);
2196 return CMD_WARNING;
2197 }
2198
2199 ret = zebra_import_table(AFI_IP, table_id, distance, rmap, 1);
2200 if (rmap)
2201 XFREE(MTYPE_ROUTE_MAP_NAME, rmap);
2202
2203 return ret;
2204 }
2205
2206 DEFUN_HIDDEN (zebra_packet_process,
2207 zebra_packet_process_cmd,
2208 "zebra zapi-packets (1-10000)",
2209 ZEBRA_STR
2210 "Zapi Protocol\n"
2211 "Number of packets to process before relinquishing thread\n")
2212 {
2213 uint32_t packets = strtoul(argv[2]->arg, NULL, 10);
2214
2215 atomic_store_explicit(&zebrad.packets_to_process, packets,
2216 memory_order_relaxed);
2217
2218 return CMD_SUCCESS;
2219 }
2220
2221 DEFUN_HIDDEN (no_zebra_packet_process,
2222 no_zebra_packet_process_cmd,
2223 "no zebra zapi-packets [(1-10000)]",
2224 NO_STR
2225 ZEBRA_STR
2226 "Zapi Protocol\n"
2227 "Number of packets to process before relinquishing thread\n")
2228 {
2229 atomic_store_explicit(&zebrad.packets_to_process,
2230 ZEBRA_ZAPI_PACKETS_TO_PROCESS,
2231 memory_order_relaxed);
2232
2233 return CMD_SUCCESS;
2234 }
2235
2236 DEFUN_HIDDEN (zebra_workqueue_timer,
2237 zebra_workqueue_timer_cmd,
2238 "zebra work-queue (0-10000)",
2239 ZEBRA_STR
2240 "Work Queue\n"
2241 "Time in milliseconds\n")
2242 {
2243 uint32_t timer = strtoul(argv[2]->arg, NULL, 10);
2244 zebrad.ribq->spec.hold = timer;
2245
2246 return CMD_SUCCESS;
2247 }
2248
2249 DEFUN_HIDDEN (no_zebra_workqueue_timer,
2250 no_zebra_workqueue_timer_cmd,
2251 "no zebra work-queue [(0-10000)]",
2252 NO_STR
2253 ZEBRA_STR
2254 "Work Queue\n"
2255 "Time in milliseconds\n")
2256 {
2257 zebrad.ribq->spec.hold = ZEBRA_RIB_PROCESS_HOLD_TIME;
2258
2259 return CMD_SUCCESS;
2260 }
2261
2262 DEFUN (no_ip_zebra_import_table,
2263 no_ip_zebra_import_table_cmd,
2264 "no ip import-table (1-252) [distance (1-255)] [route-map NAME]",
2265 NO_STR
2266 IP_STR
2267 "import routes from non-main kernel table\n"
2268 "kernel routing table id\n"
2269 "Distance for imported routes\n"
2270 "Default distance value\n"
2271 "route-map for filtering\n"
2272 "route-map name\n")
2273 {
2274 uint32_t table_id = 0;
2275 table_id = strtoul(argv[3]->arg, NULL, 10);
2276
2277 if (!is_zebra_valid_kernel_table(table_id)) {
2278 vty_out(vty,
2279 "Invalid routing table ID. Must be in range 1-252\n");
2280 return CMD_WARNING;
2281 }
2282
2283 if (is_zebra_main_routing_table(table_id)) {
2284 vty_out(vty,
2285 "Invalid routing table ID, %d. Must be non-default table\n",
2286 table_id);
2287 return CMD_WARNING;
2288 }
2289
2290 if (!is_zebra_import_table_enabled(AFI_IP, table_id))
2291 return CMD_SUCCESS;
2292
2293 return (zebra_import_table(AFI_IP, table_id, 0, NULL, 0));
2294 }
2295
2296 static int config_write_protocol(struct vty *vty)
2297 {
2298 if (allow_delete)
2299 vty_out(vty, "allow-external-route-update\n");
2300
2301 if (zebra_rnh_ip_default_route)
2302 vty_out(vty, "ip nht resolve-via-default\n");
2303
2304 if (zebra_rnh_ipv6_default_route)
2305 vty_out(vty, "ipv6 nht resolve-via-default\n");
2306
2307 if (zebrad.ribq->spec.hold != ZEBRA_RIB_PROCESS_HOLD_TIME)
2308 vty_out(vty, "zebra work-queue %u\n", zebrad.ribq->spec.hold);
2309
2310 if (zebrad.packets_to_process != ZEBRA_ZAPI_PACKETS_TO_PROCESS)
2311 vty_out(vty, "zebra zapi-packets %u\n",
2312 zebrad.packets_to_process);
2313
2314 enum multicast_mode ipv4_multicast_mode = multicast_mode_ipv4_get();
2315
2316 if (ipv4_multicast_mode != MCAST_NO_CONFIG)
2317 vty_out(vty, "ip multicast rpf-lookup-mode %s\n",
2318 ipv4_multicast_mode == MCAST_URIB_ONLY
2319 ? "urib-only"
2320 : ipv4_multicast_mode == MCAST_MRIB_ONLY
2321 ? "mrib-only"
2322 : ipv4_multicast_mode
2323 == MCAST_MIX_MRIB_FIRST
2324 ? "mrib-then-urib"
2325 : ipv4_multicast_mode
2326 == MCAST_MIX_DISTANCE
2327 ? "lower-distance"
2328 : "longer-prefix");
2329
2330 zebra_routemap_config_write_protocol(vty);
2331
2332 return 1;
2333 }
2334
2335 #ifdef HAVE_NETLINK
2336 /* Display default rtm_table for all clients. */
2337 DEFUN (show_table,
2338 show_table_cmd,
2339 "show table",
2340 SHOW_STR
2341 "default routing table to use for all clients\n")
2342 {
2343 vty_out(vty, "table %d\n", zebrad.rtm_table_default);
2344 return CMD_SUCCESS;
2345 }
2346
2347 DEFUN (config_table,
2348 config_table_cmd,
2349 "table TABLENO",
2350 "Configure target kernel routing table\n"
2351 "TABLE integer\n")
2352 {
2353 zebrad.rtm_table_default = strtol(argv[1]->arg, (char **)0, 10);
2354 return CMD_SUCCESS;
2355 }
2356
2357 DEFUN (no_config_table,
2358 no_config_table_cmd,
2359 "no table [TABLENO]",
2360 NO_STR
2361 "Configure target kernel routing table\n"
2362 "TABLE integer\n")
2363 {
2364 zebrad.rtm_table_default = 0;
2365 return CMD_SUCCESS;
2366 }
2367 #endif
2368
2369 DEFUN (show_zebra,
2370 show_zebra_cmd,
2371 "show zebra",
2372 SHOW_STR
2373 ZEBRA_STR)
2374 {
2375 struct vrf *vrf;
2376
2377 vty_out(vty,
2378 " Route Route Neighbor LSP LSP\n");
2379 vty_out(vty,
2380 "VRF Installs Removals Updates Installs Removals\n");
2381
2382 RB_FOREACH (vrf, vrf_name_head, &vrfs_by_name) {
2383 struct zebra_vrf *zvrf = vrf->info;
2384
2385 vty_out(vty, "%-25s %10" PRIu64 " %10" PRIu64 " %10" PRIu64
2386 " %10" PRIu64 " %10" PRIu64 "\n",
2387 vrf->name, zvrf->installs, zvrf->removals,
2388 zvrf->neigh_updates, zvrf->lsp_installs,
2389 zvrf->lsp_removals);
2390 }
2391
2392 return CMD_SUCCESS;
2393 }
2394
2395 DEFUN (ip_forwarding,
2396 ip_forwarding_cmd,
2397 "ip forwarding",
2398 IP_STR
2399 "Turn on IP forwarding\n")
2400 {
2401 int ret;
2402
2403 ret = ipforward();
2404 if (ret == 0)
2405 ret = ipforward_on();
2406
2407 if (ret == 0) {
2408 vty_out(vty, "Can't turn on IP forwarding\n");
2409 return CMD_WARNING_CONFIG_FAILED;
2410 }
2411
2412 return CMD_SUCCESS;
2413 }
2414
2415 DEFUN (no_ip_forwarding,
2416 no_ip_forwarding_cmd,
2417 "no ip forwarding",
2418 NO_STR
2419 IP_STR
2420 "Turn off IP forwarding\n")
2421 {
2422 int ret;
2423
2424 ret = ipforward();
2425 if (ret != 0)
2426 ret = ipforward_off();
2427
2428 if (ret != 0) {
2429 vty_out(vty, "Can't turn off IP forwarding\n");
2430 return CMD_WARNING_CONFIG_FAILED;
2431 }
2432
2433 return CMD_SUCCESS;
2434 }
2435
2436 /* Only display ip forwarding is enabled or not. */
2437 DEFUN (show_ip_forwarding,
2438 show_ip_forwarding_cmd,
2439 "show ip forwarding",
2440 SHOW_STR
2441 IP_STR
2442 "IP forwarding status\n")
2443 {
2444 int ret;
2445
2446 ret = ipforward();
2447
2448 if (ret == 0)
2449 vty_out(vty, "IP forwarding is off\n");
2450 else
2451 vty_out(vty, "IP forwarding is on\n");
2452 return CMD_SUCCESS;
2453 }
2454
2455 /* Only display ipv6 forwarding is enabled or not. */
2456 DEFUN (show_ipv6_forwarding,
2457 show_ipv6_forwarding_cmd,
2458 "show ipv6 forwarding",
2459 SHOW_STR
2460 "IPv6 information\n"
2461 "Forwarding status\n")
2462 {
2463 int ret;
2464
2465 ret = ipforward_ipv6();
2466
2467 switch (ret) {
2468 case -1:
2469 vty_out(vty, "ipv6 forwarding is unknown\n");
2470 break;
2471 case 0:
2472 vty_out(vty, "ipv6 forwarding is %s\n", "off");
2473 break;
2474 case 1:
2475 vty_out(vty, "ipv6 forwarding is %s\n", "on");
2476 break;
2477 default:
2478 vty_out(vty, "ipv6 forwarding is %s\n", "off");
2479 break;
2480 }
2481 return CMD_SUCCESS;
2482 }
2483
2484 DEFUN (ipv6_forwarding,
2485 ipv6_forwarding_cmd,
2486 "ipv6 forwarding",
2487 IPV6_STR
2488 "Turn on IPv6 forwarding\n")
2489 {
2490 int ret;
2491
2492 ret = ipforward_ipv6();
2493 if (ret == 0)
2494 ret = ipforward_ipv6_on();
2495
2496 if (ret == 0) {
2497 vty_out(vty, "Can't turn on IPv6 forwarding\n");
2498 return CMD_WARNING_CONFIG_FAILED;
2499 }
2500
2501 return CMD_SUCCESS;
2502 }
2503
2504 DEFUN (no_ipv6_forwarding,
2505 no_ipv6_forwarding_cmd,
2506 "no ipv6 forwarding",
2507 NO_STR
2508 IPV6_STR
2509 "Turn off IPv6 forwarding\n")
2510 {
2511 int ret;
2512
2513 ret = ipforward_ipv6();
2514 if (ret != 0)
2515 ret = ipforward_ipv6_off();
2516
2517 if (ret != 0) {
2518 vty_out(vty, "Can't turn off IPv6 forwarding\n");
2519 return CMD_WARNING_CONFIG_FAILED;
2520 }
2521
2522 return CMD_SUCCESS;
2523 }
2524
2525 /* Table configuration write function. */
2526 static int config_write_table(struct vty *vty)
2527 {
2528 if (zebrad.rtm_table_default)
2529 vty_out(vty, "table %d\n", zebrad.rtm_table_default);
2530 return 0;
2531 }
2532
2533 /* IPForwarding configuration write function. */
2534 static int config_write_forwarding(struct vty *vty)
2535 {
2536 /* FIXME: Find better place for that. */
2537 router_id_write(vty);
2538
2539 if (!ipforward())
2540 vty_out(vty, "no ip forwarding\n");
2541 if (!ipforward_ipv6())
2542 vty_out(vty, "no ipv6 forwarding\n");
2543 vty_out(vty, "!\n");
2544 return 0;
2545 }
2546
2547 /* IP node for static routes. */
2548 static struct cmd_node ip_node = {IP_NODE, "", 1};
2549 static struct cmd_node protocol_node = {PROTOCOL_NODE, "", 1};
2550 /* table node for routing tables. */
2551 static struct cmd_node table_node = {TABLE_NODE,
2552 "", /* This node has no interface. */
2553 1};
2554 static struct cmd_node forwarding_node = {FORWARDING_NODE,
2555 "", /* This node has no interface. */
2556 1};
2557
2558 /* Route VTY. */
2559 void zebra_vty_init(void)
2560 {
2561 /* Install configuration write function. */
2562 install_node(&table_node, config_write_table);
2563 install_node(&forwarding_node, config_write_forwarding);
2564
2565 install_element(VIEW_NODE, &show_ip_forwarding_cmd);
2566 install_element(CONFIG_NODE, &ip_forwarding_cmd);
2567 install_element(CONFIG_NODE, &no_ip_forwarding_cmd);
2568 install_element(ENABLE_NODE, &show_zebra_cmd);
2569
2570 #ifdef HAVE_NETLINK
2571 install_element(VIEW_NODE, &show_table_cmd);
2572 install_element(CONFIG_NODE, &config_table_cmd);
2573 install_element(CONFIG_NODE, &no_config_table_cmd);
2574 #endif /* HAVE_NETLINK */
2575
2576 install_element(VIEW_NODE, &show_ipv6_forwarding_cmd);
2577 install_element(CONFIG_NODE, &ipv6_forwarding_cmd);
2578 install_element(CONFIG_NODE, &no_ipv6_forwarding_cmd);
2579
2580 /* Route-map */
2581 zebra_route_map_init();
2582
2583 install_node(&ip_node, zebra_ip_config);
2584 install_node(&protocol_node, config_write_protocol);
2585
2586 install_element(CONFIG_NODE, &allow_external_route_update_cmd);
2587 install_element(CONFIG_NODE, &no_allow_external_route_update_cmd);
2588
2589 install_element(CONFIG_NODE, &ip_multicast_mode_cmd);
2590 install_element(CONFIG_NODE, &no_ip_multicast_mode_cmd);
2591
2592 install_element(CONFIG_NODE, &ip_zebra_import_table_distance_cmd);
2593 install_element(CONFIG_NODE, &no_ip_zebra_import_table_cmd);
2594 install_element(CONFIG_NODE, &zebra_workqueue_timer_cmd);
2595 install_element(CONFIG_NODE, &no_zebra_workqueue_timer_cmd);
2596 install_element(CONFIG_NODE, &zebra_packet_process_cmd);
2597 install_element(CONFIG_NODE, &no_zebra_packet_process_cmd);
2598
2599 install_element(VIEW_NODE, &show_vrf_cmd);
2600 install_element(VIEW_NODE, &show_vrf_vni_cmd);
2601 install_element(VIEW_NODE, &show_route_cmd);
2602 install_element(VIEW_NODE, &show_route_table_cmd);
2603 if (vrf_is_backend_netns())
2604 install_element(VIEW_NODE, &show_route_table_vrf_cmd);
2605 install_element(VIEW_NODE, &show_route_detail_cmd);
2606 install_element(VIEW_NODE, &show_route_summary_cmd);
2607 install_element(VIEW_NODE, &show_ip_nht_cmd);
2608 install_element(VIEW_NODE, &show_ip_nht_vrf_all_cmd);
2609 install_element(VIEW_NODE, &show_ipv6_nht_cmd);
2610 install_element(VIEW_NODE, &show_ipv6_nht_vrf_all_cmd);
2611
2612 install_element(VIEW_NODE, &show_ip_rpf_cmd);
2613 install_element(VIEW_NODE, &show_ip_rpf_addr_cmd);
2614
2615 install_element(CONFIG_NODE, &ip_nht_default_route_cmd);
2616 install_element(CONFIG_NODE, &no_ip_nht_default_route_cmd);
2617 install_element(CONFIG_NODE, &ipv6_nht_default_route_cmd);
2618 install_element(CONFIG_NODE, &no_ipv6_nht_default_route_cmd);
2619 install_element(VIEW_NODE, &show_ipv6_mroute_cmd);
2620
2621 /* Commands for VRF */
2622 install_element(VIEW_NODE, &show_ipv6_mroute_vrf_all_cmd);
2623
2624 install_element(VIEW_NODE, &show_evpn_global_cmd);
2625 install_element(VIEW_NODE, &show_evpn_vni_cmd);
2626 install_element(VIEW_NODE, &show_evpn_vni_vni_cmd);
2627 install_element(VIEW_NODE, &show_evpn_rmac_vni_mac_cmd);
2628 install_element(VIEW_NODE, &show_evpn_rmac_vni_cmd);
2629 install_element(VIEW_NODE, &show_evpn_rmac_vni_all_cmd);
2630 install_element(VIEW_NODE, &show_evpn_nh_vni_ip_cmd);
2631 install_element(VIEW_NODE, &show_evpn_nh_vni_cmd);
2632 install_element(VIEW_NODE, &show_evpn_nh_vni_all_cmd);
2633 install_element(VIEW_NODE, &show_evpn_mac_vni_cmd);
2634 install_element(VIEW_NODE, &show_evpn_mac_vni_all_cmd);
2635 install_element(VIEW_NODE, &show_evpn_mac_vni_all_vtep_cmd);
2636 install_element(VIEW_NODE, &show_evpn_mac_vni_mac_cmd);
2637 install_element(VIEW_NODE, &show_evpn_mac_vni_vtep_cmd);
2638 install_element(VIEW_NODE, &show_evpn_neigh_vni_cmd);
2639 install_element(VIEW_NODE, &show_evpn_neigh_vni_all_cmd);
2640 install_element(VIEW_NODE, &show_evpn_neigh_vni_neigh_cmd);
2641 install_element(VIEW_NODE, &show_evpn_neigh_vni_vtep_cmd);
2642
2643 install_element(VIEW_NODE, &show_pbr_ipset_cmd);
2644 install_element(VIEW_NODE, &show_pbr_iptable_cmd);
2645
2646 install_element(CONFIG_NODE, &default_vrf_vni_mapping_cmd);
2647 install_element(CONFIG_NODE, &no_default_vrf_vni_mapping_cmd);
2648 install_element(VRF_NODE, &vrf_vni_mapping_cmd);
2649 install_element(VRF_NODE, &no_vrf_vni_mapping_cmd);
2650
2651
2652 }