2 Copyright (C) 2000 Kunihiro Ishiguro <kunihiro@zebra.org>
4 This file is part of GNU Zebra.
6 GNU Zebra is free software; you can redistribute it and/or modify it
7 under the terms of the GNU General Public License as published by the
8 Free Software Foundation; either version 2, or (at your option) any
11 GNU Zebra is distributed in the hope that it will be useful, but
12 WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 General Public License for more details.
16 You should have received a copy of the GNU General Public License
17 along with GNU Zebra; see the file COPYING. If not, write to the Free
18 Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
32 #include "bgpd/bgpd.h"
33 #include "bgpd/bgp_table.h"
34 #include "bgpd/bgp_route.h"
35 #include "bgpd/bgp_attr.h"
36 #include "bgpd/bgp_mplsvpn.h"
37 #include "bgpd/bgp_packet.h"
38 #include "bgpd/bgp_vty.h"
39 #include "bgpd/bgp_vpn.h"
42 #include "bgpd/rfapi/rfapi_backend.h"
46 argv_find_and_parse_vpnvx(struct cmd_token
**argv
, int argc
, int *index
, afi_t
*afi
)
49 if (argv_find (argv
, argc
, "vpnv4", index
))
55 else if (argv_find (argv
, argc
, "vpnv6", index
))
65 decode_rd_type (u_char
*pnt
)
69 v
= ((u_int16_t
) *pnt
++ << 8);
72 * VNC L2 stores LHI in lower byte, so omit it
74 if (v
!= RD_TYPE_VNC_ETH
)
75 v
|= (u_int16_t
) *pnt
;
76 #else /* duplicate code for clarity */
77 v
|= (u_int16_t
) *pnt
;
84 encode_rd_type (u_int16_t v
, u_char
*pnt
)
86 *((u_int16_t
*)pnt
) = htons(v
);
90 decode_label (u_char
*pnt
)
94 l
= ((u_int32_t
) *pnt
++ << 12);
95 l
|= (u_int32_t
) *pnt
++ << 4;
96 l
|= (u_int32_t
) ((*pnt
& 0xf0) >> 4);
101 encode_label(u_int32_t label
,
106 *pnt
++ = (label
>>12) & 0xff;
107 *pnt
++ = (label
>>4) & 0xff;
108 *pnt
++ = ((label
<<4)+1) & 0xff; /* S=1 */
111 /* type == RD_TYPE_AS */
113 decode_rd_as (u_char
*pnt
, struct rd_as
*rd_as
)
115 rd_as
->as
= (u_int16_t
) *pnt
++ << 8;
116 rd_as
->as
|= (u_int16_t
) *pnt
++;
118 rd_as
->val
= ((u_int32_t
) *pnt
++ << 24);
119 rd_as
->val
|= ((u_int32_t
) *pnt
++ << 16);
120 rd_as
->val
|= ((u_int32_t
) *pnt
++ << 8);
121 rd_as
->val
|= (u_int32_t
) *pnt
;
124 /* type == RD_TYPE_AS4 */
126 decode_rd_as4 (u_char
*pnt
, struct rd_as
*rd_as
)
128 rd_as
->as
= (u_int32_t
) *pnt
++ << 24;
129 rd_as
->as
|= (u_int32_t
) *pnt
++ << 16;
130 rd_as
->as
|= (u_int32_t
) *pnt
++ << 8;
131 rd_as
->as
|= (u_int32_t
) *pnt
++;
133 rd_as
->val
= ((u_int16_t
) *pnt
++ << 8);
134 rd_as
->val
|= (u_int16_t
) *pnt
;
137 /* type == RD_TYPE_IP */
139 decode_rd_ip (u_char
*pnt
, struct rd_ip
*rd_ip
)
141 memcpy (&rd_ip
->ip
, pnt
, 4);
144 rd_ip
->val
= ((u_int16_t
) *pnt
++ << 8);
145 rd_ip
->val
|= (u_int16_t
) *pnt
;
149 /* type == RD_TYPE_VNC_ETH */
151 decode_rd_vnc_eth (u_char
*pnt
, struct rd_vnc_eth
*rd_vnc_eth
)
153 rd_vnc_eth
->type
= RD_TYPE_VNC_ETH
;
154 rd_vnc_eth
->local_nve_id
= pnt
[1];
155 memcpy (rd_vnc_eth
->macaddr
.octet
, pnt
+ 2, ETHER_ADDR_LEN
);
160 bgp_nlri_parse_vpn (struct peer
*peer
, struct attr
*attr
,
161 struct bgp_nlri
*packet
)
171 struct prefix_rd prd
;
176 u_int32_t addpath_id
;
178 /* Check peer status. */
179 if (peer
->status
!= Established
)
183 prd
.family
= AF_UNSPEC
;
187 lim
= pnt
+ packet
->length
;
192 addpath_encoded
= (CHECK_FLAG (peer
->af_cap
[afi
][safi
], PEER_CAP_ADDPATH_AF_RX_ADV
) &&
193 CHECK_FLAG (peer
->af_cap
[afi
][safi
], PEER_CAP_ADDPATH_AF_TX_RCV
));
195 #define VPN_PREFIXLEN_MIN_BYTES (3 + 8) /* label + RD */
196 for (; pnt
< lim
; pnt
+= psize
)
198 /* Clear prefix structure. */
199 memset (&p
, 0, sizeof (struct prefix
));
204 /* When packet overflow occurs return immediately. */
205 if (pnt
+ BGP_ADDPATH_ID_LEN
> lim
)
208 addpath_id
= ntohl(*((uint32_t*) pnt
));
209 pnt
+= BGP_ADDPATH_ID_LEN
;
212 /* Fetch prefix length. */
214 p
.family
= afi2family (packet
->afi
);
215 psize
= PSIZE (prefixlen
);
217 if (prefixlen
< VPN_PREFIXLEN_MIN_BYTES
*8)
219 zlog_err ("%s [Error] Update packet error / VPN (prefix length %d less than VPN min length)",
220 peer
->host
, prefixlen
);
224 /* sanity check against packet data */
225 if ((pnt
+ psize
) > lim
)
227 zlog_err ("%s [Error] Update packet error / VPN (prefix length %d exceeds packet size %u)",
229 prefixlen
, (uint
)(lim
-pnt
));
233 /* sanity check against storage for the IP address portion */
234 if ((psize
- VPN_PREFIXLEN_MIN_BYTES
) > (ssize_t
) sizeof(p
.u
))
236 zlog_err ("%s [Error] Update packet error / VPN (psize %d exceeds storage size %zu)",
238 prefixlen
- VPN_PREFIXLEN_MIN_BYTES
*8, sizeof(p
.u
));
242 /* Sanity check against max bitlen of the address family */
243 if ((psize
- VPN_PREFIXLEN_MIN_BYTES
) > prefix_blen (&p
))
245 zlog_err ("%s [Error] Update packet error / VPN (psize %d exceeds family (%u) max byte len %u)",
247 prefixlen
- VPN_PREFIXLEN_MIN_BYTES
*8,
248 p
.family
, prefix_blen (&p
));
252 /* Copyr label to prefix. */
255 /* Copy routing distinguisher to rd. */
256 memcpy (&prd
.val
, pnt
+ 3, 8);
258 /* Decode RD type. */
259 type
= decode_rd_type (pnt
+ 3);
264 decode_rd_as (pnt
+ 5, &rd_as
);
268 decode_rd_as4 (pnt
+ 5, &rd_as
);
272 decode_rd_ip (pnt
+ 5, &rd_ip
);
276 case RD_TYPE_VNC_ETH
:
281 zlog_err ("Unknown RD type %d", type
);
282 break; /* just report */
285 p
.prefixlen
= prefixlen
- VPN_PREFIXLEN_MIN_BYTES
*8;/* exclude label & RD */
286 memcpy (&p
.u
.prefix
, pnt
+ VPN_PREFIXLEN_MIN_BYTES
,
287 psize
- VPN_PREFIXLEN_MIN_BYTES
);
291 bgp_update (peer
, &p
, addpath_id
, attr
, packet
->afi
, SAFI_MPLS_VPN
,
292 ZEBRA_ROUTE_BGP
, BGP_ROUTE_NORMAL
, &prd
, tagpnt
, 0, NULL
);
296 bgp_withdraw (peer
, &p
, addpath_id
, attr
, packet
->afi
, SAFI_MPLS_VPN
,
297 ZEBRA_ROUTE_BGP
, BGP_ROUTE_NORMAL
, &prd
, tagpnt
, NULL
);
300 /* Packet length consistency check. */
303 zlog_err ("%s [Error] Update packet error / VPN (%zu data remaining after parsing)",
304 peer
->host
, lim
- pnt
);
309 #undef VPN_PREFIXLEN_MIN_BYTES
313 str2prefix_rd (const char *str
, struct prefix_rd
*prd
)
315 int ret
; /* ret of called functions */
316 int lret
; /* local ret, of this func */
319 struct stream
*s
= NULL
;
325 prd
->family
= AF_UNSPEC
;
329 p
= strchr (str
, ':');
333 if (! all_digit (p
+ 1))
336 half
= XMALLOC (MTYPE_TMP
, (p
- str
) + 1);
337 memcpy (half
, str
, (p
- str
));
338 half
[p
- str
] = '\0';
340 p2
= strchr (str
, '.');
344 unsigned long as_val
;
346 if (! all_digit (half
))
352 stream_putw (s
, RD_TYPE_AS4
);
353 stream_putl (s
, as_val
);
354 stream_putw (s
, atol (p
+ 1));
358 stream_putw (s
, RD_TYPE_AS
);
359 stream_putw (s
, as_val
);
360 stream_putl (s
, atol (p
+ 1));
365 ret
= inet_aton (half
, &addr
);
369 stream_putw (s
, RD_TYPE_IP
);
370 stream_put_in_addr (s
, &addr
);
371 stream_putw (s
, atol (p
+ 1));
373 memcpy (prd
->val
, s
->data
, 8);
380 XFREE(MTYPE_TMP
, half
);
385 str2tag (const char *str
, u_char
*tag
)
395 l
= strtoul (str
, &endptr
, 10);
397 if (*endptr
!= '\0' || errno
|| l
> UINT32_MAX
)
402 tag
[0] = (u_char
)(t
>> 12);
403 tag
[1] = (u_char
)(t
>> 4);
404 tag
[2] = (u_char
)(t
<< 4);
410 prefix_rd2str (struct prefix_rd
*prd
, char *buf
, size_t size
)
417 if (size
< RD_ADDRSTRLEN
)
422 type
= decode_rd_type (pnt
);
424 if (type
== RD_TYPE_AS
)
426 decode_rd_as (pnt
+ 2, &rd_as
);
427 snprintf (buf
, size
, "%u:%d", rd_as
.as
, rd_as
.val
);
430 else if (type
== RD_TYPE_AS4
)
432 decode_rd_as4 (pnt
+ 2, &rd_as
);
433 snprintf (buf
, size
, "%u:%d", rd_as
.as
, rd_as
.val
);
436 else if (type
== RD_TYPE_IP
)
438 decode_rd_ip (pnt
+ 2, &rd_ip
);
439 snprintf (buf
, size
, "%s:%d", inet_ntoa (rd_ip
.ip
), rd_ip
.val
);
443 else if (type
== RD_TYPE_VNC_ETH
)
445 snprintf(buf
, size
, "LHI:%d, %02x:%02x:%02x:%02x:%02x:%02x",
447 *(pnt
+2), /* MAC[0] */
460 /* For testing purpose, static route of MPLS-VPN. */
461 DEFUN (vpnv4_network
,
463 "network A.B.C.D/M rd ASN:nn_or_IP-address:nn tag WORD",
464 "Specify a network to announce via BGP\n"
466 "Specify Route Distinguisher\n"
467 "VPN Route Distinguisher\n"
471 int idx_ipv4_prefixlen
= 1;
472 int idx_ext_community
= 3;
474 return bgp_static_set_safi (SAFI_MPLS_VPN
, vty
, argv
[idx_ipv4_prefixlen
]->arg
, argv
[idx_ext_community
]->arg
,
475 argv
[idx_word
]->arg
, NULL
, 0, NULL
, NULL
, NULL
, NULL
);
478 DEFUN (vpnv4_network_route_map
,
479 vpnv4_network_route_map_cmd
,
480 "network A.B.C.D/M rd ASN:nn_or_IP-address:nn tag WORD route-map WORD",
481 "Specify a network to announce via BGP\n"
483 "Specify Route Distinguisher\n"
484 "VPN Route Distinguisher\n"
490 int idx_ipv4_prefixlen
= 1;
491 int idx_ext_community
= 3;
494 return bgp_static_set_safi (SAFI_MPLS_VPN
, vty
, argv
[idx_ipv4_prefixlen
]->arg
, argv
[idx_ext_community
]->arg
, argv
[idx_word
]->arg
,
495 argv
[idx_word_2
]->arg
, 0, NULL
, NULL
, NULL
, NULL
);
498 /* For testing purpose, static route of MPLS-VPN. */
499 DEFUN (no_vpnv4_network
,
500 no_vpnv4_network_cmd
,
501 "no network A.B.C.D/M rd ASN:nn_or_IP-address:nn tag WORD",
503 "Specify a network to announce via BGP\n"
505 "Specify Route Distinguisher\n"
506 "VPN Route Distinguisher\n"
510 int idx_ipv4_prefixlen
= 2;
511 int idx_ext_community
= 4;
513 return bgp_static_unset_safi (SAFI_MPLS_VPN
, vty
, argv
[idx_ipv4_prefixlen
]->arg
,
514 argv
[idx_ext_community
]->arg
, argv
[idx_word
]->arg
,
515 0, NULL
, NULL
, NULL
);
518 DEFUN (vpnv6_network
,
520 "network X:X::X:X/M rd ASN:nn_or_IP-address:nn tag WORD [route-map WORD]",
521 "Specify a network to announce via BGP\n"
522 "IPv6 prefix <network>/<length>, e.g., 3ffe::/16\n"
523 "Specify Route Distinguisher\n"
524 "VPN Route Distinguisher\n"
530 int idx_ipv6_prefix
= 1;
531 int idx_ext_community
= 3;
534 if (argv
[idx_word_2
])
535 return bgp_static_set_safi (SAFI_MPLS_VPN
, vty
, argv
[idx_ipv6_prefix
]->arg
, argv
[idx_ext_community
]->arg
, argv
[idx_word
]->arg
, argv
[idx_word_2
]->arg
, 0, NULL
, NULL
, NULL
, NULL
);
537 return bgp_static_set_safi (SAFI_MPLS_VPN
, vty
, argv
[idx_ipv6_prefix
]->arg
, argv
[idx_ext_community
]->arg
, argv
[idx_word
]->arg
, NULL
, 0, NULL
, NULL
, NULL
, NULL
);
540 /* For testing purpose, static route of MPLS-VPN. */
541 DEFUN (no_vpnv6_network
,
542 no_vpnv6_network_cmd
,
543 "no network X:X::X:X/M rd ASN:nn_or_IP-address:nn tag WORD",
545 "Specify a network to announce via BGP\n"
546 "IPv6 prefix <network>/<length>, e.g., 3ffe::/16\n"
547 "Specify Route Distinguisher\n"
548 "VPN Route Distinguisher\n"
552 int idx_ipv6_prefix
= 2;
553 int idx_ext_community
= 4;
555 return bgp_static_unset_safi (SAFI_MPLS_VPN
, vty
, argv
[idx_ipv6_prefix
]->arg
, argv
[idx_ext_community
]->arg
, argv
[idx_word
]->arg
, 0, NULL
, NULL
, NULL
);
559 bgp_show_mpls_vpn (struct vty
*vty
, afi_t afi
, struct prefix_rd
*prd
,
560 enum bgp_show_type type
, void *output_arg
, int tags
, u_char use_json
)
563 struct bgp_table
*table
;
569 char v4_header
[] = " Network Next Hop Metric LocPrf Weight Path%s";
570 char v4_header_tag
[] = " Network Next Hop In tag/Out tag%s";
571 unsigned long output_count
= 0;
572 unsigned long total_count
= 0;
573 json_object
*json
= NULL
;
574 json_object
*json_mroute
= NULL
;
575 json_object
*json_nroute
= NULL
;
576 json_object
*json_array
= NULL
;
577 json_object
*json_scode
= NULL
;
578 json_object
*json_ocode
= NULL
;
580 bgp
= bgp_get_default ();
584 vty_out (vty
, "No BGP process is configured%s", VTY_NEWLINE
);
590 json_scode
= json_object_new_object();
591 json_ocode
= json_object_new_object();
592 json
= json_object_new_object();
593 json_mroute
= json_object_new_object();
594 json_nroute
= json_object_new_object();
596 json_object_string_add(json_scode
, "suppressed", "s");
597 json_object_string_add(json_scode
, "damped", "d");
598 json_object_string_add(json_scode
, "history", "h");
599 json_object_string_add(json_scode
, "valid", "*");
600 json_object_string_add(json_scode
, "best", ">");
601 json_object_string_add(json_scode
, "internal", "i");
603 json_object_string_add(json_ocode
, "igp", "i");
604 json_object_string_add(json_ocode
, "egp", "e");
605 json_object_string_add(json_ocode
, "incomplete", "?");
608 if ((afi
!= AFI_IP
) && (afi
!= AFI_IP6
))
610 vty_out (vty
, "Afi %d not supported%s", afi
, VTY_NEWLINE
);
614 for (rn
= bgp_table_top (bgp
->rib
[afi
][SAFI_MPLS_VPN
]); rn
; rn
= bgp_route_next (rn
))
616 if (prd
&& memcmp (rn
->p
.u
.val
, prd
->val
, 8) != 0)
619 if ((table
= rn
->info
) != NULL
)
623 for (rm
= bgp_table_top (table
); rm
; rm
= bgp_route_next (rm
))
627 json_array
= json_object_new_array();
631 for (ri
= rm
->info
; ri
; ri
= ri
->next
)
633 if (type
== bgp_show_type_neighbor
)
635 union sockunion
*su
= output_arg
;
637 if (ri
->peer
->su_remote
== NULL
|| ! sockunion_same(ri
->peer
->su_remote
, su
))
646 json_object_int_add(json
, "bgpTableVersion", 0);
647 json_object_string_add(json
, "bgpLocalRouterId", inet_ntoa (bgp
->router_id
));
648 json_object_object_add(json
, "bgpStatusCodes", json_scode
);
649 json_object_object_add(json
, "bgpOriginCodes", json_ocode
);
655 vty_out (vty
, v4_header_tag
, VTY_NEWLINE
);
658 vty_out (vty
, "BGP table version is 0, local router ID is %s%s",
659 inet_ntoa (bgp
->router_id
), VTY_NEWLINE
);
660 vty_out (vty
, "Status codes: s suppressed, d damped, h history, * valid, > best, i - internal%s",
662 vty_out (vty
, "Origin codes: i - IGP, e - EGP, ? - incomplete%s%s",
663 VTY_NEWLINE
, VTY_NEWLINE
);
664 vty_out (vty
, v4_header
, VTY_NEWLINE
);
674 struct rd_ip rd_ip
= {0};
676 struct rd_vnc_eth rd_vnc_eth
= {0};
682 /* Decode RD type. */
683 type
= decode_rd_type (pnt
);
684 /* Decode RD value. */
685 if (type
== RD_TYPE_AS
)
686 decode_rd_as (pnt
+ 2, &rd_as
);
687 else if (type
== RD_TYPE_AS4
)
688 decode_rd_as4 (pnt
+ 2, &rd_as
);
689 else if (type
== RD_TYPE_IP
)
690 decode_rd_ip (pnt
+ 2, &rd_ip
);
692 else if (type
== RD_TYPE_VNC_ETH
)
693 decode_rd_vnc_eth (pnt
, &rd_vnc_eth
);
699 if (type
== RD_TYPE_AS
|| type
== RD_TYPE_AS4
)
700 sprintf (buffer
, "%u:%d", rd_as
.as
, rd_as
.val
);
701 else if (type
== RD_TYPE_IP
)
702 sprintf (buffer
, "%s:%d", inet_ntoa (rd_ip
.ip
), rd_ip
.val
);
703 json_object_string_add(json_nroute
, "routeDistinguisher", buffer
);
707 vty_out (vty
, "Route Distinguisher: ");
709 if (type
== RD_TYPE_AS
|| type
== RD_TYPE_AS4
)
710 vty_out (vty
, "%u:%d", rd_as
.as
, rd_as
.val
);
711 else if (type
== RD_TYPE_IP
)
712 vty_out (vty
, "%s:%d", inet_ntoa (rd_ip
.ip
), rd_ip
.val
);
714 else if (type
== RD_TYPE_VNC_ETH
)
715 vty_out (vty
, "%u:%02x:%02x:%02x:%02x:%02x:%02x",
716 rd_vnc_eth
.local_nve_id
,
717 rd_vnc_eth
.macaddr
.octet
[0],
718 rd_vnc_eth
.macaddr
.octet
[1],
719 rd_vnc_eth
.macaddr
.octet
[2],
720 rd_vnc_eth
.macaddr
.octet
[3],
721 rd_vnc_eth
.macaddr
.octet
[4],
722 rd_vnc_eth
.macaddr
.octet
[5]);
724 vty_out (vty
, "%s", VTY_NEWLINE
);
729 route_vty_out_tag (vty
, &rm
->p
, ri
, 0, SAFI_MPLS_VPN
, json_array
);
731 route_vty_out (vty
, &rm
->p
, ri
, 0, SAFI_MPLS_VPN
, json_array
);
741 sprintf(buf_a
, "%s/%d", inet_ntop (p
->family
, &p
->u
.prefix
, buf_b
, BUFSIZ
), p
->prefixlen
);
742 json_object_object_add(json_mroute
, buf_a
, json_array
);
752 sprintf(buf_a
, "%s/%d", inet_ntop (p
->family
, &p
->u
.prefix
, buf_b
, BUFSIZ
), p
->prefixlen
);
753 json_object_object_add(json_nroute
, buf_a
, json_mroute
);
760 json_object_object_add(json
, "routes", json_nroute
);
761 vty_out (vty
, "%s%s", json_object_to_json_string_ext(json
, JSON_C_TO_STRING_PRETTY
), VTY_NEWLINE
);
762 json_object_free(json
);
766 if (output_count
== 0)
767 vty_out (vty
, "No prefixes displayed, %ld exist%s", total_count
, VTY_NEWLINE
);
769 vty_out (vty
, "%sDisplayed %ld routes and %ld total paths%s",
770 VTY_NEWLINE
, output_count
, total_count
, VTY_NEWLINE
);
776 #ifdef KEEP_OLD_VPN_COMMANDS
777 DEFUN (show_ip_bgp_vpn_all
,
778 show_ip_bgp_vpn_all_cmd
,
779 "show [ip] bgp <vpnv4|vpnv6>",
788 if (argv_find_and_parse_vpnvx (argv
, argc
, &idx
, &afi
))
789 return bgp_show_mpls_vpn (vty
, afi
, NULL
, bgp_show_type_normal
, NULL
, 0, 0);
795 DEFUN (show_bgp_ip_vpn_all_rd
,
796 show_bgp_ip_vpn_all_rd_cmd
,
797 "show bgp "BGP_AFI_CMD_STR
" vpn all [rd ASN:nn_or_IP-address:nn] [json]",
802 "Display VPN NLRI specific information\n"
803 "Display information for a route distinguisher\n"
804 "VPN Route Distinguisher\n"
809 struct prefix_rd prd
;
813 if (argv_find_and_parse_afi (argv
, argc
, &idx
, &afi
))
815 if (argc
>= 7 && argv
[idx_rd
]->arg
)
817 ret
= str2prefix_rd (argv
[idx_rd
]->arg
, &prd
);
820 vty_out (vty
, "%% Malformed Route Distinguisher%s", VTY_NEWLINE
);
823 return bgp_show_mpls_vpn (vty
, afi
, &prd
, bgp_show_type_normal
, NULL
, 0, use_json (argc
, argv
));
827 return bgp_show_mpls_vpn (vty
, afi
, NULL
, bgp_show_type_normal
, NULL
, 0, use_json (argc
, argv
));
833 DEFUN (show_ip_bgp_vpn_rd
,
834 show_ip_bgp_vpn_rd_cmd
,
835 "show [ip] bgp "BGP_AFI_CMD_STR
" vpn rd ASN:nn_or_IP-address:nn",
840 "Address Family modifier\n"
841 "Display information for a route distinguisher\n"
842 "VPN Route Distinguisher\n")
844 int idx_ext_community
= argc
-1;
846 struct prefix_rd prd
;
850 if (argv_find_and_parse_vpnvx (argv
, argc
, &idx
, &afi
))
852 ret
= str2prefix_rd (argv
[idx_ext_community
]->arg
, &prd
);
855 vty_out (vty
, "%% Malformed Route Distinguisher%s", VTY_NEWLINE
);
858 return bgp_show_mpls_vpn (vty
, afi
, &prd
, bgp_show_type_normal
, NULL
, 0, 0);
863 #ifdef KEEP_OLD_VPN_COMMANDS
864 DEFUN (show_ip_bgp_vpn_all
,
865 show_ip_bgp_vpn_all_cmd
,
866 "show [ip] bgp <vpnv4|vpnv6>",
875 if (argv_find_and_parse_vpnvx (argv
, argc
, &idx
, &afi
))
876 return bgp_show_mpls_vpn (vty
, afi
, NULL
, bgp_show_type_normal
, NULL
, 0, 0);
880 DEFUN (show_ip_bgp_vpn_all_tags
,
881 show_ip_bgp_vpn_all_tags_cmd
,
882 "show [ip] bgp <vpnv4|vpnv6> all tags",
887 "Display information about all VPNv4/VPNV6 NLRIs\n"
888 "Display BGP tags for prefixes\n")
893 if (argv_find_and_parse_vpnvx (argv
, argc
, &idx
, &afi
))
894 return bgp_show_mpls_vpn (vty
, afi
, NULL
, bgp_show_type_normal
, NULL
, 1, 0);
898 DEFUN (show_ip_bgp_vpn_rd_tags
,
899 show_ip_bgp_vpn_rd_tags_cmd
,
900 "show [ip] bgp <vpnv4|vpnv6> rd ASN:nn_or_IP-address:nn tags",
905 "Display information for a route distinguisher\n"
906 "VPN Route Distinguisher\n"
907 "Display BGP tags for prefixes\n")
909 int idx_ext_community
= 5;
911 struct prefix_rd prd
;
915 if (argv_find_and_parse_vpnvx (argv
, argc
, &idx
, &afi
))
917 ret
= str2prefix_rd (argv
[idx_ext_community
]->arg
, &prd
);
920 vty_out (vty
, "%% Malformed Route Distinguisher%s", VTY_NEWLINE
);
923 return bgp_show_mpls_vpn (vty
, afi
, &prd
, bgp_show_type_normal
, NULL
, 1, 0);
928 DEFUN (show_ip_bgp_vpn_all_neighbor_routes
,
929 show_ip_bgp_vpn_all_neighbor_routes_cmd
,
930 "show [ip] bgp <vpnv4|vpnv6> all neighbors A.B.C.D routes [json]",
935 "Display information about all VPNv4/VPNv6 NLRIs\n"
936 "Detailed information on TCP and BGP neighbor connections\n"
937 "Neighbor to display information about\n"
938 "Display routes learned from neighbor\n"
945 u_char uj
= use_json(argc
, argv
);
949 if (argv_find_and_parse_vpnvx (argv
, argc
, &idx
, &afi
))
951 ret
= str2sockunion (argv
[idx_ipv4
]->arg
, &su
);
956 json_object
*json_no
= NULL
;
957 json_no
= json_object_new_object();
958 json_object_string_add(json_no
, "warning", "Malformed address");
959 vty_out (vty
, "%s%s", json_object_to_json_string(json_no
), VTY_NEWLINE
);
960 json_object_free(json_no
);
963 vty_out (vty
, "Malformed address: %s%s", argv
[idx_ipv4
]->arg
, VTY_NEWLINE
);
967 peer
= peer_lookup (NULL
, &su
);
968 if (! peer
|| ! peer
->afc
[afi
][SAFI_MPLS_VPN
])
972 json_object
*json_no
= NULL
;
973 json_no
= json_object_new_object();
974 json_object_string_add(json_no
, "warning", "No such neighbor or address family");
975 vty_out (vty
, "%s%s", json_object_to_json_string(json_no
), VTY_NEWLINE
);
976 json_object_free(json_no
);
979 vty_out (vty
, "%% No such neighbor or address family%s", VTY_NEWLINE
);
983 return bgp_show_mpls_vpn (vty
, afi
, NULL
, bgp_show_type_neighbor
, &su
, 0, uj
);
988 DEFUN (show_ip_bgp_vpn_rd_neighbor_routes
,
989 show_ip_bgp_vpn_rd_neighbor_routes_cmd
,
990 "show [ip] bgp <vpnv4|vpnv6> rd ASN:nn_or_IP-address:nn neighbors A.B.C.D routes [json]",
995 "Display information for a route distinguisher\n"
996 "VPN Route Distinguisher\n"
997 "Detailed information on TCP and BGP neighbor connections\n"
998 "Neighbor to display information about\n"
999 "Display routes learned from neighbor\n"
1002 int idx_ext_community
= 5;
1007 struct prefix_rd prd
;
1008 u_char uj
= use_json(argc
, argv
);
1012 if (argv_find_and_parse_vpnvx (argv
, argc
, &idx
, &afi
))
1014 ret
= str2prefix_rd (argv
[idx_ext_community
]->arg
, &prd
);
1019 json_object
*json_no
= NULL
;
1020 json_no
= json_object_new_object();
1021 json_object_string_add(json_no
, "warning", "Malformed Route Distinguisher");
1022 vty_out (vty
, "%s%s", json_object_to_json_string(json_no
), VTY_NEWLINE
);
1023 json_object_free(json_no
);
1026 vty_out (vty
, "%% Malformed Route Distinguisher%s", VTY_NEWLINE
);
1030 ret
= str2sockunion (argv
[idx_ipv4
]->arg
, &su
);
1035 json_object
*json_no
= NULL
;
1036 json_no
= json_object_new_object();
1037 json_object_string_add(json_no
, "warning", "Malformed address");
1038 vty_out (vty
, "%s%s", json_object_to_json_string(json_no
), VTY_NEWLINE
);
1039 json_object_free(json_no
);
1042 vty_out (vty
, "Malformed address: %s%s", argv
[idx_ext_community
]->arg
, VTY_NEWLINE
);
1046 peer
= peer_lookup (NULL
, &su
);
1047 if (! peer
|| ! peer
->afc
[afi
][SAFI_MPLS_VPN
])
1051 json_object
*json_no
= NULL
;
1052 json_no
= json_object_new_object();
1053 json_object_string_add(json_no
, "warning", "No such neighbor or address family");
1054 vty_out (vty
, "%s%s", json_object_to_json_string(json_no
), VTY_NEWLINE
);
1055 json_object_free(json_no
);
1058 vty_out (vty
, "%% No such neighbor or address family%s", VTY_NEWLINE
);
1062 return bgp_show_mpls_vpn (vty
, afi
, &prd
, bgp_show_type_neighbor
, &su
, 0, uj
);
1067 DEFUN (show_ip_bgp_vpn_all_neighbor_advertised_routes
,
1068 show_ip_bgp_vpn_all_neighbor_advertised_routes_cmd
,
1069 "show [ip] bgp <vpnv4|vpnv6> all neighbors A.B.C.D advertised-routes [json]",
1074 "Display information about all VPNv4/VPNv6 NLRIs\n"
1075 "Detailed information on TCP and BGP neighbor connections\n"
1076 "Neighbor to display information about\n"
1077 "Display the routes advertised to a BGP neighbor\n"
1084 u_char uj
= use_json(argc
, argv
);
1088 if (argv_find_and_parse_vpnvx (argv
, argc
, &idx
, &afi
))
1090 ret
= str2sockunion (argv
[idx_ipv4
]->arg
, &su
);
1095 json_object
*json_no
= NULL
;
1096 json_no
= json_object_new_object();
1097 json_object_string_add(json_no
, "warning", "Malformed address");
1098 vty_out (vty
, "%s%s", json_object_to_json_string(json_no
), VTY_NEWLINE
);
1099 json_object_free(json_no
);
1102 vty_out (vty
, "Malformed address: %s%s", argv
[idx_ipv4
]->arg
, VTY_NEWLINE
);
1105 peer
= peer_lookup (NULL
, &su
);
1106 if (! peer
|| ! peer
->afc
[afi
][SAFI_MPLS_VPN
])
1110 json_object
*json_no
= NULL
;
1111 json_no
= json_object_new_object();
1112 json_object_string_add(json_no
, "warning", "No such neighbor or address family");
1113 vty_out (vty
, "%s%s", json_object_to_json_string(json_no
), VTY_NEWLINE
);
1114 json_object_free(json_no
);
1117 vty_out (vty
, "%% No such neighbor or address family%s", VTY_NEWLINE
);
1120 return show_adj_route_vpn (vty
, peer
, NULL
, AFI_IP
, SAFI_MPLS_VPN
, uj
);
1125 DEFUN (show_ip_bgp_vpn_rd_neighbor_advertised_routes
,
1126 show_ip_bgp_vpn_rd_neighbor_advertised_routes_cmd
,
1127 "show [ip] bgp <vpnv4|vpnv6> rd ASN:nn_or_IP-address:nn neighbors A.B.C.D advertised-routes [json]",
1132 "Display information for a route distinguisher\n"
1133 "VPN Route Distinguisher\n"
1134 "Detailed information on TCP and BGP neighbor connections\n"
1135 "Neighbor to display information about\n"
1136 "Display the routes advertised to a BGP neighbor\n"
1139 int idx_ext_community
= 5;
1143 struct prefix_rd prd
;
1145 u_char uj
= use_json(argc
, argv
);
1149 if (argv_find_and_parse_vpnvx (argv
, argc
, &idx
, &afi
))
1151 ret
= str2sockunion (argv
[idx_ipv4
]->arg
, &su
);
1156 json_object
*json_no
= NULL
;
1157 json_no
= json_object_new_object();
1158 json_object_string_add(json_no
, "warning", "Malformed address");
1159 vty_out (vty
, "%s%s", json_object_to_json_string(json_no
), VTY_NEWLINE
);
1160 json_object_free(json_no
);
1163 vty_out (vty
, "Malformed address: %s%s", argv
[idx_ext_community
]->arg
, VTY_NEWLINE
);
1166 peer
= peer_lookup (NULL
, &su
);
1167 if (! peer
|| ! peer
->afc
[afi
][SAFI_MPLS_VPN
])
1171 json_object
*json_no
= NULL
;
1172 json_no
= json_object_new_object();
1173 json_object_string_add(json_no
, "warning", "No such neighbor or address family");
1174 vty_out (vty
, "%s%s", json_object_to_json_string(json_no
), VTY_NEWLINE
);
1175 json_object_free(json_no
);
1178 vty_out (vty
, "%% No such neighbor or address family%s", VTY_NEWLINE
);
1182 ret
= str2prefix_rd (argv
[idx_ext_community
]->arg
, &prd
);
1187 json_object
*json_no
= NULL
;
1188 json_no
= json_object_new_object();
1189 json_object_string_add(json_no
, "warning", "Malformed Route Distinguisher");
1190 vty_out (vty
, "%s%s", json_object_to_json_string(json_no
), VTY_NEWLINE
);
1191 json_object_free(json_no
);
1194 vty_out (vty
, "%% Malformed Route Distinguisher%s", VTY_NEWLINE
);
1198 return show_adj_route_vpn (vty
, peer
, &prd
, AFI_IP
, SAFI_MPLS_VPN
, uj
);
1202 #endif /* KEEP_OLD_VPN_COMMANDS */
1205 bgp_mplsvpn_init (void)
1207 install_element (BGP_VPNV4_NODE
, &vpnv4_network_cmd
);
1208 install_element (BGP_VPNV4_NODE
, &vpnv4_network_route_map_cmd
);
1209 install_element (BGP_VPNV4_NODE
, &no_vpnv4_network_cmd
);
1211 install_element (BGP_VPNV6_NODE
, &vpnv6_network_cmd
);
1212 install_element (BGP_VPNV6_NODE
, &no_vpnv6_network_cmd
);
1214 install_element (VIEW_NODE
, &show_bgp_ip_vpn_all_rd_cmd
);
1215 install_element (VIEW_NODE
, &show_ip_bgp_vpn_rd_cmd
);
1216 #ifdef KEEP_OLD_VPN_COMMANDS
1217 install_element (VIEW_NODE
, &show_ip_bgp_vpn_all_cmd
);
1218 install_element (VIEW_NODE
, &show_ip_bgp_vpn_rd_cmd
);
1219 install_element (VIEW_NODE
, &show_ip_bgp_vpn_all_tags_cmd
);
1220 install_element (VIEW_NODE
, &show_ip_bgp_vpn_rd_tags_cmd
);
1221 install_element (VIEW_NODE
, &show_ip_bgp_vpn_all_neighbor_routes_cmd
);
1222 install_element (VIEW_NODE
, &show_ip_bgp_vpn_rd_neighbor_routes_cmd
);
1223 install_element (VIEW_NODE
, &show_ip_bgp_vpn_all_neighbor_advertised_routes_cmd
);
1224 install_element (VIEW_NODE
, &show_ip_bgp_vpn_rd_neighbor_advertised_routes_cmd
);
1225 #endif /* KEEP_OLD_VPN_COMMANDS */