3 * Copyright (C) 2008 Everton da Silva Marques
5 * This program is free software; you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License as published by
7 * the Free Software Foundation; either version 2 of the License, or
8 * (at your option) any later version.
10 * This program is distributed in the hope that it will be useful, but
11 * WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 * General Public License for more details.
15 * You should have received a copy of the GNU General Public License along
16 * with this program; see the file COPYING; if not, write to the Free Software
17 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
34 #include "pim_mroute.h"
36 #include "pim_iface.h"
38 #include "pim_mroute.h"
41 #include "pim_igmpv3.h"
46 #include "pim_neighbor.h"
48 #include "pim_ifchannel.h"
49 #include "pim_hello.h"
51 #include "pim_upstream.h"
53 #include "pim_macro.h"
54 #include "pim_ssmpingd.h"
55 #include "pim_zebra.h"
56 #include "pim_static.h"
58 #include "pim_zlookup.h"
65 static struct cmd_node interface_node
= {
66 INTERFACE_NODE
, "%s(config-if)# ", 1 /* vtysh ? yes */
69 static struct cmd_node debug_node
= {DEBUG_NODE
, "", 1};
71 static struct vrf
*pim_cmd_lookup_vrf(struct vty
*vty
, struct cmd_token
*argv
[],
72 const int argc
, int *idx
)
76 if (argv_find(argv
, argc
, "NAME", idx
))
77 vrf
= vrf_lookup_by_name(argv
[*idx
]->arg
);
79 vrf
= vrf_lookup_by_id(VRF_DEFAULT
);
82 vty_out(vty
, "Specified VRF: %s does not exist\n",
88 static void pim_if_membership_clear(struct interface
*ifp
)
90 struct pim_interface
*pim_ifp
;
95 if (PIM_IF_TEST_PIM(pim_ifp
->options
)
96 && PIM_IF_TEST_IGMP(pim_ifp
->options
)) {
100 pim_ifchannel_membership_clear(ifp
);
104 When PIM is disabled on interface, IGMPv3 local membership
105 information is not injected into PIM interface state.
107 The function pim_if_membership_refresh() fetches all IGMPv3 local
108 membership information into PIM. It is intented to be called
109 whenever PIM is enabled on the interface in order to collect missed
110 local membership information.
112 static void pim_if_membership_refresh(struct interface
*ifp
)
114 struct pim_interface
*pim_ifp
;
115 struct listnode
*sock_node
;
116 struct igmp_sock
*igmp
;
121 if (!PIM_IF_TEST_PIM(pim_ifp
->options
))
123 if (!PIM_IF_TEST_IGMP(pim_ifp
->options
))
127 First clear off membership from all PIM (S,G) entries on the
131 pim_ifchannel_membership_clear(ifp
);
134 Then restore PIM (S,G) membership from all IGMPv3 (S,G) entries on
138 /* scan igmp sockets */
139 for (ALL_LIST_ELEMENTS_RO(pim_ifp
->igmp_socket_list
, sock_node
, igmp
)) {
140 struct listnode
*grpnode
;
141 struct igmp_group
*grp
;
143 /* scan igmp groups */
144 for (ALL_LIST_ELEMENTS_RO(igmp
->igmp_group_list
, grpnode
,
146 struct listnode
*srcnode
;
147 struct igmp_source
*src
;
149 /* scan group sources */
150 for (ALL_LIST_ELEMENTS_RO(grp
->group_source_list
,
153 if (IGMP_SOURCE_TEST_FORWARDING(
154 src
->source_flags
)) {
158 sizeof(struct prefix_sg
));
159 sg
.src
= src
->source_addr
;
160 sg
.grp
= grp
->group_addr
;
161 pim_ifchannel_local_membership_add(ifp
,
165 } /* scan group sources */
166 } /* scan igmp groups */
167 } /* scan igmp sockets */
170 Finally delete every PIM (S,G) entry lacking all state info
173 pim_ifchannel_delete_on_noinfo(ifp
);
176 static void pim_show_assert_helper(struct vty
*vty
,
177 struct pim_interface
*pim_ifp
,
178 struct pim_ifchannel
*ch
,
181 char ch_src_str
[INET_ADDRSTRLEN
];
182 char ch_grp_str
[INET_ADDRSTRLEN
];
183 char winner_str
[INET_ADDRSTRLEN
];
184 struct in_addr ifaddr
;
188 ifaddr
= pim_ifp
->primary_address
;
190 pim_inet4_dump("<ch_src?>", ch
->sg
.src
, ch_src_str
,
192 pim_inet4_dump("<ch_grp?>", ch
->sg
.grp
, ch_grp_str
,
194 pim_inet4_dump("<assrt_win?>", ch
->ifassert_winner
, winner_str
,
197 pim_time_uptime(uptime
, sizeof(uptime
),
198 now
- ch
->ifassert_creation
);
199 pim_time_timer_to_mmss(timer
, sizeof(timer
),
200 ch
->t_ifassert_timer
);
202 vty_out(vty
, "%-9s %-15s %-15s %-15s %-6s %-15s %-8s %-5s\n",
203 ch
->interface
->name
, inet_ntoa(ifaddr
), ch_src_str
,
205 pim_ifchannel_ifassert_name(ch
->ifassert_state
),
206 winner_str
, uptime
, timer
);
209 static void pim_show_assert(struct pim_instance
*pim
, struct vty
*vty
)
211 struct pim_interface
*pim_ifp
;
212 struct pim_ifchannel
*ch
;
213 struct interface
*ifp
;
216 now
= pim_time_monotonic_sec();
219 "Interface Address Source Group State Winner Uptime Timer\n");
221 FOR_ALL_INTERFACES (pim
->vrf
, ifp
) {
226 RB_FOREACH (ch
, pim_ifchannel_rb
, &pim_ifp
->ifchannel_rb
) {
227 pim_show_assert_helper(vty
, pim_ifp
, ch
, now
);
228 } /* scan interface channels */
232 static void pim_show_assert_internal_helper(struct vty
*vty
,
233 struct pim_interface
*pim_ifp
,
234 struct pim_ifchannel
*ch
)
236 char ch_src_str
[INET_ADDRSTRLEN
];
237 char ch_grp_str
[INET_ADDRSTRLEN
];
238 struct in_addr ifaddr
;
240 ifaddr
= pim_ifp
->primary_address
;
242 pim_inet4_dump("<ch_src?>", ch
->sg
.src
, ch_src_str
,
244 pim_inet4_dump("<ch_grp?>", ch
->sg
.grp
, ch_grp_str
,
246 vty_out(vty
, "%-9s %-15s %-15s %-15s %-3s %-3s %-3s %-4s\n",
247 ch
->interface
->name
, inet_ntoa(ifaddr
), ch_src_str
,
249 PIM_IF_FLAG_TEST_COULD_ASSERT(ch
->flags
) ? "yes" : "no",
250 pim_macro_ch_could_assert_eval(ch
) ? "yes" : "no",
251 PIM_IF_FLAG_TEST_ASSERT_TRACKING_DESIRED(ch
->flags
)
254 pim_macro_assert_tracking_desired_eval(ch
) ? "yes"
258 static void pim_show_assert_internal(struct pim_instance
*pim
, struct vty
*vty
)
260 struct pim_interface
*pim_ifp
;
261 struct pim_ifchannel
*ch
;
262 struct interface
*ifp
;
266 "ECA: Evaluate CouldAssert\n"
267 "ATD: AssertTrackingDesired\n"
268 "eATD: Evaluate AssertTrackingDesired\n\n");
271 "Interface Address Source Group CA eCA ATD eATD\n");
272 FOR_ALL_INTERFACES (pim
->vrf
, ifp
) {
277 RB_FOREACH (ch
, pim_ifchannel_rb
, &pim_ifp
->ifchannel_rb
) {
278 pim_show_assert_internal_helper(vty
, pim_ifp
, ch
);
279 } /* scan interface channels */
283 static void pim_show_assert_metric_helper(struct vty
*vty
,
284 struct pim_interface
*pim_ifp
,
285 struct pim_ifchannel
*ch
)
287 char ch_src_str
[INET_ADDRSTRLEN
];
288 char ch_grp_str
[INET_ADDRSTRLEN
];
289 char addr_str
[INET_ADDRSTRLEN
];
290 struct pim_assert_metric am
;
291 struct in_addr ifaddr
;
293 ifaddr
= pim_ifp
->primary_address
;
295 am
= pim_macro_spt_assert_metric(&ch
->upstream
->rpf
,
296 pim_ifp
->primary_address
);
298 pim_inet4_dump("<ch_src?>", ch
->sg
.src
, ch_src_str
,
300 pim_inet4_dump("<ch_grp?>", ch
->sg
.grp
, ch_grp_str
,
302 pim_inet4_dump("<addr?>", am
.ip_address
, addr_str
,
305 vty_out(vty
, "%-9s %-15s %-15s %-15s %-3s %4u %6u %-15s\n",
306 ch
->interface
->name
, inet_ntoa(ifaddr
), ch_src_str
,
307 ch_grp_str
, am
.rpt_bit_flag
? "yes" : "no",
308 am
.metric_preference
, am
.route_metric
, addr_str
);
311 static void pim_show_assert_metric(struct pim_instance
*pim
, struct vty
*vty
)
313 struct pim_interface
*pim_ifp
;
314 struct pim_ifchannel
*ch
;
315 struct interface
*ifp
;
318 "Interface Address Source Group RPT Pref Metric Address \n");
320 FOR_ALL_INTERFACES (pim
->vrf
, ifp
) {
325 RB_FOREACH (ch
, pim_ifchannel_rb
, &pim_ifp
->ifchannel_rb
) {
326 pim_show_assert_metric_helper(vty
, pim_ifp
, ch
);
327 } /* scan interface channels */
331 static void pim_show_assert_winner_metric_helper(struct vty
*vty
,
332 struct pim_interface
*pim_ifp
,
333 struct pim_ifchannel
*ch
)
335 char ch_src_str
[INET_ADDRSTRLEN
];
336 char ch_grp_str
[INET_ADDRSTRLEN
];
337 char addr_str
[INET_ADDRSTRLEN
];
338 struct pim_assert_metric
*am
;
339 struct in_addr ifaddr
;
343 ifaddr
= pim_ifp
->primary_address
;
345 am
= &ch
->ifassert_winner_metric
;
347 pim_inet4_dump("<ch_src?>", ch
->sg
.src
, ch_src_str
,
349 pim_inet4_dump("<ch_grp?>", ch
->sg
.grp
, ch_grp_str
,
351 pim_inet4_dump("<addr?>", am
->ip_address
, addr_str
,
354 if (am
->metric_preference
== PIM_ASSERT_METRIC_PREFERENCE_MAX
)
355 snprintf(pref_str
, sizeof(pref_str
), "INFI");
357 snprintf(pref_str
, sizeof(pref_str
), "%4u",
358 am
->metric_preference
);
360 if (am
->route_metric
== PIM_ASSERT_ROUTE_METRIC_MAX
)
361 snprintf(metr_str
, sizeof(metr_str
), "INFI");
363 snprintf(metr_str
, sizeof(metr_str
), "%6u",
366 vty_out(vty
, "%-9s %-15s %-15s %-15s %-3s %-4s %-6s %-15s\n",
367 ch
->interface
->name
, inet_ntoa(ifaddr
), ch_src_str
,
368 ch_grp_str
, am
->rpt_bit_flag
? "yes" : "no", pref_str
,
372 static void pim_show_assert_winner_metric(struct pim_instance
*pim
,
375 struct pim_interface
*pim_ifp
;
376 struct pim_ifchannel
*ch
;
377 struct interface
*ifp
;
380 "Interface Address Source Group RPT Pref Metric Address \n");
382 FOR_ALL_INTERFACES (pim
->vrf
, ifp
) {
387 RB_FOREACH (ch
, pim_ifchannel_rb
, &pim_ifp
->ifchannel_rb
) {
388 pim_show_assert_winner_metric_helper(vty
, pim_ifp
, ch
);
389 } /* scan interface channels */
393 static void json_object_pim_ifp_add(struct json_object
*json
,
394 struct interface
*ifp
)
396 struct pim_interface
*pim_ifp
;
399 json_object_string_add(json
, "name", ifp
->name
);
400 json_object_string_add(json
, "state", if_is_up(ifp
) ? "up" : "down");
401 json_object_string_add(json
, "address",
402 inet_ntoa(pim_ifp
->primary_address
));
403 json_object_int_add(json
, "index", ifp
->ifindex
);
405 if (if_is_multicast(ifp
))
406 json_object_boolean_true_add(json
, "flagMulticast");
408 if (if_is_broadcast(ifp
))
409 json_object_boolean_true_add(json
, "flagBroadcast");
411 if (ifp
->flags
& IFF_ALLMULTI
)
412 json_object_boolean_true_add(json
, "flagAllMulticast");
414 if (ifp
->flags
& IFF_PROMISC
)
415 json_object_boolean_true_add(json
, "flagPromiscuous");
417 if (PIM_IF_IS_DELETED(ifp
))
418 json_object_boolean_true_add(json
, "flagDeleted");
420 if (pim_if_lan_delay_enabled(ifp
))
421 json_object_boolean_true_add(json
, "lanDelayEnabled");
424 static void pim_show_membership_helper(struct vty
*vty
,
425 struct pim_interface
*pim_ifp
,
426 struct pim_ifchannel
*ch
,
427 struct json_object
*json
)
429 char ch_src_str
[INET_ADDRSTRLEN
];
430 char ch_grp_str
[INET_ADDRSTRLEN
];
431 json_object
*json_iface
= NULL
;
432 json_object
*json_row
= NULL
;
434 pim_inet4_dump("<ch_src?>", ch
->sg
.src
, ch_src_str
,
436 pim_inet4_dump("<ch_grp?>", ch
->sg
.grp
, ch_grp_str
,
439 json_object_object_get_ex(json
, ch
->interface
->name
,
442 json_iface
= json_object_new_object();
443 json_object_pim_ifp_add(json_iface
, ch
->interface
);
444 json_object_object_add(json
, ch
->interface
->name
,
448 json_row
= json_object_new_object();
449 json_object_string_add(json_row
, "source", ch_src_str
);
450 json_object_string_add(json_row
, "group", ch_grp_str
);
451 json_object_string_add(
452 json_row
, "localMembership",
453 ch
->local_ifmembership
== PIM_IFMEMBERSHIP_NOINFO
456 json_object_object_add(json_iface
, ch_grp_str
, json_row
);
459 static void pim_show_membership(struct pim_instance
*pim
, struct vty
*vty
,
462 struct pim_interface
*pim_ifp
;
463 struct pim_ifchannel
*ch
;
464 struct interface
*ifp
;
466 json_object
*json
= NULL
;
467 json_object
*json_tmp
= NULL
;
469 json
= json_object_new_object();
471 FOR_ALL_INTERFACES (pim
->vrf
, ifp
) {
476 RB_FOREACH (ch
, pim_ifchannel_rb
, &pim_ifp
->ifchannel_rb
) {
477 pim_show_membership_helper(vty
, pim_ifp
, ch
, json
);
478 } /* scan interface channels */
482 vty_out(vty
, "%s\n", json_object_to_json_string_ext(
483 json
, JSON_C_TO_STRING_PRETTY
));
486 "Interface Address Source Group Membership\n");
489 * Example of the json data we are traversing
495 * "address":"10.1.20.1",
497 * "flagMulticast":true,
498 * "flagBroadcast":true,
499 * "lanDelayEnabled":true,
502 * "group":"226.10.10.10",
503 * "localMembership":"INCLUDE"
509 /* foreach interface */
510 json_object_object_foreach(json
, key
, val
)
513 /* Find all of the keys where the val is an object. In
515 * above the only one is 226.10.10.10
517 json_object_object_foreach(val
, if_field_key
,
520 type
= json_object_get_type(if_field_val
);
522 if (type
== json_type_object
) {
523 vty_out(vty
, "%-9s ", key
);
525 json_object_object_get_ex(
526 val
, "address", &json_tmp
);
527 vty_out(vty
, "%-15s ",
528 json_object_get_string(
531 json_object_object_get_ex(if_field_val
,
534 vty_out(vty
, "%-15s ",
535 json_object_get_string(
539 vty_out(vty
, "%-15s ", if_field_key
);
541 json_object_object_get_ex(
542 if_field_val
, "localMembership",
544 vty_out(vty
, "%-10s\n",
545 json_object_get_string(
552 json_object_free(json
);
555 static void pim_print_ifp_flags(struct vty
*vty
, struct interface
*ifp
,
558 vty_out(vty
, "Flags\n");
559 vty_out(vty
, "-----\n");
560 vty_out(vty
, "All Multicast : %s\n",
561 (ifp
->flags
& IFF_ALLMULTI
) ? "yes" : "no");
562 vty_out(vty
, "Broadcast : %s\n",
563 if_is_broadcast(ifp
) ? "yes" : "no");
564 vty_out(vty
, "Deleted : %s\n",
565 PIM_IF_IS_DELETED(ifp
) ? "yes" : "no");
566 vty_out(vty
, "Interface Index : %d\n", ifp
->ifindex
);
567 vty_out(vty
, "Multicast : %s\n",
568 if_is_multicast(ifp
) ? "yes" : "no");
569 vty_out(vty
, "Multicast Loop : %d\n", mloop
);
570 vty_out(vty
, "Promiscuous : %s\n",
571 (ifp
->flags
& IFF_PROMISC
) ? "yes" : "no");
576 static void igmp_show_interfaces(struct pim_instance
*pim
, struct vty
*vty
,
579 struct interface
*ifp
;
581 json_object
*json
= NULL
;
582 json_object
*json_row
= NULL
;
584 now
= pim_time_monotonic_sec();
587 json
= json_object_new_object();
590 "Interface State Address V Querier Query Timer Uptime\n");
592 FOR_ALL_INTERFACES (pim
->vrf
, ifp
) {
593 struct pim_interface
*pim_ifp
;
594 struct listnode
*sock_node
;
595 struct igmp_sock
*igmp
;
602 for (ALL_LIST_ELEMENTS_RO(pim_ifp
->igmp_socket_list
, sock_node
,
605 char query_hhmmss
[10];
607 pim_time_uptime(uptime
, sizeof(uptime
),
608 now
- igmp
->sock_creation
);
609 pim_time_timer_to_hhmmss(query_hhmmss
,
610 sizeof(query_hhmmss
),
611 igmp
->t_igmp_query_timer
);
614 json_row
= json_object_new_object();
615 json_object_pim_ifp_add(json_row
, ifp
);
616 json_object_string_add(json_row
, "upTime",
618 json_object_int_add(json_row
, "version",
619 pim_ifp
->igmp_version
);
621 if (igmp
->t_igmp_query_timer
) {
622 json_object_boolean_true_add(json_row
,
624 json_object_string_add(json_row
,
629 json_object_object_add(json
, ifp
->name
,
634 "%-9s %5s %15s %d %7s %11s %8s\n",
636 if_is_up(ifp
) ? "up" : "down",
637 inet_ntoa(igmp
->ifaddr
),
638 pim_ifp
->igmp_version
,
639 igmp
->t_igmp_query_timer
? "local"
641 query_hhmmss
, uptime
);
647 vty_out(vty
, "%s\n", json_object_to_json_string_ext(
648 json
, JSON_C_TO_STRING_PRETTY
));
649 json_object_free(json
);
653 static void igmp_show_interfaces_single(struct pim_instance
*pim
,
654 struct vty
*vty
, const char *ifname
,
657 struct igmp_sock
*igmp
;
658 struct interface
*ifp
;
659 struct listnode
*sock_node
;
660 struct pim_interface
*pim_ifp
;
662 char query_hhmmss
[10];
663 char other_hhmmss
[10];
664 int found_ifname
= 0;
667 long gmi_msec
; /* Group Membership Interval */
670 long oqpi_msec
; /* Other Querier Present Interval */
674 json_object
*json
= NULL
;
675 json_object
*json_row
= NULL
;
678 json
= json_object_new_object();
680 now
= pim_time_monotonic_sec();
682 FOR_ALL_INTERFACES (pim
->vrf
, ifp
) {
688 if (strcmp(ifname
, "detail") && strcmp(ifname
, ifp
->name
))
691 for (ALL_LIST_ELEMENTS_RO(pim_ifp
->igmp_socket_list
, sock_node
,
694 pim_time_uptime(uptime
, sizeof(uptime
),
695 now
- igmp
->sock_creation
);
696 pim_time_timer_to_hhmmss(query_hhmmss
,
697 sizeof(query_hhmmss
),
698 igmp
->t_igmp_query_timer
);
699 pim_time_timer_to_hhmmss(other_hhmmss
,
700 sizeof(other_hhmmss
),
701 igmp
->t_other_querier_timer
);
703 gmi_msec
= PIM_IGMP_GMI_MSEC(
704 igmp
->querier_robustness_variable
,
705 igmp
->querier_query_interval
,
706 pim_ifp
->igmp_query_max_response_time_dsec
);
709 pim_ifp
->igmp_default_query_interval
);
711 oqpi_msec
= PIM_IGMP_OQPI_MSEC(
712 igmp
->querier_robustness_variable
,
713 igmp
->querier_query_interval
,
714 pim_ifp
->igmp_query_max_response_time_dsec
);
716 lmqt_msec
= PIM_IGMP_LMQT_MSEC(
717 pim_ifp
->igmp_query_max_response_time_dsec
,
718 igmp
->querier_robustness_variable
);
722 igmp
->querier_robustness_variable
,
723 igmp
->querier_query_interval
,
724 pim_ifp
->igmp_query_max_response_time_dsec
)
727 qri_msec
= pim_ifp
->igmp_query_max_response_time_dsec
729 if (pim_ifp
->pim_sock_fd
>= 0)
730 mloop
= pim_socket_mcastloop_get(
731 pim_ifp
->pim_sock_fd
);
736 json_row
= json_object_new_object();
737 json_object_pim_ifp_add(json_row
, ifp
);
738 json_object_string_add(json_row
, "upTime",
740 json_object_string_add(json_row
, "querier",
741 igmp
->t_igmp_query_timer
744 json_object_int_add(json_row
, "queryStartCount",
745 igmp
->startup_query_count
);
746 json_object_string_add(json_row
,
749 json_object_string_add(json_row
,
752 json_object_int_add(json_row
, "version",
753 pim_ifp
->igmp_version
);
756 "timerGroupMembershipIntervalMsec",
758 json_object_int_add(json_row
,
759 "timerLastMemberQueryMsec",
763 "timerOlderHostPresentIntervalMsec",
767 "timerOtherQuerierPresentIntervalMsec",
770 json_row
, "timerQueryInterval",
771 igmp
->querier_query_interval
);
774 "timerQueryResponseIntervalMsec",
777 json_row
, "timerRobustnessVariable",
778 igmp
->querier_robustness_variable
);
779 json_object_int_add(json_row
,
780 "timerStartupQueryInterval",
783 json_object_object_add(json
, ifp
->name
,
787 vty_out(vty
, "Interface : %s\n", ifp
->name
);
788 vty_out(vty
, "State : %s\n",
789 if_is_up(ifp
) ? "up" : "down");
790 vty_out(vty
, "Address : %s\n",
791 inet_ntoa(pim_ifp
->primary_address
));
792 vty_out(vty
, "Uptime : %s\n", uptime
);
793 vty_out(vty
, "Version : %d\n",
794 pim_ifp
->igmp_version
);
798 vty_out(vty
, "Querier\n");
799 vty_out(vty
, "-------\n");
800 vty_out(vty
, "Querier : %s\n",
801 igmp
->t_igmp_query_timer
? "local"
803 vty_out(vty
, "Start Count : %d\n",
804 igmp
->startup_query_count
);
805 vty_out(vty
, "Query Timer : %s\n",
807 vty_out(vty
, "Other Timer : %s\n",
812 vty_out(vty
, "Timers\n");
813 vty_out(vty
, "------\n");
815 "Group Membership Interval : %lis\n",
818 "Last Member Query Time : %lis\n",
821 "Older Host Present Interval : %lis\n",
824 "Other Querier Present Interval : %lis\n",
827 "Query Interval : %ds\n",
828 igmp
->querier_query_interval
);
830 "Query Response Interval : %lis\n",
833 "Robustness Variable : %d\n",
834 igmp
->querier_robustness_variable
);
836 "Startup Query Interval : %ds\n",
841 pim_print_ifp_flags(vty
, ifp
, mloop
);
847 vty_out(vty
, "%s\n", json_object_to_json_string_ext(
848 json
, JSON_C_TO_STRING_PRETTY
));
849 json_object_free(json
);
852 vty_out(vty
, "%% No such interface\n");
856 static void igmp_show_interface_join(struct pim_instance
*pim
, struct vty
*vty
)
858 struct interface
*ifp
;
861 now
= pim_time_monotonic_sec();
864 "Interface Address Source Group Socket Uptime \n");
866 FOR_ALL_INTERFACES (pim
->vrf
, ifp
) {
867 struct pim_interface
*pim_ifp
;
868 struct listnode
*join_node
;
869 struct igmp_join
*ij
;
870 struct in_addr pri_addr
;
871 char pri_addr_str
[INET_ADDRSTRLEN
];
878 if (!pim_ifp
->igmp_join_list
)
881 pri_addr
= pim_find_primary_addr(ifp
);
882 pim_inet4_dump("<pri?>", pri_addr
, pri_addr_str
,
883 sizeof(pri_addr_str
));
885 for (ALL_LIST_ELEMENTS_RO(pim_ifp
->igmp_join_list
, join_node
,
887 char group_str
[INET_ADDRSTRLEN
];
888 char source_str
[INET_ADDRSTRLEN
];
891 pim_time_uptime(uptime
, sizeof(uptime
),
892 now
- ij
->sock_creation
);
893 pim_inet4_dump("<grp?>", ij
->group_addr
, group_str
,
895 pim_inet4_dump("<src?>", ij
->source_addr
, source_str
,
898 vty_out(vty
, "%-9s %-15s %-15s %-15s %6d %8s\n",
899 ifp
->name
, pri_addr_str
, source_str
, group_str
,
900 ij
->sock_fd
, uptime
);
901 } /* for (pim_ifp->igmp_join_list) */
906 static void pim_show_interfaces_single(struct pim_instance
*pim
,
907 struct vty
*vty
, const char *ifname
,
910 struct in_addr ifaddr
;
911 struct interface
*ifp
;
912 struct listnode
*neighnode
;
913 struct listnode
*upnode
;
914 struct pim_interface
*pim_ifp
;
915 struct pim_neighbor
*neigh
;
916 struct pim_upstream
*up
;
918 char dr_str
[INET_ADDRSTRLEN
];
921 char grp_str
[INET_ADDRSTRLEN
];
922 char hello_period
[10];
923 char hello_timer
[10];
924 char neigh_src_str
[INET_ADDRSTRLEN
];
925 char src_str
[INET_ADDRSTRLEN
];
926 char stat_uptime
[10];
929 int found_ifname
= 0;
931 json_object
*json
= NULL
;
932 json_object
*json_row
= NULL
;
933 json_object
*json_pim_neighbor
= NULL
;
934 json_object
*json_pim_neighbors
= NULL
;
935 json_object
*json_group
= NULL
;
936 json_object
*json_group_source
= NULL
;
937 json_object
*json_fhr_sources
= NULL
;
938 struct pim_secondary_addr
*sec_addr
;
939 struct listnode
*sec_node
;
941 now
= pim_time_monotonic_sec();
944 json
= json_object_new_object();
946 FOR_ALL_INTERFACES (pim
->vrf
, ifp
) {
952 if (strcmp(ifname
, "detail") && strcmp(ifname
, ifp
->name
))
956 ifaddr
= pim_ifp
->primary_address
;
957 pim_inet4_dump("<dr?>", pim_ifp
->pim_dr_addr
, dr_str
,
959 pim_time_uptime_begin(dr_uptime
, sizeof(dr_uptime
), now
,
960 pim_ifp
->pim_dr_election_last
);
961 pim_time_timer_to_hhmmss(hello_timer
, sizeof(hello_timer
),
962 pim_ifp
->t_pim_hello_timer
);
963 pim_time_mmss(hello_period
, sizeof(hello_period
),
964 pim_ifp
->pim_hello_period
);
965 pim_time_uptime(stat_uptime
, sizeof(stat_uptime
),
966 now
- pim_ifp
->pim_ifstat_start
);
967 if (pim_ifp
->pim_sock_fd
>= 0)
968 mloop
= pim_socket_mcastloop_get(pim_ifp
->pim_sock_fd
);
973 char pbuf
[PREFIX2STR_BUFFER
];
974 json_row
= json_object_new_object();
975 json_object_pim_ifp_add(json_row
, ifp
);
977 if (pim_ifp
->update_source
.s_addr
!= INADDR_ANY
) {
978 json_object_string_add(
979 json_row
, "useSource",
980 inet_ntoa(pim_ifp
->update_source
));
982 if (pim_ifp
->sec_addr_list
) {
983 json_object
*sec_list
= NULL
;
985 sec_list
= json_object_new_array();
986 for (ALL_LIST_ELEMENTS_RO(
987 pim_ifp
->sec_addr_list
, sec_node
,
989 json_object_array_add(
991 json_object_new_string(
997 json_object_object_add(json_row
,
998 "secondaryAddressList",
1003 if (pim_ifp
->pim_neighbor_list
->count
) {
1004 json_pim_neighbors
= json_object_new_object();
1006 for (ALL_LIST_ELEMENTS_RO(
1007 pim_ifp
->pim_neighbor_list
,
1008 neighnode
, neigh
)) {
1010 json_object_new_object();
1011 pim_inet4_dump("<src?>",
1014 sizeof(neigh_src_str
));
1015 pim_time_uptime(uptime
, sizeof(uptime
),
1016 now
- neigh
->creation
);
1017 pim_time_timer_to_hhmmss(
1018 expire
, sizeof(expire
),
1019 neigh
->t_expire_timer
);
1021 json_object_string_add(
1022 json_pim_neighbor
, "address",
1024 json_object_string_add(
1025 json_pim_neighbor
, "upTime",
1027 json_object_string_add(
1028 json_pim_neighbor
, "holdtime",
1031 json_object_object_add(
1037 json_object_object_add(json_row
, "neighbors",
1038 json_pim_neighbors
);
1041 json_object_string_add(json_row
, "drAddress", dr_str
);
1042 json_object_int_add(json_row
, "drPriority",
1043 pim_ifp
->pim_dr_priority
);
1044 json_object_string_add(json_row
, "drUptime", dr_uptime
);
1045 json_object_int_add(json_row
, "drElections",
1046 pim_ifp
->pim_dr_election_count
);
1047 json_object_int_add(json_row
, "drChanges",
1048 pim_ifp
->pim_dr_election_changes
);
1051 for (ALL_LIST_ELEMENTS_RO(pim
->upstream_list
, upnode
,
1053 if (ifp
!= up
->rpf
.source_nexthop
.interface
)
1056 if (!(up
->flags
& PIM_UPSTREAM_FLAG_MASK_FHR
))
1059 if (!json_fhr_sources
)
1061 json_object_new_object();
1063 pim_inet4_dump("<src?>", up
->sg
.src
,
1064 src_str
, sizeof(src_str
));
1065 pim_inet4_dump("<grp?>", up
->sg
.grp
,
1066 grp_str
, sizeof(grp_str
));
1067 pim_time_uptime(uptime
, sizeof(uptime
),
1068 now
- up
->state_transition
);
1071 * Does this group live in json_fhr_sources?
1074 json_object_object_get_ex(json_fhr_sources
,
1079 json_group
= json_object_new_object();
1080 json_object_object_add(
1086 json_group_source
= json_object_new_object();
1087 json_object_string_add(json_group_source
,
1089 json_object_string_add(json_group_source
,
1091 json_object_string_add(json_group_source
,
1093 json_object_object_add(json_group
, src_str
,
1097 if (json_fhr_sources
) {
1098 json_object_object_add(json_row
,
1103 json_object_int_add(json_row
, "helloPeriod",
1104 pim_ifp
->pim_hello_period
);
1105 json_object_string_add(json_row
, "helloTimer",
1107 json_object_string_add(json_row
, "helloStatStart",
1109 json_object_int_add(json_row
, "helloReceived",
1110 pim_ifp
->pim_ifstat_hello_recv
);
1111 json_object_int_add(json_row
, "helloReceivedFailed",
1112 pim_ifp
->pim_ifstat_hello_recvfail
);
1113 json_object_int_add(json_row
, "helloSend",
1114 pim_ifp
->pim_ifstat_hello_sent
);
1115 json_object_int_add(json_row
, "hellosendFailed",
1116 pim_ifp
->pim_ifstat_hello_sendfail
);
1117 json_object_int_add(json_row
, "helloGenerationId",
1118 pim_ifp
->pim_generation_id
);
1119 json_object_int_add(json_row
, "flagMulticastLoop",
1122 json_object_int_add(
1123 json_row
, "effectivePropagationDelay",
1124 pim_if_effective_propagation_delay_msec(ifp
));
1125 json_object_int_add(
1126 json_row
, "effectiveOverrideInterval",
1127 pim_if_effective_override_interval_msec(ifp
));
1128 json_object_int_add(
1129 json_row
, "joinPruneOverrideInterval",
1130 pim_if_jp_override_interval_msec(ifp
));
1132 json_object_int_add(
1133 json_row
, "propagationDelay",
1134 pim_ifp
->pim_propagation_delay_msec
);
1135 json_object_int_add(
1136 json_row
, "propagationDelayHighest",
1137 pim_ifp
->pim_neighbors_highest_propagation_delay_msec
);
1138 json_object_int_add(
1139 json_row
, "overrideInterval",
1140 pim_ifp
->pim_override_interval_msec
);
1141 json_object_int_add(
1142 json_row
, "overrideIntervalHighest",
1143 pim_ifp
->pim_neighbors_highest_override_interval_msec
);
1144 json_object_object_add(json
, ifp
->name
, json_row
);
1147 vty_out(vty
, "Interface : %s\n", ifp
->name
);
1148 vty_out(vty
, "State : %s\n",
1149 if_is_up(ifp
) ? "up" : "down");
1150 if (pim_ifp
->update_source
.s_addr
!= INADDR_ANY
) {
1151 vty_out(vty
, "Use Source : %s\n",
1152 inet_ntoa(pim_ifp
->update_source
));
1154 if (pim_ifp
->sec_addr_list
) {
1155 char pbuf
[PREFIX2STR_BUFFER
];
1156 vty_out(vty
, "Address : %s (primary)\n",
1158 for (ALL_LIST_ELEMENTS_RO(
1159 pim_ifp
->sec_addr_list
, sec_node
,
1161 vty_out(vty
, " %s\n",
1162 prefix2str(&sec_addr
->addr
,
1163 pbuf
, sizeof(pbuf
)));
1166 vty_out(vty
, "Address : %s\n",
1174 for (ALL_LIST_ELEMENTS_RO(pim_ifp
->pim_neighbor_list
,
1175 neighnode
, neigh
)) {
1178 vty_out(vty
, "PIM Neighbors\n");
1179 vty_out(vty
, "-------------\n");
1183 pim_inet4_dump("<src?>", neigh
->source_addr
,
1185 sizeof(neigh_src_str
));
1186 pim_time_uptime(uptime
, sizeof(uptime
),
1187 now
- neigh
->creation
);
1188 pim_time_timer_to_hhmmss(expire
, sizeof(expire
),
1189 neigh
->t_expire_timer
);
1191 "%-15s : up for %s, holdtime expires in %s\n",
1192 neigh_src_str
, uptime
, expire
);
1195 if (!print_header
) {
1200 vty_out(vty
, "Designated Router\n");
1201 vty_out(vty
, "-----------------\n");
1202 vty_out(vty
, "Address : %s\n", dr_str
);
1203 vty_out(vty
, "Priority : %d\n",
1204 pim_ifp
->pim_dr_priority
);
1205 vty_out(vty
, "Uptime : %s\n", dr_uptime
);
1206 vty_out(vty
, "Elections : %d\n",
1207 pim_ifp
->pim_dr_election_count
);
1208 vty_out(vty
, "Changes : %d\n",
1209 pim_ifp
->pim_dr_election_changes
);
1215 for (ALL_LIST_ELEMENTS_RO(pim
->upstream_list
, upnode
,
1218 if (strcmp(ifp
->name
,
1219 up
->rpf
.source_nexthop
.
1220 interface
->name
) != 0)
1223 if (!(up
->flags
& PIM_UPSTREAM_FLAG_MASK_FHR
))
1228 "FHR - First Hop Router\n");
1230 "----------------------\n");
1234 pim_inet4_dump("<src?>", up
->sg
.src
,
1235 src_str
, sizeof(src_str
));
1236 pim_inet4_dump("<grp?>", up
->sg
.grp
,
1237 grp_str
, sizeof(grp_str
));
1238 pim_time_uptime(uptime
, sizeof(uptime
),
1239 now
- up
->state_transition
);
1241 "%s : %s is a source, uptime is %s\n",
1246 if (!print_header
) {
1251 vty_out(vty
, "Hellos\n");
1252 vty_out(vty
, "------\n");
1253 vty_out(vty
, "Period : %d\n",
1254 pim_ifp
->pim_hello_period
);
1255 vty_out(vty
, "Timer : %s\n", hello_timer
);
1256 vty_out(vty
, "StatStart : %s\n", stat_uptime
);
1257 vty_out(vty
, "Receive : %d\n",
1258 pim_ifp
->pim_ifstat_hello_recv
);
1259 vty_out(vty
, "Receive Failed : %d\n",
1260 pim_ifp
->pim_ifstat_hello_recvfail
);
1261 vty_out(vty
, "Send : %d\n",
1262 pim_ifp
->pim_ifstat_hello_sent
);
1263 vty_out(vty
, "Send Failed : %d\n",
1264 pim_ifp
->pim_ifstat_hello_sendfail
);
1265 vty_out(vty
, "Generation ID : %08x\n",
1266 pim_ifp
->pim_generation_id
);
1270 pim_print_ifp_flags(vty
, ifp
, mloop
);
1272 vty_out(vty
, "Join Prune Interval\n");
1273 vty_out(vty
, "-------------------\n");
1274 vty_out(vty
, "LAN Delay : %s\n",
1275 pim_if_lan_delay_enabled(ifp
) ? "yes" : "no");
1276 vty_out(vty
, "Effective Propagation Delay : %d msec\n",
1277 pim_if_effective_propagation_delay_msec(ifp
));
1278 vty_out(vty
, "Effective Override Interval : %d msec\n",
1279 pim_if_effective_override_interval_msec(ifp
));
1280 vty_out(vty
, "Join Prune Override Interval : %d msec\n",
1281 pim_if_jp_override_interval_msec(ifp
));
1285 vty_out(vty
, "LAN Prune Delay\n");
1286 vty_out(vty
, "---------------\n");
1287 vty_out(vty
, "Propagation Delay : %d msec\n",
1288 pim_ifp
->pim_propagation_delay_msec
);
1289 vty_out(vty
, "Propagation Delay (Highest) : %d msec\n",
1290 pim_ifp
->pim_neighbors_highest_propagation_delay_msec
);
1291 vty_out(vty
, "Override Interval : %d msec\n",
1292 pim_ifp
->pim_override_interval_msec
);
1293 vty_out(vty
, "Override Interval (Highest) : %d msec\n",
1294 pim_ifp
->pim_neighbors_highest_override_interval_msec
);
1301 vty_out(vty
, "%s\n", json_object_to_json_string_ext(
1302 json
, JSON_C_TO_STRING_PRETTY
));
1303 json_object_free(json
);
1306 vty_out(vty
, "%% No such interface\n");
1310 static void pim_show_interfaces(struct pim_instance
*pim
, struct vty
*vty
,
1313 struct interface
*ifp
;
1314 struct listnode
*upnode
;
1315 struct pim_interface
*pim_ifp
;
1316 struct pim_upstream
*up
;
1319 int pim_ifchannels
= 0;
1320 json_object
*json
= NULL
;
1321 json_object
*json_row
= NULL
;
1322 json_object
*json_tmp
;
1324 json
= json_object_new_object();
1326 FOR_ALL_INTERFACES (pim
->vrf
, ifp
) {
1327 pim_ifp
= ifp
->info
;
1332 pim_nbrs
= pim_ifp
->pim_neighbor_list
->count
;
1333 pim_ifchannels
= pim_if_ifchannel_count(pim_ifp
);
1336 for (ALL_LIST_ELEMENTS_RO(pim
->upstream_list
, upnode
, up
))
1337 if (ifp
== up
->rpf
.source_nexthop
.interface
)
1338 if (up
->flags
& PIM_UPSTREAM_FLAG_MASK_FHR
)
1341 json_row
= json_object_new_object();
1342 json_object_pim_ifp_add(json_row
, ifp
);
1343 json_object_int_add(json_row
, "pimNeighbors", pim_nbrs
);
1344 json_object_int_add(json_row
, "pimIfChannels", pim_ifchannels
);
1345 json_object_int_add(json_row
, "firstHopRouterCount", fhr
);
1346 json_object_string_add(json_row
, "pimDesignatedRouter",
1347 inet_ntoa(pim_ifp
->pim_dr_addr
));
1349 if (pim_ifp
->pim_dr_addr
.s_addr
1350 == pim_ifp
->primary_address
.s_addr
)
1351 json_object_boolean_true_add(
1352 json_row
, "pimDesignatedRouterLocal");
1354 json_object_object_add(json
, ifp
->name
, json_row
);
1358 vty_out(vty
, "%s\n", json_object_to_json_string_ext(
1359 json
, JSON_C_TO_STRING_PRETTY
));
1362 "Interface State Address PIM Nbrs PIM DR FHR IfChannels\n");
1364 json_object_object_foreach(json
, key
, val
)
1366 vty_out(vty
, "%-9s ", key
);
1368 json_object_object_get_ex(val
, "state", &json_tmp
);
1369 vty_out(vty
, "%5s ", json_object_get_string(json_tmp
));
1371 json_object_object_get_ex(val
, "address", &json_tmp
);
1372 vty_out(vty
, "%15s ",
1373 json_object_get_string(json_tmp
));
1375 json_object_object_get_ex(val
, "pimNeighbors",
1377 vty_out(vty
, "%8d ", json_object_get_int(json_tmp
));
1379 if (json_object_object_get_ex(
1380 val
, "pimDesignatedRouterLocal",
1382 vty_out(vty
, "%15s ", "local");
1384 json_object_object_get_ex(
1385 val
, "pimDesignatedRouter", &json_tmp
);
1386 vty_out(vty
, "%15s ",
1387 json_object_get_string(json_tmp
));
1390 json_object_object_get_ex(val
, "firstHopRouter",
1392 vty_out(vty
, "%3d ", json_object_get_int(json_tmp
));
1394 json_object_object_get_ex(val
, "pimIfChannels",
1396 vty_out(vty
, "%9d\n", json_object_get_int(json_tmp
));
1400 json_object_free(json
);
1403 static void pim_show_interface_traffic(struct pim_instance
*pim
,
1404 struct vty
*vty
, u_char uj
)
1406 struct interface
*ifp
= NULL
;
1407 struct pim_interface
*pim_ifp
= NULL
;
1408 json_object
*json
= NULL
;
1409 json_object
*json_row
= NULL
;
1412 json
= json_object_new_object();
1415 vty_out(vty
, "%-12s%-17s%-17s%-17s%-17s%-17s%-17s\n",
1416 "Interface", " HELLO", " JOIN", " PRUNE",
1417 " REGISTER", " REGISTER-STOP", " ASSERT");
1418 vty_out(vty
, "%-10s%-18s%-17s%-17s%-17s%-17s%-17s\n", "",
1419 " Rx/Tx", " Rx/Tx", " Rx/Tx", " Rx/Tx",
1420 " Rx/Tx", " Rx/Tx");
1422 "---------------------------------------------------------------------------------------------------------------\n");
1425 FOR_ALL_INTERFACES (pim
->vrf
, ifp
) {
1426 pim_ifp
= ifp
->info
;
1431 if (pim_ifp
->pim_sock_fd
< 0)
1434 json_row
= json_object_new_object();
1435 json_object_pim_ifp_add(json_row
, ifp
);
1436 json_object_int_add(json_row
, "helloRx",
1437 pim_ifp
->pim_ifstat_hello_recv
);
1438 json_object_int_add(json_row
, "helloTx",
1439 pim_ifp
->pim_ifstat_hello_sent
);
1440 json_object_int_add(json_row
, "joinRx",
1441 pim_ifp
->pim_ifstat_join_recv
);
1442 json_object_int_add(json_row
, "joinTx",
1443 pim_ifp
->pim_ifstat_join_send
);
1444 json_object_int_add(json_row
, "registerRx",
1445 pim_ifp
->pim_ifstat_reg_recv
);
1446 json_object_int_add(json_row
, "registerTx",
1447 pim_ifp
->pim_ifstat_reg_recv
);
1448 json_object_int_add(json_row
, "registerStopRx",
1449 pim_ifp
->pim_ifstat_reg_stop_recv
);
1450 json_object_int_add(json_row
, "registerStopTx",
1451 pim_ifp
->pim_ifstat_reg_stop_send
);
1452 json_object_int_add(json_row
, "assertRx",
1453 pim_ifp
->pim_ifstat_assert_recv
);
1454 json_object_int_add(json_row
, "assertTx",
1455 pim_ifp
->pim_ifstat_assert_send
);
1457 json_object_object_add(json
, ifp
->name
, json_row
);
1460 "%-10s %8u/%-8u %7u/%-7u %7u/%-7u %7u/%-7u %7u/%-7u %7u/%-7u \n",
1461 ifp
->name
, pim_ifp
->pim_ifstat_hello_recv
,
1462 pim_ifp
->pim_ifstat_hello_sent
,
1463 pim_ifp
->pim_ifstat_join_recv
,
1464 pim_ifp
->pim_ifstat_join_send
,
1465 pim_ifp
->pim_ifstat_prune_recv
,
1466 pim_ifp
->pim_ifstat_prune_send
,
1467 pim_ifp
->pim_ifstat_reg_recv
,
1468 pim_ifp
->pim_ifstat_reg_send
,
1469 pim_ifp
->pim_ifstat_reg_stop_recv
,
1470 pim_ifp
->pim_ifstat_reg_stop_send
,
1471 pim_ifp
->pim_ifstat_assert_recv
,
1472 pim_ifp
->pim_ifstat_assert_send
);
1476 vty_out(vty
, "%s\n", json_object_to_json_string_ext(
1477 json
, JSON_C_TO_STRING_PRETTY
));
1478 json_object_free(json
);
1482 static void pim_show_interface_traffic_single(struct pim_instance
*pim
,
1484 const char *ifname
, u_char uj
)
1486 struct interface
*ifp
= NULL
;
1487 struct pim_interface
*pim_ifp
= NULL
;
1488 json_object
*json
= NULL
;
1489 json_object
*json_row
= NULL
;
1490 uint8_t found_ifname
= 0;
1493 json
= json_object_new_object();
1496 vty_out(vty
, "%-12s%-17s%-17s%-17s%-17s%-17s%-17s\n",
1497 "Interface", " HELLO", " JOIN", " PRUNE",
1498 " REGISTER", " REGISTER-STOP", " ASSERT");
1499 vty_out(vty
, "%-10s%-18s%-17s%-17s%-17s%-17s%-17s\n", "",
1500 " Rx/Tx", " Rx/Tx", " Rx/Tx", " Rx/Tx",
1501 " Rx/Tx", " Rx/Tx");
1503 "---------------------------------------------------------------------------------------------------------------\n");
1506 FOR_ALL_INTERFACES (pim
->vrf
, ifp
) {
1507 if (strcmp(ifname
, ifp
->name
))
1510 pim_ifp
= ifp
->info
;
1515 if (pim_ifp
->pim_sock_fd
< 0)
1520 json_row
= json_object_new_object();
1521 json_object_pim_ifp_add(json_row
, ifp
);
1522 json_object_int_add(json_row
, "helloRx",
1523 pim_ifp
->pim_ifstat_hello_recv
);
1524 json_object_int_add(json_row
, "helloTx",
1525 pim_ifp
->pim_ifstat_hello_sent
);
1526 json_object_int_add(json_row
, "joinRx",
1527 pim_ifp
->pim_ifstat_join_recv
);
1528 json_object_int_add(json_row
, "joinTx",
1529 pim_ifp
->pim_ifstat_join_send
);
1530 json_object_int_add(json_row
, "registerRx",
1531 pim_ifp
->pim_ifstat_reg_recv
);
1532 json_object_int_add(json_row
, "registerTx",
1533 pim_ifp
->pim_ifstat_reg_recv
);
1534 json_object_int_add(json_row
, "registerStopRx",
1535 pim_ifp
->pim_ifstat_reg_stop_recv
);
1536 json_object_int_add(json_row
, "registerStopTx",
1537 pim_ifp
->pim_ifstat_reg_stop_send
);
1538 json_object_int_add(json_row
, "assertRx",
1539 pim_ifp
->pim_ifstat_assert_recv
);
1540 json_object_int_add(json_row
, "assertTx",
1541 pim_ifp
->pim_ifstat_assert_send
);
1543 json_object_object_add(json
, ifp
->name
, json_row
);
1546 "%-10s %8u/%-8u %7u/%-7u %7u/%-7u %7u/%-7u %7u/%-7u %7u/%-7u \n",
1547 ifp
->name
, pim_ifp
->pim_ifstat_hello_recv
,
1548 pim_ifp
->pim_ifstat_hello_sent
,
1549 pim_ifp
->pim_ifstat_join_recv
,
1550 pim_ifp
->pim_ifstat_join_send
,
1551 pim_ifp
->pim_ifstat_prune_recv
,
1552 pim_ifp
->pim_ifstat_prune_send
,
1553 pim_ifp
->pim_ifstat_reg_recv
,
1554 pim_ifp
->pim_ifstat_reg_send
,
1555 pim_ifp
->pim_ifstat_reg_stop_recv
,
1556 pim_ifp
->pim_ifstat_reg_stop_send
,
1557 pim_ifp
->pim_ifstat_assert_recv
,
1558 pim_ifp
->pim_ifstat_assert_send
);
1562 vty_out(vty
, "%s\n", json_object_to_json_string_ext(
1563 json
, JSON_C_TO_STRING_PRETTY
));
1564 json_object_free(json
);
1567 vty_out(vty
, "%% No such interface\n");
1571 static void pim_show_join_helper(struct vty
*vty
,
1572 struct pim_interface
*pim_ifp
,
1573 struct pim_ifchannel
*ch
,
1578 char ch_src_str
[INET_ADDRSTRLEN
];
1579 char ch_grp_str
[INET_ADDRSTRLEN
];
1580 json_object
*json_iface
= NULL
;
1581 json_object
*json_row
= NULL
;
1582 json_object
*json_grp
= NULL
;
1583 struct in_addr ifaddr
;
1588 ifaddr
= pim_ifp
->primary_address
;
1590 pim_inet4_dump("<ch_src?>", ch
->sg
.src
, ch_src_str
,
1591 sizeof(ch_src_str
));
1592 pim_inet4_dump("<ch_grp?>", ch
->sg
.grp
, ch_grp_str
,
1593 sizeof(ch_grp_str
));
1595 pim_time_uptime_begin(uptime
, sizeof(uptime
), now
,
1596 ch
->ifjoin_creation
);
1597 pim_time_timer_to_mmss(expire
, sizeof(expire
),
1598 ch
->t_ifjoin_expiry_timer
);
1599 pim_time_timer_to_mmss(prune
, sizeof(prune
),
1600 ch
->t_ifjoin_prune_pending_timer
);
1603 json_object_object_get_ex(json
, ch
->interface
->name
,
1607 json_iface
= json_object_new_object();
1608 json_object_pim_ifp_add(json_iface
,
1610 json_object_object_add(
1611 json
, ch
->interface
->name
, json_iface
);
1614 json_row
= json_object_new_object();
1615 json_object_string_add(json_row
, "source", ch_src_str
);
1616 json_object_string_add(json_row
, "group", ch_grp_str
);
1617 json_object_string_add(json_row
, "upTime", uptime
);
1618 json_object_string_add(json_row
, "expire", expire
);
1619 json_object_string_add(json_row
, "prune", prune
);
1620 json_object_string_add(
1621 json_row
, "channelJoinName",
1622 pim_ifchannel_ifjoin_name(ch
->ifjoin_state
,
1624 if (PIM_IF_FLAG_TEST_S_G_RPT(ch
->flags
))
1625 json_object_int_add(json_row
, "SGRpt", 1);
1627 json_object_object_get_ex(json_iface
, ch_grp_str
,
1630 json_grp
= json_object_new_object();
1631 json_object_object_add(json_grp
, ch_src_str
,
1633 json_object_object_add(json_iface
, ch_grp_str
,
1636 json_object_object_add(json_grp
, ch_src_str
,
1640 "%-9s %-15s %-15s %-15s %-10s %8s %-6s %5s\n",
1641 ch
->interface
->name
, inet_ntoa(ifaddr
),
1642 ch_src_str
, ch_grp_str
,
1643 pim_ifchannel_ifjoin_name(ch
->ifjoin_state
,
1645 uptime
, expire
, prune
);
1649 static void pim_show_join(struct pim_instance
*pim
, struct vty
*vty
, u_char uj
)
1651 struct pim_interface
*pim_ifp
;
1652 struct pim_ifchannel
*ch
;
1653 struct interface
*ifp
;
1655 json_object
*json
= NULL
;
1657 now
= pim_time_monotonic_sec();
1660 json
= json_object_new_object();
1663 "Interface Address Source Group State Uptime Expire Prune\n");
1665 FOR_ALL_INTERFACES (pim
->vrf
, ifp
) {
1666 pim_ifp
= ifp
->info
;
1670 RB_FOREACH (ch
, pim_ifchannel_rb
, &pim_ifp
->ifchannel_rb
) {
1671 pim_show_join_helper(vty
, pim_ifp
, ch
, json
, now
, uj
);
1672 } /* scan interface channels */
1676 vty_out(vty
, "%s\n", json_object_to_json_string_ext(
1677 json
, JSON_C_TO_STRING_PRETTY
));
1678 json_object_free(json
);
1682 static void pim_show_neighbors_single(struct pim_instance
*pim
, struct vty
*vty
,
1683 const char *neighbor
, u_char uj
)
1685 struct listnode
*neighnode
;
1686 struct interface
*ifp
;
1687 struct pim_interface
*pim_ifp
;
1688 struct pim_neighbor
*neigh
;
1690 int found_neighbor
= 0;
1691 int option_address_list
;
1692 int option_dr_priority
;
1693 int option_generation_id
;
1694 int option_holdtime
;
1695 int option_lan_prune_delay
;
1699 char neigh_src_str
[INET_ADDRSTRLEN
];
1701 json_object
*json
= NULL
;
1702 json_object
*json_ifp
= NULL
;
1703 json_object
*json_row
= NULL
;
1705 now
= pim_time_monotonic_sec();
1708 json
= json_object_new_object();
1710 FOR_ALL_INTERFACES (pim
->vrf
, ifp
) {
1711 pim_ifp
= ifp
->info
;
1716 if (pim_ifp
->pim_sock_fd
< 0)
1719 for (ALL_LIST_ELEMENTS_RO(pim_ifp
->pim_neighbor_list
, neighnode
,
1721 pim_inet4_dump("<src?>", neigh
->source_addr
,
1722 neigh_src_str
, sizeof(neigh_src_str
));
1725 * The user can specify either the interface name or the
1727 * If this pim_ifp matches neither then skip.
1729 if (strcmp(neighbor
, "detail")
1730 && strcmp(neighbor
, ifp
->name
)
1731 && strcmp(neighbor
, neigh_src_str
))
1735 pim_time_uptime(uptime
, sizeof(uptime
),
1736 now
- neigh
->creation
);
1737 pim_time_timer_to_hhmmss(expire
, sizeof(expire
),
1738 neigh
->t_expire_timer
);
1740 option_address_list
= 0;
1741 option_dr_priority
= 0;
1742 option_generation_id
= 0;
1743 option_holdtime
= 0;
1744 option_lan_prune_delay
= 0;
1747 if (PIM_OPTION_IS_SET(neigh
->hello_options
,
1748 PIM_OPTION_MASK_ADDRESS_LIST
))
1749 option_address_list
= 1;
1751 if (PIM_OPTION_IS_SET(neigh
->hello_options
,
1752 PIM_OPTION_MASK_DR_PRIORITY
))
1753 option_dr_priority
= 1;
1755 if (PIM_OPTION_IS_SET(neigh
->hello_options
,
1756 PIM_OPTION_MASK_GENERATION_ID
))
1757 option_generation_id
= 1;
1759 if (PIM_OPTION_IS_SET(neigh
->hello_options
,
1760 PIM_OPTION_MASK_HOLDTIME
))
1761 option_holdtime
= 1;
1763 if (PIM_OPTION_IS_SET(neigh
->hello_options
,
1764 PIM_OPTION_MASK_LAN_PRUNE_DELAY
))
1765 option_lan_prune_delay
= 1;
1767 if (PIM_OPTION_IS_SET(
1768 neigh
->hello_options
,
1769 PIM_OPTION_MASK_CAN_DISABLE_JOIN_SUPPRESSION
))
1774 /* Does this ifp live in json? If not create
1776 json_object_object_get_ex(json
, ifp
->name
,
1780 json_ifp
= json_object_new_object();
1781 json_object_pim_ifp_add(json_ifp
, ifp
);
1782 json_object_object_add(json
, ifp
->name
,
1786 json_row
= json_object_new_object();
1787 json_object_string_add(json_row
, "interface",
1789 json_object_string_add(json_row
, "address",
1791 json_object_string_add(json_row
, "upTime",
1793 json_object_string_add(json_row
, "holdtime",
1795 json_object_int_add(json_row
, "drPriority",
1796 neigh
->dr_priority
);
1797 json_object_int_add(json_row
, "generationId",
1798 neigh
->generation_id
);
1800 if (option_address_list
)
1801 json_object_boolean_true_add(
1803 "helloOptionAddressList");
1805 if (option_dr_priority
)
1806 json_object_boolean_true_add(
1808 "helloOptionDrPriority");
1810 if (option_generation_id
)
1811 json_object_boolean_true_add(
1813 "helloOptionGenerationId");
1815 if (option_holdtime
)
1816 json_object_boolean_true_add(
1818 "helloOptionHoldtime");
1820 if (option_lan_prune_delay
)
1821 json_object_boolean_true_add(
1823 "helloOptionLanPruneDelay");
1826 json_object_boolean_true_add(
1827 json_row
, "helloOptionTBit");
1829 json_object_object_add(json_ifp
, neigh_src_str
,
1833 vty_out(vty
, "Interface : %s\n", ifp
->name
);
1834 vty_out(vty
, "Neighbor : %s\n", neigh_src_str
);
1842 " DR Priority : %d\n",
1843 neigh
->dr_priority
);
1845 " Generation ID : %08x\n",
1846 neigh
->generation_id
);
1848 " Override Interval (msec) : %d\n",
1849 neigh
->override_interval_msec
);
1851 " Propagation Delay (msec) : %d\n",
1852 neigh
->propagation_delay_msec
);
1854 " Hello Option - Address List : %s\n",
1855 option_address_list
? "yes" : "no");
1857 " Hello Option - DR Priority : %s\n",
1858 option_dr_priority
? "yes" : "no");
1860 " Hello Option - Generation ID : %s\n",
1861 option_generation_id
? "yes" : "no");
1863 " Hello Option - Holdtime : %s\n",
1864 option_holdtime
? "yes" : "no");
1866 " Hello Option - LAN Prune Delay : %s\n",
1867 option_lan_prune_delay
? "yes" : "no");
1869 " Hello Option - T-bit : %s\n",
1870 option_t_bit
? "yes" : "no");
1871 pim_bfd_show_info(vty
, neigh
->bfd_info
,
1879 vty_out(vty
, "%s\n", json_object_to_json_string_ext(
1880 json
, JSON_C_TO_STRING_PRETTY
));
1881 json_object_free(json
);
1884 if (!found_neighbor
)
1886 "%% No such interface or neighbor\n");
1891 static void pim_show_state(struct pim_instance
*pim
, struct vty
*vty
,
1892 const char *src_or_group
, const char *group
,
1895 struct channel_oil
*c_oil
;
1896 struct listnode
*node
;
1897 json_object
*json
= NULL
;
1898 json_object
*json_group
= NULL
;
1899 json_object
*json_ifp_in
= NULL
;
1900 json_object
*json_ifp_out
= NULL
;
1901 json_object
*json_source
= NULL
;
1904 now
= pim_time_monotonic_sec();
1907 json
= json_object_new_object();
1910 "Codes: J -> Pim Join, I -> IGMP Report, S -> Source, * -> Inherited from (*,G)");
1912 "\nInstalled Source Group IIF OIL\n");
1915 for (ALL_LIST_ELEMENTS_RO(pim
->channel_oil_list
, node
, c_oil
)) {
1916 char grp_str
[INET_ADDRSTRLEN
];
1917 char src_str
[INET_ADDRSTRLEN
];
1918 char in_ifname
[INTERFACE_NAMSIZ
+ 1];
1919 char out_ifname
[INTERFACE_NAMSIZ
+ 1];
1921 struct interface
*ifp_in
;
1924 pim_inet4_dump("<group?>", c_oil
->oil
.mfcc_mcastgrp
, grp_str
,
1926 pim_inet4_dump("<source?>", c_oil
->oil
.mfcc_origin
, src_str
,
1928 ifp_in
= pim_if_find_by_vif_index(pim
, c_oil
->oil
.mfcc_parent
);
1931 strcpy(in_ifname
, ifp_in
->name
);
1933 strcpy(in_ifname
, "<iif?>");
1936 if (strcmp(src_or_group
, src_str
)
1937 && strcmp(src_or_group
, grp_str
))
1940 if (group
&& strcmp(group
, grp_str
))
1946 /* Find the group, create it if it doesn't exist */
1947 json_object_object_get_ex(json
, grp_str
, &json_group
);
1950 json_group
= json_object_new_object();
1951 json_object_object_add(json
, grp_str
,
1955 /* Find the source nested under the group, create it if
1956 * it doesn't exist */
1957 json_object_object_get_ex(json_group
, src_str
,
1961 json_source
= json_object_new_object();
1962 json_object_object_add(json_group
, src_str
,
1966 /* Find the inbound interface nested under the source,
1967 * create it if it doesn't exist */
1968 json_object_object_get_ex(json_source
, in_ifname
,
1972 json_ifp_in
= json_object_new_object();
1973 json_object_object_add(json_source
, in_ifname
,
1975 json_object_int_add(json_source
, "Installed",
1977 json_object_int_add(json_source
, "RefCount",
1978 c_oil
->oil_ref_count
);
1979 json_object_int_add(json_source
, "OilListSize",
1981 json_object_int_add(
1982 json_source
, "OilRescan",
1983 c_oil
->oil_inherited_rescan
);
1984 json_object_int_add(json_source
, "LastUsed",
1985 c_oil
->cc
.lastused
);
1986 json_object_int_add(json_source
, "PacketCount",
1988 json_object_int_add(json_source
, "ByteCount",
1990 json_object_int_add(json_source
,
1992 c_oil
->cc
.wrong_if
);
1995 vty_out(vty
, "%-9d %-15s %-15s %-7s ",
1996 c_oil
->installed
, src_str
, grp_str
,
2000 for (oif_vif_index
= 0; oif_vif_index
< MAXVIFS
;
2002 struct interface
*ifp_out
;
2003 char oif_uptime
[10];
2006 ttl
= c_oil
->oil
.mfcc_ttls
[oif_vif_index
];
2010 ifp_out
= pim_if_find_by_vif_index(pim
, oif_vif_index
);
2012 oif_uptime
, sizeof(oif_uptime
),
2013 now
- c_oil
->oif_creation
[oif_vif_index
]);
2016 strcpy(out_ifname
, ifp_out
->name
);
2018 strcpy(out_ifname
, "<oif?>");
2021 json_ifp_out
= json_object_new_object();
2022 json_object_string_add(json_ifp_out
, "source",
2024 json_object_string_add(json_ifp_out
, "group",
2026 json_object_string_add(json_ifp_out
,
2029 json_object_string_add(json_ifp_out
,
2030 "outboundInterface",
2032 json_object_int_add(json_ifp_out
, "installed",
2035 json_object_object_add(json_ifp_in
, out_ifname
,
2040 vty_out(vty
, "%s(%c%c%c%c)", out_ifname
,
2041 (c_oil
->oif_flags
[oif_vif_index
]
2042 & PIM_OIF_FLAG_PROTO_IGMP
)
2045 (c_oil
->oif_flags
[oif_vif_index
]
2046 & PIM_OIF_FLAG_PROTO_PIM
)
2049 (c_oil
->oif_flags
[oif_vif_index
]
2050 & PIM_OIF_FLAG_PROTO_SOURCE
)
2053 (c_oil
->oif_flags
[oif_vif_index
]
2054 & PIM_OIF_FLAG_PROTO_STAR
)
2058 vty_out(vty
, ", %s(%c%c%c%c)",
2060 (c_oil
->oif_flags
[oif_vif_index
]
2061 & PIM_OIF_FLAG_PROTO_IGMP
)
2064 (c_oil
->oif_flags
[oif_vif_index
]
2065 & PIM_OIF_FLAG_PROTO_PIM
)
2068 (c_oil
->oif_flags
[oif_vif_index
]
2069 & PIM_OIF_FLAG_PROTO_SOURCE
)
2072 (c_oil
->oif_flags
[oif_vif_index
]
2073 & PIM_OIF_FLAG_PROTO_STAR
)
2085 vty_out(vty
, "%s\n", json_object_to_json_string_ext(
2086 json
, JSON_C_TO_STRING_PRETTY
));
2087 json_object_free(json
);
2093 static void pim_show_neighbors(struct pim_instance
*pim
, struct vty
*vty
,
2096 struct listnode
*neighnode
;
2097 struct interface
*ifp
;
2098 struct pim_interface
*pim_ifp
;
2099 struct pim_neighbor
*neigh
;
2103 char neigh_src_str
[INET_ADDRSTRLEN
];
2104 json_object
*json
= NULL
;
2105 json_object
*json_ifp_rows
= NULL
;
2106 json_object
*json_row
= NULL
;
2108 now
= pim_time_monotonic_sec();
2111 json
= json_object_new_object();
2114 "Interface Neighbor Uptime Holdtime DR Pri\n");
2117 FOR_ALL_INTERFACES (pim
->vrf
, ifp
) {
2118 pim_ifp
= ifp
->info
;
2123 if (pim_ifp
->pim_sock_fd
< 0)
2127 json_ifp_rows
= json_object_new_object();
2129 for (ALL_LIST_ELEMENTS_RO(pim_ifp
->pim_neighbor_list
, neighnode
,
2131 pim_inet4_dump("<src?>", neigh
->source_addr
,
2132 neigh_src_str
, sizeof(neigh_src_str
));
2133 pim_time_uptime(uptime
, sizeof(uptime
),
2134 now
- neigh
->creation
);
2135 pim_time_timer_to_hhmmss(expire
, sizeof(expire
),
2136 neigh
->t_expire_timer
);
2139 json_row
= json_object_new_object();
2140 json_object_string_add(json_row
, "interface",
2142 json_object_string_add(json_row
, "neighbor",
2144 json_object_string_add(json_row
, "upTime",
2146 json_object_string_add(json_row
, "holdTime",
2148 json_object_int_add(json_row
, "holdTimeMax",
2150 json_object_int_add(json_row
, "drPriority",
2151 neigh
->dr_priority
);
2152 json_object_object_add(json_ifp_rows
,
2153 neigh_src_str
, json_row
);
2156 vty_out(vty
, "%-9s %15s %8s %8s %6d\n",
2157 ifp
->name
, neigh_src_str
, uptime
,
2158 expire
, neigh
->dr_priority
);
2163 json_object_object_add(json
, ifp
->name
, json_ifp_rows
);
2164 json_ifp_rows
= NULL
;
2169 vty_out(vty
, "%s\n", json_object_to_json_string_ext(
2170 json
, JSON_C_TO_STRING_PRETTY
));
2171 json_object_free(json
);
2175 static void pim_show_neighbors_secondary(struct pim_instance
*pim
,
2178 struct interface
*ifp
;
2181 "Interface Address Neighbor Secondary \n");
2183 FOR_ALL_INTERFACES (pim
->vrf
, ifp
) {
2184 struct pim_interface
*pim_ifp
;
2185 struct in_addr ifaddr
;
2186 struct listnode
*neighnode
;
2187 struct pim_neighbor
*neigh
;
2189 pim_ifp
= ifp
->info
;
2194 if (pim_ifp
->pim_sock_fd
< 0)
2197 ifaddr
= pim_ifp
->primary_address
;
2199 for (ALL_LIST_ELEMENTS_RO(pim_ifp
->pim_neighbor_list
, neighnode
,
2201 char neigh_src_str
[INET_ADDRSTRLEN
];
2202 struct listnode
*prefix_node
;
2205 if (!neigh
->prefix_list
)
2208 pim_inet4_dump("<src?>", neigh
->source_addr
,
2209 neigh_src_str
, sizeof(neigh_src_str
));
2211 for (ALL_LIST_ELEMENTS_RO(neigh
->prefix_list
,
2213 char neigh_sec_str
[PREFIX2STR_BUFFER
];
2215 prefix2str(p
, neigh_sec_str
,
2216 sizeof(neigh_sec_str
));
2218 vty_out(vty
, "%-9s %-15s %-15s %-15s\n",
2219 ifp
->name
, inet_ntoa(ifaddr
),
2220 neigh_src_str
, neigh_sec_str
);
2226 static void json_object_pim_upstream_add(json_object
*json
,
2227 struct pim_upstream
*up
)
2229 if (up
->flags
& PIM_UPSTREAM_FLAG_MASK_DR_JOIN_DESIRED
)
2230 json_object_boolean_true_add(json
, "drJoinDesired");
2232 if (up
->flags
& PIM_UPSTREAM_FLAG_MASK_DR_JOIN_DESIRED_UPDATED
)
2233 json_object_boolean_true_add(json
, "drJoinDesiredUpdated");
2235 if (up
->flags
& PIM_UPSTREAM_FLAG_MASK_FHR
)
2236 json_object_boolean_true_add(json
, "firstHopRouter");
2238 if (up
->flags
& PIM_UPSTREAM_FLAG_MASK_SRC_IGMP
)
2239 json_object_boolean_true_add(json
, "sourceIgmp");
2241 if (up
->flags
& PIM_UPSTREAM_FLAG_MASK_SRC_PIM
)
2242 json_object_boolean_true_add(json
, "sourcePim");
2244 if (up
->flags
& PIM_UPSTREAM_FLAG_MASK_SRC_STREAM
)
2245 json_object_boolean_true_add(json
, "sourceStream");
2247 /* XXX: need to print ths flag in the plain text display as well */
2248 if (up
->flags
& PIM_UPSTREAM_FLAG_MASK_SRC_MSDP
)
2249 json_object_boolean_true_add(json
, "sourceMsdp");
2253 pim_upstream_state2brief_str(enum pim_upstream_state join_state
,
2256 switch (join_state
) {
2257 case PIM_UPSTREAM_NOTJOINED
:
2258 strcpy(state_str
, "NotJ");
2260 case PIM_UPSTREAM_JOINED
:
2261 strcpy(state_str
, "J");
2264 strcpy(state_str
, "Unk");
2269 static const char *pim_reg_state2brief_str(enum pim_reg_state reg_state
,
2272 switch (reg_state
) {
2273 case PIM_REG_NOINFO
:
2274 strcpy(state_str
, "RegNI");
2277 strcpy(state_str
, "RegJ");
2279 case PIM_REG_JOIN_PENDING
:
2281 strcpy(state_str
, "RegP");
2284 strcpy(state_str
, "Unk");
2289 static void pim_show_upstream(struct pim_instance
*pim
, struct vty
*vty
,
2292 struct listnode
*upnode
;
2293 struct pim_upstream
*up
;
2295 json_object
*json
= NULL
;
2296 json_object
*json_group
= NULL
;
2297 json_object
*json_row
= NULL
;
2299 now
= pim_time_monotonic_sec();
2302 json
= json_object_new_object();
2305 "Iif Source Group State Uptime JoinTimer RSTimer KATimer RefCnt\n");
2307 for (ALL_LIST_ELEMENTS_RO(pim
->upstream_list
, upnode
, up
)) {
2308 char src_str
[INET_ADDRSTRLEN
];
2309 char grp_str
[INET_ADDRSTRLEN
];
2311 char join_timer
[10];
2314 char msdp_reg_timer
[10];
2315 char state_str
[PIM_REG_STATE_STR_LEN
];
2317 pim_inet4_dump("<src?>", up
->sg
.src
, src_str
, sizeof(src_str
));
2318 pim_inet4_dump("<grp?>", up
->sg
.grp
, grp_str
, sizeof(grp_str
));
2319 pim_time_uptime(uptime
, sizeof(uptime
),
2320 now
- up
->state_transition
);
2321 pim_time_timer_to_hhmmss(join_timer
, sizeof(join_timer
),
2325 * If we have a J/P timer for the neighbor display that
2327 if (!up
->t_join_timer
) {
2328 struct pim_neighbor
*nbr
;
2330 nbr
= pim_neighbor_find(
2331 up
->rpf
.source_nexthop
.interface
,
2332 up
->rpf
.rpf_addr
.u
.prefix4
);
2334 pim_time_timer_to_hhmmss(join_timer
,
2339 pim_time_timer_to_hhmmss(rs_timer
, sizeof(rs_timer
),
2341 pim_time_timer_to_hhmmss(ka_timer
, sizeof(ka_timer
),
2343 pim_time_timer_to_hhmmss(msdp_reg_timer
, sizeof(msdp_reg_timer
),
2344 up
->t_msdp_reg_timer
);
2346 pim_upstream_state2brief_str(up
->join_state
, state_str
);
2347 if (up
->reg_state
!= PIM_REG_NOINFO
) {
2348 char tmp_str
[PIM_REG_STATE_STR_LEN
];
2350 sprintf(state_str
+ strlen(state_str
), ",%s",
2351 pim_reg_state2brief_str(up
->reg_state
,
2356 json_object_object_get_ex(json
, grp_str
, &json_group
);
2359 json_group
= json_object_new_object();
2360 json_object_object_add(json
, grp_str
,
2364 json_row
= json_object_new_object();
2365 json_object_pim_upstream_add(json_row
, up
);
2366 json_object_string_add(
2367 json_row
, "inboundInterface",
2368 up
->rpf
.source_nexthop
.interface
->name
);
2371 * The RPF address we use is slightly different
2372 * based upon what we are looking up.
2373 * If we have a S, list that unless
2374 * we are the FHR, else we just put
2375 * the RP as the rpfAddress
2377 if (up
->flags
& PIM_UPSTREAM_FLAG_MASK_FHR
||
2378 up
->sg
.src
.s_addr
== INADDR_ANY
) {
2379 char rpf
[PREFIX_STRLEN
];
2380 struct pim_rpf
*rpg
;
2382 rpg
= RP(pim
, up
->sg
.grp
);
2383 pim_inet4_dump("<rpf?>",
2384 rpg
->rpf_addr
.u
.prefix4
,
2386 json_object_string_add(json_row
,
2389 json_object_string_add(json_row
,
2390 "rpfAddress", src_str
);
2393 json_object_string_add(json_row
, "source", src_str
);
2394 json_object_string_add(json_row
, "group", grp_str
);
2395 json_object_string_add(json_row
, "state", state_str
);
2396 json_object_string_add(
2397 json_row
, "joinState",
2398 pim_upstream_state2str(up
->join_state
));
2399 json_object_string_add(
2400 json_row
, "regState",
2401 pim_reg_state2str(up
->reg_state
, state_str
));
2402 json_object_string_add(json_row
, "upTime", uptime
);
2403 json_object_string_add(json_row
, "joinTimer",
2405 json_object_string_add(json_row
, "resetTimer",
2407 json_object_string_add(json_row
, "keepaliveTimer",
2409 json_object_string_add(json_row
, "msdpRegTimer",
2411 json_object_int_add(json_row
, "refCount",
2413 json_object_int_add(json_row
, "sptBit", up
->sptbit
);
2414 json_object_object_add(json_group
, src_str
, json_row
);
2417 "%-10s%-15s %-15s %-11s %-8s %-9s %-9s %-9s %6d\n",
2418 up
->rpf
.source_nexthop
.interface
->name
, src_str
,
2419 grp_str
, state_str
, uptime
, join_timer
,
2420 rs_timer
, ka_timer
, up
->ref_count
);
2425 vty_out(vty
, "%s\n", json_object_to_json_string_ext(
2426 json
, JSON_C_TO_STRING_PRETTY
));
2427 json_object_free(json
);
2431 static void pim_show_join_desired_helper(struct pim_instance
*pim
,
2433 struct pim_interface
*pim_ifp
,
2434 struct pim_ifchannel
*ch
,
2438 struct pim_upstream
*up
= ch
->upstream
;
2439 json_object
*json_group
= NULL
;
2440 char src_str
[INET_ADDRSTRLEN
];
2441 char grp_str
[INET_ADDRSTRLEN
];
2442 json_object
*json_row
= NULL
;
2444 pim_inet4_dump("<src?>", up
->sg
.src
, src_str
, sizeof(src_str
));
2445 pim_inet4_dump("<grp?>", up
->sg
.grp
, grp_str
, sizeof(grp_str
));
2448 json_object_object_get_ex(json
, grp_str
, &json_group
);
2451 json_group
= json_object_new_object();
2452 json_object_object_add(json
, grp_str
,
2456 json_row
= json_object_new_object();
2457 json_object_pim_upstream_add(json_row
, up
);
2458 json_object_string_add(json_row
, "interface",
2459 ch
->interface
->name
);
2460 json_object_string_add(json_row
, "source", src_str
);
2461 json_object_string_add(json_row
, "group", grp_str
);
2463 if (pim_macro_ch_lost_assert(ch
))
2464 json_object_boolean_true_add(json_row
,
2467 if (pim_macro_chisin_joins(ch
))
2468 json_object_boolean_true_add(json_row
, "joins");
2470 if (pim_macro_chisin_pim_include(ch
))
2471 json_object_boolean_true_add(json_row
,
2474 if (pim_upstream_evaluate_join_desired(pim
, up
))
2475 json_object_boolean_true_add(
2476 json_row
, "evaluateJoinDesired");
2478 json_object_object_add(json_group
, src_str
, json_row
);
2482 "%-9s %-15s %-15s %-10s %-5s %-10s %-11s %-6s\n",
2483 ch
->interface
->name
, src_str
, grp_str
,
2484 pim_macro_ch_lost_assert(ch
) ? "yes" : "no",
2485 pim_macro_chisin_joins(ch
) ? "yes" : "no",
2486 pim_macro_chisin_pim_include(ch
) ? "yes" : "no",
2487 PIM_UPSTREAM_FLAG_TEST_DR_JOIN_DESIRED(
2491 pim_upstream_evaluate_join_desired(pim
, up
)
2497 static void pim_show_join_desired(struct pim_instance
*pim
, struct vty
*vty
,
2500 struct pim_interface
*pim_ifp
;
2501 struct pim_ifchannel
*ch
;
2502 struct interface
*ifp
;
2504 json_object
*json
= NULL
;
2507 json
= json_object_new_object();
2510 "Interface Source Group LostAssert Joins PimInclude JoinDesired EvalJD\n");
2512 /* scan per-interface (S,G) state */
2513 FOR_ALL_INTERFACES (pim
->vrf
, ifp
) {
2514 pim_ifp
= ifp
->info
;
2519 RB_FOREACH (ch
, pim_ifchannel_rb
, &pim_ifp
->ifchannel_rb
) {
2520 /* scan all interfaces */
2521 pim_show_join_desired_helper(pim
, vty
,
2528 vty_out(vty
, "%s\n", json_object_to_json_string_ext(
2529 json
, JSON_C_TO_STRING_PRETTY
));
2530 json_object_free(json
);
2534 static void pim_show_upstream_rpf(struct pim_instance
*pim
, struct vty
*vty
,
2537 struct listnode
*upnode
;
2538 struct pim_upstream
*up
;
2539 json_object
*json
= NULL
;
2540 json_object
*json_group
= NULL
;
2541 json_object
*json_row
= NULL
;
2544 json
= json_object_new_object();
2547 "Source Group RpfIface RibNextHop RpfAddress \n");
2549 for (ALL_LIST_ELEMENTS_RO(pim
->upstream_list
, upnode
, up
)) {
2550 char src_str
[INET_ADDRSTRLEN
];
2551 char grp_str
[INET_ADDRSTRLEN
];
2552 char rpf_nexthop_str
[PREFIX_STRLEN
];
2553 char rpf_addr_str
[PREFIX_STRLEN
];
2554 struct pim_rpf
*rpf
;
2555 const char *rpf_ifname
;
2559 pim_inet4_dump("<src?>", up
->sg
.src
, src_str
, sizeof(src_str
));
2560 pim_inet4_dump("<grp?>", up
->sg
.grp
, grp_str
, sizeof(grp_str
));
2561 pim_addr_dump("<nexthop?>",
2562 &rpf
->source_nexthop
.mrib_nexthop_addr
,
2563 rpf_nexthop_str
, sizeof(rpf_nexthop_str
));
2564 pim_addr_dump("<rpf?>", &rpf
->rpf_addr
, rpf_addr_str
,
2565 sizeof(rpf_addr_str
));
2567 rpf_ifname
= rpf
->source_nexthop
.interface
? rpf
->source_nexthop
.interface
->name
: "<ifname?>";
2570 json_object_object_get_ex(json
, grp_str
, &json_group
);
2573 json_group
= json_object_new_object();
2574 json_object_object_add(json
, grp_str
,
2578 json_row
= json_object_new_object();
2579 json_object_pim_upstream_add(json_row
, up
);
2580 json_object_string_add(json_row
, "source", src_str
);
2581 json_object_string_add(json_row
, "group", grp_str
);
2582 json_object_string_add(json_row
, "rpfInterface",
2584 json_object_string_add(json_row
, "ribNexthop",
2586 json_object_string_add(json_row
, "rpfAddress",
2588 json_object_object_add(json_group
, src_str
, json_row
);
2590 vty_out(vty
, "%-15s %-15s %-8s %-15s %-15s\n", src_str
,
2591 grp_str
, rpf_ifname
, rpf_nexthop_str
,
2597 vty_out(vty
, "%s\n", json_object_to_json_string_ext(
2598 json
, JSON_C_TO_STRING_PRETTY
));
2599 json_object_free(json
);
2603 static void show_rpf_refresh_stats(struct vty
*vty
, time_t now
,
2606 char refresh_uptime
[10];
2608 pim_time_uptime_begin(refresh_uptime
, sizeof(refresh_uptime
), now
,
2609 qpim_rpf_cache_refresh_last
);
2612 json_object_int_add(json
, "rpfCacheRefreshDelayMsecs",
2613 qpim_rpf_cache_refresh_delay_msec
);
2614 json_object_int_add(
2615 json
, "rpfCacheRefreshTimer",
2616 pim_time_timer_remain_msec(qpim_rpf_cache_refresher
));
2617 json_object_int_add(json
, "rpfCacheRefreshRequests",
2618 qpim_rpf_cache_refresh_requests
);
2619 json_object_int_add(json
, "rpfCacheRefreshEvents",
2620 qpim_rpf_cache_refresh_events
);
2621 json_object_string_add(json
, "rpfCacheRefreshLast",
2623 json_object_int_add(json
, "nexthopLookups",
2624 qpim_nexthop_lookups
);
2625 json_object_int_add(json
, "nexthopLookupsAvoided",
2626 nexthop_lookups_avoided
);
2629 "RPF Cache Refresh Delay: %ld msecs\n"
2630 "RPF Cache Refresh Timer: %ld msecs\n"
2631 "RPF Cache Refresh Requests: %lld\n"
2632 "RPF Cache Refresh Events: %lld\n"
2633 "RPF Cache Refresh Last: %s\n"
2634 "Nexthop Lookups: %lld\n"
2635 "Nexthop Lookups Avoided: %lld\n",
2636 qpim_rpf_cache_refresh_delay_msec
,
2637 pim_time_timer_remain_msec(qpim_rpf_cache_refresher
),
2638 (long long)qpim_rpf_cache_refresh_requests
,
2639 (long long)qpim_rpf_cache_refresh_events
,
2640 refresh_uptime
, (long long)qpim_nexthop_lookups
,
2641 (long long)nexthop_lookups_avoided
);
2645 static void show_scan_oil_stats(struct pim_instance
*pim
, struct vty
*vty
,
2648 char uptime_scan_oil
[10];
2649 char uptime_mroute_add
[10];
2650 char uptime_mroute_del
[10];
2652 pim_time_uptime_begin(uptime_scan_oil
, sizeof(uptime_scan_oil
), now
,
2653 qpim_scan_oil_last
);
2654 pim_time_uptime_begin(uptime_mroute_add
, sizeof(uptime_mroute_add
), now
,
2655 pim
->mroute_add_last
);
2656 pim_time_uptime_begin(uptime_mroute_del
, sizeof(uptime_mroute_del
), now
,
2657 pim
->mroute_del_last
);
2660 "Scan OIL - Last: %s Events: %lld\n"
2661 "MFC Add - Last: %s Events: %lld\n"
2662 "MFC Del - Last: %s Events: %lld\n",
2663 uptime_scan_oil
, (long long)qpim_scan_oil_events
,
2664 uptime_mroute_add
, (long long)pim
->mroute_add_events
,
2665 uptime_mroute_del
, (long long)pim
->mroute_del_events
);
2668 static void pim_show_rpf(struct pim_instance
*pim
, struct vty
*vty
, u_char uj
)
2670 struct listnode
*up_node
;
2671 struct pim_upstream
*up
;
2672 time_t now
= pim_time_monotonic_sec();
2673 json_object
*json
= NULL
;
2674 json_object
*json_group
= NULL
;
2675 json_object
*json_row
= NULL
;
2678 json
= json_object_new_object();
2679 show_rpf_refresh_stats(vty
, now
, json
);
2681 show_rpf_refresh_stats(vty
, now
, json
);
2684 "Source Group RpfIface RpfAddress RibNextHop Metric Pref\n");
2687 for (ALL_LIST_ELEMENTS_RO(pim
->upstream_list
, up_node
, up
)) {
2688 char src_str
[INET_ADDRSTRLEN
];
2689 char grp_str
[INET_ADDRSTRLEN
];
2690 char rpf_addr_str
[PREFIX_STRLEN
];
2691 char rib_nexthop_str
[PREFIX_STRLEN
];
2692 const char *rpf_ifname
;
2693 struct pim_rpf
*rpf
= &up
->rpf
;
2695 pim_inet4_dump("<src?>", up
->sg
.src
, src_str
, sizeof(src_str
));
2696 pim_inet4_dump("<grp?>", up
->sg
.grp
, grp_str
, sizeof(grp_str
));
2697 pim_addr_dump("<rpf?>", &rpf
->rpf_addr
, rpf_addr_str
,
2698 sizeof(rpf_addr_str
));
2699 pim_addr_dump("<nexthop?>",
2700 &rpf
->source_nexthop
.mrib_nexthop_addr
,
2701 rib_nexthop_str
, sizeof(rib_nexthop_str
));
2703 rpf_ifname
= rpf
->source_nexthop
.interface
? rpf
->source_nexthop
.interface
->name
: "<ifname?>";
2706 json_object_object_get_ex(json
, grp_str
, &json_group
);
2709 json_group
= json_object_new_object();
2710 json_object_object_add(json
, grp_str
,
2714 json_row
= json_object_new_object();
2715 json_object_string_add(json_row
, "source", src_str
);
2716 json_object_string_add(json_row
, "group", grp_str
);
2717 json_object_string_add(json_row
, "rpfInterface",
2719 json_object_string_add(json_row
, "rpfAddress",
2721 json_object_string_add(json_row
, "ribNexthop",
2723 json_object_int_add(
2724 json_row
, "routeMetric",
2725 rpf
->source_nexthop
.mrib_route_metric
);
2726 json_object_int_add(
2727 json_row
, "routePreference",
2728 rpf
->source_nexthop
.mrib_metric_preference
);
2729 json_object_object_add(json_group
, src_str
, json_row
);
2732 vty_out(vty
, "%-15s %-15s %-8s %-15s %-15s %6d %4d\n",
2733 src_str
, grp_str
, rpf_ifname
, rpf_addr_str
,
2735 rpf
->source_nexthop
.mrib_route_metric
,
2736 rpf
->source_nexthop
.mrib_metric_preference
);
2741 vty_out(vty
, "%s\n", json_object_to_json_string_ext(
2742 json
, JSON_C_TO_STRING_PRETTY
));
2743 json_object_free(json
);
2747 struct pnc_cache_walk_data
{
2749 struct pim_instance
*pim
;
2752 static int pim_print_pnc_cache_walkcb(struct hash_backet
*backet
, void *arg
)
2754 struct pim_nexthop_cache
*pnc
= backet
->data
;
2755 struct pnc_cache_walk_data
*cwd
= arg
;
2756 struct vty
*vty
= cwd
->vty
;
2757 struct pim_instance
*pim
= cwd
->pim
;
2758 struct nexthop
*nh_node
= NULL
;
2759 ifindex_t first_ifindex
;
2760 struct interface
*ifp
= NULL
;
2765 for (nh_node
= pnc
->nexthop
; nh_node
; nh_node
= nh_node
->next
) {
2766 first_ifindex
= nh_node
->ifindex
;
2767 ifp
= if_lookup_by_index(first_ifindex
, pim
->vrf_id
);
2769 vty_out(vty
, "%-15s ", inet_ntoa(pnc
->rpf
.rpf_addr
.u
.prefix4
));
2770 vty_out(vty
, "%-14s ", ifp
? ifp
->name
: "NULL");
2771 vty_out(vty
, "%s ", inet_ntoa(nh_node
->gate
.ipv4
));
2777 static void pim_show_nexthop(struct pim_instance
*pim
, struct vty
*vty
)
2779 struct pnc_cache_walk_data cwd
;
2783 vty_out(vty
, "Number of registered addresses: %lu\n",
2784 pim
->rpf_hash
->count
);
2785 vty_out(vty
, "Address Interface Nexthop\n");
2786 vty_out(vty
, "-------------------------------------------\n");
2788 hash_walk(pim
->rpf_hash
, pim_print_pnc_cache_walkcb
, &cwd
);
2791 static void igmp_show_groups(struct pim_instance
*pim
, struct vty
*vty
,
2794 struct interface
*ifp
;
2796 json_object
*json
= NULL
;
2797 json_object
*json_iface
= NULL
;
2798 json_object
*json_row
= NULL
;
2800 now
= pim_time_monotonic_sec();
2803 json
= json_object_new_object();
2806 "Interface Address Group Mode Timer Srcs V Uptime \n");
2808 /* scan interfaces */
2809 FOR_ALL_INTERFACES (pim
->vrf
, ifp
) {
2810 struct pim_interface
*pim_ifp
= ifp
->info
;
2811 struct listnode
*sock_node
;
2812 struct igmp_sock
*igmp
;
2817 /* scan igmp sockets */
2818 for (ALL_LIST_ELEMENTS_RO(pim_ifp
->igmp_socket_list
, sock_node
,
2820 char ifaddr_str
[INET_ADDRSTRLEN
];
2821 struct listnode
*grpnode
;
2822 struct igmp_group
*grp
;
2824 pim_inet4_dump("<ifaddr?>", igmp
->ifaddr
, ifaddr_str
,
2825 sizeof(ifaddr_str
));
2827 /* scan igmp groups */
2828 for (ALL_LIST_ELEMENTS_RO(igmp
->igmp_group_list
,
2830 char group_str
[INET_ADDRSTRLEN
];
2834 pim_inet4_dump("<group?>", grp
->group_addr
,
2835 group_str
, sizeof(group_str
));
2836 pim_time_timer_to_hhmmss(hhmmss
, sizeof(hhmmss
),
2837 grp
->t_group_timer
);
2838 pim_time_uptime(uptime
, sizeof(uptime
),
2839 now
- grp
->group_creation
);
2842 json_object_object_get_ex(
2843 json
, ifp
->name
, &json_iface
);
2847 json_object_new_object();
2848 json_object_pim_ifp_add(
2850 json_object_object_add(
2855 json_row
= json_object_new_object();
2856 json_object_string_add(
2857 json_row
, "source", ifaddr_str
);
2858 json_object_string_add(
2859 json_row
, "group", group_str
);
2861 if (grp
->igmp_version
== 3)
2862 json_object_string_add(
2864 grp
->group_filtermode_isexcl
2868 json_object_string_add(json_row
,
2870 json_object_int_add(
2871 json_row
, "sourcesCount",
2872 grp
->group_source_list
2874 grp
->group_source_list
)
2876 json_object_int_add(json_row
, "version",
2878 json_object_string_add(
2879 json_row
, "uptime", uptime
);
2880 json_object_object_add(json_iface
,
2886 "%-9s %-15s %-15s %4s %8s %4d %d %8s\n",
2887 ifp
->name
, ifaddr_str
,
2889 grp
->igmp_version
== 3
2890 ? (grp
->group_filtermode_isexcl
2895 grp
->group_source_list
2897 grp
->group_source_list
)
2899 grp
->igmp_version
, uptime
);
2901 } /* scan igmp groups */
2902 } /* scan igmp sockets */
2903 } /* scan interfaces */
2906 vty_out(vty
, "%s\n", json_object_to_json_string_ext(
2907 json
, JSON_C_TO_STRING_PRETTY
));
2908 json_object_free(json
);
2912 static void igmp_show_group_retransmission(struct pim_instance
*pim
,
2915 struct interface
*ifp
;
2918 "Interface Address Group RetTimer Counter RetSrcs\n");
2920 /* scan interfaces */
2921 FOR_ALL_INTERFACES (pim
->vrf
, ifp
) {
2922 struct pim_interface
*pim_ifp
= ifp
->info
;
2923 struct listnode
*sock_node
;
2924 struct igmp_sock
*igmp
;
2929 /* scan igmp sockets */
2930 for (ALL_LIST_ELEMENTS_RO(pim_ifp
->igmp_socket_list
, sock_node
,
2932 char ifaddr_str
[INET_ADDRSTRLEN
];
2933 struct listnode
*grpnode
;
2934 struct igmp_group
*grp
;
2936 pim_inet4_dump("<ifaddr?>", igmp
->ifaddr
, ifaddr_str
,
2937 sizeof(ifaddr_str
));
2939 /* scan igmp groups */
2940 for (ALL_LIST_ELEMENTS_RO(igmp
->igmp_group_list
,
2942 char group_str
[INET_ADDRSTRLEN
];
2943 char grp_retr_mmss
[10];
2944 struct listnode
*src_node
;
2945 struct igmp_source
*src
;
2946 int grp_retr_sources
= 0;
2948 pim_inet4_dump("<group?>", grp
->group_addr
,
2949 group_str
, sizeof(group_str
));
2950 pim_time_timer_to_mmss(
2951 grp_retr_mmss
, sizeof(grp_retr_mmss
),
2952 grp
->t_group_query_retransmit_timer
);
2955 /* count group sources with retransmission state
2957 for (ALL_LIST_ELEMENTS_RO(
2958 grp
->group_source_list
, src_node
,
2960 if (src
->source_query_retransmit_count
2966 vty_out(vty
, "%-9s %-15s %-15s %-8s %7d %7d\n",
2967 ifp
->name
, ifaddr_str
, group_str
,
2969 grp
->group_specific_query_retransmit_count
,
2972 } /* scan igmp groups */
2973 } /* scan igmp sockets */
2974 } /* scan interfaces */
2977 static void igmp_show_sources(struct pim_instance
*pim
, struct vty
*vty
)
2979 struct interface
*ifp
;
2982 now
= pim_time_monotonic_sec();
2985 "Interface Address Group Source Timer Fwd Uptime \n");
2987 /* scan interfaces */
2988 FOR_ALL_INTERFACES (pim
->vrf
, ifp
) {
2989 struct pim_interface
*pim_ifp
= ifp
->info
;
2990 struct listnode
*sock_node
;
2991 struct igmp_sock
*igmp
;
2996 /* scan igmp sockets */
2997 for (ALL_LIST_ELEMENTS_RO(pim_ifp
->igmp_socket_list
, sock_node
,
2999 char ifaddr_str
[INET_ADDRSTRLEN
];
3000 struct listnode
*grpnode
;
3001 struct igmp_group
*grp
;
3003 pim_inet4_dump("<ifaddr?>", igmp
->ifaddr
, ifaddr_str
,
3004 sizeof(ifaddr_str
));
3006 /* scan igmp groups */
3007 for (ALL_LIST_ELEMENTS_RO(igmp
->igmp_group_list
,
3009 char group_str
[INET_ADDRSTRLEN
];
3010 struct listnode
*srcnode
;
3011 struct igmp_source
*src
;
3013 pim_inet4_dump("<group?>", grp
->group_addr
,
3014 group_str
, sizeof(group_str
));
3016 /* scan group sources */
3017 for (ALL_LIST_ELEMENTS_RO(
3018 grp
->group_source_list
, srcnode
,
3020 char source_str
[INET_ADDRSTRLEN
];
3025 "<source?>", src
->source_addr
,
3026 source_str
, sizeof(source_str
));
3028 pim_time_timer_to_mmss(
3030 src
->t_source_timer
);
3033 uptime
, sizeof(uptime
),
3034 now
- src
->source_creation
);
3037 "%-9s %-15s %-15s %-15s %5s %3s %8s\n",
3038 ifp
->name
, ifaddr_str
,
3039 group_str
, source_str
, mmss
,
3040 IGMP_SOURCE_TEST_FORWARDING(
3046 } /* scan group sources */
3047 } /* scan igmp groups */
3048 } /* scan igmp sockets */
3049 } /* scan interfaces */
3052 static void igmp_show_source_retransmission(struct pim_instance
*pim
,
3055 struct interface
*ifp
;
3058 "Interface Address Group Source Counter\n");
3060 /* scan interfaces */
3061 FOR_ALL_INTERFACES (pim
->vrf
, ifp
) {
3062 struct pim_interface
*pim_ifp
= ifp
->info
;
3063 struct listnode
*sock_node
;
3064 struct igmp_sock
*igmp
;
3069 /* scan igmp sockets */
3070 for (ALL_LIST_ELEMENTS_RO(pim_ifp
->igmp_socket_list
, sock_node
,
3072 char ifaddr_str
[INET_ADDRSTRLEN
];
3073 struct listnode
*grpnode
;
3074 struct igmp_group
*grp
;
3076 pim_inet4_dump("<ifaddr?>", igmp
->ifaddr
, ifaddr_str
,
3077 sizeof(ifaddr_str
));
3079 /* scan igmp groups */
3080 for (ALL_LIST_ELEMENTS_RO(igmp
->igmp_group_list
,
3082 char group_str
[INET_ADDRSTRLEN
];
3083 struct listnode
*srcnode
;
3084 struct igmp_source
*src
;
3086 pim_inet4_dump("<group?>", grp
->group_addr
,
3087 group_str
, sizeof(group_str
));
3089 /* scan group sources */
3090 for (ALL_LIST_ELEMENTS_RO(
3091 grp
->group_source_list
, srcnode
,
3093 char source_str
[INET_ADDRSTRLEN
];
3096 "<source?>", src
->source_addr
,
3097 source_str
, sizeof(source_str
));
3100 "%-9s %-15s %-15s %-15s %7d\n",
3101 ifp
->name
, ifaddr_str
,
3102 group_str
, source_str
,
3103 src
->source_query_retransmit_count
);
3105 } /* scan group sources */
3106 } /* scan igmp groups */
3107 } /* scan igmp sockets */
3108 } /* scan interfaces */
3111 static void clear_igmp_interfaces(struct pim_instance
*pim
)
3113 struct interface
*ifp
;
3115 FOR_ALL_INTERFACES (pim
->vrf
, ifp
)
3116 pim_if_addr_del_all_igmp(ifp
);
3118 FOR_ALL_INTERFACES (pim
->vrf
, ifp
)
3119 pim_if_addr_add_all(ifp
);
3122 static void clear_pim_interfaces(struct pim_instance
*pim
)
3124 struct interface
*ifp
;
3126 FOR_ALL_INTERFACES (pim
->vrf
, ifp
) {
3128 pim_neighbor_delete_all(ifp
, "interface cleared");
3133 static void clear_interfaces(struct pim_instance
*pim
)
3135 clear_igmp_interfaces(pim
);
3136 clear_pim_interfaces(pim
);
3139 #define PIM_GET_PIM_INTERFACE(pim_ifp, ifp) \
3140 pim_ifp = ifp->info; \
3143 "%% Enable PIM and/or IGMP on this interface first\n"); \
3144 return CMD_WARNING_CONFIG_FAILED; \
3147 DEFUN (clear_ip_interfaces
,
3148 clear_ip_interfaces_cmd
,
3149 "clear ip interfaces [vrf NAME]",
3152 "Reset interfaces\n"
3156 struct vrf
*vrf
= pim_cmd_lookup_vrf(vty
, argv
, argc
, &idx
);
3161 clear_interfaces(vrf
->info
);
3166 DEFUN (clear_ip_igmp_interfaces
,
3167 clear_ip_igmp_interfaces_cmd
,
3168 "clear ip igmp [vrf NAME] interfaces",
3173 "Reset IGMP interfaces\n")
3176 struct vrf
*vrf
= pim_cmd_lookup_vrf(vty
, argv
, argc
, &idx
);
3181 clear_igmp_interfaces(vrf
->info
);
3186 static void mroute_add_all(struct pim_instance
*pim
)
3188 struct listnode
*node
;
3189 struct channel_oil
*c_oil
;
3191 for (ALL_LIST_ELEMENTS_RO(pim
->channel_oil_list
, node
, c_oil
)) {
3192 if (pim_mroute_add(c_oil
, __PRETTY_FUNCTION__
)) {
3193 /* just log warning */
3194 char source_str
[INET_ADDRSTRLEN
];
3195 char group_str
[INET_ADDRSTRLEN
];
3196 pim_inet4_dump("<source?>", c_oil
->oil
.mfcc_origin
,
3197 source_str
, sizeof(source_str
));
3198 pim_inet4_dump("<group?>", c_oil
->oil
.mfcc_mcastgrp
,
3199 group_str
, sizeof(group_str
));
3200 zlog_warn("%s %s: (S,G)=(%s,%s) failure writing MFC",
3201 __FILE__
, __PRETTY_FUNCTION__
, source_str
,
3207 static void mroute_del_all(struct pim_instance
*pim
)
3209 struct listnode
*node
;
3210 struct channel_oil
*c_oil
;
3212 for (ALL_LIST_ELEMENTS_RO(pim
->channel_oil_list
, node
, c_oil
)) {
3213 if (pim_mroute_del(c_oil
, __PRETTY_FUNCTION__
)) {
3214 /* just log warning */
3215 char source_str
[INET_ADDRSTRLEN
];
3216 char group_str
[INET_ADDRSTRLEN
];
3217 pim_inet4_dump("<source?>", c_oil
->oil
.mfcc_origin
,
3218 source_str
, sizeof(source_str
));
3219 pim_inet4_dump("<group?>", c_oil
->oil
.mfcc_mcastgrp
,
3220 group_str
, sizeof(group_str
));
3221 zlog_warn("%s %s: (S,G)=(%s,%s) failure clearing MFC",
3222 __FILE__
, __PRETTY_FUNCTION__
, source_str
,
3228 DEFUN (clear_ip_mroute
,
3229 clear_ip_mroute_cmd
,
3230 "clear ip mroute [vrf NAME]",
3233 "Reset multicast routes\n"
3237 struct vrf
*vrf
= pim_cmd_lookup_vrf(vty
, argv
, argc
, &idx
);
3242 mroute_del_all(vrf
->info
);
3243 mroute_add_all(vrf
->info
);
3248 DEFUN (clear_ip_pim_interfaces
,
3249 clear_ip_pim_interfaces_cmd
,
3250 "clear ip pim [vrf NAME] interfaces",
3255 "Reset PIM interfaces\n")
3258 struct vrf
*vrf
= pim_cmd_lookup_vrf(vty
, argv
, argc
, &idx
);
3263 clear_pim_interfaces(vrf
->info
);
3268 DEFUN (clear_ip_pim_interface_traffic
,
3269 clear_ip_pim_interface_traffic_cmd
,
3270 "clear ip pim [vrf NAME] interface traffic",
3273 "PIM clear commands\n"
3275 "Reset PIM interfaces\n"
3276 "Reset Protocol Packet counters\n")
3279 struct vrf
*vrf
= pim_cmd_lookup_vrf(vty
, argv
, argc
, &idx
);
3280 struct interface
*ifp
= NULL
;
3281 struct pim_interface
*pim_ifp
= NULL
;
3286 FOR_ALL_INTERFACES (vrf
, ifp
) {
3287 pim_ifp
= ifp
->info
;
3292 pim_ifp
->pim_ifstat_hello_recv
= 0;
3293 pim_ifp
->pim_ifstat_hello_sent
= 0;
3294 pim_ifp
->pim_ifstat_join_recv
= 0;
3295 pim_ifp
->pim_ifstat_join_send
= 0;
3296 pim_ifp
->pim_ifstat_prune_recv
= 0;
3297 pim_ifp
->pim_ifstat_prune_send
= 0;
3298 pim_ifp
->pim_ifstat_reg_recv
= 0;
3299 pim_ifp
->pim_ifstat_reg_send
= 0;
3300 pim_ifp
->pim_ifstat_reg_stop_recv
= 0;
3301 pim_ifp
->pim_ifstat_reg_stop_send
= 0;
3302 pim_ifp
->pim_ifstat_assert_recv
= 0;
3303 pim_ifp
->pim_ifstat_assert_send
= 0;
3309 DEFUN (clear_ip_pim_oil
,
3310 clear_ip_pim_oil_cmd
,
3311 "clear ip pim [vrf NAME] oil",
3316 "Rescan PIM OIL (output interface list)\n")
3319 struct vrf
*vrf
= pim_cmd_lookup_vrf(vty
, argv
, argc
, &idx
);
3324 pim_scan_oil(vrf
->info
);
3329 DEFUN (show_ip_igmp_interface
,
3330 show_ip_igmp_interface_cmd
,
3331 "show ip igmp [vrf NAME] interface [detail|WORD] [json]",
3336 "IGMP interface information\n"
3342 struct vrf
*vrf
= pim_cmd_lookup_vrf(vty
, argv
, argc
, &idx
);
3343 u_char uj
= use_json(argc
, argv
);
3348 if (argv_find(argv
, argc
, "detail", &idx
)
3349 || argv_find(argv
, argc
, "WORD", &idx
))
3350 igmp_show_interfaces_single(vrf
->info
, vty
, argv
[idx
]->arg
, uj
);
3352 igmp_show_interfaces(vrf
->info
, vty
, uj
);
3357 DEFUN (show_ip_igmp_interface_vrf_all
,
3358 show_ip_igmp_interface_vrf_all_cmd
,
3359 "show ip igmp vrf all interface [detail|WORD] [json]",
3364 "IGMP interface information\n"
3370 u_char uj
= use_json(argc
, argv
);
3376 RB_FOREACH (vrf
, vrf_name_head
, &vrfs_by_name
) {
3380 vty_out(vty
, " \"%s\": ", vrf
->name
);
3383 vty_out(vty
, "VRF: %s\n", vrf
->name
);
3384 if (argv_find(argv
, argc
, "detail", &idx
)
3385 || argv_find(argv
, argc
, "WORD", &idx
))
3386 igmp_show_interfaces_single(vrf
->info
, vty
,
3387 argv
[idx
]->arg
, uj
);
3389 igmp_show_interfaces(vrf
->info
, vty
, uj
);
3392 vty_out(vty
, "}\n");
3397 DEFUN (show_ip_igmp_join
,
3398 show_ip_igmp_join_cmd
,
3399 "show ip igmp [vrf NAME] join",
3404 "IGMP static join information\n")
3407 struct vrf
*vrf
= pim_cmd_lookup_vrf(vty
, argv
, argc
, &idx
);
3412 igmp_show_interface_join(vrf
->info
, vty
);
3417 DEFUN (show_ip_igmp_join_vrf_all
,
3418 show_ip_igmp_join_vrf_all_cmd
,
3419 "show ip igmp vrf all join",
3424 "IGMP static join information\n")
3426 u_char uj
= use_json(argc
, argv
);
3432 RB_FOREACH (vrf
, vrf_name_head
, &vrfs_by_name
) {
3436 vty_out(vty
, " \"%s\": ", vrf
->name
);
3439 vty_out(vty
, "VRF: %s\n", vrf
->name
);
3440 igmp_show_interface_join(vrf
->info
, vty
);
3443 vty_out(vty
, "}\n");
3448 DEFUN (show_ip_igmp_groups
,
3449 show_ip_igmp_groups_cmd
,
3450 "show ip igmp [vrf NAME] groups [json]",
3459 struct vrf
*vrf
= pim_cmd_lookup_vrf(vty
, argv
, argc
, &idx
);
3460 u_char uj
= use_json(argc
, argv
);
3465 igmp_show_groups(vrf
->info
, vty
, uj
);
3470 DEFUN (show_ip_igmp_groups_vrf_all
,
3471 show_ip_igmp_groups_vrf_all_cmd
,
3472 "show ip igmp vrf all groups [json]",
3480 u_char uj
= use_json(argc
, argv
);
3486 RB_FOREACH (vrf
, vrf_name_head
, &vrfs_by_name
) {
3490 vty_out(vty
, " \"%s\": ", vrf
->name
);
3493 vty_out(vty
, "VRF: %s\n", vrf
->name
);
3494 igmp_show_groups(vrf
->info
, vty
, uj
);
3497 vty_out(vty
, "}\n");
3502 DEFUN (show_ip_igmp_groups_retransmissions
,
3503 show_ip_igmp_groups_retransmissions_cmd
,
3504 "show ip igmp [vrf NAME] groups retransmissions",
3510 "IGMP group retransmissions\n")
3513 struct vrf
*vrf
= pim_cmd_lookup_vrf(vty
, argv
, argc
, &idx
);
3518 igmp_show_group_retransmission(vrf
->info
, vty
);
3523 DEFUN (show_ip_igmp_sources
,
3524 show_ip_igmp_sources_cmd
,
3525 "show ip igmp [vrf NAME] sources",
3533 struct vrf
*vrf
= pim_cmd_lookup_vrf(vty
, argv
, argc
, &idx
);
3538 igmp_show_sources(vrf
->info
, vty
);
3543 DEFUN (show_ip_igmp_sources_retransmissions
,
3544 show_ip_igmp_sources_retransmissions_cmd
,
3545 "show ip igmp [vrf NAME] sources retransmissions",
3551 "IGMP source retransmissions\n")
3554 struct vrf
*vrf
= pim_cmd_lookup_vrf(vty
, argv
, argc
, &idx
);
3559 igmp_show_source_retransmission(vrf
->info
, vty
);
3564 DEFUN (show_ip_pim_assert
,
3565 show_ip_pim_assert_cmd
,
3566 "show ip pim [vrf NAME] assert",
3571 "PIM interface assert\n")
3574 struct vrf
*vrf
= pim_cmd_lookup_vrf(vty
, argv
, argc
, &idx
);
3579 pim_show_assert(vrf
->info
, vty
);
3584 DEFUN (show_ip_pim_assert_internal
,
3585 show_ip_pim_assert_internal_cmd
,
3586 "show ip pim [vrf NAME] assert-internal",
3591 "PIM interface internal assert state\n")
3594 struct vrf
*vrf
= pim_cmd_lookup_vrf(vty
, argv
, argc
, &idx
);
3599 pim_show_assert_internal(vrf
->info
, vty
);
3604 DEFUN (show_ip_pim_assert_metric
,
3605 show_ip_pim_assert_metric_cmd
,
3606 "show ip pim [vrf NAME] assert-metric",
3611 "PIM interface assert metric\n")
3614 struct vrf
*vrf
= pim_cmd_lookup_vrf(vty
, argv
, argc
, &idx
);
3619 pim_show_assert_metric(vrf
->info
, vty
);
3624 DEFUN (show_ip_pim_assert_winner_metric
,
3625 show_ip_pim_assert_winner_metric_cmd
,
3626 "show ip pim [vrf NAME] assert-winner-metric",
3631 "PIM interface assert winner metric\n")
3634 struct vrf
*vrf
= pim_cmd_lookup_vrf(vty
, argv
, argc
, &idx
);
3639 pim_show_assert_winner_metric(vrf
->info
, vty
);
3644 DEFUN (show_ip_pim_interface
,
3645 show_ip_pim_interface_cmd
,
3646 "show ip pim [vrf NAME] interface [detail|WORD] [json]",
3651 "PIM interface information\n"
3657 struct vrf
*vrf
= pim_cmd_lookup_vrf(vty
, argv
, argc
, &idx
);
3658 u_char uj
= use_json(argc
, argv
);
3663 if (argv_find(argv
, argc
, "WORD", &idx
)
3664 || argv_find(argv
, argc
, "detail", &idx
))
3665 pim_show_interfaces_single(vrf
->info
, vty
, argv
[idx
]->arg
, uj
);
3667 pim_show_interfaces(vrf
->info
, vty
, uj
);
3672 DEFUN (show_ip_pim_interface_vrf_all
,
3673 show_ip_pim_interface_vrf_all_cmd
,
3674 "show ip pim vrf all interface [detail|WORD] [json]",
3679 "PIM interface information\n"
3685 u_char uj
= use_json(argc
, argv
);
3691 RB_FOREACH (vrf
, vrf_name_head
, &vrfs_by_name
) {
3695 vty_out(vty
, " \"%s\": ", vrf
->name
);
3698 vty_out(vty
, "VRF: %s\n", vrf
->name
);
3699 if (argv_find(argv
, argc
, "WORD", &idx
)
3700 || argv_find(argv
, argc
, "detail", &idx
))
3701 pim_show_interfaces_single(vrf
->info
, vty
,
3702 argv
[idx
]->arg
, uj
);
3704 pim_show_interfaces(vrf
->info
, vty
, uj
);
3707 vty_out(vty
, "}\n");
3712 DEFUN (show_ip_pim_join
,
3713 show_ip_pim_join_cmd
,
3714 "show ip pim [vrf NAME] join [json]",
3719 "PIM interface join information\n"
3723 struct vrf
*vrf
= pim_cmd_lookup_vrf(vty
, argv
, argc
, &idx
);
3724 u_char uj
= use_json(argc
, argv
);
3729 pim_show_join(vrf
->info
, vty
, uj
);
3734 DEFUN (show_ip_pim_join_vrf_all
,
3735 show_ip_pim_join_vrf_all_cmd
,
3736 "show ip pim vrf all join [json]",
3741 "PIM interface join information\n"
3744 u_char uj
= use_json(argc
, argv
);
3750 RB_FOREACH (vrf
, vrf_name_head
, &vrfs_by_name
) {
3754 vty_out(vty
, " \"%s\": ", vrf
->name
);
3757 vty_out(vty
, "VRF: %s\n", vrf
->name
);
3758 pim_show_join(vrf
->info
, vty
, uj
);
3761 vty_out(vty
, "}\n");
3766 DEFUN (show_ip_pim_local_membership
,
3767 show_ip_pim_local_membership_cmd
,
3768 "show ip pim [vrf NAME] local-membership [json]",
3773 "PIM interface local-membership\n"
3777 struct vrf
*vrf
= pim_cmd_lookup_vrf(vty
, argv
, argc
, &idx
);
3778 u_char uj
= use_json(argc
, argv
);
3783 pim_show_membership(vrf
->info
, vty
, uj
);
3788 DEFUN (show_ip_pim_neighbor
,
3789 show_ip_pim_neighbor_cmd
,
3790 "show ip pim [vrf NAME] neighbor [detail|WORD] [json]",
3795 "PIM neighbor information\n"
3797 "Name of interface or neighbor\n"
3801 struct vrf
*vrf
= pim_cmd_lookup_vrf(vty
, argv
, argc
, &idx
);
3802 u_char uj
= use_json(argc
, argv
);
3807 if (argv_find(argv
, argc
, "detail", &idx
)
3808 || argv_find(argv
, argc
, "WORD", &idx
))
3809 pim_show_neighbors_single(vrf
->info
, vty
, argv
[idx
]->arg
, uj
);
3811 pim_show_neighbors(vrf
->info
, vty
, uj
);
3816 DEFUN (show_ip_pim_neighbor_vrf_all
,
3817 show_ip_pim_neighbor_vrf_all_cmd
,
3818 "show ip pim vrf all neighbor [detail|WORD] [json]",
3823 "PIM neighbor information\n"
3825 "Name of interface or neighbor\n"
3829 u_char uj
= use_json(argc
, argv
);
3835 RB_FOREACH (vrf
, vrf_name_head
, &vrfs_by_name
) {
3839 vty_out(vty
, " \"%s\": ", vrf
->name
);
3842 vty_out(vty
, "VRF: %s\n", vrf
->name
);
3843 if (argv_find(argv
, argc
, "detail", &idx
)
3844 || argv_find(argv
, argc
, "WORD", &idx
))
3845 pim_show_neighbors_single(vrf
->info
, vty
,
3846 argv
[idx
]->arg
, uj
);
3848 pim_show_neighbors(vrf
->info
, vty
, uj
);
3851 vty_out(vty
, "}\n");
3856 DEFUN (show_ip_pim_secondary
,
3857 show_ip_pim_secondary_cmd
,
3858 "show ip pim [vrf NAME] secondary",
3863 "PIM neighbor addresses\n")
3866 struct vrf
*vrf
= pim_cmd_lookup_vrf(vty
, argv
, argc
, &idx
);
3871 pim_show_neighbors_secondary(vrf
->info
, vty
);
3876 DEFUN (show_ip_pim_state
,
3877 show_ip_pim_state_cmd
,
3878 "show ip pim [vrf NAME] state [A.B.C.D [A.B.C.D]] [json]",
3883 "PIM state information\n"
3884 "Unicast or Multicast address\n"
3885 "Multicast address\n"
3888 const char *src_or_group
= NULL
;
3889 const char *group
= NULL
;
3891 struct vrf
*vrf
= pim_cmd_lookup_vrf(vty
, argv
, argc
, &idx
);
3892 u_char uj
= use_json(argc
, argv
);
3900 if (argv_find(argv
, argc
, "A.B.C.D", &idx
)) {
3901 src_or_group
= argv
[idx
]->arg
;
3903 group
= argv
[idx
+ 1]->arg
;
3906 pim_show_state(vrf
->info
, vty
, src_or_group
, group
, uj
);
3911 DEFUN (show_ip_pim_state_vrf_all
,
3912 show_ip_pim_state_vrf_all_cmd
,
3913 "show ip pim vrf all state [A.B.C.D [A.B.C.D]] [json]",
3918 "PIM state information\n"
3919 "Unicast or Multicast address\n"
3920 "Multicast address\n"
3923 const char *src_or_group
= NULL
;
3924 const char *group
= NULL
;
3926 u_char uj
= use_json(argc
, argv
);
3935 if (argv_find(argv
, argc
, "A.B.C.D", &idx
)) {
3936 src_or_group
= argv
[idx
]->arg
;
3938 group
= argv
[idx
+ 1]->arg
;
3941 RB_FOREACH (vrf
, vrf_name_head
, &vrfs_by_name
) {
3945 vty_out(vty
, " \"%s\": ", vrf
->name
);
3948 vty_out(vty
, "VRF: %s\n", vrf
->name
);
3949 pim_show_state(vrf
->info
, vty
, src_or_group
, group
, uj
);
3952 vty_out(vty
, "}\n");
3957 DEFUN (show_ip_pim_upstream
,
3958 show_ip_pim_upstream_cmd
,
3959 "show ip pim [vrf NAME] upstream [json]",
3964 "PIM upstream information\n"
3968 struct vrf
*vrf
= pim_cmd_lookup_vrf(vty
, argv
, argc
, &idx
);
3969 u_char uj
= use_json(argc
, argv
);
3974 pim_show_upstream(vrf
->info
, vty
, uj
);
3979 DEFUN (show_ip_pim_upstream_vrf_all
,
3980 show_ip_pim_upstream_vrf_all_cmd
,
3981 "show ip pim vrf all upstream [json]",
3986 "PIM upstream information\n"
3989 u_char uj
= use_json(argc
, argv
);
3995 RB_FOREACH (vrf
, vrf_name_head
, &vrfs_by_name
) {
3999 vty_out(vty
, " \"%s\": ", vrf
->name
);
4002 vty_out(vty
, "VRF: %s\n", vrf
->name
);
4003 pim_show_upstream(vrf
->info
, vty
, uj
);
4009 DEFUN (show_ip_pim_upstream_join_desired
,
4010 show_ip_pim_upstream_join_desired_cmd
,
4011 "show ip pim [vrf NAME] upstream-join-desired [json]",
4016 "PIM upstream join-desired\n"
4020 struct vrf
*vrf
= pim_cmd_lookup_vrf(vty
, argv
, argc
, &idx
);
4021 u_char uj
= use_json(argc
, argv
);
4026 pim_show_join_desired(vrf
->info
, vty
, uj
);
4031 DEFUN (show_ip_pim_upstream_rpf
,
4032 show_ip_pim_upstream_rpf_cmd
,
4033 "show ip pim [vrf NAME] upstream-rpf [json]",
4038 "PIM upstream source rpf\n"
4042 struct vrf
*vrf
= pim_cmd_lookup_vrf(vty
, argv
, argc
, &idx
);
4043 u_char uj
= use_json(argc
, argv
);
4048 pim_show_upstream_rpf(vrf
->info
, vty
, uj
);
4053 DEFUN (show_ip_pim_rp
,
4055 "show ip pim [vrf NAME] rp-info [json]",
4060 "PIM RP information\n"
4064 struct vrf
*vrf
= pim_cmd_lookup_vrf(vty
, argv
, argc
, &idx
);
4065 u_char uj
= use_json(argc
, argv
);
4070 pim_rp_show_information(vrf
->info
, vty
, uj
);
4075 DEFUN (show_ip_pim_rp_vrf_all
,
4076 show_ip_pim_rp_vrf_all_cmd
,
4077 "show ip pim vrf all rp-info [json]",
4082 "PIM RP information\n"
4085 u_char uj
= use_json(argc
, argv
);
4091 RB_FOREACH (vrf
, vrf_name_head
, &vrfs_by_name
) {
4095 vty_out(vty
, " \"%s\": ", vrf
->name
);
4098 vty_out(vty
, "VRF: %s\n", vrf
->name
);
4099 pim_rp_show_information(vrf
->info
, vty
, uj
);
4102 vty_out(vty
, "}\n");
4107 DEFUN (show_ip_pim_rpf
,
4108 show_ip_pim_rpf_cmd
,
4109 "show ip pim [vrf NAME] rpf [json]",
4114 "PIM cached source rpf information\n"
4118 struct vrf
*vrf
= pim_cmd_lookup_vrf(vty
, argv
, argc
, &idx
);
4119 u_char uj
= use_json(argc
, argv
);
4124 pim_show_rpf(vrf
->info
, vty
, uj
);
4129 DEFUN (show_ip_pim_rpf_vrf_all
,
4130 show_ip_pim_rpf_vrf_all_cmd
,
4131 "show ip pim vrf all rpf [json]",
4136 "PIM cached source rpf information\n"
4139 u_char uj
= use_json(argc
, argv
);
4145 RB_FOREACH (vrf
, vrf_name_head
, &vrfs_by_name
) {
4149 vty_out(vty
, " \"%s\": ", vrf
->name
);
4152 vty_out(vty
, "VRF: %s\n", vrf
->name
);
4153 pim_show_rpf(vrf
->info
, vty
, uj
);
4156 vty_out(vty
, "}\n");
4161 DEFUN (show_ip_pim_nexthop
,
4162 show_ip_pim_nexthop_cmd
,
4163 "show ip pim [vrf NAME] nexthop",
4168 "PIM cached nexthop rpf information\n")
4171 struct vrf
*vrf
= pim_cmd_lookup_vrf(vty
, argv
, argc
, &idx
);
4176 pim_show_nexthop(vrf
->info
, vty
);
4181 DEFUN (show_ip_pim_nexthop_lookup
,
4182 show_ip_pim_nexthop_lookup_cmd
,
4183 "show ip pim [vrf NAME] nexthop-lookup A.B.C.D A.B.C.D",
4188 "PIM cached nexthop rpf lookup\n"
4189 "Source/RP address\n"
4190 "Multicast Group address\n")
4192 struct pim_nexthop_cache pnc
;
4193 struct prefix nht_p
;
4195 struct in_addr src_addr
, grp_addr
;
4196 struct in_addr vif_source
;
4197 const char *addr_str
, *addr_str1
;
4199 struct pim_nexthop nexthop
;
4200 char nexthop_addr_str
[PREFIX_STRLEN
];
4201 char grp_str
[PREFIX_STRLEN
];
4203 struct vrf
*vrf
= pim_cmd_lookup_vrf(vty
, argv
, argc
, &idx
);
4208 argv_find(argv
, argc
, "A.B.C.D", &idx
);
4209 addr_str
= argv
[idx
]->arg
;
4210 result
= inet_pton(AF_INET
, addr_str
, &src_addr
);
4212 vty_out(vty
, "Bad unicast address %s: errno=%d: %s\n", addr_str
,
4213 errno
, safe_strerror(errno
));
4217 if (pim_is_group_224_4(src_addr
)) {
4219 "Invalid argument. Expected Valid Source Address.\n");
4223 addr_str1
= argv
[idx
+ 1]->arg
;
4224 result
= inet_pton(AF_INET
, addr_str1
, &grp_addr
);
4226 vty_out(vty
, "Bad unicast address %s: errno=%d: %s\n", addr_str
,
4227 errno
, safe_strerror(errno
));
4231 if (!pim_is_group_224_4(grp_addr
)) {
4233 "Invalid argument. Expected Valid Multicast Group Address.\n");
4237 if (!pim_rp_set_upstream_addr(vrf
->info
, &vif_source
, src_addr
,
4241 memset(&pnc
, 0, sizeof(struct pim_nexthop_cache
));
4242 nht_p
.family
= AF_INET
;
4243 nht_p
.prefixlen
= IPV4_MAX_BITLEN
;
4244 nht_p
.u
.prefix4
= vif_source
;
4245 grp
.family
= AF_INET
;
4246 grp
.prefixlen
= IPV4_MAX_BITLEN
;
4247 grp
.u
.prefix4
= grp_addr
;
4248 memset(&nexthop
, 0, sizeof(nexthop
));
4250 if (pim_find_or_track_nexthop(vrf
->info
, &nht_p
, NULL
, NULL
, &pnc
))
4251 result
= pim_ecmp_nexthop_search(vrf
->info
, &pnc
, &nexthop
,
4254 result
= pim_ecmp_nexthop_lookup(vrf
->info
, &nexthop
, vif_source
,
4258 vty_out(vty
, "Nexthop Lookup failed, no usable routes returned.\n");
4262 pim_addr_dump("<grp?>", &grp
, grp_str
, sizeof(grp_str
));
4263 pim_addr_dump("<nexthop?>", &nexthop
.mrib_nexthop_addr
,
4264 nexthop_addr_str
, sizeof(nexthop_addr_str
));
4265 vty_out(vty
, "Group %s --- Nexthop %s Interface %s \n", grp_str
,
4266 nexthop_addr_str
, nexthop
.interface
->name
);
4271 DEFUN (show_ip_pim_interface_traffic
,
4272 show_ip_pim_interface_traffic_cmd
,
4273 "show ip pim [vrf NAME] interface traffic [WORD] [json]",
4278 "PIM interface information\n"
4279 "Protocol Packet counters\n"
4284 struct vrf
*vrf
= pim_cmd_lookup_vrf(vty
, argv
, argc
, &idx
);
4285 u_char uj
= use_json(argc
, argv
);
4290 if (argv_find(argv
, argc
, "WORD", &idx
))
4291 pim_show_interface_traffic_single(vrf
->info
, vty
,
4292 argv
[idx
]->arg
, uj
);
4294 pim_show_interface_traffic(vrf
->info
, vty
, uj
);
4299 static void show_multicast_interfaces(struct pim_instance
*pim
, struct vty
*vty
)
4301 struct interface
*ifp
;
4306 "Interface Address ifi Vif PktsIn PktsOut BytesIn BytesOut\n");
4308 FOR_ALL_INTERFACES (pim
->vrf
, ifp
) {
4309 struct pim_interface
*pim_ifp
;
4310 struct in_addr ifaddr
;
4311 struct sioc_vif_req vreq
;
4313 pim_ifp
= ifp
->info
;
4318 memset(&vreq
, 0, sizeof(vreq
));
4319 vreq
.vifi
= pim_ifp
->mroute_vif_index
;
4321 if (ioctl(pim
->mroute_socket
, SIOCGETVIFCNT
, &vreq
)) {
4323 "ioctl(SIOCGETVIFCNT=%lu) failure for interface %s vif_index=%d: errno=%d: %s",
4324 (unsigned long)SIOCGETVIFCNT
, ifp
->name
,
4325 pim_ifp
->mroute_vif_index
, errno
,
4326 safe_strerror(errno
));
4329 ifaddr
= pim_ifp
->primary_address
;
4331 vty_out(vty
, "%-12s %-15s %3d %3d %7lu %7lu %10lu %10lu\n",
4332 ifp
->name
, inet_ntoa(ifaddr
), ifp
->ifindex
,
4333 pim_ifp
->mroute_vif_index
, (unsigned long)vreq
.icount
,
4334 (unsigned long)vreq
.ocount
, (unsigned long)vreq
.ibytes
,
4335 (unsigned long)vreq
.obytes
);
4339 static void pim_cmd_show_ip_multicast_helper(struct pim_instance
*pim
,
4342 struct vrf
*vrf
= pim
->vrf
;
4343 time_t now
= pim_time_monotonic_sec();
4348 vty_out(vty
, "Mroute socket descriptor:");
4350 vty_out(vty
, " %d(%s)\n", pim
->mroute_socket
, vrf
->name
);
4352 pim_time_uptime(uptime
, sizeof(uptime
),
4353 now
- pim
->mroute_socket_creation
);
4354 vty_out(vty
, "Mroute socket uptime: %s\n", uptime
);
4358 pim_zebra_zclient_update(vty
);
4359 pim_zlookup_show_ip_multicast(vty
);
4362 vty_out(vty
, "Maximum highest VifIndex: %d\n", PIM_MAX_USABLE_VIFS
);
4365 vty_out(vty
, "Upstream Join Timer: %d secs\n", qpim_t_periodic
);
4366 vty_out(vty
, "Join/Prune Holdtime: %d secs\n", PIM_JP_HOLDTIME
);
4367 vty_out(vty
, "PIM ECMP: %s\n", qpim_ecmp_enable
? "Enable" : "Disable");
4368 vty_out(vty
, "PIM ECMP Rebalance: %s\n",
4369 qpim_ecmp_rebalance_enable
? "Enable" : "Disable");
4373 show_rpf_refresh_stats(vty
, now
, NULL
);
4377 show_scan_oil_stats(pim
, vty
, now
);
4379 show_multicast_interfaces(pim
, vty
);
4382 DEFUN (show_ip_multicast
,
4383 show_ip_multicast_cmd
,
4384 "show ip multicast [vrf NAME]",
4388 "Multicast global information\n")
4391 struct vrf
*vrf
= pim_cmd_lookup_vrf(vty
, argv
, argc
, &idx
);
4396 pim_cmd_show_ip_multicast_helper(vrf
->info
, vty
);
4401 DEFUN (show_ip_multicast_vrf_all
,
4402 show_ip_multicast_vrf_all_cmd
,
4403 "show ip multicast vrf all",
4407 "Multicast global information\n")
4409 u_char uj
= use_json(argc
, argv
);
4415 RB_FOREACH (vrf
, vrf_name_head
, &vrfs_by_name
) {
4419 vty_out(vty
, " \"%s\": ", vrf
->name
);
4422 vty_out(vty
, "VRF: %s\n", vrf
->name
);
4423 pim_cmd_show_ip_multicast_helper(vrf
->info
, vty
);
4426 vty_out(vty
, "}\n");
4431 static void show_mroute(struct pim_instance
*pim
, struct vty
*vty
,
4432 bool fill
, u_char uj
)
4434 struct listnode
*node
;
4435 struct channel_oil
*c_oil
;
4436 struct static_route
*s_route
;
4438 json_object
*json
= NULL
;
4439 json_object
*json_group
= NULL
;
4440 json_object
*json_source
= NULL
;
4441 json_object
*json_oil
= NULL
;
4442 json_object
*json_ifp_out
= NULL
;
4445 char grp_str
[INET_ADDRSTRLEN
];
4446 char src_str
[INET_ADDRSTRLEN
];
4447 char in_ifname
[INTERFACE_NAMSIZ
+ 1];
4448 char out_ifname
[INTERFACE_NAMSIZ
+ 1];
4450 struct interface
*ifp_in
;
4454 json
= json_object_new_object();
4457 "Source Group Proto Input Output TTL Uptime\n");
4460 now
= pim_time_monotonic_sec();
4462 /* print list of PIM and IGMP routes */
4463 for (ALL_LIST_ELEMENTS_RO(pim
->channel_oil_list
, node
, c_oil
)) {
4466 if (!c_oil
->installed
&& !uj
)
4469 pim_inet4_dump("<group?>", c_oil
->oil
.mfcc_mcastgrp
, grp_str
,
4471 pim_inet4_dump("<source?>", c_oil
->oil
.mfcc_origin
, src_str
,
4473 ifp_in
= pim_if_find_by_vif_index(pim
, c_oil
->oil
.mfcc_parent
);
4476 strcpy(in_ifname
, ifp_in
->name
);
4478 strcpy(in_ifname
, "<iif?>");
4482 /* Find the group, create it if it doesn't exist */
4483 json_object_object_get_ex(json
, grp_str
, &json_group
);
4486 json_group
= json_object_new_object();
4487 json_object_object_add(json
, grp_str
,
4491 /* Find the source nested under the group, create it if
4492 * it doesn't exist */
4493 json_object_object_get_ex(json_group
, src_str
,
4497 json_source
= json_object_new_object();
4498 json_object_object_add(json_group
, src_str
,
4502 /* Find the inbound interface nested under the source,
4503 * create it if it doesn't exist */
4504 json_object_int_add(json_source
, "installed",
4506 json_object_int_add(json_source
, "refCount",
4507 c_oil
->oil_ref_count
);
4508 json_object_int_add(json_source
, "oilSize",
4510 json_object_int_add(json_source
, "OilInheritedRescan",
4511 c_oil
->oil_inherited_rescan
);
4512 json_object_string_add(json_source
, "iif", in_ifname
);
4516 for (oif_vif_index
= 0; oif_vif_index
< MAXVIFS
;
4518 struct interface
*ifp_out
;
4519 char oif_uptime
[10];
4522 ttl
= c_oil
->oil
.mfcc_ttls
[oif_vif_index
];
4526 ifp_out
= pim_if_find_by_vif_index(pim
, oif_vif_index
);
4528 oif_uptime
, sizeof(oif_uptime
),
4529 now
- c_oil
->oif_creation
[oif_vif_index
]);
4533 strcpy(out_ifname
, ifp_out
->name
);
4535 strcpy(out_ifname
, "<oif?>");
4538 json_ifp_out
= json_object_new_object();
4539 json_object_string_add(json_ifp_out
, "source",
4541 json_object_string_add(json_ifp_out
, "group",
4544 if (c_oil
->oif_flags
[oif_vif_index
]
4545 & PIM_OIF_FLAG_PROTO_PIM
)
4546 json_object_boolean_true_add(
4547 json_ifp_out
, "protocolPim");
4549 if (c_oil
->oif_flags
[oif_vif_index
]
4550 & PIM_OIF_FLAG_PROTO_IGMP
)
4551 json_object_boolean_true_add(
4552 json_ifp_out
, "protocolIgmp");
4554 if (c_oil
->oif_flags
[oif_vif_index
]
4555 & PIM_OIF_FLAG_PROTO_SOURCE
)
4556 json_object_boolean_true_add(
4557 json_ifp_out
, "protocolSource");
4559 if (c_oil
->oif_flags
[oif_vif_index
]
4560 & PIM_OIF_FLAG_PROTO_STAR
)
4561 json_object_boolean_true_add(
4563 "protocolInherited");
4565 json_object_string_add(json_ifp_out
,
4568 json_object_int_add(json_ifp_out
, "iVifI",
4569 c_oil
->oil
.mfcc_parent
);
4570 json_object_string_add(json_ifp_out
,
4571 "outboundInterface",
4573 json_object_int_add(json_ifp_out
, "oVifI",
4575 json_object_int_add(json_ifp_out
, "ttl", ttl
);
4576 json_object_string_add(json_ifp_out
, "upTime",
4579 json_oil
= json_object_new_object();
4580 json_object_object_add(json_source
,
4583 json_object_object_add(json_oil
, out_ifname
,
4586 if (c_oil
->oif_flags
[oif_vif_index
]
4587 & PIM_OIF_FLAG_PROTO_PIM
) {
4588 strcpy(proto
, "PIM");
4591 if (c_oil
->oif_flags
[oif_vif_index
]
4592 & PIM_OIF_FLAG_PROTO_IGMP
) {
4593 strcpy(proto
, "IGMP");
4596 if (c_oil
->oif_flags
[oif_vif_index
]
4597 & PIM_OIF_FLAG_PROTO_SOURCE
) {
4598 strcpy(proto
, "SRC");
4601 if (c_oil
->oif_flags
[oif_vif_index
]
4602 & PIM_OIF_FLAG_PROTO_STAR
) {
4603 strcpy(proto
, "STAR");
4607 "%-15s %-15s %-6s %-10s %-10s %-3d %8s\n",
4608 src_str
, grp_str
, proto
, in_ifname
,
4609 out_ifname
, ttl
, oif_uptime
);
4614 in_ifname
[0] = '\0';
4620 if (!uj
&& !found_oif
) {
4621 vty_out(vty
, "%-15s %-15s %-6s %-10s %-10s %-3d %8s\n",
4622 src_str
, grp_str
, "none", in_ifname
, "none", 0,
4627 /* Print list of static routes */
4628 for (ALL_LIST_ELEMENTS_RO(pim
->static_routes
, node
, s_route
)) {
4631 if (!s_route
->c_oil
.installed
)
4634 pim_inet4_dump("<group?>", s_route
->group
, grp_str
,
4636 pim_inet4_dump("<source?>", s_route
->source
, src_str
,
4638 ifp_in
= pim_if_find_by_vif_index(pim
, s_route
->iif
);
4642 strcpy(in_ifname
, ifp_in
->name
);
4644 strcpy(in_ifname
, "<iif?>");
4648 /* Find the group, create it if it doesn't exist */
4649 json_object_object_get_ex(json
, grp_str
, &json_group
);
4652 json_group
= json_object_new_object();
4653 json_object_object_add(json
, grp_str
,
4657 /* Find the source nested under the group, create it if
4658 * it doesn't exist */
4659 json_object_object_get_ex(json_group
, src_str
,
4663 json_source
= json_object_new_object();
4664 json_object_object_add(json_group
, src_str
,
4668 json_object_string_add(json_source
, "iif", in_ifname
);
4671 strcpy(proto
, "STATIC");
4674 for (oif_vif_index
= 0; oif_vif_index
< MAXVIFS
;
4676 struct interface
*ifp_out
;
4677 char oif_uptime
[10];
4680 ttl
= s_route
->oif_ttls
[oif_vif_index
];
4684 ifp_out
= pim_if_find_by_vif_index(pim
, oif_vif_index
);
4685 pim_time_uptime(oif_uptime
, sizeof(oif_uptime
),
4687 s_route
->c_oil
.oif_creation
[oif_vif_index
]);
4691 strcpy(out_ifname
, ifp_out
->name
);
4693 strcpy(out_ifname
, "<oif?>");
4696 json_ifp_out
= json_object_new_object();
4697 json_object_string_add(json_ifp_out
, "source",
4699 json_object_string_add(json_ifp_out
, "group",
4701 json_object_boolean_true_add(json_ifp_out
,
4703 json_object_string_add(json_ifp_out
,
4706 json_object_int_add(
4707 json_ifp_out
, "iVifI",
4708 s_route
->c_oil
.oil
.mfcc_parent
);
4709 json_object_string_add(json_ifp_out
,
4710 "outboundInterface",
4712 json_object_int_add(json_ifp_out
, "oVifI",
4714 json_object_int_add(json_ifp_out
, "ttl", ttl
);
4715 json_object_string_add(json_ifp_out
, "upTime",
4718 json_oil
= json_object_new_object();
4719 json_object_object_add(json_source
,
4722 json_object_object_add(json_oil
, out_ifname
,
4726 "%-15s %-15s %-6s %-10s %-10s %-3d %8s %s\n",
4727 src_str
, grp_str
, proto
, in_ifname
,
4728 out_ifname
, ttl
, oif_uptime
,
4730 if (first
&& !fill
) {
4733 in_ifname
[0] = '\0';
4739 if (!uj
&& !found_oif
) {
4741 "%-15s %-15s %-6s %-10s %-10s %-3d %8s %s\n",
4742 src_str
, grp_str
, proto
, in_ifname
, "none", 0,
4743 "--:--:--", pim
->vrf
->name
);
4748 vty_out(vty
, "%s\n", json_object_to_json_string_ext(
4749 json
, JSON_C_TO_STRING_PRETTY
));
4750 json_object_free(json
);
4754 DEFUN (show_ip_mroute
,
4756 "show ip mroute [vrf NAME] [fill] [json]",
4761 "Fill in Assumed data\n"
4764 u_char uj
= use_json(argc
, argv
);
4767 struct vrf
*vrf
= pim_cmd_lookup_vrf(vty
, argv
, argc
, &idx
);
4772 if (argv_find(argv
, argc
, "fill", &idx
))
4775 show_mroute(vrf
->info
, vty
, fill
, uj
);
4779 DEFUN (show_ip_mroute_vrf_all
,
4780 show_ip_mroute_vrf_all_cmd
,
4781 "show ip mroute vrf all [fill] [json]",
4786 "Fill in Assumed data\n"
4789 u_char uj
= use_json(argc
, argv
);
4795 if (argv_find(argv
, argc
, "fill", &idx
))
4800 RB_FOREACH (vrf
, vrf_name_head
, &vrfs_by_name
) {
4804 vty_out(vty
, " \"%s\": ", vrf
->name
);
4807 vty_out(vty
, "VRF: %s\n", vrf
->name
);
4808 show_mroute(vrf
->info
, vty
, fill
, uj
);
4811 vty_out(vty
, "}\n");
4816 static void show_mroute_count(struct pim_instance
*pim
, struct vty
*vty
)
4818 struct listnode
*node
;
4819 struct channel_oil
*c_oil
;
4820 struct static_route
*s_route
;
4825 "Source Group LastUsed Packets Bytes WrongIf \n");
4827 /* Print PIM and IGMP route counts */
4828 for (ALL_LIST_ELEMENTS_RO(pim
->channel_oil_list
, node
, c_oil
)) {
4829 char group_str
[INET_ADDRSTRLEN
];
4830 char source_str
[INET_ADDRSTRLEN
];
4832 if (!c_oil
->installed
)
4835 pim_mroute_update_counters(c_oil
);
4837 pim_inet4_dump("<group?>", c_oil
->oil
.mfcc_mcastgrp
, group_str
,
4839 pim_inet4_dump("<source?>", c_oil
->oil
.mfcc_origin
, source_str
,
4840 sizeof(source_str
));
4842 vty_out(vty
, "%-15s %-15s %-8llu %-7ld %-10ld %-7ld\n",
4843 source_str
, group_str
, c_oil
->cc
.lastused
/ 100,
4844 c_oil
->cc
.pktcnt
, c_oil
->cc
.bytecnt
,
4845 c_oil
->cc
.wrong_if
);
4848 for (ALL_LIST_ELEMENTS_RO(pim
->static_routes
, node
, s_route
)) {
4849 char group_str
[INET_ADDRSTRLEN
];
4850 char source_str
[INET_ADDRSTRLEN
];
4852 if (!s_route
->c_oil
.installed
)
4855 pim_mroute_update_counters(&s_route
->c_oil
);
4857 pim_inet4_dump("<group?>", s_route
->c_oil
.oil
.mfcc_mcastgrp
,
4858 group_str
, sizeof(group_str
));
4859 pim_inet4_dump("<source?>", s_route
->c_oil
.oil
.mfcc_origin
,
4860 source_str
, sizeof(source_str
));
4862 vty_out(vty
, "%-15s %-15s %-8llu %-7ld %-10ld %-7ld\n",
4863 source_str
, group_str
, s_route
->c_oil
.cc
.lastused
,
4864 s_route
->c_oil
.cc
.pktcnt
, s_route
->c_oil
.cc
.bytecnt
,
4865 s_route
->c_oil
.cc
.wrong_if
);
4869 DEFUN (show_ip_mroute_count
,
4870 show_ip_mroute_count_cmd
,
4871 "show ip mroute [vrf NAME] count",
4876 "Route and packet count data\n")
4879 struct vrf
*vrf
= pim_cmd_lookup_vrf(vty
, argv
, argc
, &idx
);
4884 show_mroute_count(vrf
->info
, vty
);
4888 DEFUN (show_ip_mroute_count_vrf_all
,
4889 show_ip_mroute_count_vrf_all_cmd
,
4890 "show ip mroute vrf all count",
4895 "Route and packet count data\n")
4897 u_char uj
= use_json(argc
, argv
);
4903 RB_FOREACH (vrf
, vrf_name_head
, &vrfs_by_name
) {
4907 vty_out(vty
, " \"%s\": ", vrf
->name
);
4910 vty_out(vty
, "VRF: %s\n", vrf
->name
);
4911 show_mroute_count(vrf
->info
, vty
);
4914 vty_out(vty
, "}\n");
4921 "show ip rib [vrf NAME] A.B.C.D",
4926 "Unicast address\n")
4929 struct vrf
*vrf
= pim_cmd_lookup_vrf(vty
, argv
, argc
, &idx
);
4930 struct in_addr addr
;
4931 const char *addr_str
;
4932 struct pim_nexthop nexthop
;
4933 char nexthop_addr_str
[PREFIX_STRLEN
];
4939 memset(&nexthop
, 0, sizeof(nexthop
));
4940 argv_find(argv
, argc
, "A.B.C.D", &idx
);
4941 addr_str
= argv
[idx
]->arg
;
4942 result
= inet_pton(AF_INET
, addr_str
, &addr
);
4944 vty_out(vty
, "Bad unicast address %s: errno=%d: %s\n", addr_str
,
4945 errno
, safe_strerror(errno
));
4949 if (pim_nexthop_lookup(vrf
->info
, &nexthop
, addr
, 0)) {
4951 "Failure querying RIB nexthop for unicast address %s\n",
4957 "Address NextHop Interface Metric Preference\n");
4959 pim_addr_dump("<nexthop?>", &nexthop
.mrib_nexthop_addr
,
4960 nexthop_addr_str
, sizeof(nexthop_addr_str
));
4962 vty_out(vty
, "%-15s %-15s %-9s %6d %10d\n", addr_str
, nexthop_addr_str
,
4963 nexthop
.interface
? nexthop
.interface
->name
: "<ifname?>",
4964 nexthop
.mrib_route_metric
, nexthop
.mrib_metric_preference
);
4969 static void show_ssmpingd(struct pim_instance
*pim
, struct vty
*vty
)
4971 struct listnode
*node
;
4972 struct ssmpingd_sock
*ss
;
4976 "Source Socket Address Port Uptime Requests\n");
4978 if (!pim
->ssmpingd_list
)
4981 now
= pim_time_monotonic_sec();
4983 for (ALL_LIST_ELEMENTS_RO(pim
->ssmpingd_list
, node
, ss
)) {
4984 char source_str
[INET_ADDRSTRLEN
];
4986 struct sockaddr_in bind_addr
;
4987 socklen_t len
= sizeof(bind_addr
);
4988 char bind_addr_str
[INET_ADDRSTRLEN
];
4990 pim_inet4_dump("<src?>", ss
->source_addr
, source_str
,
4991 sizeof(source_str
));
4993 if (pim_socket_getsockname(
4994 ss
->sock_fd
, (struct sockaddr
*)&bind_addr
, &len
)) {
4996 "%% Failure reading socket name for ssmpingd source %s on fd=%d\n",
4997 source_str
, ss
->sock_fd
);
5000 pim_inet4_dump("<addr?>", bind_addr
.sin_addr
, bind_addr_str
,
5001 sizeof(bind_addr_str
));
5002 pim_time_uptime(ss_uptime
, sizeof(ss_uptime
),
5003 now
- ss
->creation
);
5005 vty_out(vty
, "%-15s %6d %-15s %5d %8s %8lld\n", source_str
,
5006 ss
->sock_fd
, bind_addr_str
, ntohs(bind_addr
.sin_port
),
5007 ss_uptime
, (long long)ss
->requests
);
5011 DEFUN (show_ip_ssmpingd
,
5012 show_ip_ssmpingd_cmd
,
5013 "show ip ssmpingd [vrf NAME]",
5020 struct vrf
*vrf
= pim_cmd_lookup_vrf(vty
, argv
, argc
, &idx
);
5025 show_ssmpingd(vrf
->info
, vty
);
5029 static int pim_rp_cmd_worker(struct pim_instance
*pim
, struct vty
*vty
,
5030 const char *rp
, const char *group
,
5035 result
= pim_rp_new(pim
, rp
, group
, plist
);
5037 if (result
== PIM_MALLOC_FAIL
) {
5038 vty_out(vty
, "%% Out of memory\n");
5039 return CMD_WARNING_CONFIG_FAILED
;
5042 if (result
== PIM_GROUP_BAD_ADDRESS
) {
5043 vty_out(vty
, "%% Bad group address specified: %s\n", group
);
5044 return CMD_WARNING_CONFIG_FAILED
;
5047 if (result
== PIM_RP_BAD_ADDRESS
) {
5048 vty_out(vty
, "%% Bad RP address specified: %s\n", rp
);
5049 return CMD_WARNING_CONFIG_FAILED
;
5052 if (result
== PIM_RP_NO_PATH
) {
5053 vty_out(vty
, "%% No Path to RP address specified: %s\n", rp
);
5057 if (result
== PIM_GROUP_OVERLAP
) {
5058 vty_out(vty
, "%% Group range specified cannot exact match another\n");
5059 return CMD_WARNING_CONFIG_FAILED
;
5062 if (result
== PIM_GROUP_PFXLIST_OVERLAP
) {
5064 "%% This group is already covered by a RP prefix-list\n");
5065 return CMD_WARNING_CONFIG_FAILED
;
5068 if (result
== PIM_RP_PFXLIST_IN_USE
) {
5070 "%% The same prefix-list cannot be applied to multiple RPs\n");
5071 return CMD_WARNING_CONFIG_FAILED
;
5077 static int pim_cmd_spt_switchover(struct pim_instance
*pim
,
5078 enum pim_spt_switchover spt
,
5081 pim
->spt
.switchover
= spt
;
5083 switch (pim
->spt
.switchover
) {
5084 case PIM_SPT_IMMEDIATE
:
5086 XFREE(MTYPE_PIM_SPT_PLIST_NAME
, pim
->spt
.plist
);
5088 pim_upstream_add_lhr_star_pimreg(pim
);
5090 case PIM_SPT_INFINITY
:
5091 pim_upstream_remove_lhr_star_pimreg(pim
, plist
);
5094 XFREE(MTYPE_PIM_SPT_PLIST_NAME
, pim
->spt
.plist
);
5098 XSTRDUP(MTYPE_PIM_SPT_PLIST_NAME
, plist
);
5105 DEFUN (ip_pim_spt_switchover_infinity
,
5106 ip_pim_spt_switchover_infinity_cmd
,
5107 "ip pim spt-switchover infinity-and-beyond",
5111 "Never switch to SPT Tree\n")
5113 PIM_DECLVAR_CONTEXT(vrf
, pim
);
5114 return pim_cmd_spt_switchover(pim
, PIM_SPT_INFINITY
, NULL
);
5117 DEFUN (ip_pim_spt_switchover_infinity_plist
,
5118 ip_pim_spt_switchover_infinity_plist_cmd
,
5119 "ip pim spt-switchover infinity-and-beyond prefix-list WORD",
5123 "Never switch to SPT Tree\n"
5124 "Prefix-List to control which groups to switch\n"
5125 "Prefix-List name\n")
5127 PIM_DECLVAR_CONTEXT(vrf
, pim
);
5128 return pim_cmd_spt_switchover(pim
, PIM_SPT_INFINITY
, argv
[5]->arg
);
5131 DEFUN (no_ip_pim_spt_switchover_infinity
,
5132 no_ip_pim_spt_switchover_infinity_cmd
,
5133 "no ip pim spt-switchover infinity-and-beyond",
5138 "Never switch to SPT Tree\n")
5140 PIM_DECLVAR_CONTEXT(vrf
, pim
);
5141 return pim_cmd_spt_switchover(pim
, PIM_SPT_IMMEDIATE
, NULL
);
5144 DEFUN (no_ip_pim_spt_switchover_infinity_plist
,
5145 no_ip_pim_spt_switchover_infinity_plist_cmd
,
5146 "no ip pim spt-switchover infinity-and-beyond prefix-list WORD",
5151 "Never switch to SPT Tree\n"
5152 "Prefix-List to control which groups to switch\n"
5153 "Prefix-List name\n")
5155 PIM_DECLVAR_CONTEXT(vrf
, pim
);
5156 return pim_cmd_spt_switchover(pim
, PIM_SPT_IMMEDIATE
, NULL
);
5159 DEFUN (ip_pim_joinprune_time
,
5160 ip_pim_joinprune_time_cmd
,
5161 "ip pim join-prune-interval (60-600)",
5163 "pim multicast routing\n"
5164 "Join Prune Send Interval\n"
5167 PIM_DECLVAR_CONTEXT(vrf
, pim
);
5168 qpim_t_periodic
= atoi(argv
[3]->arg
);
5172 DEFUN (no_ip_pim_joinprune_time
,
5173 no_ip_pim_joinprune_time_cmd
,
5174 "no ip pim join-prune-interval (60-600)",
5177 "pim multicast routing\n"
5178 "Join Prune Send Interval\n"
5181 PIM_DECLVAR_CONTEXT(vrf
, pim
);
5182 qpim_t_periodic
= PIM_DEFAULT_T_PERIODIC
;
5186 DEFUN (ip_pim_register_suppress
,
5187 ip_pim_register_suppress_cmd
,
5188 "ip pim register-suppress-time (5-60000)",
5190 "pim multicast routing\n"
5191 "Register Suppress Timer\n"
5194 PIM_DECLVAR_CONTEXT(vrf
, pim
);
5195 qpim_register_suppress_time
= atoi(argv
[3]->arg
);
5199 DEFUN (no_ip_pim_register_suppress
,
5200 no_ip_pim_register_suppress_cmd
,
5201 "no ip pim register-suppress-time (5-60000)",
5204 "pim multicast routing\n"
5205 "Register Suppress Timer\n"
5208 PIM_DECLVAR_CONTEXT(vrf
, pim
);
5209 qpim_register_suppress_time
= PIM_REGISTER_SUPPRESSION_TIME_DEFAULT
;
5213 DEFUN (ip_pim_rp_keep_alive
,
5214 ip_pim_rp_keep_alive_cmd
,
5215 "ip pim rp keep-alive-timer (31-60000)",
5217 "pim multicast routing\n"
5219 "Keep alive Timer\n"
5222 PIM_DECLVAR_CONTEXT(vrf
, pim
);
5223 pim
->rp_keep_alive_time
= atoi(argv
[4]->arg
);
5227 DEFUN (no_ip_pim_rp_keep_alive
,
5228 no_ip_pim_rp_keep_alive_cmd
,
5229 "no ip pim rp keep-alive-timer (31-60000)",
5232 "pim multicast routing\n"
5234 "Keep alive Timer\n"
5237 PIM_DECLVAR_CONTEXT(vrf
, pim
);
5238 pim
->rp_keep_alive_time
= PIM_KEEPALIVE_PERIOD
;
5242 DEFUN (ip_pim_keep_alive
,
5243 ip_pim_keep_alive_cmd
,
5244 "ip pim keep-alive-timer (31-60000)",
5246 "pim multicast routing\n"
5247 "Keep alive Timer\n"
5250 PIM_DECLVAR_CONTEXT(vrf
, pim
);
5251 pim
->keep_alive_time
= atoi(argv
[3]->arg
);
5255 DEFUN (no_ip_pim_keep_alive
,
5256 no_ip_pim_keep_alive_cmd
,
5257 "no ip pim keep-alive-timer (31-60000)",
5260 "pim multicast routing\n"
5261 "Keep alive Timer\n"
5264 PIM_DECLVAR_CONTEXT(vrf
, pim
);
5265 pim
->keep_alive_time
= PIM_KEEPALIVE_PERIOD
;
5269 DEFUN (ip_pim_packets
,
5271 "ip pim packets (1-100)",
5273 "pim multicast routing\n"
5274 "packets to process at one time per fd\n"
5275 "Number of packets\n")
5277 PIM_DECLVAR_CONTEXT(vrf
, pim
);
5278 qpim_packet_process
= atoi(argv
[3]->arg
);
5282 DEFUN (no_ip_pim_packets
,
5283 no_ip_pim_packets_cmd
,
5284 "no ip pim packets (1-100)",
5287 "pim multicast routing\n"
5288 "packets to process at one time per fd\n"
5289 "Number of packets\n")
5291 PIM_DECLVAR_CONTEXT(vrf
, pim
);
5292 qpim_packet_process
= PIM_DEFAULT_PACKET_PROCESS
;
5296 DEFUN (ip_pim_v6_secondary
,
5297 ip_pim_v6_secondary_cmd
,
5298 "ip pim send-v6-secondary",
5300 "pim multicast routing\n"
5301 "Send v6 secondary addresses\n")
5303 PIM_DECLVAR_CONTEXT(vrf
, pim
);
5304 pim
->send_v6_secondary
= 1;
5309 DEFUN (no_ip_pim_v6_secondary
,
5310 no_ip_pim_v6_secondary_cmd
,
5311 "no ip pim send-v6-secondary",
5314 "pim multicast routing\n"
5315 "Send v6 secondary addresses\n")
5317 PIM_DECLVAR_CONTEXT(vrf
, pim
);
5318 pim
->send_v6_secondary
= 0;
5325 "ip pim rp A.B.C.D [A.B.C.D/M]",
5327 "pim multicast routing\n"
5329 "ip address of RP\n"
5330 "Group Address range to cover\n")
5332 PIM_DECLVAR_CONTEXT(vrf
, pim
);
5335 if (argc
== (idx_ipv4
+ 1))
5336 return pim_rp_cmd_worker(pim
, vty
, argv
[idx_ipv4
]->arg
, NULL
,
5339 return pim_rp_cmd_worker(pim
, vty
, argv
[idx_ipv4
]->arg
,
5340 argv
[idx_ipv4
+ 1]->arg
, NULL
);
5343 DEFUN (ip_pim_rp_prefix_list
,
5344 ip_pim_rp_prefix_list_cmd
,
5345 "ip pim rp A.B.C.D prefix-list WORD",
5347 "pim multicast routing\n"
5349 "ip address of RP\n"
5350 "group prefix-list filter\n"
5351 "Name of a prefix-list\n")
5353 PIM_DECLVAR_CONTEXT(vrf
, pim
);
5354 return pim_rp_cmd_worker(pim
, vty
, argv
[3]->arg
, NULL
, argv
[5]->arg
);
5357 static int pim_no_rp_cmd_worker(struct pim_instance
*pim
, struct vty
*vty
,
5358 const char *rp
, const char *group
,
5361 int result
= pim_rp_del(pim
, rp
, group
, plist
);
5363 if (result
== PIM_GROUP_BAD_ADDRESS
) {
5364 vty_out(vty
, "%% Bad group address specified: %s\n", group
);
5365 return CMD_WARNING_CONFIG_FAILED
;
5368 if (result
== PIM_RP_BAD_ADDRESS
) {
5369 vty_out(vty
, "%% Bad RP address specified: %s\n", rp
);
5370 return CMD_WARNING_CONFIG_FAILED
;
5373 if (result
== PIM_RP_NOT_FOUND
) {
5374 vty_out(vty
, "%% Unable to find specified RP\n");
5375 return CMD_WARNING_CONFIG_FAILED
;
5381 DEFUN (no_ip_pim_rp
,
5383 "no ip pim rp A.B.C.D [A.B.C.D/M]",
5386 "pim multicast routing\n"
5388 "ip address of RP\n"
5389 "Group Address range to cover\n")
5391 PIM_DECLVAR_CONTEXT(vrf
, pim
);
5392 int idx_ipv4
= 4, idx_group
= 0;
5394 if (argv_find(argv
, argc
, "A.B.C.D/M", &idx_group
))
5395 return pim_no_rp_cmd_worker(pim
, vty
, argv
[idx_ipv4
]->arg
,
5396 argv
[idx_group
]->arg
, NULL
);
5398 return pim_no_rp_cmd_worker(pim
, vty
, argv
[idx_ipv4
]->arg
, NULL
,
5402 DEFUN (no_ip_pim_rp_prefix_list
,
5403 no_ip_pim_rp_prefix_list_cmd
,
5404 "no ip pim rp A.B.C.D prefix-list WORD",
5407 "pim multicast routing\n"
5409 "ip address of RP\n"
5410 "group prefix-list filter\n"
5411 "Name of a prefix-list\n")
5413 PIM_DECLVAR_CONTEXT(vrf
, pim
);
5414 return pim_no_rp_cmd_worker(pim
, vty
, argv
[4]->arg
, NULL
, argv
[6]->arg
);
5417 static int pim_ssm_cmd_worker(struct pim_instance
*pim
, struct vty
*vty
,
5420 int result
= pim_ssm_range_set(pim
, pim
->vrf_id
, plist
);
5422 if (result
== PIM_SSM_ERR_NONE
)
5426 case PIM_SSM_ERR_NO_VRF
:
5427 vty_out(vty
, "%% VRF doesn't exist\n");
5429 case PIM_SSM_ERR_DUP
:
5430 vty_out(vty
, "%% duplicate config\n");
5433 vty_out(vty
, "%% ssm range config failed\n");
5436 return CMD_WARNING_CONFIG_FAILED
;
5439 DEFUN (ip_pim_ssm_prefix_list
,
5440 ip_pim_ssm_prefix_list_cmd
,
5441 "ip pim ssm prefix-list WORD",
5443 "pim multicast routing\n"
5444 "Source Specific Multicast\n"
5445 "group range prefix-list filter\n"
5446 "Name of a prefix-list\n")
5448 PIM_DECLVAR_CONTEXT(vrf
, pim
);
5449 return pim_ssm_cmd_worker(pim
, vty
, argv
[4]->arg
);
5452 DEFUN (no_ip_pim_ssm_prefix_list
,
5453 no_ip_pim_ssm_prefix_list_cmd
,
5454 "no ip pim ssm prefix-list",
5457 "pim multicast routing\n"
5458 "Source Specific Multicast\n"
5459 "group range prefix-list filter\n")
5461 PIM_DECLVAR_CONTEXT(vrf
, pim
);
5462 return pim_ssm_cmd_worker(pim
, vty
, NULL
);
5465 DEFUN (no_ip_pim_ssm_prefix_list_name
,
5466 no_ip_pim_ssm_prefix_list_name_cmd
,
5467 "no ip pim ssm prefix-list WORD",
5470 "pim multicast routing\n"
5471 "Source Specific Multicast\n"
5472 "group range prefix-list filter\n"
5473 "Name of a prefix-list\n")
5475 PIM_DECLVAR_CONTEXT(vrf
, pim
);
5476 struct pim_ssm
*ssm
= pim
->ssm_info
;
5478 if (ssm
->plist_name
&& !strcmp(ssm
->plist_name
, argv
[5]->arg
))
5479 return pim_ssm_cmd_worker(pim
, vty
, NULL
);
5481 vty_out(vty
, "%% pim ssm prefix-list %s doesn't exist\n", argv
[5]->arg
);
5483 return CMD_WARNING_CONFIG_FAILED
;
5486 static void ip_pim_ssm_show_group_range(struct pim_instance
*pim
,
5487 struct vty
*vty
, u_char uj
)
5489 struct pim_ssm
*ssm
= pim
->ssm_info
;
5490 const char *range_str
=
5491 ssm
->plist_name
? ssm
->plist_name
: PIM_SSM_STANDARD_RANGE
;
5495 json
= json_object_new_object();
5496 json_object_string_add(json
, "ssmGroups", range_str
);
5497 vty_out(vty
, "%s\n", json_object_to_json_string_ext(
5498 json
, JSON_C_TO_STRING_PRETTY
));
5499 json_object_free(json
);
5501 vty_out(vty
, "SSM group range : %s\n", range_str
);
5504 DEFUN (show_ip_pim_ssm_range
,
5505 show_ip_pim_ssm_range_cmd
,
5506 "show ip pim [vrf NAME] group-type [json]",
5515 struct vrf
*vrf
= pim_cmd_lookup_vrf(vty
, argv
, argc
, &idx
);
5516 u_char uj
= use_json(argc
, argv
);
5521 ip_pim_ssm_show_group_range(vrf
->info
, vty
, uj
);
5526 static void ip_pim_ssm_show_group_type(struct pim_instance
*pim
,
5527 struct vty
*vty
, u_char uj
,
5530 struct in_addr group_addr
;
5531 const char *type_str
;
5534 result
= inet_pton(AF_INET
, group
, &group_addr
);
5536 type_str
= "invalid";
5538 if (pim_is_group_224_4(group_addr
))
5540 pim_is_grp_ssm(pim
, group_addr
) ? "SSM" : "ASM";
5542 type_str
= "not-multicast";
5547 json
= json_object_new_object();
5548 json_object_string_add(json
, "groupType", type_str
);
5549 vty_out(vty
, "%s\n", json_object_to_json_string_ext(
5550 json
, JSON_C_TO_STRING_PRETTY
));
5551 json_object_free(json
);
5553 vty_out(vty
, "Group type : %s\n", type_str
);
5556 DEFUN (show_ip_pim_group_type
,
5557 show_ip_pim_group_type_cmd
,
5558 "show ip pim [vrf NAME] group-type A.B.C.D [json]",
5563 "multicast group type\n"
5568 struct vrf
*vrf
= pim_cmd_lookup_vrf(vty
, argv
, argc
, &idx
);
5569 u_char uj
= use_json(argc
, argv
);
5574 argv_find(argv
, argc
, "A.B.C.D", &idx
);
5575 ip_pim_ssm_show_group_type(vrf
->info
, vty
, uj
, argv
[idx
]->arg
);
5580 DEFUN_HIDDEN (ip_multicast_routing
,
5581 ip_multicast_routing_cmd
,
5582 "ip multicast-routing",
5584 "Enable IP multicast forwarding\n")
5589 DEFUN_HIDDEN (no_ip_multicast_routing
,
5590 no_ip_multicast_routing_cmd
,
5591 "no ip multicast-routing",
5594 "Enable IP multicast forwarding\n")
5597 "Command is Disabled and will be removed in a future version\n");
5603 "ip ssmpingd [A.B.C.D]",
5608 PIM_DECLVAR_CONTEXT(vrf
, pim
);
5611 struct in_addr source_addr
;
5612 const char *source_str
= (argc
== 3) ? argv
[idx_ipv4
]->arg
: "0.0.0.0";
5614 result
= inet_pton(AF_INET
, source_str
, &source_addr
);
5616 vty_out(vty
, "%% Bad source address %s: errno=%d: %s\n",
5617 source_str
, errno
, safe_strerror(errno
));
5618 return CMD_WARNING_CONFIG_FAILED
;
5621 result
= pim_ssmpingd_start(pim
, source_addr
);
5623 vty_out(vty
, "%% Failure starting ssmpingd for source %s: %d\n",
5624 source_str
, result
);
5625 return CMD_WARNING_CONFIG_FAILED
;
5631 DEFUN (no_ip_ssmpingd
,
5633 "no ip ssmpingd [A.B.C.D]",
5639 PIM_DECLVAR_CONTEXT(vrf
, pim
);
5642 struct in_addr source_addr
;
5643 const char *source_str
= (argc
== 4) ? argv
[idx_ipv4
]->arg
: "0.0.0.0";
5645 result
= inet_pton(AF_INET
, source_str
, &source_addr
);
5647 vty_out(vty
, "%% Bad source address %s: errno=%d: %s\n",
5648 source_str
, errno
, safe_strerror(errno
));
5649 return CMD_WARNING_CONFIG_FAILED
;
5652 result
= pim_ssmpingd_stop(pim
, source_addr
);
5654 vty_out(vty
, "%% Failure stopping ssmpingd for source %s: %d\n",
5655 source_str
, result
);
5656 return CMD_WARNING_CONFIG_FAILED
;
5666 "pim multicast routing\n"
5667 "Enable PIM ECMP \n")
5669 PIM_DECLVAR_CONTEXT(vrf
, pim
);
5670 qpim_ecmp_enable
= 1;
5675 DEFUN (no_ip_pim_ecmp
,
5680 "pim multicast routing\n"
5681 "Disable PIM ECMP \n")
5683 PIM_DECLVAR_CONTEXT(vrf
, pim
);
5684 qpim_ecmp_enable
= 0;
5689 DEFUN (ip_pim_ecmp_rebalance
,
5690 ip_pim_ecmp_rebalance_cmd
,
5691 "ip pim ecmp rebalance",
5693 "pim multicast routing\n"
5694 "Enable PIM ECMP \n"
5695 "Enable PIM ECMP Rebalance\n")
5697 PIM_DECLVAR_CONTEXT(vrf
, pim
);
5698 qpim_ecmp_enable
= 1;
5699 qpim_ecmp_rebalance_enable
= 1;
5704 DEFUN (no_ip_pim_ecmp_rebalance
,
5705 no_ip_pim_ecmp_rebalance_cmd
,
5706 "no ip pim ecmp rebalance",
5709 "pim multicast routing\n"
5710 "Disable PIM ECMP \n"
5711 "Disable PIM ECMP Rebalance\n")
5713 PIM_DECLVAR_CONTEXT(vrf
, pim
);
5714 qpim_ecmp_rebalance_enable
= 0;
5719 static int pim_cmd_igmp_start(struct vty
*vty
, struct interface
*ifp
)
5721 struct pim_interface
*pim_ifp
;
5722 uint8_t need_startup
= 0;
5724 pim_ifp
= ifp
->info
;
5727 pim_ifp
= pim_if_new(ifp
, 1 /* igmp=true */, 0 /* pim=false */);
5729 vty_out(vty
, "Could not enable IGMP on interface %s\n",
5731 return CMD_WARNING_CONFIG_FAILED
;
5735 if (!PIM_IF_TEST_IGMP(pim_ifp
->options
)) {
5736 PIM_IF_DO_IGMP(pim_ifp
->options
);
5741 /* 'ip igmp' executed multiple times, with need_startup
5742 avoid multiple if add all and membership refresh */
5744 pim_if_addr_add_all(ifp
);
5745 pim_if_membership_refresh(ifp
);
5751 DEFUN (interface_ip_igmp
,
5752 interface_ip_igmp_cmd
,
5757 VTY_DECLVAR_CONTEXT(interface
, ifp
);
5759 return pim_cmd_igmp_start(vty
, ifp
);
5762 DEFUN (interface_no_ip_igmp
,
5763 interface_no_ip_igmp_cmd
,
5769 VTY_DECLVAR_CONTEXT(interface
, ifp
);
5770 struct pim_interface
*pim_ifp
= ifp
->info
;
5775 PIM_IF_DONT_IGMP(pim_ifp
->options
);
5777 pim_if_membership_clear(ifp
);
5779 pim_if_addr_del_all_igmp(ifp
);
5781 if (!PIM_IF_TEST_PIM(pim_ifp
->options
)) {
5788 DEFUN (interface_ip_igmp_join
,
5789 interface_ip_igmp_join_cmd
,
5790 "ip igmp join A.B.C.D A.B.C.D",
5793 "IGMP join multicast group\n"
5794 "Multicast group address\n"
5797 VTY_DECLVAR_CONTEXT(interface
, ifp
);
5800 const char *group_str
;
5801 const char *source_str
;
5802 struct in_addr group_addr
;
5803 struct in_addr source_addr
;
5807 group_str
= argv
[idx_ipv4
]->arg
;
5808 result
= inet_pton(AF_INET
, group_str
, &group_addr
);
5810 vty_out(vty
, "Bad group address %s: errno=%d: %s\n", group_str
,
5811 errno
, safe_strerror(errno
));
5812 return CMD_WARNING_CONFIG_FAILED
;
5815 /* Source address */
5816 source_str
= argv
[idx_ipv4_2
]->arg
;
5817 result
= inet_pton(AF_INET
, source_str
, &source_addr
);
5819 vty_out(vty
, "Bad source address %s: errno=%d: %s\n",
5820 source_str
, errno
, safe_strerror(errno
));
5821 return CMD_WARNING_CONFIG_FAILED
;
5824 CMD_FERR_RETURN(pim_if_igmp_join_add(ifp
, group_addr
, source_addr
),
5825 "Failure joining IGMP group: $ERR");
5830 DEFUN (interface_no_ip_igmp_join
,
5831 interface_no_ip_igmp_join_cmd
,
5832 "no ip igmp join A.B.C.D A.B.C.D",
5836 "IGMP join multicast group\n"
5837 "Multicast group address\n"
5840 VTY_DECLVAR_CONTEXT(interface
, ifp
);
5843 const char *group_str
;
5844 const char *source_str
;
5845 struct in_addr group_addr
;
5846 struct in_addr source_addr
;
5850 group_str
= argv
[idx_ipv4
]->arg
;
5851 result
= inet_pton(AF_INET
, group_str
, &group_addr
);
5853 vty_out(vty
, "Bad group address %s: errno=%d: %s\n", group_str
,
5854 errno
, safe_strerror(errno
));
5855 return CMD_WARNING_CONFIG_FAILED
;
5858 /* Source address */
5859 source_str
= argv
[idx_ipv4_2
]->arg
;
5860 result
= inet_pton(AF_INET
, source_str
, &source_addr
);
5862 vty_out(vty
, "Bad source address %s: errno=%d: %s\n",
5863 source_str
, errno
, safe_strerror(errno
));
5864 return CMD_WARNING_CONFIG_FAILED
;
5867 result
= pim_if_igmp_join_del(ifp
, group_addr
, source_addr
);
5870 "%% Failure leaving IGMP group %s source %s on interface %s: %d\n",
5871 group_str
, source_str
, ifp
->name
, result
);
5872 return CMD_WARNING_CONFIG_FAILED
;
5879 CLI reconfiguration affects the interface level (struct pim_interface).
5880 This function propagates the reconfiguration to every active socket
5883 static void igmp_sock_query_interval_reconfig(struct igmp_sock
*igmp
)
5885 struct interface
*ifp
;
5886 struct pim_interface
*pim_ifp
;
5890 /* other querier present? */
5892 if (igmp
->t_other_querier_timer
)
5895 /* this is the querier */
5897 zassert(igmp
->interface
);
5898 zassert(igmp
->interface
->info
);
5900 ifp
= igmp
->interface
;
5901 pim_ifp
= ifp
->info
;
5903 if (PIM_DEBUG_IGMP_TRACE
) {
5904 char ifaddr_str
[INET_ADDRSTRLEN
];
5905 pim_inet4_dump("<ifaddr?>", igmp
->ifaddr
, ifaddr_str
,
5906 sizeof(ifaddr_str
));
5907 zlog_debug("%s: Querier %s on %s reconfig query_interval=%d",
5908 __PRETTY_FUNCTION__
, ifaddr_str
, ifp
->name
,
5909 pim_ifp
->igmp_default_query_interval
);
5913 igmp_startup_mode_on() will reset QQI:
5915 igmp->querier_query_interval = pim_ifp->igmp_default_query_interval;
5917 igmp_startup_mode_on(igmp
);
5920 static void igmp_sock_query_reschedule(struct igmp_sock
*igmp
)
5922 if (igmp
->t_igmp_query_timer
) {
5923 /* other querier present */
5924 zassert(igmp
->t_igmp_query_timer
);
5925 zassert(!igmp
->t_other_querier_timer
);
5927 pim_igmp_general_query_off(igmp
);
5928 pim_igmp_general_query_on(igmp
);
5930 zassert(igmp
->t_igmp_query_timer
);
5931 zassert(!igmp
->t_other_querier_timer
);
5933 /* this is the querier */
5935 zassert(!igmp
->t_igmp_query_timer
);
5936 zassert(igmp
->t_other_querier_timer
);
5938 pim_igmp_other_querier_timer_off(igmp
);
5939 pim_igmp_other_querier_timer_on(igmp
);
5941 zassert(!igmp
->t_igmp_query_timer
);
5942 zassert(igmp
->t_other_querier_timer
);
5946 static void change_query_interval(struct pim_interface
*pim_ifp
,
5949 struct listnode
*sock_node
;
5950 struct igmp_sock
*igmp
;
5952 pim_ifp
->igmp_default_query_interval
= query_interval
;
5954 for (ALL_LIST_ELEMENTS_RO(pim_ifp
->igmp_socket_list
, sock_node
, igmp
)) {
5955 igmp_sock_query_interval_reconfig(igmp
);
5956 igmp_sock_query_reschedule(igmp
);
5960 static void change_query_max_response_time(struct pim_interface
*pim_ifp
,
5961 int query_max_response_time_dsec
)
5963 struct listnode
*sock_node
;
5964 struct igmp_sock
*igmp
;
5966 pim_ifp
->igmp_query_max_response_time_dsec
=
5967 query_max_response_time_dsec
;
5970 Below we modify socket/group/source timers in order to quickly
5971 reflect the change. Otherwise, those timers would eventually catch
5975 /* scan all sockets */
5976 for (ALL_LIST_ELEMENTS_RO(pim_ifp
->igmp_socket_list
, sock_node
, igmp
)) {
5977 struct listnode
*grp_node
;
5978 struct igmp_group
*grp
;
5980 /* reschedule socket general query */
5981 igmp_sock_query_reschedule(igmp
);
5983 /* scan socket groups */
5984 for (ALL_LIST_ELEMENTS_RO(igmp
->igmp_group_list
, grp_node
,
5986 struct listnode
*src_node
;
5987 struct igmp_source
*src
;
5989 /* reset group timers for groups in EXCLUDE mode */
5990 if (grp
->group_filtermode_isexcl
) {
5991 igmp_group_reset_gmi(grp
);
5994 /* scan group sources */
5995 for (ALL_LIST_ELEMENTS_RO(grp
->group_source_list
,
5998 /* reset source timers for sources with running
6000 if (src
->t_source_timer
) {
6001 igmp_source_reset_gmi(igmp
, grp
, src
);
6008 #define IGMP_QUERY_INTERVAL_MIN (1)
6009 #define IGMP_QUERY_INTERVAL_MAX (1800)
6011 DEFUN (interface_ip_igmp_query_interval
,
6012 interface_ip_igmp_query_interval_cmd
,
6013 "ip igmp query-interval (1-1800)",
6016 IFACE_IGMP_QUERY_INTERVAL_STR
6017 "Query interval in seconds\n")
6019 VTY_DECLVAR_CONTEXT(interface
, ifp
);
6020 struct pim_interface
*pim_ifp
= ifp
->info
;
6022 int query_interval_dsec
;
6026 ret
= pim_cmd_igmp_start(vty
, ifp
);
6027 if (ret
!= CMD_SUCCESS
)
6029 pim_ifp
= ifp
->info
;
6032 query_interval
= atoi(argv
[3]->arg
);
6033 query_interval_dsec
= 10 * query_interval
;
6036 It seems we don't need to check bounds since command.c does it
6037 already, but we verify them anyway for extra safety.
6039 if (query_interval
< IGMP_QUERY_INTERVAL_MIN
) {
6041 "General query interval %d lower than minimum %d\n",
6042 query_interval
, IGMP_QUERY_INTERVAL_MIN
);
6043 return CMD_WARNING_CONFIG_FAILED
;
6045 if (query_interval
> IGMP_QUERY_INTERVAL_MAX
) {
6047 "General query interval %d higher than maximum %d\n",
6048 query_interval
, IGMP_QUERY_INTERVAL_MAX
);
6049 return CMD_WARNING_CONFIG_FAILED
;
6052 if (query_interval_dsec
<= pim_ifp
->igmp_query_max_response_time_dsec
) {
6054 "Can't set general query interval %d dsec <= query max response time %d dsec.\n",
6055 query_interval_dsec
,
6056 pim_ifp
->igmp_query_max_response_time_dsec
);
6057 return CMD_WARNING_CONFIG_FAILED
;
6060 change_query_interval(pim_ifp
, query_interval
);
6065 DEFUN (interface_no_ip_igmp_query_interval
,
6066 interface_no_ip_igmp_query_interval_cmd
,
6067 "no ip igmp query-interval",
6071 IFACE_IGMP_QUERY_INTERVAL_STR
)
6073 VTY_DECLVAR_CONTEXT(interface
, ifp
);
6074 struct pim_interface
*pim_ifp
= ifp
->info
;
6075 int default_query_interval_dsec
;
6080 default_query_interval_dsec
= IGMP_GENERAL_QUERY_INTERVAL
* 10;
6082 if (default_query_interval_dsec
6083 <= pim_ifp
->igmp_query_max_response_time_dsec
) {
6085 "Can't set default general query interval %d dsec <= query max response time %d dsec.\n",
6086 default_query_interval_dsec
,
6087 pim_ifp
->igmp_query_max_response_time_dsec
);
6088 return CMD_WARNING_CONFIG_FAILED
;
6091 change_query_interval(pim_ifp
, IGMP_GENERAL_QUERY_INTERVAL
);
6096 DEFUN (interface_ip_igmp_version
,
6097 interface_ip_igmp_version_cmd
,
6098 "ip igmp version (2-3)",
6102 "IGMP version number\n")
6104 VTY_DECLVAR_CONTEXT(interface
, ifp
);
6105 struct pim_interface
*pim_ifp
= ifp
->info
;
6106 int igmp_version
, old_version
= 0;
6110 ret
= pim_cmd_igmp_start(vty
, ifp
);
6111 if (ret
!= CMD_SUCCESS
)
6113 pim_ifp
= ifp
->info
;
6116 igmp_version
= atoi(argv
[3]->arg
);
6117 old_version
= pim_ifp
->igmp_version
;
6118 pim_ifp
->igmp_version
= igmp_version
;
6120 // Check if IGMP is Enabled otherwise, enable on interface
6121 if (!PIM_IF_TEST_IGMP(pim_ifp
->options
)) {
6122 PIM_IF_DO_IGMP(pim_ifp
->options
);
6123 pim_if_addr_add_all(ifp
);
6124 pim_if_membership_refresh(ifp
);
6125 old_version
= igmp_version
; // avoid refreshing membership
6128 /* Current and new version is different refresh existing
6129 membership. Going from 3 -> 2 or 2 -> 3. */
6130 if (old_version
!= igmp_version
)
6131 pim_if_membership_refresh(ifp
);
6136 DEFUN (interface_no_ip_igmp_version
,
6137 interface_no_ip_igmp_version_cmd
,
6138 "no ip igmp version (2-3)",
6143 "IGMP version number\n")
6145 VTY_DECLVAR_CONTEXT(interface
, ifp
);
6146 struct pim_interface
*pim_ifp
= ifp
->info
;
6151 pim_ifp
->igmp_version
= IGMP_DEFAULT_VERSION
;
6156 #define IGMP_QUERY_MAX_RESPONSE_TIME_MIN_DSEC (10)
6157 #define IGMP_QUERY_MAX_RESPONSE_TIME_MAX_DSEC (250)
6159 DEFUN (interface_ip_igmp_query_max_response_time
,
6160 interface_ip_igmp_query_max_response_time_cmd
,
6161 "ip igmp query-max-response-time (10-250)",
6164 IFACE_IGMP_QUERY_MAX_RESPONSE_TIME_STR
6165 "Query response value in deci-seconds\n")
6167 VTY_DECLVAR_CONTEXT(interface
, ifp
);
6168 struct pim_interface
*pim_ifp
= ifp
->info
;
6169 int query_max_response_time
;
6173 ret
= pim_cmd_igmp_start(vty
, ifp
);
6174 if (ret
!= CMD_SUCCESS
)
6176 pim_ifp
= ifp
->info
;
6179 query_max_response_time
= atoi(argv
[3]->arg
);
6181 if (query_max_response_time
6182 >= pim_ifp
->igmp_default_query_interval
* 10) {
6184 "Can't set query max response time %d sec >= general query interval %d sec\n",
6185 query_max_response_time
,
6186 pim_ifp
->igmp_default_query_interval
);
6187 return CMD_WARNING_CONFIG_FAILED
;
6190 change_query_max_response_time(pim_ifp
, query_max_response_time
);
6195 DEFUN (interface_no_ip_igmp_query_max_response_time
,
6196 interface_no_ip_igmp_query_max_response_time_cmd
,
6197 "no ip igmp query-max-response-time (10-250)",
6201 IFACE_IGMP_QUERY_MAX_RESPONSE_TIME_STR
6202 "Time for response in deci-seconds\n")
6204 VTY_DECLVAR_CONTEXT(interface
, ifp
);
6205 struct pim_interface
*pim_ifp
= ifp
->info
;
6210 change_query_max_response_time(pim_ifp
,
6211 IGMP_QUERY_MAX_RESPONSE_TIME_DSEC
);
6216 #define IGMP_QUERY_MAX_RESPONSE_TIME_MIN_DSEC (10)
6217 #define IGMP_QUERY_MAX_RESPONSE_TIME_MAX_DSEC (250)
6219 DEFUN_HIDDEN (interface_ip_igmp_query_max_response_time_dsec
,
6220 interface_ip_igmp_query_max_response_time_dsec_cmd
,
6221 "ip igmp query-max-response-time-dsec (10-250)",
6224 IFACE_IGMP_QUERY_MAX_RESPONSE_TIME_DSEC_STR
6225 "Query response value in deciseconds\n")
6227 VTY_DECLVAR_CONTEXT(interface
, ifp
);
6228 struct pim_interface
*pim_ifp
= ifp
->info
;
6229 int query_max_response_time_dsec
;
6230 int default_query_interval_dsec
;
6234 ret
= pim_cmd_igmp_start(vty
, ifp
);
6235 if (ret
!= CMD_SUCCESS
)
6237 pim_ifp
= ifp
->info
;
6240 query_max_response_time_dsec
= atoi(argv
[4]->arg
);
6242 default_query_interval_dsec
= 10 * pim_ifp
->igmp_default_query_interval
;
6244 if (query_max_response_time_dsec
>= default_query_interval_dsec
) {
6246 "Can't set query max response time %d dsec >= general query interval %d dsec\n",
6247 query_max_response_time_dsec
,
6248 default_query_interval_dsec
);
6249 return CMD_WARNING_CONFIG_FAILED
;
6252 change_query_max_response_time(pim_ifp
, query_max_response_time_dsec
);
6257 DEFUN_HIDDEN (interface_no_ip_igmp_query_max_response_time_dsec
,
6258 interface_no_ip_igmp_query_max_response_time_dsec_cmd
,
6259 "no ip igmp query-max-response-time-dsec",
6263 IFACE_IGMP_QUERY_MAX_RESPONSE_TIME_DSEC_STR
)
6265 VTY_DECLVAR_CONTEXT(interface
, ifp
);
6266 struct pim_interface
*pim_ifp
= ifp
->info
;
6271 change_query_max_response_time(pim_ifp
,
6272 IGMP_QUERY_MAX_RESPONSE_TIME_DSEC
);
6277 DEFUN (interface_ip_pim_drprio
,
6278 interface_ip_pim_drprio_cmd
,
6279 "ip pim drpriority (1-4294967295)",
6282 "Set the Designated Router Election Priority\n"
6283 "Value of the new DR Priority\n")
6285 VTY_DECLVAR_CONTEXT(interface
, ifp
);
6287 struct pim_interface
*pim_ifp
= ifp
->info
;
6288 uint32_t old_dr_prio
;
6291 vty_out(vty
, "Please enable PIM on interface, first\n");
6292 return CMD_WARNING_CONFIG_FAILED
;
6295 old_dr_prio
= pim_ifp
->pim_dr_priority
;
6297 pim_ifp
->pim_dr_priority
= strtol(argv
[idx_number
]->arg
, NULL
, 10);
6299 if (old_dr_prio
!= pim_ifp
->pim_dr_priority
) {
6300 if (pim_if_dr_election(ifp
))
6301 pim_hello_restart_now(ifp
);
6307 DEFUN (interface_no_ip_pim_drprio
,
6308 interface_no_ip_pim_drprio_cmd
,
6309 "no ip pim drpriority [(1-4294967295)]",
6313 "Revert the Designated Router Priority to default\n"
6314 "Old Value of the Priority\n")
6316 VTY_DECLVAR_CONTEXT(interface
, ifp
);
6317 struct pim_interface
*pim_ifp
= ifp
->info
;
6320 vty_out(vty
, "Pim not enabled on this interface\n");
6321 return CMD_WARNING_CONFIG_FAILED
;
6324 if (pim_ifp
->pim_dr_priority
!= PIM_DEFAULT_DR_PRIORITY
) {
6325 pim_ifp
->pim_dr_priority
= PIM_DEFAULT_DR_PRIORITY
;
6326 if (pim_if_dr_election(ifp
))
6327 pim_hello_restart_now(ifp
);
6333 static int pim_cmd_interface_add(struct interface
*ifp
)
6335 struct pim_interface
*pim_ifp
= ifp
->info
;
6338 pim_ifp
= pim_if_new(ifp
, 0 /* igmp=false */, 1 /* pim=true */);
6343 PIM_IF_DO_PIM(pim_ifp
->options
);
6346 pim_if_addr_add_all(ifp
);
6347 pim_if_membership_refresh(ifp
);
6351 DEFUN_HIDDEN (interface_ip_pim_ssm
,
6352 interface_ip_pim_ssm_cmd
,
6358 VTY_DECLVAR_CONTEXT(interface
, ifp
);
6360 if (!pim_cmd_interface_add(ifp
)) {
6361 vty_out(vty
, "Could not enable PIM SM on interface\n");
6362 return CMD_WARNING_CONFIG_FAILED
;
6366 "WARN: Enabled PIM SM on interface; configure PIM SSM "
6367 "range if needed\n");
6371 DEFUN (interface_ip_pim_sm
,
6372 interface_ip_pim_sm_cmd
,
6378 struct pim_interface
*pim_ifp
;
6380 VTY_DECLVAR_CONTEXT(interface
, ifp
);
6381 if (!pim_cmd_interface_add(ifp
)) {
6382 vty_out(vty
, "Could not enable PIM SM on interface\n");
6383 return CMD_WARNING_CONFIG_FAILED
;
6386 pim_ifp
= ifp
->info
;
6388 pim_if_create_pimreg(pim_ifp
->pim
);
6393 static int pim_cmd_interface_delete(struct interface
*ifp
)
6395 struct pim_interface
*pim_ifp
= ifp
->info
;
6400 PIM_IF_DONT_PIM(pim_ifp
->options
);
6402 pim_if_membership_clear(ifp
);
6405 pim_sock_delete() removes all neighbors from
6406 pim_ifp->pim_neighbor_list.
6408 pim_sock_delete(ifp
, "pim unconfigured on interface");
6410 if (!PIM_IF_TEST_IGMP(pim_ifp
->options
)) {
6411 pim_if_addr_del_all(ifp
);
6418 DEFUN_HIDDEN (interface_no_ip_pim_ssm
,
6419 interface_no_ip_pim_ssm_cmd
,
6426 VTY_DECLVAR_CONTEXT(interface
, ifp
);
6427 if (!pim_cmd_interface_delete(ifp
)) {
6428 vty_out(vty
, "Unable to delete interface information\n");
6429 return CMD_WARNING_CONFIG_FAILED
;
6435 DEFUN (interface_no_ip_pim_sm
,
6436 interface_no_ip_pim_sm_cmd
,
6443 VTY_DECLVAR_CONTEXT(interface
, ifp
);
6444 if (!pim_cmd_interface_delete(ifp
)) {
6445 vty_out(vty
, "Unable to delete interface information\n");
6446 return CMD_WARNING_CONFIG_FAILED
;
6453 DEFUN(interface_ip_pim_boundary_oil
,
6454 interface_ip_pim_boundary_oil_cmd
,
6455 "ip multicast boundary oil WORD",
6457 "Generic multicast configuration options\n"
6458 "Define multicast boundary\n"
6459 "Filter OIL by group using prefix list\n"
6460 "Prefix list to filter OIL with\n")
6462 VTY_DECLVAR_CONTEXT(interface
, iif
);
6463 struct pim_interface
*pim_ifp
;
6466 argv_find(argv
, argc
, "WORD", &idx
);
6468 PIM_GET_PIM_INTERFACE(pim_ifp
, iif
);
6470 if (pim_ifp
->boundary_oil_plist
)
6471 XFREE(MTYPE_PIM_INTERFACE
, pim_ifp
->boundary_oil_plist
);
6473 pim_ifp
->boundary_oil_plist
=
6474 XSTRDUP(MTYPE_PIM_INTERFACE
, argv
[idx
]->arg
);
6476 /* Interface will be pruned from OIL on next Join */
6480 DEFUN(interface_no_ip_pim_boundary_oil
,
6481 interface_no_ip_pim_boundary_oil_cmd
,
6482 "no ip multicast boundary oil [WORD]",
6485 "Generic multicast configuration options\n"
6486 "Define multicast boundary\n"
6487 "Filter OIL by group using prefix list\n"
6488 "Prefix list to filter OIL with\n")
6490 VTY_DECLVAR_CONTEXT(interface
, iif
);
6491 struct pim_interface
*pim_ifp
;
6494 argv_find(argv
, argc
, "WORD", &idx
);
6496 PIM_GET_PIM_INTERFACE(pim_ifp
, iif
);
6498 if (pim_ifp
->boundary_oil_plist
)
6499 XFREE(MTYPE_PIM_INTERFACE
, pim_ifp
->boundary_oil_plist
);
6504 DEFUN (interface_ip_mroute
,
6505 interface_ip_mroute_cmd
,
6506 "ip mroute INTERFACE A.B.C.D",
6508 "Add multicast route\n"
6509 "Outgoing interface name\n"
6512 VTY_DECLVAR_CONTEXT(interface
, iif
);
6513 struct pim_interface
*pim_ifp
;
6514 struct pim_instance
*pim
;
6515 int idx_interface
= 2;
6517 struct interface
*oif
;
6518 const char *oifname
;
6519 const char *grp_str
;
6520 struct in_addr grp_addr
;
6521 struct in_addr src_addr
;
6524 PIM_GET_PIM_INTERFACE(pim_ifp
, iif
);
6527 oifname
= argv
[idx_interface
]->arg
;
6528 oif
= if_lookup_by_name(oifname
, pim
->vrf_id
);
6530 vty_out(vty
, "No such interface name %s\n", oifname
);
6534 grp_str
= argv
[idx_ipv4
]->arg
;
6535 result
= inet_pton(AF_INET
, grp_str
, &grp_addr
);
6537 vty_out(vty
, "Bad group address %s: errno=%d: %s\n", grp_str
,
6538 errno
, safe_strerror(errno
));
6542 src_addr
.s_addr
= INADDR_ANY
;
6544 if (pim_static_add(pim
, iif
, oif
, grp_addr
, src_addr
)) {
6545 vty_out(vty
, "Failed to add route\n");
6552 DEFUN (interface_ip_mroute_source
,
6553 interface_ip_mroute_source_cmd
,
6554 "ip mroute INTERFACE A.B.C.D A.B.C.D",
6556 "Add multicast route\n"
6557 "Outgoing interface name\n"
6561 VTY_DECLVAR_CONTEXT(interface
, iif
);
6562 struct pim_interface
*pim_ifp
;
6563 struct pim_instance
*pim
;
6564 int idx_interface
= 2;
6567 struct interface
*oif
;
6568 const char *oifname
;
6569 const char *grp_str
;
6570 struct in_addr grp_addr
;
6571 const char *src_str
;
6572 struct in_addr src_addr
;
6575 PIM_GET_PIM_INTERFACE(pim_ifp
, iif
);
6578 oifname
= argv
[idx_interface
]->arg
;
6579 oif
= if_lookup_by_name(oifname
, pim
->vrf_id
);
6581 vty_out(vty
, "No such interface name %s\n", oifname
);
6585 grp_str
= argv
[idx_ipv4
]->arg
;
6586 result
= inet_pton(AF_INET
, grp_str
, &grp_addr
);
6588 vty_out(vty
, "Bad group address %s: errno=%d: %s\n", grp_str
,
6589 errno
, safe_strerror(errno
));
6593 src_str
= argv
[idx_ipv4_2
]->arg
;
6594 result
= inet_pton(AF_INET
, src_str
, &src_addr
);
6596 vty_out(vty
, "Bad source address %s: errno=%d: %s\n", src_str
,
6597 errno
, safe_strerror(errno
));
6601 if (pim_static_add(pim
, iif
, oif
, grp_addr
, src_addr
)) {
6602 vty_out(vty
, "Failed to add route\n");
6609 DEFUN (interface_no_ip_mroute
,
6610 interface_no_ip_mroute_cmd
,
6611 "no ip mroute INTERFACE A.B.C.D",
6614 "Add multicast route\n"
6615 "Outgoing interface name\n"
6618 VTY_DECLVAR_CONTEXT(interface
, iif
);
6619 struct pim_interface
*pim_ifp
;
6620 struct pim_instance
*pim
;
6621 int idx_interface
= 3;
6623 struct interface
*oif
;
6624 const char *oifname
;
6625 const char *grp_str
;
6626 struct in_addr grp_addr
;
6627 struct in_addr src_addr
;
6630 PIM_GET_PIM_INTERFACE(pim_ifp
, iif
);
6633 oifname
= argv
[idx_interface
]->arg
;
6634 oif
= if_lookup_by_name(oifname
, pim
->vrf_id
);
6636 vty_out(vty
, "No such interface name %s\n", oifname
);
6640 grp_str
= argv
[idx_ipv4
]->arg
;
6641 result
= inet_pton(AF_INET
, grp_str
, &grp_addr
);
6643 vty_out(vty
, "Bad group address %s: errno=%d: %s\n", grp_str
,
6644 errno
, safe_strerror(errno
));
6648 src_addr
.s_addr
= INADDR_ANY
;
6650 if (pim_static_del(pim
, iif
, oif
, grp_addr
, src_addr
)) {
6651 vty_out(vty
, "Failed to remove route\n");
6658 DEFUN (interface_no_ip_mroute_source
,
6659 interface_no_ip_mroute_source_cmd
,
6660 "no ip mroute INTERFACE A.B.C.D A.B.C.D",
6663 "Add multicast route\n"
6664 "Outgoing interface name\n"
6668 VTY_DECLVAR_CONTEXT(interface
, iif
);
6669 struct pim_interface
*pim_ifp
;
6670 struct pim_instance
*pim
;
6671 int idx_interface
= 3;
6674 struct interface
*oif
;
6675 const char *oifname
;
6676 const char *grp_str
;
6677 struct in_addr grp_addr
;
6678 const char *src_str
;
6679 struct in_addr src_addr
;
6682 PIM_GET_PIM_INTERFACE(pim_ifp
, iif
);
6685 oifname
= argv
[idx_interface
]->arg
;
6686 oif
= if_lookup_by_name(oifname
, pim
->vrf_id
);
6688 vty_out(vty
, "No such interface name %s\n", oifname
);
6692 grp_str
= argv
[idx_ipv4
]->arg
;
6693 result
= inet_pton(AF_INET
, grp_str
, &grp_addr
);
6695 vty_out(vty
, "Bad group address %s: errno=%d: %s\n", grp_str
,
6696 errno
, safe_strerror(errno
));
6700 src_str
= argv
[idx_ipv4_2
]->arg
;
6701 result
= inet_pton(AF_INET
, src_str
, &src_addr
);
6703 vty_out(vty
, "Bad source address %s: errno=%d: %s\n", src_str
,
6704 errno
, safe_strerror(errno
));
6708 if (pim_static_del(pim
, iif
, oif
, grp_addr
, src_addr
)) {
6709 vty_out(vty
, "Failed to remove route\n");
6716 DEFUN (interface_ip_pim_hello
,
6717 interface_ip_pim_hello_cmd
,
6718 "ip pim hello (1-180) [(1-180)]",
6722 IFACE_PIM_HELLO_TIME_STR
6723 IFACE_PIM_HELLO_HOLD_STR
)
6725 VTY_DECLVAR_CONTEXT(interface
, ifp
);
6728 struct pim_interface
*pim_ifp
= ifp
->info
;
6731 if (!pim_cmd_interface_add(ifp
)) {
6732 vty_out(vty
, "Could not enable PIM SM on interface\n");
6733 return CMD_WARNING_CONFIG_FAILED
;
6737 pim_ifp
= ifp
->info
;
6738 pim_ifp
->pim_hello_period
= strtol(argv
[idx_time
]->arg
, NULL
, 10);
6740 if (argc
== idx_hold
+ 1)
6741 pim_ifp
->pim_default_holdtime
=
6742 strtol(argv
[idx_hold
]->arg
, NULL
, 10);
6747 DEFUN (interface_no_ip_pim_hello
,
6748 interface_no_ip_pim_hello_cmd
,
6749 "no ip pim hello [(1-180) (1-180)]",
6754 IFACE_PIM_HELLO_TIME_STR
6755 IFACE_PIM_HELLO_HOLD_STR
)
6757 VTY_DECLVAR_CONTEXT(interface
, ifp
);
6758 struct pim_interface
*pim_ifp
= ifp
->info
;
6761 vty_out(vty
, "Pim not enabled on this interface\n");
6762 return CMD_WARNING_CONFIG_FAILED
;
6765 pim_ifp
->pim_hello_period
= PIM_DEFAULT_HELLO_PERIOD
;
6766 pim_ifp
->pim_default_holdtime
= -1;
6777 PIM_DO_DEBUG_IGMP_EVENTS
;
6778 PIM_DO_DEBUG_IGMP_PACKETS
;
6779 PIM_DO_DEBUG_IGMP_TRACE
;
6783 DEFUN (no_debug_igmp
,
6790 PIM_DONT_DEBUG_IGMP_EVENTS
;
6791 PIM_DONT_DEBUG_IGMP_PACKETS
;
6792 PIM_DONT_DEBUG_IGMP_TRACE
;
6797 DEFUN (debug_igmp_events
,
6798 debug_igmp_events_cmd
,
6799 "debug igmp events",
6802 DEBUG_IGMP_EVENTS_STR
)
6804 PIM_DO_DEBUG_IGMP_EVENTS
;
6808 DEFUN (no_debug_igmp_events
,
6809 no_debug_igmp_events_cmd
,
6810 "no debug igmp events",
6814 DEBUG_IGMP_EVENTS_STR
)
6816 PIM_DONT_DEBUG_IGMP_EVENTS
;
6821 DEFUN (debug_igmp_packets
,
6822 debug_igmp_packets_cmd
,
6823 "debug igmp packets",
6826 DEBUG_IGMP_PACKETS_STR
)
6828 PIM_DO_DEBUG_IGMP_PACKETS
;
6832 DEFUN (no_debug_igmp_packets
,
6833 no_debug_igmp_packets_cmd
,
6834 "no debug igmp packets",
6838 DEBUG_IGMP_PACKETS_STR
)
6840 PIM_DONT_DEBUG_IGMP_PACKETS
;
6845 DEFUN (debug_igmp_trace
,
6846 debug_igmp_trace_cmd
,
6850 DEBUG_IGMP_TRACE_STR
)
6852 PIM_DO_DEBUG_IGMP_TRACE
;
6856 DEFUN (no_debug_igmp_trace
,
6857 no_debug_igmp_trace_cmd
,
6858 "no debug igmp trace",
6862 DEBUG_IGMP_TRACE_STR
)
6864 PIM_DONT_DEBUG_IGMP_TRACE
;
6869 DEFUN (debug_mroute
,
6875 PIM_DO_DEBUG_MROUTE
;
6879 DEFUN (debug_mroute_detail
,
6880 debug_mroute_detail_cmd
,
6881 "debug mroute detail",
6886 PIM_DO_DEBUG_MROUTE_DETAIL
;
6890 DEFUN (no_debug_mroute
,
6891 no_debug_mroute_cmd
,
6897 PIM_DONT_DEBUG_MROUTE
;
6901 DEFUN (no_debug_mroute_detail
,
6902 no_debug_mroute_detail_cmd
,
6903 "no debug mroute detail",
6909 PIM_DONT_DEBUG_MROUTE_DETAIL
;
6913 DEFUN (debug_static
,
6919 PIM_DO_DEBUG_STATIC
;
6923 DEFUN (no_debug_static
,
6924 no_debug_static_cmd
,
6930 PIM_DONT_DEBUG_STATIC
;
6941 PIM_DO_DEBUG_PIM_EVENTS
;
6942 PIM_DO_DEBUG_PIM_PACKETS
;
6943 PIM_DO_DEBUG_PIM_TRACE
;
6944 PIM_DO_DEBUG_MSDP_EVENTS
;
6945 PIM_DO_DEBUG_MSDP_PACKETS
;
6949 DEFUN (no_debug_pim
,
6956 PIM_DONT_DEBUG_PIM_EVENTS
;
6957 PIM_DONT_DEBUG_PIM_PACKETS
;
6958 PIM_DONT_DEBUG_PIM_TRACE
;
6959 PIM_DONT_DEBUG_MSDP_EVENTS
;
6960 PIM_DONT_DEBUG_MSDP_PACKETS
;
6962 PIM_DONT_DEBUG_PIM_PACKETDUMP_SEND
;
6963 PIM_DONT_DEBUG_PIM_PACKETDUMP_RECV
;
6968 DEFUN (debug_pim_nht
,
6973 "Nexthop Tracking\n")
6975 PIM_DO_DEBUG_PIM_NHT
;
6979 DEFUN (no_debug_pim_nht
,
6980 no_debug_pim_nht_cmd
,
6985 "Nexthop Tracking\n")
6987 PIM_DONT_DEBUG_PIM_NHT
;
6991 DEFUN (debug_pim_nht_rp
,
6992 debug_pim_nht_rp_cmd
,
6996 "Nexthop Tracking\n"
6997 "RP Nexthop Tracking\n")
6999 PIM_DO_DEBUG_PIM_NHT_RP
;
7003 DEFUN (no_debug_pim_nht_rp
,
7004 no_debug_pim_nht_rp_cmd
,
7005 "no debug pim nht rp",
7009 "Nexthop Tracking\n"
7010 "RP Nexthop Tracking\n")
7012 PIM_DONT_DEBUG_PIM_NHT_RP
;
7016 DEFUN (debug_pim_events
,
7017 debug_pim_events_cmd
,
7021 DEBUG_PIM_EVENTS_STR
)
7023 PIM_DO_DEBUG_PIM_EVENTS
;
7027 DEFUN (no_debug_pim_events
,
7028 no_debug_pim_events_cmd
,
7029 "no debug pim events",
7033 DEBUG_PIM_EVENTS_STR
)
7035 PIM_DONT_DEBUG_PIM_EVENTS
;
7039 DEFUN (debug_pim_packets
,
7040 debug_pim_packets_cmd
,
7041 "debug pim packets [<hello|joins|register>]",
7044 DEBUG_PIM_PACKETS_STR
7045 DEBUG_PIM_HELLO_PACKETS_STR
7046 DEBUG_PIM_J_P_PACKETS_STR
7047 DEBUG_PIM_PIM_REG_PACKETS_STR
)
7050 if (argv_find(argv
, argc
, "hello", &idx
)) {
7051 PIM_DO_DEBUG_PIM_HELLO
;
7052 vty_out(vty
, "PIM Hello debugging is on\n");
7053 } else if (argv_find(argv
, argc
, "joins", &idx
)) {
7054 PIM_DO_DEBUG_PIM_J_P
;
7055 vty_out(vty
, "PIM Join/Prune debugging is on\n");
7056 } else if (argv_find(argv
, argc
, "register", &idx
)) {
7057 PIM_DO_DEBUG_PIM_REG
;
7058 vty_out(vty
, "PIM Register debugging is on\n");
7060 PIM_DO_DEBUG_PIM_PACKETS
;
7061 vty_out(vty
, "PIM Packet debugging is on \n");
7066 DEFUN (no_debug_pim_packets
,
7067 no_debug_pim_packets_cmd
,
7068 "no debug pim packets [<hello|joins|register>]",
7072 DEBUG_PIM_PACKETS_STR
7073 DEBUG_PIM_HELLO_PACKETS_STR
7074 DEBUG_PIM_J_P_PACKETS_STR
7075 DEBUG_PIM_PIM_REG_PACKETS_STR
)
7078 if (argv_find(argv
, argc
, "hello", &idx
)) {
7079 PIM_DONT_DEBUG_PIM_HELLO
;
7080 vty_out(vty
, "PIM Hello debugging is off \n");
7081 } else if (argv_find(argv
, argc
, "joins", &idx
)) {
7082 PIM_DONT_DEBUG_PIM_J_P
;
7083 vty_out(vty
, "PIM Join/Prune debugging is off \n");
7084 } else if (argv_find(argv
, argc
, "register", &idx
)) {
7085 PIM_DONT_DEBUG_PIM_REG
;
7086 vty_out(vty
, "PIM Register debugging is off\n");
7088 PIM_DONT_DEBUG_PIM_PACKETS
;
7094 DEFUN (debug_pim_packetdump_send
,
7095 debug_pim_packetdump_send_cmd
,
7096 "debug pim packet-dump send",
7099 DEBUG_PIM_PACKETDUMP_STR
7100 DEBUG_PIM_PACKETDUMP_SEND_STR
)
7102 PIM_DO_DEBUG_PIM_PACKETDUMP_SEND
;
7106 DEFUN (no_debug_pim_packetdump_send
,
7107 no_debug_pim_packetdump_send_cmd
,
7108 "no debug pim packet-dump send",
7112 DEBUG_PIM_PACKETDUMP_STR
7113 DEBUG_PIM_PACKETDUMP_SEND_STR
)
7115 PIM_DONT_DEBUG_PIM_PACKETDUMP_SEND
;
7119 DEFUN (debug_pim_packetdump_recv
,
7120 debug_pim_packetdump_recv_cmd
,
7121 "debug pim packet-dump receive",
7124 DEBUG_PIM_PACKETDUMP_STR
7125 DEBUG_PIM_PACKETDUMP_RECV_STR
)
7127 PIM_DO_DEBUG_PIM_PACKETDUMP_RECV
;
7131 DEFUN (no_debug_pim_packetdump_recv
,
7132 no_debug_pim_packetdump_recv_cmd
,
7133 "no debug pim packet-dump receive",
7137 DEBUG_PIM_PACKETDUMP_STR
7138 DEBUG_PIM_PACKETDUMP_RECV_STR
)
7140 PIM_DONT_DEBUG_PIM_PACKETDUMP_RECV
;
7144 DEFUN (debug_pim_trace
,
7145 debug_pim_trace_cmd
,
7149 DEBUG_PIM_TRACE_STR
)
7151 PIM_DO_DEBUG_PIM_TRACE
;
7155 DEFUN (debug_pim_trace_detail
,
7156 debug_pim_trace_detail_cmd
,
7157 "debug pim trace detail",
7161 "Detailed Information\n")
7163 PIM_DO_DEBUG_PIM_TRACE_DETAIL
;
7167 DEFUN (no_debug_pim_trace
,
7168 no_debug_pim_trace_cmd
,
7169 "no debug pim trace",
7173 DEBUG_PIM_TRACE_STR
)
7175 PIM_DONT_DEBUG_PIM_TRACE
;
7179 DEFUN (no_debug_pim_trace_detail
,
7180 no_debug_pim_trace_detail_cmd
,
7181 "no debug pim trace detail",
7186 "Detailed Information\n")
7188 PIM_DONT_DEBUG_PIM_TRACE_DETAIL
;
7192 DEFUN (debug_ssmpingd
,
7198 PIM_DO_DEBUG_SSMPINGD
;
7202 DEFUN (no_debug_ssmpingd
,
7203 no_debug_ssmpingd_cmd
,
7204 "no debug ssmpingd",
7209 PIM_DONT_DEBUG_SSMPINGD
;
7213 DEFUN (debug_pim_zebra
,
7214 debug_pim_zebra_cmd
,
7218 DEBUG_PIM_ZEBRA_STR
)
7224 DEFUN (no_debug_pim_zebra
,
7225 no_debug_pim_zebra_cmd
,
7226 "no debug pim zebra",
7230 DEBUG_PIM_ZEBRA_STR
)
7232 PIM_DONT_DEBUG_ZEBRA
;
7242 PIM_DO_DEBUG_MSDP_EVENTS
;
7243 PIM_DO_DEBUG_MSDP_PACKETS
;
7247 DEFUN (no_debug_msdp
,
7254 PIM_DONT_DEBUG_MSDP_EVENTS
;
7255 PIM_DONT_DEBUG_MSDP_PACKETS
;
7259 ALIAS(no_debug_msdp
, undebug_msdp_cmd
, "undebug msdp",
7260 UNDEBUG_STR DEBUG_MSDP_STR
)
7262 DEFUN (debug_msdp_events
,
7263 debug_msdp_events_cmd
,
7264 "debug msdp events",
7267 DEBUG_MSDP_EVENTS_STR
)
7269 PIM_DO_DEBUG_MSDP_EVENTS
;
7273 DEFUN (no_debug_msdp_events
,
7274 no_debug_msdp_events_cmd
,
7275 "no debug msdp events",
7279 DEBUG_MSDP_EVENTS_STR
)
7281 PIM_DONT_DEBUG_MSDP_EVENTS
;
7285 ALIAS(no_debug_msdp_events
, undebug_msdp_events_cmd
, "undebug msdp events",
7286 UNDEBUG_STR DEBUG_MSDP_STR DEBUG_MSDP_EVENTS_STR
)
7288 DEFUN (debug_msdp_packets
,
7289 debug_msdp_packets_cmd
,
7290 "debug msdp packets",
7293 DEBUG_MSDP_PACKETS_STR
)
7295 PIM_DO_DEBUG_MSDP_PACKETS
;
7299 DEFUN (no_debug_msdp_packets
,
7300 no_debug_msdp_packets_cmd
,
7301 "no debug msdp packets",
7305 DEBUG_MSDP_PACKETS_STR
)
7307 PIM_DONT_DEBUG_MSDP_PACKETS
;
7311 ALIAS(no_debug_msdp_packets
, undebug_msdp_packets_cmd
, "undebug msdp packets",
7312 UNDEBUG_STR DEBUG_MSDP_STR DEBUG_MSDP_PACKETS_STR
)
7314 DEFUN_NOSH (show_debugging_pim
,
7315 show_debugging_pim_cmd
,
7316 "show debugging [pim]",
7321 vty_out(vty
, "PIM debugging status\n");
7323 pim_debug_config_write(vty
);
7328 static int interface_pim_use_src_cmd_worker(struct vty
*vty
, const char *source
)
7331 struct in_addr source_addr
;
7332 int ret
= CMD_SUCCESS
;
7333 VTY_DECLVAR_CONTEXT(interface
, ifp
);
7335 result
= inet_pton(AF_INET
, source
, &source_addr
);
7337 vty_out(vty
, "%% Bad source address %s: errno=%d: %s\n", source
,
7338 errno
, safe_strerror(errno
));
7339 return CMD_WARNING_CONFIG_FAILED
;
7342 result
= pim_update_source_set(ifp
, source_addr
);
7346 case PIM_IFACE_NOT_FOUND
:
7347 ret
= CMD_WARNING_CONFIG_FAILED
;
7348 vty_out(vty
, "Pim not enabled on this interface\n");
7350 case PIM_UPDATE_SOURCE_DUP
:
7352 vty_out(vty
, "%% Source already set to %s\n", source
);
7355 ret
= CMD_WARNING_CONFIG_FAILED
;
7356 vty_out(vty
, "%% Source set failed\n");
7362 DEFUN (interface_pim_use_source
,
7363 interface_pim_use_source_cmd
,
7364 "ip pim use-source A.B.C.D",
7366 "pim multicast routing\n"
7367 "Configure primary IP address\n"
7368 "source ip address\n")
7370 return interface_pim_use_src_cmd_worker(vty
, argv
[3]->arg
);
7373 DEFUN (interface_no_pim_use_source
,
7374 interface_no_pim_use_source_cmd
,
7375 "no ip pim use-source [A.B.C.D]",
7378 "pim multicast routing\n"
7379 "Delete source IP address\n"
7380 "source ip address\n")
7382 return interface_pim_use_src_cmd_worker(vty
, "0.0.0.0");
7390 "Enables BFD support\n")
7392 VTY_DECLVAR_CONTEXT(interface
, ifp
);
7393 struct pim_interface
*pim_ifp
= ifp
->info
;
7394 struct bfd_info
*bfd_info
= NULL
;
7397 if (!pim_cmd_interface_add(ifp
)) {
7398 vty_out(vty
, "Could not enable PIM SM on interface\n");
7402 pim_ifp
= ifp
->info
;
7404 bfd_info
= pim_ifp
->bfd_info
;
7406 if (!bfd_info
|| !CHECK_FLAG(bfd_info
->flags
, BFD_FLAG_PARAM_CFG
))
7407 pim_bfd_if_param_set(ifp
, BFD_DEF_MIN_RX
, BFD_DEF_MIN_TX
,
7408 BFD_DEF_DETECT_MULT
, 1);
7413 DEFUN (no_ip_pim_bfd
,
7419 "Disables BFD support\n")
7421 VTY_DECLVAR_CONTEXT(interface
, ifp
);
7422 struct pim_interface
*pim_ifp
= ifp
->info
;
7425 vty_out(vty
, "Pim not enabled on this interface\n");
7429 if (pim_ifp
->bfd_info
) {
7430 pim_bfd_reg_dereg_all_nbr(ifp
, ZEBRA_BFD_DEST_DEREGISTER
);
7431 bfd_info_free(&(pim_ifp
->bfd_info
));
7437 DEFUN (ip_pim_bfd_param
,
7438 ip_pim_bfd_param_cmd
,
7439 "ip pim bfd (2-255) (50-60000) (50-60000)",
7442 "Enables BFD support\n"
7443 "Detect Multiplier\n"
7444 "Required min receive interval\n"
7445 "Desired min transmit interval\n")
7447 VTY_DECLVAR_CONTEXT(interface
, ifp
);
7449 int idx_number_2
= 4;
7450 int idx_number_3
= 5;
7455 struct pim_interface
*pim_ifp
= ifp
->info
;
7458 if (!pim_cmd_interface_add(ifp
)) {
7459 vty_out(vty
, "Could not enable PIM SM on interface\n");
7464 if ((ret
= bfd_validate_param(
7465 vty
, argv
[idx_number
]->arg
, argv
[idx_number_2
]->arg
,
7466 argv
[idx_number_3
]->arg
, &dm_val
, &rx_val
, &tx_val
))
7470 pim_bfd_if_param_set(ifp
, rx_val
, tx_val
, dm_val
, 0);
7475 ALIAS(no_ip_pim_bfd
, no_ip_pim_bfd_param_cmd
,
7476 "no ip pim bfd (2-255) (50-60000) (50-60000)", NO_STR IP_STR PIM_STR
7477 "Enables BFD support\n"
7478 "Detect Multiplier\n"
7479 "Required min receive interval\n"
7480 "Desired min transmit interval\n")
7482 static int ip_msdp_peer_cmd_worker(struct pim_instance
*pim
, struct vty
*vty
,
7483 const char *peer
, const char *local
)
7485 enum pim_msdp_err result
;
7486 struct in_addr peer_addr
;
7487 struct in_addr local_addr
;
7488 int ret
= CMD_SUCCESS
;
7490 result
= inet_pton(AF_INET
, peer
, &peer_addr
);
7492 vty_out(vty
, "%% Bad peer address %s: errno=%d: %s\n", peer
,
7493 errno
, safe_strerror(errno
));
7494 return CMD_WARNING_CONFIG_FAILED
;
7497 result
= inet_pton(AF_INET
, local
, &local_addr
);
7499 vty_out(vty
, "%% Bad source address %s: errno=%d: %s\n", local
,
7500 errno
, safe_strerror(errno
));
7501 return CMD_WARNING_CONFIG_FAILED
;
7504 result
= pim_msdp_peer_add(pim
, peer_addr
, local_addr
, "default",
7507 case PIM_MSDP_ERR_NONE
:
7509 case PIM_MSDP_ERR_OOM
:
7510 ret
= CMD_WARNING_CONFIG_FAILED
;
7511 vty_out(vty
, "%% Out of memory\n");
7513 case PIM_MSDP_ERR_PEER_EXISTS
:
7515 vty_out(vty
, "%% Peer exists\n");
7517 case PIM_MSDP_ERR_MAX_MESH_GROUPS
:
7518 ret
= CMD_WARNING_CONFIG_FAILED
;
7519 vty_out(vty
, "%% Only one mesh-group allowed currently\n");
7522 ret
= CMD_WARNING_CONFIG_FAILED
;
7523 vty_out(vty
, "%% peer add failed\n");
7529 DEFUN_HIDDEN (ip_msdp_peer
,
7531 "ip msdp peer A.B.C.D source A.B.C.D",
7534 "Configure MSDP peer\n"
7536 "Source address for TCP connection\n"
7537 "local ip address\n")
7539 PIM_DECLVAR_CONTEXT(vrf
, pim
);
7540 return ip_msdp_peer_cmd_worker(pim
, vty
, argv
[3]->arg
, argv
[5]->arg
);
7543 static int ip_no_msdp_peer_cmd_worker(struct pim_instance
*pim
, struct vty
*vty
,
7546 enum pim_msdp_err result
;
7547 struct in_addr peer_addr
;
7549 result
= inet_pton(AF_INET
, peer
, &peer_addr
);
7551 vty_out(vty
, "%% Bad peer address %s: errno=%d: %s\n", peer
,
7552 errno
, safe_strerror(errno
));
7553 return CMD_WARNING_CONFIG_FAILED
;
7556 result
= pim_msdp_peer_del(pim
, peer_addr
);
7558 case PIM_MSDP_ERR_NONE
:
7560 case PIM_MSDP_ERR_NO_PEER
:
7561 vty_out(vty
, "%% Peer does not exist\n");
7564 vty_out(vty
, "%% peer del failed\n");
7567 return result
? CMD_WARNING_CONFIG_FAILED
: CMD_SUCCESS
;
7570 DEFUN_HIDDEN (no_ip_msdp_peer
,
7571 no_ip_msdp_peer_cmd
,
7572 "no ip msdp peer A.B.C.D",
7576 "Delete MSDP peer\n"
7577 "peer ip address\n")
7579 PIM_DECLVAR_CONTEXT(vrf
, pim
);
7580 return ip_no_msdp_peer_cmd_worker(pim
, vty
, argv
[4]->arg
);
7583 static int ip_msdp_mesh_group_member_cmd_worker(struct pim_instance
*pim
,
7584 struct vty
*vty
, const char *mg
,
7587 enum pim_msdp_err result
;
7588 struct in_addr mbr_ip
;
7589 int ret
= CMD_SUCCESS
;
7591 result
= inet_pton(AF_INET
, mbr
, &mbr_ip
);
7593 vty_out(vty
, "%% Bad member address %s: errno=%d: %s\n", mbr
,
7594 errno
, safe_strerror(errno
));
7595 return CMD_WARNING_CONFIG_FAILED
;
7598 result
= pim_msdp_mg_mbr_add(pim
, mg
, mbr_ip
);
7600 case PIM_MSDP_ERR_NONE
:
7602 case PIM_MSDP_ERR_OOM
:
7603 ret
= CMD_WARNING_CONFIG_FAILED
;
7604 vty_out(vty
, "%% Out of memory\n");
7606 case PIM_MSDP_ERR_MG_MBR_EXISTS
:
7608 vty_out(vty
, "%% mesh-group member exists\n");
7610 case PIM_MSDP_ERR_MAX_MESH_GROUPS
:
7611 ret
= CMD_WARNING_CONFIG_FAILED
;
7612 vty_out(vty
, "%% Only one mesh-group allowed currently\n");
7615 ret
= CMD_WARNING_CONFIG_FAILED
;
7616 vty_out(vty
, "%% member add failed\n");
7622 DEFUN (ip_msdp_mesh_group_member
,
7623 ip_msdp_mesh_group_member_cmd
,
7624 "ip msdp mesh-group WORD member A.B.C.D",
7627 "Configure MSDP mesh-group\n"
7629 "mesh group member\n"
7630 "peer ip address\n")
7632 PIM_DECLVAR_CONTEXT(vrf
, pim
);
7633 return ip_msdp_mesh_group_member_cmd_worker(pim
, vty
, argv
[3]->arg
,
7637 static int ip_no_msdp_mesh_group_member_cmd_worker(struct pim_instance
*pim
,
7642 enum pim_msdp_err result
;
7643 struct in_addr mbr_ip
;
7645 result
= inet_pton(AF_INET
, mbr
, &mbr_ip
);
7647 vty_out(vty
, "%% Bad member address %s: errno=%d: %s\n", mbr
,
7648 errno
, safe_strerror(errno
));
7649 return CMD_WARNING_CONFIG_FAILED
;
7652 result
= pim_msdp_mg_mbr_del(pim
, mg
, mbr_ip
);
7654 case PIM_MSDP_ERR_NONE
:
7656 case PIM_MSDP_ERR_NO_MG
:
7657 vty_out(vty
, "%% mesh-group does not exist\n");
7659 case PIM_MSDP_ERR_NO_MG_MBR
:
7660 vty_out(vty
, "%% mesh-group member does not exist\n");
7663 vty_out(vty
, "%% mesh-group member del failed\n");
7666 return result
? CMD_WARNING_CONFIG_FAILED
: CMD_SUCCESS
;
7668 DEFUN (no_ip_msdp_mesh_group_member
,
7669 no_ip_msdp_mesh_group_member_cmd
,
7670 "no ip msdp mesh-group WORD member A.B.C.D",
7674 "Delete MSDP mesh-group member\n"
7676 "mesh group member\n"
7677 "peer ip address\n")
7679 PIM_DECLVAR_CONTEXT(vrf
, pim
);
7680 return ip_no_msdp_mesh_group_member_cmd_worker(pim
, vty
, argv
[4]->arg
,
7684 static int ip_msdp_mesh_group_source_cmd_worker(struct pim_instance
*pim
,
7685 struct vty
*vty
, const char *mg
,
7688 enum pim_msdp_err result
;
7689 struct in_addr src_ip
;
7691 result
= inet_pton(AF_INET
, src
, &src_ip
);
7693 vty_out(vty
, "%% Bad source address %s: errno=%d: %s\n", src
,
7694 errno
, safe_strerror(errno
));
7695 return CMD_WARNING_CONFIG_FAILED
;
7698 result
= pim_msdp_mg_src_add(pim
, mg
, src_ip
);
7700 case PIM_MSDP_ERR_NONE
:
7702 case PIM_MSDP_ERR_OOM
:
7703 vty_out(vty
, "%% Out of memory\n");
7705 case PIM_MSDP_ERR_MAX_MESH_GROUPS
:
7706 vty_out(vty
, "%% Only one mesh-group allowed currently\n");
7709 vty_out(vty
, "%% source add failed\n");
7712 return result
? CMD_WARNING_CONFIG_FAILED
: CMD_SUCCESS
;
7716 DEFUN (ip_msdp_mesh_group_source
,
7717 ip_msdp_mesh_group_source_cmd
,
7718 "ip msdp mesh-group WORD source A.B.C.D",
7721 "Configure MSDP mesh-group\n"
7723 "mesh group local address\n"
7724 "source ip address for the TCP connection\n")
7726 PIM_DECLVAR_CONTEXT(vrf
, pim
);
7727 return ip_msdp_mesh_group_source_cmd_worker(pim
, vty
, argv
[3]->arg
,
7731 static int ip_no_msdp_mesh_group_source_cmd_worker(struct pim_instance
*pim
,
7735 enum pim_msdp_err result
;
7737 result
= pim_msdp_mg_src_del(pim
, mg
);
7739 case PIM_MSDP_ERR_NONE
:
7741 case PIM_MSDP_ERR_NO_MG
:
7742 vty_out(vty
, "%% mesh-group does not exist\n");
7745 vty_out(vty
, "%% mesh-group source del failed\n");
7748 return result
? CMD_WARNING_CONFIG_FAILED
: CMD_SUCCESS
;
7751 static int ip_no_msdp_mesh_group_cmd_worker(struct pim_instance
*pim
,
7752 struct vty
*vty
, const char *mg
)
7754 enum pim_msdp_err result
;
7756 result
= pim_msdp_mg_del(pim
, mg
);
7758 case PIM_MSDP_ERR_NONE
:
7760 case PIM_MSDP_ERR_NO_MG
:
7761 vty_out(vty
, "%% mesh-group does not exist\n");
7764 vty_out(vty
, "%% mesh-group source del failed\n");
7767 return result
? CMD_WARNING_CONFIG_FAILED
: CMD_SUCCESS
;
7770 DEFUN (no_ip_msdp_mesh_group_source
,
7771 no_ip_msdp_mesh_group_source_cmd
,
7772 "no ip msdp mesh-group WORD source [A.B.C.D]",
7776 "Delete MSDP mesh-group source\n"
7778 "mesh group source\n"
7779 "mesh group local address\n")
7781 PIM_DECLVAR_CONTEXT(vrf
, pim
);
7783 return ip_no_msdp_mesh_group_cmd_worker(pim
, vty
, argv
[6]->arg
);
7785 return ip_no_msdp_mesh_group_source_cmd_worker(pim
, vty
,
7789 static void print_empty_json_obj(struct vty
*vty
)
7792 json
= json_object_new_object();
7793 vty_out(vty
, "%s\n",
7794 json_object_to_json_string_ext(json
, JSON_C_TO_STRING_PRETTY
));
7795 json_object_free(json
);
7798 static void ip_msdp_show_mesh_group(struct pim_instance
*pim
, struct vty
*vty
,
7801 struct listnode
*mbrnode
;
7802 struct pim_msdp_mg_mbr
*mbr
;
7803 struct pim_msdp_mg
*mg
= pim
->msdp
.mg
;
7804 char mbr_str
[INET_ADDRSTRLEN
];
7805 char src_str
[INET_ADDRSTRLEN
];
7806 char state_str
[PIM_MSDP_STATE_STRLEN
];
7807 enum pim_msdp_peer_state state
;
7808 json_object
*json
= NULL
;
7809 json_object
*json_mg_row
= NULL
;
7810 json_object
*json_members
= NULL
;
7811 json_object
*json_row
= NULL
;
7815 print_empty_json_obj(vty
);
7819 pim_inet4_dump("<source?>", mg
->src_ip
, src_str
, sizeof(src_str
));
7821 json
= json_object_new_object();
7822 /* currently there is only one mesh group but we should still
7824 * it a dict with mg-name as key */
7825 json_mg_row
= json_object_new_object();
7826 json_object_string_add(json_mg_row
, "name",
7827 mg
->mesh_group_name
);
7828 json_object_string_add(json_mg_row
, "source", src_str
);
7830 vty_out(vty
, "Mesh group : %s\n", mg
->mesh_group_name
);
7831 vty_out(vty
, " Source : %s\n", src_str
);
7832 vty_out(vty
, " Member State\n");
7835 for (ALL_LIST_ELEMENTS_RO(mg
->mbr_list
, mbrnode
, mbr
)) {
7836 pim_inet4_dump("<mbr?>", mbr
->mbr_ip
, mbr_str
, sizeof(mbr_str
));
7838 state
= mbr
->mp
->state
;
7840 state
= PIM_MSDP_DISABLED
;
7842 pim_msdp_state_dump(state
, state_str
, sizeof(state_str
));
7844 json_row
= json_object_new_object();
7845 json_object_string_add(json_row
, "member", mbr_str
);
7846 json_object_string_add(json_row
, "state", state_str
);
7847 if (!json_members
) {
7848 json_members
= json_object_new_object();
7849 json_object_object_add(json_mg_row
, "members",
7852 json_object_object_add(json_members
, mbr_str
, json_row
);
7854 vty_out(vty
, " %-15s %11s\n", mbr_str
, state_str
);
7859 json_object_object_add(json
, mg
->mesh_group_name
, json_mg_row
);
7860 vty_out(vty
, "%s\n", json_object_to_json_string_ext(
7861 json
, JSON_C_TO_STRING_PRETTY
));
7862 json_object_free(json
);
7866 DEFUN (show_ip_msdp_mesh_group
,
7867 show_ip_msdp_mesh_group_cmd
,
7868 "show ip msdp [vrf NAME] mesh-group [json]",
7873 "MSDP mesh-group information\n"
7876 u_char uj
= use_json(argc
, argv
);
7878 struct vrf
*vrf
= pim_cmd_lookup_vrf(vty
, argv
, argc
, &idx
);
7883 ip_msdp_show_mesh_group(vrf
->info
, vty
, uj
);
7888 DEFUN (show_ip_msdp_mesh_group_vrf_all
,
7889 show_ip_msdp_mesh_group_vrf_all_cmd
,
7890 "show ip msdp vrf all mesh-group [json]",
7895 "MSDP mesh-group information\n"
7898 u_char uj
= use_json(argc
, argv
);
7904 RB_FOREACH (vrf
, vrf_name_head
, &vrfs_by_name
) {
7908 vty_out(vty
, " \"%s\": ", vrf
->name
);
7911 vty_out(vty
, "VRF: %s\n", vrf
->name
);
7912 ip_msdp_show_mesh_group(vrf
->info
, vty
, uj
);
7915 vty_out(vty
, "}\n");
7920 static void ip_msdp_show_peers(struct pim_instance
*pim
, struct vty
*vty
,
7923 struct listnode
*mpnode
;
7924 struct pim_msdp_peer
*mp
;
7925 char peer_str
[INET_ADDRSTRLEN
];
7926 char local_str
[INET_ADDRSTRLEN
];
7927 char state_str
[PIM_MSDP_STATE_STRLEN
];
7928 char timebuf
[PIM_MSDP_UPTIME_STRLEN
];
7930 json_object
*json
= NULL
;
7931 json_object
*json_row
= NULL
;
7935 json
= json_object_new_object();
7938 "Peer Local State Uptime SaCnt\n");
7941 for (ALL_LIST_ELEMENTS_RO(pim
->msdp
.peer_list
, mpnode
, mp
)) {
7942 if (mp
->state
== PIM_MSDP_ESTABLISHED
) {
7943 now
= pim_time_monotonic_sec();
7944 pim_time_uptime(timebuf
, sizeof(timebuf
),
7947 strcpy(timebuf
, "-");
7949 pim_inet4_dump("<peer?>", mp
->peer
, peer_str
, sizeof(peer_str
));
7950 pim_inet4_dump("<local?>", mp
->local
, local_str
,
7952 pim_msdp_state_dump(mp
->state
, state_str
, sizeof(state_str
));
7954 json_row
= json_object_new_object();
7955 json_object_string_add(json_row
, "peer", peer_str
);
7956 json_object_string_add(json_row
, "local", local_str
);
7957 json_object_string_add(json_row
, "state", state_str
);
7958 json_object_string_add(json_row
, "upTime", timebuf
);
7959 json_object_int_add(json_row
, "saCount", mp
->sa_cnt
);
7960 json_object_object_add(json
, peer_str
, json_row
);
7962 vty_out(vty
, "%-15s %15s %11s %8s %6d\n", peer_str
,
7963 local_str
, state_str
, timebuf
, mp
->sa_cnt
);
7968 vty_out(vty
, "%s\n", json_object_to_json_string_ext(
7969 json
, JSON_C_TO_STRING_PRETTY
));
7970 json_object_free(json
);
7974 static void ip_msdp_show_peers_detail(struct pim_instance
*pim
, struct vty
*vty
,
7975 const char *peer
, u_char uj
)
7977 struct listnode
*mpnode
;
7978 struct pim_msdp_peer
*mp
;
7979 char peer_str
[INET_ADDRSTRLEN
];
7980 char local_str
[INET_ADDRSTRLEN
];
7981 char state_str
[PIM_MSDP_STATE_STRLEN
];
7982 char timebuf
[PIM_MSDP_UPTIME_STRLEN
];
7983 char katimer
[PIM_MSDP_TIMER_STRLEN
];
7984 char crtimer
[PIM_MSDP_TIMER_STRLEN
];
7985 char holdtimer
[PIM_MSDP_TIMER_STRLEN
];
7987 json_object
*json
= NULL
;
7988 json_object
*json_row
= NULL
;
7991 json
= json_object_new_object();
7994 for (ALL_LIST_ELEMENTS_RO(pim
->msdp
.peer_list
, mpnode
, mp
)) {
7995 pim_inet4_dump("<peer?>", mp
->peer
, peer_str
, sizeof(peer_str
));
7996 if (strcmp(peer
, "detail") && strcmp(peer
, peer_str
))
7999 if (mp
->state
== PIM_MSDP_ESTABLISHED
) {
8000 now
= pim_time_monotonic_sec();
8001 pim_time_uptime(timebuf
, sizeof(timebuf
),
8004 strcpy(timebuf
, "-");
8006 pim_inet4_dump("<local?>", mp
->local
, local_str
,
8008 pim_msdp_state_dump(mp
->state
, state_str
, sizeof(state_str
));
8009 pim_time_timer_to_hhmmss(katimer
, sizeof(katimer
),
8011 pim_time_timer_to_hhmmss(crtimer
, sizeof(crtimer
),
8013 pim_time_timer_to_hhmmss(holdtimer
, sizeof(holdtimer
),
8017 json_row
= json_object_new_object();
8018 json_object_string_add(json_row
, "peer", peer_str
);
8019 json_object_string_add(json_row
, "local", local_str
);
8020 json_object_string_add(json_row
, "meshGroupName",
8021 mp
->mesh_group_name
);
8022 json_object_string_add(json_row
, "state", state_str
);
8023 json_object_string_add(json_row
, "upTime", timebuf
);
8024 json_object_string_add(json_row
, "keepAliveTimer",
8026 json_object_string_add(json_row
, "connRetryTimer",
8028 json_object_string_add(json_row
, "holdTimer",
8030 json_object_string_add(json_row
, "lastReset",
8032 json_object_int_add(json_row
, "connAttempts",
8034 json_object_int_add(json_row
, "establishedChanges",
8036 json_object_int_add(json_row
, "saCount", mp
->sa_cnt
);
8037 json_object_int_add(json_row
, "kaSent", mp
->ka_tx_cnt
);
8038 json_object_int_add(json_row
, "kaRcvd", mp
->ka_rx_cnt
);
8039 json_object_int_add(json_row
, "saSent", mp
->sa_tx_cnt
);
8040 json_object_int_add(json_row
, "saRcvd", mp
->sa_rx_cnt
);
8041 json_object_object_add(json
, peer_str
, json_row
);
8043 vty_out(vty
, "Peer : %s\n", peer_str
);
8044 vty_out(vty
, " Local : %s\n", local_str
);
8045 vty_out(vty
, " Mesh Group : %s\n",
8046 mp
->mesh_group_name
);
8047 vty_out(vty
, " State : %s\n", state_str
);
8048 vty_out(vty
, " Uptime : %s\n", timebuf
);
8050 vty_out(vty
, " Keepalive Timer : %s\n", katimer
);
8051 vty_out(vty
, " Conn Retry Timer : %s\n", crtimer
);
8052 vty_out(vty
, " Hold Timer : %s\n", holdtimer
);
8053 vty_out(vty
, " Last Reset : %s\n",
8055 vty_out(vty
, " Conn Attempts : %d\n",
8057 vty_out(vty
, " Established Changes : %d\n",
8059 vty_out(vty
, " SA Count : %d\n",
8061 vty_out(vty
, " Statistics :\n");
8064 vty_out(vty
, " Keepalives : %10d %10d\n",
8065 mp
->ka_tx_cnt
, mp
->ka_rx_cnt
);
8066 vty_out(vty
, " SAs : %10d %10d\n",
8067 mp
->sa_tx_cnt
, mp
->sa_rx_cnt
);
8073 vty_out(vty
, "%s\n", json_object_to_json_string_ext(
8074 json
, JSON_C_TO_STRING_PRETTY
));
8075 json_object_free(json
);
8079 DEFUN (show_ip_msdp_peer_detail
,
8080 show_ip_msdp_peer_detail_cmd
,
8081 "show ip msdp [vrf NAME] peer [detail|A.B.C.D] [json]",
8086 "MSDP peer information\n"
8091 u_char uj
= use_json(argc
, argv
);
8093 struct vrf
*vrf
= pim_cmd_lookup_vrf(vty
, argv
, argc
, &idx
);
8100 if (argv_find(argv
, argc
, "detail", &idx
))
8101 arg
= argv
[idx
]->text
;
8102 else if (argv_find(argv
, argc
, "A.B.C.D", &idx
))
8103 arg
= argv
[idx
]->arg
;
8106 ip_msdp_show_peers_detail(vrf
->info
, vty
, argv
[idx
]->arg
, uj
);
8108 ip_msdp_show_peers(vrf
->info
, vty
, uj
);
8113 DEFUN (show_ip_msdp_peer_detail_vrf_all
,
8114 show_ip_msdp_peer_detail_vrf_all_cmd
,
8115 "show ip msdp vrf all peer [detail|A.B.C.D] [json]",
8120 "MSDP peer information\n"
8126 u_char uj
= use_json(argc
, argv
);
8132 RB_FOREACH (vrf
, vrf_name_head
, &vrfs_by_name
) {
8136 vty_out(vty
, " \"%s\": ", vrf
->name
);
8139 vty_out(vty
, "VRF: %s\n", vrf
->name
);
8140 if (argv_find(argv
, argc
, "detail", &idx
)
8141 || argv_find(argv
, argc
, "A.B.C.D", &idx
))
8142 ip_msdp_show_peers_detail(vrf
->info
, vty
,
8143 argv
[idx
]->arg
, uj
);
8145 ip_msdp_show_peers(vrf
->info
, vty
, uj
);
8148 vty_out(vty
, "}\n");
8153 static void ip_msdp_show_sa(struct pim_instance
*pim
, struct vty
*vty
,
8156 struct listnode
*sanode
;
8157 struct pim_msdp_sa
*sa
;
8158 char src_str
[INET_ADDRSTRLEN
];
8159 char grp_str
[INET_ADDRSTRLEN
];
8160 char rp_str
[INET_ADDRSTRLEN
];
8161 char timebuf
[PIM_MSDP_UPTIME_STRLEN
];
8165 json_object
*json
= NULL
;
8166 json_object
*json_group
= NULL
;
8167 json_object
*json_row
= NULL
;
8170 json
= json_object_new_object();
8173 "Source Group RP Local SPT Uptime\n");
8176 for (ALL_LIST_ELEMENTS_RO(pim
->msdp
.sa_list
, sanode
, sa
)) {
8177 now
= pim_time_monotonic_sec();
8178 pim_time_uptime(timebuf
, sizeof(timebuf
), now
- sa
->uptime
);
8179 pim_inet4_dump("<src?>", sa
->sg
.src
, src_str
, sizeof(src_str
));
8180 pim_inet4_dump("<grp?>", sa
->sg
.grp
, grp_str
, sizeof(grp_str
));
8181 if (sa
->flags
& PIM_MSDP_SAF_PEER
) {
8182 pim_inet4_dump("<rp?>", sa
->rp
, rp_str
, sizeof(rp_str
));
8184 strcpy(spt_str
, "yes");
8186 strcpy(spt_str
, "no");
8189 strcpy(rp_str
, "-");
8190 strcpy(spt_str
, "-");
8192 if (sa
->flags
& PIM_MSDP_SAF_LOCAL
) {
8193 strcpy(local_str
, "yes");
8195 strcpy(local_str
, "no");
8198 json_object_object_get_ex(json
, grp_str
, &json_group
);
8201 json_group
= json_object_new_object();
8202 json_object_object_add(json
, grp_str
,
8206 json_row
= json_object_new_object();
8207 json_object_string_add(json_row
, "source", src_str
);
8208 json_object_string_add(json_row
, "group", grp_str
);
8209 json_object_string_add(json_row
, "rp", rp_str
);
8210 json_object_string_add(json_row
, "local", local_str
);
8211 json_object_string_add(json_row
, "sptSetup", spt_str
);
8212 json_object_string_add(json_row
, "upTime", timebuf
);
8213 json_object_object_add(json_group
, src_str
, json_row
);
8215 vty_out(vty
, "%-15s %15s %15s %5c %3c %8s\n",
8216 src_str
, grp_str
, rp_str
, local_str
[0],
8217 spt_str
[0], timebuf
);
8222 vty_out(vty
, "%s\n", json_object_to_json_string_ext(
8223 json
, JSON_C_TO_STRING_PRETTY
));
8224 json_object_free(json
);
8228 static void ip_msdp_show_sa_entry_detail(struct pim_msdp_sa
*sa
,
8229 const char *src_str
,
8230 const char *grp_str
, struct vty
*vty
,
8231 u_char uj
, json_object
*json
)
8233 char rp_str
[INET_ADDRSTRLEN
];
8234 char peer_str
[INET_ADDRSTRLEN
];
8235 char timebuf
[PIM_MSDP_UPTIME_STRLEN
];
8238 char statetimer
[PIM_MSDP_TIMER_STRLEN
];
8240 json_object
*json_group
= NULL
;
8241 json_object
*json_row
= NULL
;
8243 now
= pim_time_monotonic_sec();
8244 pim_time_uptime(timebuf
, sizeof(timebuf
), now
- sa
->uptime
);
8245 if (sa
->flags
& PIM_MSDP_SAF_PEER
) {
8246 pim_inet4_dump("<rp?>", sa
->rp
, rp_str
, sizeof(rp_str
));
8247 pim_inet4_dump("<peer?>", sa
->peer
, peer_str
, sizeof(peer_str
));
8249 strcpy(spt_str
, "yes");
8251 strcpy(spt_str
, "no");
8254 strcpy(rp_str
, "-");
8255 strcpy(peer_str
, "-");
8256 strcpy(spt_str
, "-");
8258 if (sa
->flags
& PIM_MSDP_SAF_LOCAL
) {
8259 strcpy(local_str
, "yes");
8261 strcpy(local_str
, "no");
8263 pim_time_timer_to_hhmmss(statetimer
, sizeof(statetimer
),
8264 sa
->sa_state_timer
);
8266 json_object_object_get_ex(json
, grp_str
, &json_group
);
8269 json_group
= json_object_new_object();
8270 json_object_object_add(json
, grp_str
, json_group
);
8273 json_row
= json_object_new_object();
8274 json_object_string_add(json_row
, "source", src_str
);
8275 json_object_string_add(json_row
, "group", grp_str
);
8276 json_object_string_add(json_row
, "rp", rp_str
);
8277 json_object_string_add(json_row
, "local", local_str
);
8278 json_object_string_add(json_row
, "sptSetup", spt_str
);
8279 json_object_string_add(json_row
, "upTime", timebuf
);
8280 json_object_string_add(json_row
, "stateTimer", statetimer
);
8281 json_object_object_add(json_group
, src_str
, json_row
);
8283 vty_out(vty
, "SA : %s\n", sa
->sg_str
);
8284 vty_out(vty
, " RP : %s\n", rp_str
);
8285 vty_out(vty
, " Peer : %s\n", peer_str
);
8286 vty_out(vty
, " Local : %s\n", local_str
);
8287 vty_out(vty
, " SPT Setup : %s\n", spt_str
);
8288 vty_out(vty
, " Uptime : %s\n", timebuf
);
8289 vty_out(vty
, " State Timer : %s\n", statetimer
);
8294 static void ip_msdp_show_sa_detail(struct pim_instance
*pim
, struct vty
*vty
,
8297 struct listnode
*sanode
;
8298 struct pim_msdp_sa
*sa
;
8299 char src_str
[INET_ADDRSTRLEN
];
8300 char grp_str
[INET_ADDRSTRLEN
];
8301 json_object
*json
= NULL
;
8304 json
= json_object_new_object();
8307 for (ALL_LIST_ELEMENTS_RO(pim
->msdp
.sa_list
, sanode
, sa
)) {
8308 pim_inet4_dump("<src?>", sa
->sg
.src
, src_str
, sizeof(src_str
));
8309 pim_inet4_dump("<grp?>", sa
->sg
.grp
, grp_str
, sizeof(grp_str
));
8310 ip_msdp_show_sa_entry_detail(sa
, src_str
, grp_str
, vty
, uj
,
8315 vty_out(vty
, "%s\n", json_object_to_json_string_ext(
8316 json
, JSON_C_TO_STRING_PRETTY
));
8317 json_object_free(json
);
8321 DEFUN (show_ip_msdp_sa_detail
,
8322 show_ip_msdp_sa_detail_cmd
,
8323 "show ip msdp [vrf NAME] sa detail [json]",
8328 "MSDP active-source information\n"
8332 u_char uj
= use_json(argc
, argv
);
8334 struct vrf
*vrf
= pim_cmd_lookup_vrf(vty
, argv
, argc
, &idx
);
8339 ip_msdp_show_sa_detail(vrf
->info
, vty
, uj
);
8344 DEFUN (show_ip_msdp_sa_detail_vrf_all
,
8345 show_ip_msdp_sa_detail_vrf_all_cmd
,
8346 "show ip msdp vrf all sa detail [json]",
8351 "MSDP active-source information\n"
8355 u_char uj
= use_json(argc
, argv
);
8361 RB_FOREACH (vrf
, vrf_name_head
, &vrfs_by_name
) {
8365 vty_out(vty
, " \"%s\": ", vrf
->name
);
8368 vty_out(vty
, "VRF: %s\n", vrf
->name
);
8369 ip_msdp_show_sa_detail(vrf
->info
, vty
, uj
);
8372 vty_out(vty
, "}\n");
8377 static void ip_msdp_show_sa_addr(struct pim_instance
*pim
, struct vty
*vty
,
8378 const char *addr
, u_char uj
)
8380 struct listnode
*sanode
;
8381 struct pim_msdp_sa
*sa
;
8382 char src_str
[INET_ADDRSTRLEN
];
8383 char grp_str
[INET_ADDRSTRLEN
];
8384 json_object
*json
= NULL
;
8387 json
= json_object_new_object();
8390 for (ALL_LIST_ELEMENTS_RO(pim
->msdp
.sa_list
, sanode
, sa
)) {
8391 pim_inet4_dump("<src?>", sa
->sg
.src
, src_str
, sizeof(src_str
));
8392 pim_inet4_dump("<grp?>", sa
->sg
.grp
, grp_str
, sizeof(grp_str
));
8393 if (!strcmp(addr
, src_str
) || !strcmp(addr
, grp_str
)) {
8394 ip_msdp_show_sa_entry_detail(sa
, src_str
, grp_str
, vty
,
8400 vty_out(vty
, "%s\n", json_object_to_json_string_ext(
8401 json
, JSON_C_TO_STRING_PRETTY
));
8402 json_object_free(json
);
8406 static void ip_msdp_show_sa_sg(struct pim_instance
*pim
, struct vty
*vty
,
8407 const char *src
, const char *grp
, u_char uj
)
8409 struct listnode
*sanode
;
8410 struct pim_msdp_sa
*sa
;
8411 char src_str
[INET_ADDRSTRLEN
];
8412 char grp_str
[INET_ADDRSTRLEN
];
8413 json_object
*json
= NULL
;
8416 json
= json_object_new_object();
8419 for (ALL_LIST_ELEMENTS_RO(pim
->msdp
.sa_list
, sanode
, sa
)) {
8420 pim_inet4_dump("<src?>", sa
->sg
.src
, src_str
, sizeof(src_str
));
8421 pim_inet4_dump("<grp?>", sa
->sg
.grp
, grp_str
, sizeof(grp_str
));
8422 if (!strcmp(src
, src_str
) && !strcmp(grp
, grp_str
)) {
8423 ip_msdp_show_sa_entry_detail(sa
, src_str
, grp_str
, vty
,
8429 vty_out(vty
, "%s\n", json_object_to_json_string_ext(
8430 json
, JSON_C_TO_STRING_PRETTY
));
8431 json_object_free(json
);
8435 DEFUN (show_ip_msdp_sa_sg
,
8436 show_ip_msdp_sa_sg_cmd
,
8437 "show ip msdp [vrf NAME] sa [A.B.C.D [A.B.C.D]] [json]",
8442 "MSDP active-source information\n"
8443 "source or group ip\n"
8447 u_char uj
= use_json(argc
, argv
);
8451 vrf
= pim_cmd_lookup_vrf(vty
, argv
, argc
, &idx
);
8456 char *src_ip
= argv_find(argv
, argc
, "A.B.C.D", &idx
) ? argv
[idx
++]->arg
8458 char *grp_ip
= idx
< argc
&& argv_find(argv
, argc
, "A.B.C.D", &idx
)
8462 if (src_ip
&& grp_ip
)
8463 ip_msdp_show_sa_sg(vrf
->info
, vty
, src_ip
, grp_ip
, uj
);
8465 ip_msdp_show_sa_addr(vrf
->info
, vty
, src_ip
, uj
);
8467 ip_msdp_show_sa(vrf
->info
, vty
, uj
);
8472 DEFUN (show_ip_msdp_sa_sg_vrf_all
,
8473 show_ip_msdp_sa_sg_vrf_all_cmd
,
8474 "show ip msdp vrf all sa [A.B.C.D [A.B.C.D]] [json]",
8479 "MSDP active-source information\n"
8480 "source or group ip\n"
8484 u_char uj
= use_json(argc
, argv
);
8489 char *src_ip
= argv_find(argv
, argc
, "A.B.C.D", &idx
) ? argv
[idx
++]->arg
8491 char *grp_ip
= idx
< argc
&& argv_find(argv
, argc
, "A.B.C.D", &idx
)
8497 RB_FOREACH (vrf
, vrf_name_head
, &vrfs_by_name
) {
8501 vty_out(vty
, " \"%s\": ", vrf
->name
);
8504 vty_out(vty
, "VRF: %s\n", vrf
->name
);
8506 if (src_ip
&& grp_ip
)
8507 ip_msdp_show_sa_sg(vrf
->info
, vty
, src_ip
, grp_ip
, uj
);
8509 ip_msdp_show_sa_addr(vrf
->info
, vty
, src_ip
, uj
);
8511 ip_msdp_show_sa(vrf
->info
, vty
, uj
);
8514 vty_out(vty
, "}\n");
8520 void pim_cmd_init(void)
8522 install_node(&interface_node
,
8523 pim_interface_config_write
); /* INTERFACE_NODE */
8526 install_node(&debug_node
, pim_debug_config_write
);
8528 install_element(CONFIG_NODE
, &ip_multicast_routing_cmd
);
8529 install_element(CONFIG_NODE
, &no_ip_multicast_routing_cmd
);
8530 install_element(CONFIG_NODE
, &ip_pim_rp_cmd
);
8531 install_element(VRF_NODE
, &ip_pim_rp_cmd
);
8532 install_element(CONFIG_NODE
, &no_ip_pim_rp_cmd
);
8533 install_element(VRF_NODE
, &no_ip_pim_rp_cmd
);
8534 install_element(CONFIG_NODE
, &ip_pim_rp_prefix_list_cmd
);
8535 install_element(VRF_NODE
, &ip_pim_rp_prefix_list_cmd
);
8536 install_element(CONFIG_NODE
, &no_ip_pim_rp_prefix_list_cmd
);
8537 install_element(VRF_NODE
, &no_ip_pim_rp_prefix_list_cmd
);
8538 install_element(CONFIG_NODE
, &no_ip_pim_ssm_prefix_list_cmd
);
8539 install_element(VRF_NODE
, &no_ip_pim_ssm_prefix_list_cmd
);
8540 install_element(CONFIG_NODE
, &no_ip_pim_ssm_prefix_list_name_cmd
);
8541 install_element(VRF_NODE
, &no_ip_pim_ssm_prefix_list_name_cmd
);
8542 install_element(CONFIG_NODE
, &ip_pim_ssm_prefix_list_cmd
);
8543 install_element(VRF_NODE
, &ip_pim_ssm_prefix_list_cmd
);
8544 install_element(CONFIG_NODE
, &ip_pim_register_suppress_cmd
);
8545 install_element(VRF_NODE
, &ip_pim_register_suppress_cmd
);
8546 install_element(CONFIG_NODE
, &no_ip_pim_register_suppress_cmd
);
8547 install_element(VRF_NODE
, &no_ip_pim_register_suppress_cmd
);
8548 install_element(CONFIG_NODE
, &ip_pim_spt_switchover_infinity_cmd
);
8549 install_element(VRF_NODE
, &ip_pim_spt_switchover_infinity_cmd
);
8550 install_element(CONFIG_NODE
, &ip_pim_spt_switchover_infinity_plist_cmd
);
8551 install_element(VRF_NODE
, &ip_pim_spt_switchover_infinity_plist_cmd
);
8552 install_element(CONFIG_NODE
, &no_ip_pim_spt_switchover_infinity_cmd
);
8553 install_element(VRF_NODE
, &no_ip_pim_spt_switchover_infinity_cmd
);
8554 install_element(CONFIG_NODE
,
8555 &no_ip_pim_spt_switchover_infinity_plist_cmd
);
8556 install_element(VRF_NODE
, &no_ip_pim_spt_switchover_infinity_plist_cmd
);
8557 install_element(CONFIG_NODE
, &ip_pim_joinprune_time_cmd
);
8558 install_element(VRF_NODE
, &ip_pim_joinprune_time_cmd
);
8559 install_element(CONFIG_NODE
, &no_ip_pim_joinprune_time_cmd
);
8560 install_element(VRF_NODE
, &no_ip_pim_joinprune_time_cmd
);
8561 install_element(CONFIG_NODE
, &ip_pim_keep_alive_cmd
);
8562 install_element(VRF_NODE
, &ip_pim_keep_alive_cmd
);
8563 install_element(CONFIG_NODE
, &ip_pim_rp_keep_alive_cmd
);
8564 install_element(VRF_NODE
, &ip_pim_rp_keep_alive_cmd
);
8565 install_element(CONFIG_NODE
, &no_ip_pim_keep_alive_cmd
);
8566 install_element(VRF_NODE
, &no_ip_pim_keep_alive_cmd
);
8567 install_element(CONFIG_NODE
, &no_ip_pim_rp_keep_alive_cmd
);
8568 install_element(VRF_NODE
, &no_ip_pim_rp_keep_alive_cmd
);
8569 install_element(CONFIG_NODE
, &ip_pim_packets_cmd
);
8570 install_element(VRF_NODE
, &ip_pim_packets_cmd
);
8571 install_element(CONFIG_NODE
, &no_ip_pim_packets_cmd
);
8572 install_element(VRF_NODE
, &no_ip_pim_packets_cmd
);
8573 install_element(CONFIG_NODE
, &ip_pim_v6_secondary_cmd
);
8574 install_element(VRF_NODE
, &ip_pim_v6_secondary_cmd
);
8575 install_element(CONFIG_NODE
, &no_ip_pim_v6_secondary_cmd
);
8576 install_element(VRF_NODE
, &no_ip_pim_v6_secondary_cmd
);
8577 install_element(CONFIG_NODE
, &ip_ssmpingd_cmd
);
8578 install_element(VRF_NODE
, &ip_ssmpingd_cmd
);
8579 install_element(CONFIG_NODE
, &no_ip_ssmpingd_cmd
);
8580 install_element(VRF_NODE
, &no_ip_ssmpingd_cmd
);
8581 install_element(CONFIG_NODE
, &ip_msdp_peer_cmd
);
8582 install_element(VRF_NODE
, &ip_msdp_peer_cmd
);
8583 install_element(CONFIG_NODE
, &no_ip_msdp_peer_cmd
);
8584 install_element(VRF_NODE
, &no_ip_msdp_peer_cmd
);
8585 install_element(CONFIG_NODE
, &ip_pim_ecmp_cmd
);
8586 install_element(VRF_NODE
, &ip_pim_ecmp_cmd
);
8587 install_element(CONFIG_NODE
, &no_ip_pim_ecmp_cmd
);
8588 install_element(VRF_NODE
, &no_ip_pim_ecmp_cmd
);
8589 install_element(CONFIG_NODE
, &ip_pim_ecmp_rebalance_cmd
);
8590 install_element(VRF_NODE
, &ip_pim_ecmp_rebalance_cmd
);
8591 install_element(CONFIG_NODE
, &no_ip_pim_ecmp_rebalance_cmd
);
8592 install_element(VRF_NODE
, &no_ip_pim_ecmp_rebalance_cmd
);
8594 install_element(INTERFACE_NODE
, &interface_ip_igmp_cmd
);
8595 install_element(INTERFACE_NODE
, &interface_no_ip_igmp_cmd
);
8596 install_element(INTERFACE_NODE
, &interface_ip_igmp_join_cmd
);
8597 install_element(INTERFACE_NODE
, &interface_no_ip_igmp_join_cmd
);
8598 install_element(INTERFACE_NODE
, &interface_ip_igmp_version_cmd
);
8599 install_element(INTERFACE_NODE
, &interface_no_ip_igmp_version_cmd
);
8600 install_element(INTERFACE_NODE
, &interface_ip_igmp_query_interval_cmd
);
8601 install_element(INTERFACE_NODE
,
8602 &interface_no_ip_igmp_query_interval_cmd
);
8603 install_element(INTERFACE_NODE
,
8604 &interface_ip_igmp_query_max_response_time_cmd
);
8605 install_element(INTERFACE_NODE
,
8606 &interface_no_ip_igmp_query_max_response_time_cmd
);
8607 install_element(INTERFACE_NODE
,
8608 &interface_ip_igmp_query_max_response_time_dsec_cmd
);
8609 install_element(INTERFACE_NODE
,
8610 &interface_no_ip_igmp_query_max_response_time_dsec_cmd
);
8611 install_element(INTERFACE_NODE
, &interface_ip_pim_ssm_cmd
);
8612 install_element(INTERFACE_NODE
, &interface_no_ip_pim_ssm_cmd
);
8613 install_element(INTERFACE_NODE
, &interface_ip_pim_sm_cmd
);
8614 install_element(INTERFACE_NODE
, &interface_no_ip_pim_sm_cmd
);
8615 install_element(INTERFACE_NODE
, &interface_ip_pim_drprio_cmd
);
8616 install_element(INTERFACE_NODE
, &interface_no_ip_pim_drprio_cmd
);
8617 install_element(INTERFACE_NODE
, &interface_ip_pim_hello_cmd
);
8618 install_element(INTERFACE_NODE
, &interface_no_ip_pim_hello_cmd
);
8619 install_element(INTERFACE_NODE
, &interface_ip_pim_boundary_oil_cmd
);
8620 install_element(INTERFACE_NODE
, &interface_no_ip_pim_boundary_oil_cmd
);
8622 // Static mroutes NEB
8623 install_element(INTERFACE_NODE
, &interface_ip_mroute_cmd
);
8624 install_element(INTERFACE_NODE
, &interface_ip_mroute_source_cmd
);
8625 install_element(INTERFACE_NODE
, &interface_no_ip_mroute_cmd
);
8626 install_element(INTERFACE_NODE
, &interface_no_ip_mroute_source_cmd
);
8628 install_element(VIEW_NODE
, &show_ip_igmp_interface_cmd
);
8629 install_element(VIEW_NODE
, &show_ip_igmp_interface_vrf_all_cmd
);
8630 install_element(VIEW_NODE
, &show_ip_igmp_join_cmd
);
8631 install_element(VIEW_NODE
, &show_ip_igmp_join_vrf_all_cmd
);
8632 install_element(VIEW_NODE
, &show_ip_igmp_groups_cmd
);
8633 install_element(VIEW_NODE
, &show_ip_igmp_groups_vrf_all_cmd
);
8634 install_element(VIEW_NODE
, &show_ip_igmp_groups_retransmissions_cmd
);
8635 install_element(VIEW_NODE
, &show_ip_igmp_sources_cmd
);
8636 install_element(VIEW_NODE
, &show_ip_igmp_sources_retransmissions_cmd
);
8637 install_element(VIEW_NODE
, &show_ip_pim_assert_cmd
);
8638 install_element(VIEW_NODE
, &show_ip_pim_assert_internal_cmd
);
8639 install_element(VIEW_NODE
, &show_ip_pim_assert_metric_cmd
);
8640 install_element(VIEW_NODE
, &show_ip_pim_assert_winner_metric_cmd
);
8641 install_element(VIEW_NODE
, &show_ip_pim_interface_traffic_cmd
);
8642 install_element(VIEW_NODE
, &show_ip_pim_interface_cmd
);
8643 install_element(VIEW_NODE
, &show_ip_pim_interface_vrf_all_cmd
);
8644 install_element(VIEW_NODE
, &show_ip_pim_join_cmd
);
8645 install_element(VIEW_NODE
, &show_ip_pim_join_vrf_all_cmd
);
8646 install_element(VIEW_NODE
, &show_ip_pim_local_membership_cmd
);
8647 install_element(VIEW_NODE
, &show_ip_pim_neighbor_cmd
);
8648 install_element(VIEW_NODE
, &show_ip_pim_neighbor_vrf_all_cmd
);
8649 install_element(VIEW_NODE
, &show_ip_pim_rpf_cmd
);
8650 install_element(VIEW_NODE
, &show_ip_pim_rpf_vrf_all_cmd
);
8651 install_element(VIEW_NODE
, &show_ip_pim_secondary_cmd
);
8652 install_element(VIEW_NODE
, &show_ip_pim_state_cmd
);
8653 install_element(VIEW_NODE
, &show_ip_pim_state_vrf_all_cmd
);
8654 install_element(VIEW_NODE
, &show_ip_pim_upstream_cmd
);
8655 install_element(VIEW_NODE
, &show_ip_pim_upstream_vrf_all_cmd
);
8656 install_element(VIEW_NODE
, &show_ip_pim_upstream_join_desired_cmd
);
8657 install_element(VIEW_NODE
, &show_ip_pim_upstream_rpf_cmd
);
8658 install_element(VIEW_NODE
, &show_ip_pim_rp_cmd
);
8659 install_element(VIEW_NODE
, &show_ip_pim_rp_vrf_all_cmd
);
8660 install_element(VIEW_NODE
, &show_ip_multicast_cmd
);
8661 install_element(VIEW_NODE
, &show_ip_multicast_vrf_all_cmd
);
8662 install_element(VIEW_NODE
, &show_ip_mroute_cmd
);
8663 install_element(VIEW_NODE
, &show_ip_mroute_vrf_all_cmd
);
8664 install_element(VIEW_NODE
, &show_ip_mroute_count_cmd
);
8665 install_element(VIEW_NODE
, &show_ip_mroute_count_vrf_all_cmd
);
8666 install_element(VIEW_NODE
, &show_ip_rib_cmd
);
8667 install_element(VIEW_NODE
, &show_ip_ssmpingd_cmd
);
8668 install_element(VIEW_NODE
, &show_debugging_pim_cmd
);
8669 install_element(VIEW_NODE
, &show_ip_pim_nexthop_cmd
);
8670 install_element(VIEW_NODE
, &show_ip_pim_nexthop_lookup_cmd
);
8672 install_element(ENABLE_NODE
, &clear_ip_interfaces_cmd
);
8673 install_element(ENABLE_NODE
, &clear_ip_igmp_interfaces_cmd
);
8674 install_element(ENABLE_NODE
, &clear_ip_mroute_cmd
);
8675 install_element(ENABLE_NODE
, &clear_ip_pim_interfaces_cmd
);
8676 install_element(ENABLE_NODE
, &clear_ip_pim_interface_traffic_cmd
);
8677 install_element(ENABLE_NODE
, &clear_ip_pim_oil_cmd
);
8679 install_element(ENABLE_NODE
, &debug_igmp_cmd
);
8680 install_element(ENABLE_NODE
, &no_debug_igmp_cmd
);
8681 install_element(ENABLE_NODE
, &debug_igmp_events_cmd
);
8682 install_element(ENABLE_NODE
, &no_debug_igmp_events_cmd
);
8683 install_element(ENABLE_NODE
, &debug_igmp_packets_cmd
);
8684 install_element(ENABLE_NODE
, &no_debug_igmp_packets_cmd
);
8685 install_element(ENABLE_NODE
, &debug_igmp_trace_cmd
);
8686 install_element(ENABLE_NODE
, &no_debug_igmp_trace_cmd
);
8687 install_element(ENABLE_NODE
, &debug_mroute_cmd
);
8688 install_element(ENABLE_NODE
, &debug_mroute_detail_cmd
);
8689 install_element(ENABLE_NODE
, &no_debug_mroute_cmd
);
8690 install_element(ENABLE_NODE
, &no_debug_mroute_detail_cmd
);
8691 install_element(ENABLE_NODE
, &debug_static_cmd
);
8692 install_element(ENABLE_NODE
, &no_debug_static_cmd
);
8693 install_element(ENABLE_NODE
, &debug_pim_cmd
);
8694 install_element(ENABLE_NODE
, &no_debug_pim_cmd
);
8695 install_element(ENABLE_NODE
, &debug_pim_nht_cmd
);
8696 install_element(ENABLE_NODE
, &no_debug_pim_nht_cmd
);
8697 install_element(ENABLE_NODE
, &debug_pim_nht_rp_cmd
);
8698 install_element(ENABLE_NODE
, &no_debug_pim_nht_rp_cmd
);
8699 install_element(ENABLE_NODE
, &debug_pim_events_cmd
);
8700 install_element(ENABLE_NODE
, &no_debug_pim_events_cmd
);
8701 install_element(ENABLE_NODE
, &debug_pim_packets_cmd
);
8702 install_element(ENABLE_NODE
, &no_debug_pim_packets_cmd
);
8703 install_element(ENABLE_NODE
, &debug_pim_packetdump_send_cmd
);
8704 install_element(ENABLE_NODE
, &no_debug_pim_packetdump_send_cmd
);
8705 install_element(ENABLE_NODE
, &debug_pim_packetdump_recv_cmd
);
8706 install_element(ENABLE_NODE
, &no_debug_pim_packetdump_recv_cmd
);
8707 install_element(ENABLE_NODE
, &debug_pim_trace_cmd
);
8708 install_element(ENABLE_NODE
, &no_debug_pim_trace_cmd
);
8709 install_element(ENABLE_NODE
, &debug_pim_trace_detail_cmd
);
8710 install_element(ENABLE_NODE
, &no_debug_pim_trace_detail_cmd
);
8711 install_element(ENABLE_NODE
, &debug_ssmpingd_cmd
);
8712 install_element(ENABLE_NODE
, &no_debug_ssmpingd_cmd
);
8713 install_element(ENABLE_NODE
, &debug_pim_zebra_cmd
);
8714 install_element(ENABLE_NODE
, &no_debug_pim_zebra_cmd
);
8715 install_element(ENABLE_NODE
, &debug_msdp_cmd
);
8716 install_element(ENABLE_NODE
, &no_debug_msdp_cmd
);
8717 install_element(ENABLE_NODE
, &undebug_msdp_cmd
);
8718 install_element(ENABLE_NODE
, &debug_msdp_events_cmd
);
8719 install_element(ENABLE_NODE
, &no_debug_msdp_events_cmd
);
8720 install_element(ENABLE_NODE
, &undebug_msdp_events_cmd
);
8721 install_element(ENABLE_NODE
, &debug_msdp_packets_cmd
);
8722 install_element(ENABLE_NODE
, &no_debug_msdp_packets_cmd
);
8723 install_element(ENABLE_NODE
, &undebug_msdp_packets_cmd
);
8725 install_element(CONFIG_NODE
, &debug_igmp_cmd
);
8726 install_element(CONFIG_NODE
, &no_debug_igmp_cmd
);
8727 install_element(CONFIG_NODE
, &debug_igmp_events_cmd
);
8728 install_element(CONFIG_NODE
, &no_debug_igmp_events_cmd
);
8729 install_element(CONFIG_NODE
, &debug_igmp_packets_cmd
);
8730 install_element(CONFIG_NODE
, &no_debug_igmp_packets_cmd
);
8731 install_element(CONFIG_NODE
, &debug_igmp_trace_cmd
);
8732 install_element(CONFIG_NODE
, &no_debug_igmp_trace_cmd
);
8733 install_element(CONFIG_NODE
, &debug_mroute_cmd
);
8734 install_element(CONFIG_NODE
, &debug_mroute_detail_cmd
);
8735 install_element(CONFIG_NODE
, &no_debug_mroute_cmd
);
8736 install_element(CONFIG_NODE
, &no_debug_mroute_detail_cmd
);
8737 install_element(CONFIG_NODE
, &debug_static_cmd
);
8738 install_element(CONFIG_NODE
, &no_debug_static_cmd
);
8739 install_element(CONFIG_NODE
, &debug_pim_cmd
);
8740 install_element(CONFIG_NODE
, &no_debug_pim_cmd
);
8741 install_element(CONFIG_NODE
, &debug_pim_nht_cmd
);
8742 install_element(CONFIG_NODE
, &no_debug_pim_nht_cmd
);
8743 install_element(CONFIG_NODE
, &debug_pim_nht_rp_cmd
);
8744 install_element(CONFIG_NODE
, &no_debug_pim_nht_rp_cmd
);
8745 install_element(CONFIG_NODE
, &debug_pim_events_cmd
);
8746 install_element(CONFIG_NODE
, &no_debug_pim_events_cmd
);
8747 install_element(CONFIG_NODE
, &debug_pim_packets_cmd
);
8748 install_element(CONFIG_NODE
, &no_debug_pim_packets_cmd
);
8749 install_element(CONFIG_NODE
, &debug_pim_trace_cmd
);
8750 install_element(CONFIG_NODE
, &no_debug_pim_trace_cmd
);
8751 install_element(CONFIG_NODE
, &debug_pim_trace_detail_cmd
);
8752 install_element(CONFIG_NODE
, &no_debug_pim_trace_detail_cmd
);
8753 install_element(CONFIG_NODE
, &debug_ssmpingd_cmd
);
8754 install_element(CONFIG_NODE
, &no_debug_ssmpingd_cmd
);
8755 install_element(CONFIG_NODE
, &debug_pim_zebra_cmd
);
8756 install_element(CONFIG_NODE
, &no_debug_pim_zebra_cmd
);
8757 install_element(CONFIG_NODE
, &debug_msdp_cmd
);
8758 install_element(CONFIG_NODE
, &no_debug_msdp_cmd
);
8759 install_element(CONFIG_NODE
, &undebug_msdp_cmd
);
8760 install_element(CONFIG_NODE
, &debug_msdp_events_cmd
);
8761 install_element(CONFIG_NODE
, &no_debug_msdp_events_cmd
);
8762 install_element(CONFIG_NODE
, &undebug_msdp_events_cmd
);
8763 install_element(CONFIG_NODE
, &debug_msdp_packets_cmd
);
8764 install_element(CONFIG_NODE
, &no_debug_msdp_packets_cmd
);
8765 install_element(CONFIG_NODE
, &undebug_msdp_packets_cmd
);
8767 install_element(CONFIG_NODE
, &ip_msdp_mesh_group_member_cmd
);
8768 install_element(VRF_NODE
, &ip_msdp_mesh_group_member_cmd
);
8769 install_element(CONFIG_NODE
, &no_ip_msdp_mesh_group_member_cmd
);
8770 install_element(VRF_NODE
, &no_ip_msdp_mesh_group_member_cmd
);
8771 install_element(CONFIG_NODE
, &ip_msdp_mesh_group_source_cmd
);
8772 install_element(VRF_NODE
, &ip_msdp_mesh_group_source_cmd
);
8773 install_element(CONFIG_NODE
, &no_ip_msdp_mesh_group_source_cmd
);
8774 install_element(VRF_NODE
, &no_ip_msdp_mesh_group_source_cmd
);
8775 install_element(VIEW_NODE
, &show_ip_msdp_peer_detail_cmd
);
8776 install_element(VIEW_NODE
, &show_ip_msdp_peer_detail_vrf_all_cmd
);
8777 install_element(VIEW_NODE
, &show_ip_msdp_sa_detail_cmd
);
8778 install_element(VIEW_NODE
, &show_ip_msdp_sa_detail_vrf_all_cmd
);
8779 install_element(VIEW_NODE
, &show_ip_msdp_sa_sg_cmd
);
8780 install_element(VIEW_NODE
, &show_ip_msdp_sa_sg_vrf_all_cmd
);
8781 install_element(VIEW_NODE
, &show_ip_msdp_mesh_group_cmd
);
8782 install_element(VIEW_NODE
, &show_ip_msdp_mesh_group_vrf_all_cmd
);
8783 install_element(VIEW_NODE
, &show_ip_pim_ssm_range_cmd
);
8784 install_element(VIEW_NODE
, &show_ip_pim_group_type_cmd
);
8785 install_element(INTERFACE_NODE
, &interface_pim_use_source_cmd
);
8786 install_element(INTERFACE_NODE
, &interface_no_pim_use_source_cmd
);
8787 /* Install BFD command */
8788 install_element(INTERFACE_NODE
, &ip_pim_bfd_cmd
);
8789 install_element(INTERFACE_NODE
, &ip_pim_bfd_param_cmd
);
8790 install_element(INTERFACE_NODE
, &no_ip_pim_bfd_cmd
);
8791 install_element(INTERFACE_NODE
, &no_ip_pim_bfd_param_cmd
);