]> git.proxmox.com Git - mirror_frr.git/blob - bgpd/bgp_route.c
Expand #defines in command strings
[mirror_frr.git] / bgpd / bgp_route.c
1 /* BGP routing information
2 Copyright (C) 1996, 97, 98, 99 Kunihiro Ishiguro
3
4 This file is part of GNU Zebra.
5
6 GNU Zebra is free software; you can redistribute it and/or modify it
7 under the terms of the GNU General Public License as published by the
8 Free Software Foundation; either version 2, or (at your option) any
9 later version.
10
11 GNU Zebra is distributed in the hope that it will be useful, but
12 WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 General Public License for more details.
15
16 You should have received a copy of the GNU General Public License
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
19 02111-1307, USA. */
20
21 #include <zebra.h>
22
23 #include "prefix.h"
24 #include "linklist.h"
25 #include "memory.h"
26 #include "command.h"
27 #include "stream.h"
28 #include "filter.h"
29 #include "str.h"
30 #include "log.h"
31 #include "routemap.h"
32 #include "buffer.h"
33 #include "sockunion.h"
34 #include "plist.h"
35 #include "thread.h"
36 #include "workqueue.h"
37 #include "queue.h"
38 #include "memory.h"
39 #include "lib/json.h"
40
41 #include "bgpd/bgpd.h"
42 #include "bgpd/bgp_table.h"
43 #include "bgpd/bgp_route.h"
44 #include "bgpd/bgp_attr.h"
45 #include "bgpd/bgp_debug.h"
46 #include "bgpd/bgp_aspath.h"
47 #include "bgpd/bgp_regex.h"
48 #include "bgpd/bgp_community.h"
49 #include "bgpd/bgp_ecommunity.h"
50 #include "bgpd/bgp_clist.h"
51 #include "bgpd/bgp_packet.h"
52 #include "bgpd/bgp_filter.h"
53 #include "bgpd/bgp_fsm.h"
54 #include "bgpd/bgp_mplsvpn.h"
55 #include "bgpd/bgp_nexthop.h"
56 #include "bgpd/bgp_damp.h"
57 #include "bgpd/bgp_advertise.h"
58 #include "bgpd/bgp_zebra.h"
59 #include "bgpd/bgp_vty.h"
60 #include "bgpd/bgp_mpath.h"
61 #include "bgpd/bgp_nht.h"
62 #include "bgpd/bgp_updgrp.h"
63 #include "bgpd/bgp_vty.h"
64
65 /* Extern from bgp_dump.c */
66 extern const char *bgp_origin_str[];
67 extern const char *bgp_origin_long_str[];
68
69 struct bgp_node *
70 bgp_afi_node_get (struct bgp_table *table, afi_t afi, safi_t safi, struct prefix *p,
71 struct prefix_rd *prd)
72 {
73 struct bgp_node *rn;
74 struct bgp_node *prn = NULL;
75
76 assert (table);
77 if (!table)
78 return NULL;
79
80 if ((safi == SAFI_MPLS_VPN) || (safi == SAFI_ENCAP))
81 {
82 prn = bgp_node_get (table, (struct prefix *) prd);
83
84 if (prn->info == NULL)
85 prn->info = bgp_table_init (afi, safi);
86 else
87 bgp_unlock_node (prn);
88 table = prn->info;
89 }
90
91 rn = bgp_node_get (table, p);
92
93 if ((safi == SAFI_MPLS_VPN) || (safi == SAFI_ENCAP))
94 rn->prn = prn;
95
96 return rn;
97 }
98
99 /* Allocate bgp_info_extra */
100 static struct bgp_info_extra *
101 bgp_info_extra_new (void)
102 {
103 struct bgp_info_extra *new;
104 new = XCALLOC (MTYPE_BGP_ROUTE_EXTRA, sizeof (struct bgp_info_extra));
105 return new;
106 }
107
108 static void
109 bgp_info_extra_free (struct bgp_info_extra **extra)
110 {
111 if (extra && *extra)
112 {
113 if ((*extra)->damp_info)
114 bgp_damp_info_free ((*extra)->damp_info, 0);
115
116 (*extra)->damp_info = NULL;
117
118 XFREE (MTYPE_BGP_ROUTE_EXTRA, *extra);
119
120 *extra = NULL;
121 }
122 }
123
124 /* Get bgp_info extra information for the given bgp_info, lazy allocated
125 * if required.
126 */
127 struct bgp_info_extra *
128 bgp_info_extra_get (struct bgp_info *ri)
129 {
130 if (!ri->extra)
131 ri->extra = bgp_info_extra_new();
132 return ri->extra;
133 }
134
135 /* Free bgp route information. */
136 static void
137 bgp_info_free (struct bgp_info *binfo)
138 {
139 if (binfo->attr)
140 bgp_attr_unintern (&binfo->attr);
141
142 bgp_unlink_nexthop(binfo);
143 bgp_info_extra_free (&binfo->extra);
144 bgp_info_mpath_free (&binfo->mpath);
145
146 peer_unlock (binfo->peer); /* bgp_info peer reference */
147
148 XFREE (MTYPE_BGP_ROUTE, binfo);
149 }
150
151 struct bgp_info *
152 bgp_info_lock (struct bgp_info *binfo)
153 {
154 binfo->lock++;
155 return binfo;
156 }
157
158 struct bgp_info *
159 bgp_info_unlock (struct bgp_info *binfo)
160 {
161 assert (binfo && binfo->lock > 0);
162 binfo->lock--;
163
164 if (binfo->lock == 0)
165 {
166 #if 0
167 zlog_debug ("%s: unlocked and freeing", __func__);
168 zlog_backtrace (LOG_DEBUG);
169 #endif
170 bgp_info_free (binfo);
171 return NULL;
172 }
173
174 #if 0
175 if (binfo->lock == 1)
176 {
177 zlog_debug ("%s: unlocked to 1", __func__);
178 zlog_backtrace (LOG_DEBUG);
179 }
180 #endif
181
182 return binfo;
183 }
184
185 void
186 bgp_info_add (struct bgp_node *rn, struct bgp_info *ri)
187 {
188 struct bgp_info *top;
189
190 top = rn->info;
191
192 ri->next = rn->info;
193 ri->prev = NULL;
194 if (top)
195 top->prev = ri;
196 rn->info = ri;
197
198 bgp_info_lock (ri);
199 bgp_lock_node (rn);
200 peer_lock (ri->peer); /* bgp_info peer reference */
201 }
202
203 /* Do the actual removal of info from RIB, for use by bgp_process
204 completion callback *only* */
205 static void
206 bgp_info_reap (struct bgp_node *rn, struct bgp_info *ri)
207 {
208 if (ri->next)
209 ri->next->prev = ri->prev;
210 if (ri->prev)
211 ri->prev->next = ri->next;
212 else
213 rn->info = ri->next;
214
215 bgp_info_mpath_dequeue (ri);
216 bgp_info_unlock (ri);
217 bgp_unlock_node (rn);
218 }
219
220 void
221 bgp_info_delete (struct bgp_node *rn, struct bgp_info *ri)
222 {
223 bgp_info_set_flag (rn, ri, BGP_INFO_REMOVED);
224 /* set of previous already took care of pcount */
225 UNSET_FLAG (ri->flags, BGP_INFO_VALID);
226 }
227
228 /* undo the effects of a previous call to bgp_info_delete; typically
229 called when a route is deleted and then quickly re-added before the
230 deletion has been processed */
231 static void
232 bgp_info_restore (struct bgp_node *rn, struct bgp_info *ri)
233 {
234 bgp_info_unset_flag (rn, ri, BGP_INFO_REMOVED);
235 /* unset of previous already took care of pcount */
236 SET_FLAG (ri->flags, BGP_INFO_VALID);
237 }
238
239 /* Adjust pcount as required */
240 static void
241 bgp_pcount_adjust (struct bgp_node *rn, struct bgp_info *ri)
242 {
243 struct bgp_table *table;
244
245 assert (rn && bgp_node_table (rn));
246 assert (ri && ri->peer && ri->peer->bgp);
247
248 table = bgp_node_table (rn);
249
250 if (ri->peer == ri->peer->bgp->peer_self)
251 return;
252
253 if (!BGP_INFO_COUNTABLE (ri)
254 && CHECK_FLAG (ri->flags, BGP_INFO_COUNTED))
255 {
256
257 UNSET_FLAG (ri->flags, BGP_INFO_COUNTED);
258
259 /* slight hack, but more robust against errors. */
260 if (ri->peer->pcount[table->afi][table->safi])
261 ri->peer->pcount[table->afi][table->safi]--;
262 else
263 {
264 zlog_warn ("%s: Asked to decrement 0 prefix count for peer %s",
265 __func__, ri->peer->host);
266 zlog_backtrace (LOG_WARNING);
267 zlog_warn ("%s: Please report to Quagga bugzilla", __func__);
268 }
269 }
270 else if (BGP_INFO_COUNTABLE (ri)
271 && !CHECK_FLAG (ri->flags, BGP_INFO_COUNTED))
272 {
273 SET_FLAG (ri->flags, BGP_INFO_COUNTED);
274 ri->peer->pcount[table->afi][table->safi]++;
275 }
276 }
277
278
279 /* Set/unset bgp_info flags, adjusting any other state as needed.
280 * This is here primarily to keep prefix-count in check.
281 */
282 void
283 bgp_info_set_flag (struct bgp_node *rn, struct bgp_info *ri, u_int32_t flag)
284 {
285 SET_FLAG (ri->flags, flag);
286
287 /* early bath if we know it's not a flag that changes countability state */
288 if (!CHECK_FLAG (flag, BGP_INFO_VALID|BGP_INFO_HISTORY|BGP_INFO_REMOVED))
289 return;
290
291 bgp_pcount_adjust (rn, ri);
292 }
293
294 void
295 bgp_info_unset_flag (struct bgp_node *rn, struct bgp_info *ri, u_int32_t flag)
296 {
297 UNSET_FLAG (ri->flags, flag);
298
299 /* early bath if we know it's not a flag that changes countability state */
300 if (!CHECK_FLAG (flag, BGP_INFO_VALID|BGP_INFO_HISTORY|BGP_INFO_REMOVED))
301 return;
302
303 bgp_pcount_adjust (rn, ri);
304 }
305
306 /* Get MED value. If MED value is missing and "bgp bestpath
307 missing-as-worst" is specified, treat it as the worst value. */
308 static u_int32_t
309 bgp_med_value (struct attr *attr, struct bgp *bgp)
310 {
311 if (attr->flag & ATTR_FLAG_BIT (BGP_ATTR_MULTI_EXIT_DISC))
312 return attr->med;
313 else
314 {
315 if (bgp_flag_check (bgp, BGP_FLAG_MED_MISSING_AS_WORST))
316 return BGP_MED_MAX;
317 else
318 return 0;
319 }
320 }
321
322 void
323 bgp_info_path_with_addpath_rx_str (struct bgp_info *ri, char *buf)
324 {
325 if (ri->addpath_rx_id)
326 sprintf(buf, "path %s (addpath rxid %d)", ri->peer->host, ri->addpath_rx_id);
327 else
328 sprintf(buf, "path %s", ri->peer->host);
329 }
330
331 /* Compare two bgp route entity. If 'new' is preferable over 'exist' return 1. */
332 static int
333 bgp_info_cmp (struct bgp *bgp, struct bgp_info *new, struct bgp_info *exist,
334 int *paths_eq, struct bgp_maxpaths_cfg *mpath_cfg, int debug,
335 char *pfx_buf)
336 {
337 struct attr *newattr, *existattr;
338 struct attr_extra *newattre, *existattre;
339 bgp_peer_sort_t new_sort;
340 bgp_peer_sort_t exist_sort;
341 u_int32_t new_pref;
342 u_int32_t exist_pref;
343 u_int32_t new_med;
344 u_int32_t exist_med;
345 u_int32_t new_weight;
346 u_int32_t exist_weight;
347 uint32_t newm, existm;
348 struct in_addr new_id;
349 struct in_addr exist_id;
350 int new_cluster;
351 int exist_cluster;
352 int internal_as_route;
353 int confed_as_route;
354 int ret;
355 char new_buf[PATH_ADDPATH_STR_BUFFER];
356 char exist_buf[PATH_ADDPATH_STR_BUFFER];
357
358 *paths_eq = 0;
359
360 /* 0. Null check. */
361 if (new == NULL)
362 {
363 if (debug)
364 zlog_debug("%s: new is NULL", pfx_buf);
365 return 0;
366 }
367
368 if (debug)
369 bgp_info_path_with_addpath_rx_str (new, new_buf);
370
371 if (exist == NULL)
372 {
373 if (debug)
374 zlog_debug("%s: %s is the initial bestpath", pfx_buf, new_buf);
375 return 1;
376 }
377
378 if (debug)
379 {
380 bgp_info_path_with_addpath_rx_str (exist, exist_buf);
381 zlog_debug("%s: Comparing %s flags 0x%x with %s flags 0x%x",
382 pfx_buf, new_buf, new->flags, exist_buf, exist->flags);
383 }
384
385 newattr = new->attr;
386 existattr = exist->attr;
387 newattre = newattr->extra;
388 existattre = existattr->extra;
389
390 /* 1. Weight check. */
391 new_weight = exist_weight = 0;
392
393 if (newattre)
394 new_weight = newattre->weight;
395 if (existattre)
396 exist_weight = existattre->weight;
397
398 if (new_weight > exist_weight)
399 {
400 if (debug)
401 zlog_debug("%s: %s wins over %s due to weight %d > %d",
402 pfx_buf, new_buf, exist_buf, new_weight, exist_weight);
403 return 1;
404 }
405
406 if (new_weight < exist_weight)
407 {
408 if (debug)
409 zlog_debug("%s: %s loses to %s due to weight %d < %d",
410 pfx_buf, new_buf, exist_buf, new_weight, exist_weight);
411 return 0;
412 }
413
414 /* 2. Local preference check. */
415 new_pref = exist_pref = bgp->default_local_pref;
416
417 if (newattr->flag & ATTR_FLAG_BIT (BGP_ATTR_LOCAL_PREF))
418 new_pref = newattr->local_pref;
419 if (existattr->flag & ATTR_FLAG_BIT (BGP_ATTR_LOCAL_PREF))
420 exist_pref = existattr->local_pref;
421
422 if (new_pref > exist_pref)
423 {
424 if (debug)
425 zlog_debug("%s: %s wins over %s due to localpref %d > %d",
426 pfx_buf, new_buf, exist_buf, new_pref, exist_pref);
427 return 1;
428 }
429
430 if (new_pref < exist_pref)
431 {
432 if (debug)
433 zlog_debug("%s: %s loses to %s due to localpref %d < %d",
434 pfx_buf, new_buf, exist_buf, new_pref, exist_pref);
435 return 0;
436 }
437
438 /* 3. Local route check. We prefer:
439 * - BGP_ROUTE_STATIC
440 * - BGP_ROUTE_AGGREGATE
441 * - BGP_ROUTE_REDISTRIBUTE
442 */
443 if (! (new->sub_type == BGP_ROUTE_NORMAL))
444 {
445 if (debug)
446 zlog_debug("%s: %s wins over %s due to preferred BGP_ROUTE type",
447 pfx_buf, new_buf, exist_buf);
448 return 1;
449 }
450
451 if (! (exist->sub_type == BGP_ROUTE_NORMAL))
452 {
453 if (debug)
454 zlog_debug("%s: %s loses to %s due to preferred BGP_ROUTE type",
455 pfx_buf, new_buf, exist_buf);
456 return 0;
457 }
458
459 /* 4. AS path length check. */
460 if (! bgp_flag_check (bgp, BGP_FLAG_ASPATH_IGNORE))
461 {
462 int exist_hops = aspath_count_hops (existattr->aspath);
463 int exist_confeds = aspath_count_confeds (existattr->aspath);
464
465 if (bgp_flag_check (bgp, BGP_FLAG_ASPATH_CONFED))
466 {
467 int aspath_hops;
468
469 aspath_hops = aspath_count_hops (newattr->aspath);
470 aspath_hops += aspath_count_confeds (newattr->aspath);
471
472 if ( aspath_hops < (exist_hops + exist_confeds))
473 {
474 if (debug)
475 zlog_debug("%s: %s wins over %s due to aspath (with confeds) hopcount %d < %d",
476 pfx_buf, new_buf, exist_buf,
477 aspath_hops, (exist_hops + exist_confeds));
478 return 1;
479 }
480
481 if ( aspath_hops > (exist_hops + exist_confeds))
482 {
483 if (debug)
484 zlog_debug("%s: %s loses to %s due to aspath (with confeds) hopcount %d > %d",
485 pfx_buf, new_buf, exist_buf,
486 aspath_hops, (exist_hops + exist_confeds));
487 return 0;
488 }
489 }
490 else
491 {
492 int newhops = aspath_count_hops (newattr->aspath);
493
494 if (newhops < exist_hops)
495 {
496 if (debug)
497 zlog_debug("%s: %s wins over %s due to aspath hopcount %d < %d",
498 pfx_buf, new_buf, exist_buf, newhops, exist_hops);
499 return 1;
500 }
501
502 if (newhops > exist_hops)
503 {
504 if (debug)
505 zlog_debug("%s: %s loses to %s due to aspath hopcount %d > %d",
506 pfx_buf, new_buf, exist_buf, newhops, exist_hops);
507 return 0;
508 }
509 }
510 }
511
512 /* 5. Origin check. */
513 if (newattr->origin < existattr->origin)
514 {
515 if (debug)
516 zlog_debug("%s: %s wins over %s due to ORIGIN %s < %s",
517 pfx_buf, new_buf, exist_buf,
518 bgp_origin_long_str[newattr->origin],
519 bgp_origin_long_str[existattr->origin]);
520 return 1;
521 }
522
523 if (newattr->origin > existattr->origin)
524 {
525 if (debug)
526 zlog_debug("%s: %s loses to %s due to ORIGIN %s > %s",
527 pfx_buf, new_buf, exist_buf,
528 bgp_origin_long_str[newattr->origin],
529 bgp_origin_long_str[existattr->origin]);
530 return 0;
531 }
532
533 /* 6. MED check. */
534 internal_as_route = (aspath_count_hops (newattr->aspath) == 0
535 && aspath_count_hops (existattr->aspath) == 0);
536 confed_as_route = (aspath_count_confeds (newattr->aspath) > 0
537 && aspath_count_confeds (existattr->aspath) > 0
538 && aspath_count_hops (newattr->aspath) == 0
539 && aspath_count_hops (existattr->aspath) == 0);
540
541 if (bgp_flag_check (bgp, BGP_FLAG_ALWAYS_COMPARE_MED)
542 || (bgp_flag_check (bgp, BGP_FLAG_MED_CONFED)
543 && confed_as_route)
544 || aspath_cmp_left (newattr->aspath, existattr->aspath)
545 || aspath_cmp_left_confed (newattr->aspath, existattr->aspath)
546 || internal_as_route)
547 {
548 new_med = bgp_med_value (new->attr, bgp);
549 exist_med = bgp_med_value (exist->attr, bgp);
550
551 if (new_med < exist_med)
552 {
553 if (debug)
554 zlog_debug("%s: %s wins over %s due to MED %d < %d",
555 pfx_buf, new_buf, exist_buf, new_med, exist_med);
556 return 1;
557 }
558
559 if (new_med > exist_med)
560 {
561 if (debug)
562 zlog_debug("%s: %s loses to %s due to MED %d > %d",
563 pfx_buf, new_buf, exist_buf, new_med, exist_med);
564 return 0;
565 }
566 }
567
568 /* 7. Peer type check. */
569 new_sort = new->peer->sort;
570 exist_sort = exist->peer->sort;
571
572 if (new_sort == BGP_PEER_EBGP
573 && (exist_sort == BGP_PEER_IBGP || exist_sort == BGP_PEER_CONFED))
574 {
575 if (debug)
576 zlog_debug("%s: %s wins over %s due to eBGP peer > iBGP peer",
577 pfx_buf, new_buf, exist_buf);
578 return 1;
579 }
580
581 if (exist_sort == BGP_PEER_EBGP
582 && (new_sort == BGP_PEER_IBGP || new_sort == BGP_PEER_CONFED))
583 {
584 if (debug)
585 zlog_debug("%s: %s loses to %s due to iBGP peer < eBGP peer",
586 pfx_buf, new_buf, exist_buf);
587 return 0;
588 }
589
590 /* 8. IGP metric check. */
591 newm = existm = 0;
592
593 if (new->extra)
594 newm = new->extra->igpmetric;
595 if (exist->extra)
596 existm = exist->extra->igpmetric;
597
598 if (newm < existm)
599 {
600 if (debug)
601 zlog_debug("%s: %s wins over %s due to IGP metric %d < %d",
602 pfx_buf, new_buf, exist_buf, newm, existm);
603 ret = 1;
604 }
605
606 if (newm > existm)
607 {
608 if (debug)
609 zlog_debug("%s: %s loses to %s due to IGP metric %d > %d",
610 pfx_buf, new_buf, exist_buf, newm, existm);
611 ret = 0;
612 }
613
614 /* 9. Same IGP metric. Compare the cluster list length as
615 representative of IGP hops metric. Rewrite the metric value
616 pair (newm, existm) with the cluster list length. Prefer the
617 path with smaller cluster list length. */
618 if (newm == existm)
619 {
620 if (peer_sort (new->peer) == BGP_PEER_IBGP
621 && peer_sort (exist->peer) == BGP_PEER_IBGP
622 && CHECK_FLAG (mpath_cfg->ibgp_flags,
623 BGP_FLAG_IBGP_MULTIPATH_SAME_CLUSTERLEN))
624 {
625 newm = BGP_CLUSTER_LIST_LENGTH(new->attr);
626 existm = BGP_CLUSTER_LIST_LENGTH(exist->attr);
627
628 if (newm < existm)
629 {
630 if (debug)
631 zlog_debug("%s: %s wins over %s due to CLUSTER_LIST length %d < %d",
632 pfx_buf, new_buf, exist_buf, newm, existm);
633 ret = 1;
634 }
635
636 if (newm > existm)
637 {
638 if (debug)
639 zlog_debug("%s: %s loses to %s due to CLUSTER_LIST length %d > %d",
640 pfx_buf, new_buf, exist_buf, newm, existm);
641 ret = 0;
642 }
643 }
644 }
645
646 /* 10. confed-external vs. confed-internal */
647 if (CHECK_FLAG(bgp->config, BGP_CONFIG_CONFEDERATION))
648 {
649 if (new_sort == BGP_PEER_CONFED && exist_sort == BGP_PEER_IBGP)
650 {
651 if (debug)
652 zlog_debug("%s: %s wins over %s due to confed-external peer > confed-internal peer",
653 pfx_buf, new_buf, exist_buf);
654 return 1;
655 }
656
657 if (exist_sort == BGP_PEER_CONFED && new_sort == BGP_PEER_IBGP)
658 {
659 if (debug)
660 zlog_debug("%s: %s loses to %s due to confed-internal peer < confed-external peer",
661 pfx_buf, new_buf, exist_buf);
662 return 0;
663 }
664 }
665
666 /* 11. Maximum path check. */
667 if (newm == existm)
668 {
669 if (bgp_flag_check(bgp, BGP_FLAG_ASPATH_MULTIPATH_RELAX))
670 {
671
672 /*
673 * For the two paths, all comparison steps till IGP metric
674 * have succeeded - including AS_PATH hop count. Since 'bgp
675 * bestpath as-path multipath-relax' knob is on, we don't need
676 * an exact match of AS_PATH. Thus, mark the paths are equal.
677 * That will trigger both these paths to get into the multipath
678 * array.
679 */
680 *paths_eq = 1;
681
682 if (debug)
683 zlog_debug("%s: %s and %s are equal via multipath-relax",
684 pfx_buf, new_buf, exist_buf);
685 }
686 else if (new->peer->sort == BGP_PEER_IBGP)
687 {
688 if (aspath_cmp (new->attr->aspath, exist->attr->aspath))
689 {
690 *paths_eq = 1;
691
692 if (debug)
693 zlog_debug("%s: %s and %s are equal via matching aspaths",
694 pfx_buf, new_buf, exist_buf);
695 }
696 }
697 else if (new->peer->as == exist->peer->as)
698 {
699 *paths_eq = 1;
700
701 if (debug)
702 zlog_debug("%s: %s and %s are equal via same remote-as",
703 pfx_buf, new_buf, exist_buf);
704 }
705 }
706 else
707 {
708 /*
709 * TODO: If unequal cost ibgp multipath is enabled we can
710 * mark the paths as equal here instead of returning
711 */
712 if (debug)
713 {
714 if (ret == 1)
715 zlog_debug("%s: %s wins over %s after IGP metric comparison",
716 pfx_buf, new_buf, exist_buf);
717 else
718 zlog_debug("%s: %s loses to %s after IGP metric comparison",
719 pfx_buf, new_buf, exist_buf);
720 }
721 return ret;
722 }
723
724 /* 12. If both paths are external, prefer the path that was received
725 first (the oldest one). This step minimizes route-flap, since a
726 newer path won't displace an older one, even if it was the
727 preferred route based on the additional decision criteria below. */
728 if (! bgp_flag_check (bgp, BGP_FLAG_COMPARE_ROUTER_ID)
729 && new_sort == BGP_PEER_EBGP
730 && exist_sort == BGP_PEER_EBGP)
731 {
732 if (CHECK_FLAG (new->flags, BGP_INFO_SELECTED))
733 {
734 if (debug)
735 zlog_debug("%s: %s wins over %s due to oldest external",
736 pfx_buf, new_buf, exist_buf);
737 return 1;
738 }
739
740 if (CHECK_FLAG (exist->flags, BGP_INFO_SELECTED))
741 {
742 if (debug)
743 zlog_debug("%s: %s loses to %s due to oldest external",
744 pfx_buf, new_buf, exist_buf);
745 return 0;
746 }
747 }
748
749 /* 13. Router-ID comparision. */
750 /* If one of the paths is "stale", the corresponding peer router-id will
751 * be 0 and would always win over the other path. If originator id is
752 * used for the comparision, it will decide which path is better.
753 */
754 if (newattr->flag & ATTR_FLAG_BIT(BGP_ATTR_ORIGINATOR_ID))
755 new_id.s_addr = newattre->originator_id.s_addr;
756 else
757 new_id.s_addr = new->peer->remote_id.s_addr;
758 if (existattr->flag & ATTR_FLAG_BIT(BGP_ATTR_ORIGINATOR_ID))
759 exist_id.s_addr = existattre->originator_id.s_addr;
760 else
761 exist_id.s_addr = exist->peer->remote_id.s_addr;
762
763 if (ntohl (new_id.s_addr) < ntohl (exist_id.s_addr))
764 {
765 if (debug)
766 zlog_debug("%s: %s wins over %s due to Router-ID comparison",
767 pfx_buf, new_buf, exist_buf);
768 return 1;
769 }
770
771 if (ntohl (new_id.s_addr) > ntohl (exist_id.s_addr))
772 {
773 if (debug)
774 zlog_debug("%s: %s loses to %s due to Router-ID comparison",
775 pfx_buf, new_buf, exist_buf);
776 return 0;
777 }
778
779 /* 14. Cluster length comparision. */
780 new_cluster = BGP_CLUSTER_LIST_LENGTH(new->attr);
781 exist_cluster = BGP_CLUSTER_LIST_LENGTH(exist->attr);
782
783 if (new_cluster < exist_cluster)
784 {
785 if (debug)
786 zlog_debug("%s: %s wins over %s due to CLUSTER_LIST length %d < %d",
787 pfx_buf, new_buf, exist_buf, new_cluster, exist_cluster);
788 return 1;
789 }
790
791 if (new_cluster > exist_cluster)
792 {
793 if (debug)
794 zlog_debug("%s: %s loses to %s due to CLUSTER_LIST length %d > %d",
795 pfx_buf, new_buf, exist_buf, new_cluster, exist_cluster);
796 return 0;
797 }
798
799 /* 15. Neighbor address comparision. */
800 /* Do this only if neither path is "stale" as stale paths do not have
801 * valid peer information (as the connection may or may not be up).
802 */
803 if (CHECK_FLAG (exist->flags, BGP_INFO_STALE))
804 {
805 if (debug)
806 zlog_debug("%s: %s wins over %s due to latter path being STALE",
807 pfx_buf, new_buf, exist_buf);
808 return 1;
809 }
810
811 if (CHECK_FLAG (new->flags, BGP_INFO_STALE))
812 {
813 if (debug)
814 zlog_debug("%s: %s loses to %s due to former path being STALE",
815 pfx_buf, new_buf, exist_buf);
816 return 0;
817 }
818
819 /* locally configured routes to advertise do not have su_remote */
820 if (new->peer->su_remote == NULL)
821 return 0;
822 if (exist->peer->su_remote == NULL)
823 return 1;
824
825 ret = sockunion_cmp (new->peer->su_remote, exist->peer->su_remote);
826
827 if (ret == 1)
828 {
829 if (debug)
830 zlog_debug("%s: %s loses to %s due to Neighor IP comparison",
831 pfx_buf, new_buf, exist_buf);
832 return 0;
833 }
834
835 if (ret == -1)
836 {
837 if (debug)
838 zlog_debug("%s: %s wins over %s due to Neighor IP comparison",
839 pfx_buf, new_buf, exist_buf);
840 return 1;
841 }
842
843 if (debug)
844 zlog_debug("%s: %s wins over %s due to nothing left to compare",
845 pfx_buf, new_buf, exist_buf);
846
847 return 1;
848 }
849
850 static enum filter_type
851 bgp_input_filter (struct peer *peer, struct prefix *p, struct attr *attr,
852 afi_t afi, safi_t safi)
853 {
854 struct bgp_filter *filter;
855
856 filter = &peer->filter[afi][safi];
857
858 #define FILTER_EXIST_WARN(F,f,filter) \
859 if (BGP_DEBUG (update, UPDATE_IN) \
860 && !(F ## _IN (filter))) \
861 zlog_warn ("%s: Could not find configured input %s-list %s!", \
862 peer->host, #f, F ## _IN_NAME(filter));
863
864 if (DISTRIBUTE_IN_NAME (filter)) {
865 FILTER_EXIST_WARN(DISTRIBUTE, distribute, filter);
866
867 if (access_list_apply (DISTRIBUTE_IN (filter), p) == FILTER_DENY)
868 return FILTER_DENY;
869 }
870
871 if (PREFIX_LIST_IN_NAME (filter)) {
872 FILTER_EXIST_WARN(PREFIX_LIST, prefix, filter);
873
874 if (prefix_list_apply (PREFIX_LIST_IN (filter), p) == PREFIX_DENY)
875 return FILTER_DENY;
876 }
877
878 if (FILTER_LIST_IN_NAME (filter)) {
879 FILTER_EXIST_WARN(FILTER_LIST, as, filter);
880
881 if (as_list_apply (FILTER_LIST_IN (filter), attr->aspath)== AS_FILTER_DENY)
882 return FILTER_DENY;
883 }
884
885 return FILTER_PERMIT;
886 #undef FILTER_EXIST_WARN
887 }
888
889 static enum filter_type
890 bgp_output_filter (struct peer *peer, struct prefix *p, struct attr *attr,
891 afi_t afi, safi_t safi)
892 {
893 struct bgp_filter *filter;
894
895 filter = &peer->filter[afi][safi];
896
897 #define FILTER_EXIST_WARN(F,f,filter) \
898 if (BGP_DEBUG (update, UPDATE_OUT) \
899 && !(F ## _OUT (filter))) \
900 zlog_warn ("%s: Could not find configured output %s-list %s!", \
901 peer->host, #f, F ## _OUT_NAME(filter));
902
903 if (DISTRIBUTE_OUT_NAME (filter)) {
904 FILTER_EXIST_WARN(DISTRIBUTE, distribute, filter);
905
906 if (access_list_apply (DISTRIBUTE_OUT (filter), p) == FILTER_DENY)
907 return FILTER_DENY;
908 }
909
910 if (PREFIX_LIST_OUT_NAME (filter)) {
911 FILTER_EXIST_WARN(PREFIX_LIST, prefix, filter);
912
913 if (prefix_list_apply (PREFIX_LIST_OUT (filter), p) == PREFIX_DENY)
914 return FILTER_DENY;
915 }
916
917 if (FILTER_LIST_OUT_NAME (filter)) {
918 FILTER_EXIST_WARN(FILTER_LIST, as, filter);
919
920 if (as_list_apply (FILTER_LIST_OUT (filter), attr->aspath) == AS_FILTER_DENY)
921 return FILTER_DENY;
922 }
923
924 return FILTER_PERMIT;
925 #undef FILTER_EXIST_WARN
926 }
927
928 /* If community attribute includes no_export then return 1. */
929 static int
930 bgp_community_filter (struct peer *peer, struct attr *attr)
931 {
932 if (attr->community)
933 {
934 /* NO_ADVERTISE check. */
935 if (community_include (attr->community, COMMUNITY_NO_ADVERTISE))
936 return 1;
937
938 /* NO_EXPORT check. */
939 if (peer->sort == BGP_PEER_EBGP &&
940 community_include (attr->community, COMMUNITY_NO_EXPORT))
941 return 1;
942
943 /* NO_EXPORT_SUBCONFED check. */
944 if (peer->sort == BGP_PEER_EBGP
945 || peer->sort == BGP_PEER_CONFED)
946 if (community_include (attr->community, COMMUNITY_NO_EXPORT_SUBCONFED))
947 return 1;
948 }
949 return 0;
950 }
951
952 /* Route reflection loop check. */
953 static int
954 bgp_cluster_filter (struct peer *peer, struct attr *attr)
955 {
956 struct in_addr cluster_id;
957
958 if (attr->extra && attr->extra->cluster)
959 {
960 if (peer->bgp->config & BGP_CONFIG_CLUSTER_ID)
961 cluster_id = peer->bgp->cluster_id;
962 else
963 cluster_id = peer->bgp->router_id;
964
965 if (cluster_loop_check (attr->extra->cluster, cluster_id))
966 return 1;
967 }
968 return 0;
969 }
970
971 static int
972 bgp_input_modifier (struct peer *peer, struct prefix *p, struct attr *attr,
973 afi_t afi, safi_t safi, const char *rmap_name)
974 {
975 struct bgp_filter *filter;
976 struct bgp_info info;
977 route_map_result_t ret;
978 struct route_map *rmap = NULL;
979
980 filter = &peer->filter[afi][safi];
981
982 /* Apply default weight value. */
983 if (peer->weight)
984 (bgp_attr_extra_get (attr))->weight = peer->weight;
985
986 if (rmap_name)
987 {
988 rmap = route_map_lookup_by_name(rmap_name);
989
990 if (rmap == NULL)
991 return RMAP_DENY;
992 }
993 else
994 {
995 if (ROUTE_MAP_IN_NAME(filter))
996 {
997 rmap = ROUTE_MAP_IN (filter);
998
999 if (rmap == NULL)
1000 return RMAP_DENY;
1001 }
1002 }
1003
1004 /* Route map apply. */
1005 if (rmap)
1006 {
1007 /* Duplicate current value to new strucutre for modification. */
1008 info.peer = peer;
1009 info.attr = attr;
1010
1011 SET_FLAG (peer->rmap_type, PEER_RMAP_TYPE_IN);
1012
1013 /* Apply BGP route map to the attribute. */
1014 ret = route_map_apply (rmap, p, RMAP_BGP, &info);
1015
1016 peer->rmap_type = 0;
1017
1018 if (ret == RMAP_DENYMATCH)
1019 {
1020 /* Free newly generated AS path and community by route-map. */
1021 bgp_attr_flush (attr);
1022 return RMAP_DENY;
1023 }
1024 }
1025 return RMAP_PERMIT;
1026 }
1027
1028 static int
1029 bgp_output_modifier (struct peer *peer, struct prefix *p, struct attr *attr,
1030 afi_t afi, safi_t safi, const char *rmap_name)
1031 {
1032 struct bgp_filter *filter;
1033 struct bgp_info info;
1034 route_map_result_t ret;
1035 struct route_map *rmap = NULL;
1036
1037 filter = &peer->filter[afi][safi];
1038
1039 /* Apply default weight value. */
1040 if (peer->weight)
1041 (bgp_attr_extra_get (attr))->weight = peer->weight;
1042
1043 if (rmap_name)
1044 {
1045 rmap = route_map_lookup_by_name(rmap_name);
1046
1047 if (rmap == NULL)
1048 return RMAP_DENY;
1049 }
1050 else
1051 {
1052 if (ROUTE_MAP_OUT_NAME(filter))
1053 {
1054 rmap = ROUTE_MAP_OUT (filter);
1055
1056 if (rmap == NULL)
1057 return RMAP_DENY;
1058 }
1059 }
1060
1061 /* Route map apply. */
1062 if (rmap)
1063 {
1064 /* Duplicate current value to new strucutre for modification. */
1065 info.peer = peer;
1066 info.attr = attr;
1067
1068 SET_FLAG (peer->rmap_type, PEER_RMAP_TYPE_OUT);
1069
1070 /* Apply BGP route map to the attribute. */
1071 ret = route_map_apply (rmap, p, RMAP_BGP, &info);
1072
1073 peer->rmap_type = 0;
1074
1075 if (ret == RMAP_DENYMATCH)
1076 /* caller has multiple error paths with bgp_attr_flush() */
1077 return RMAP_DENY;
1078 }
1079 return RMAP_PERMIT;
1080 }
1081
1082 /* If this is an EBGP peer with remove-private-AS */
1083 static void
1084 bgp_peer_remove_private_as(struct bgp *bgp, afi_t afi, safi_t safi,
1085 struct peer *peer, struct attr *attr)
1086 {
1087 if (peer->sort == BGP_PEER_EBGP &&
1088 (peer_af_flag_check (peer, afi, safi, PEER_FLAG_REMOVE_PRIVATE_AS_ALL_REPLACE) ||
1089 peer_af_flag_check (peer, afi, safi, PEER_FLAG_REMOVE_PRIVATE_AS_REPLACE) ||
1090 peer_af_flag_check (peer, afi, safi, PEER_FLAG_REMOVE_PRIVATE_AS_ALL) ||
1091 peer_af_flag_check (peer, afi, safi, PEER_FLAG_REMOVE_PRIVATE_AS)))
1092 {
1093 // Take action on the entire aspath
1094 if (peer_af_flag_check (peer, afi, safi, PEER_FLAG_REMOVE_PRIVATE_AS_ALL_REPLACE) ||
1095 peer_af_flag_check (peer, afi, safi, PEER_FLAG_REMOVE_PRIVATE_AS_ALL))
1096 {
1097 if (peer_af_flag_check (peer, afi, safi, PEER_FLAG_REMOVE_PRIVATE_AS_ALL_REPLACE))
1098 attr->aspath = aspath_replace_private_asns (attr->aspath, bgp->as);
1099
1100 // The entire aspath consists of private ASNs so create an empty aspath
1101 else if (aspath_private_as_check (attr->aspath))
1102 attr->aspath = aspath_empty_get ();
1103
1104 // There are some public and some private ASNs, remove the private ASNs
1105 else
1106 attr->aspath = aspath_remove_private_asns (attr->aspath);
1107 }
1108
1109 // 'all' was not specified so the entire aspath must be private ASNs
1110 // for us to do anything
1111 else if (aspath_private_as_check (attr->aspath))
1112 {
1113 if (peer_af_flag_check (peer, afi, safi, PEER_FLAG_REMOVE_PRIVATE_AS_REPLACE))
1114 attr->aspath = aspath_replace_private_asns (attr->aspath, bgp->as);
1115 else
1116 attr->aspath = aspath_empty_get ();
1117 }
1118 }
1119 }
1120
1121 /* If this is an EBGP peer with as-override */
1122 static void
1123 bgp_peer_as_override(struct bgp *bgp, afi_t afi, safi_t safi,
1124 struct peer *peer, struct attr *attr)
1125 {
1126 if (peer->sort == BGP_PEER_EBGP &&
1127 peer_af_flag_check (peer, afi, safi, PEER_FLAG_AS_OVERRIDE))
1128 {
1129 if (aspath_single_asn_check (attr->aspath, peer->as))
1130 attr->aspath = aspath_replace_specific_asn (attr->aspath, peer->as, bgp->as);
1131 }
1132 }
1133
1134 static void
1135 subgroup_announce_reset_nhop (u_char family, struct attr *attr)
1136 {
1137 if (family == AF_INET)
1138 attr->nexthop.s_addr = 0;
1139 #ifdef HAVE_IPV6
1140 if (family == AF_INET6)
1141 memset (&attr->extra->mp_nexthop_global, 0, IPV6_MAX_BYTELEN);
1142 #endif
1143 }
1144
1145 int
1146 subgroup_announce_check (struct bgp_info *ri, struct update_subgroup *subgrp,
1147 struct prefix *p, struct attr *attr)
1148 {
1149 struct bgp_filter *filter;
1150 struct peer *from;
1151 struct peer *peer;
1152 struct peer *onlypeer;
1153 struct bgp *bgp;
1154 struct attr *riattr;
1155 struct peer_af *paf;
1156 char buf[SU_ADDRSTRLEN];
1157 int ret;
1158 int transparent;
1159 int reflect;
1160 afi_t afi;
1161 safi_t safi;
1162
1163 if (DISABLE_BGP_ANNOUNCE)
1164 return 0;
1165
1166 afi = SUBGRP_AFI(subgrp);
1167 safi = SUBGRP_SAFI(subgrp);
1168 peer = SUBGRP_PEER(subgrp);
1169 onlypeer = NULL;
1170 if (CHECK_FLAG (peer->flags, PEER_FLAG_LONESOUL))
1171 onlypeer = SUBGRP_PFIRST(subgrp)->peer;
1172
1173 from = ri->peer;
1174 filter = &peer->filter[afi][safi];
1175 bgp = SUBGRP_INST(subgrp);
1176 riattr = bgp_info_mpath_count (ri) ? bgp_info_mpath_attr (ri) : ri->attr;
1177
1178 /* With addpath we may be asked to TX all kinds of paths so make sure
1179 * ri is valid */
1180 if (!CHECK_FLAG (ri->flags, BGP_INFO_VALID) ||
1181 CHECK_FLAG (ri->flags, BGP_INFO_HISTORY) ||
1182 CHECK_FLAG (ri->flags, BGP_INFO_REMOVED))
1183 {
1184 return 0;
1185 }
1186
1187 /* If this is not the bestpath then check to see if there is an enabled addpath
1188 * feature that requires us to advertise it */
1189 if (! CHECK_FLAG (ri->flags, BGP_INFO_SELECTED))
1190 {
1191 if (! bgp_addpath_tx_path(peer, afi, safi, ri))
1192 {
1193 return 0;
1194 }
1195 }
1196
1197 /* Aggregate-address suppress check. */
1198 if (ri->extra && ri->extra->suppress)
1199 if (! UNSUPPRESS_MAP_NAME (filter))
1200 {
1201 return 0;
1202 }
1203
1204 /* Do not send back route to sender. */
1205 if (onlypeer && from == onlypeer)
1206 {
1207 return 0;
1208 }
1209
1210 /* Do not send the default route in the BGP table if the neighbor is
1211 * configured for default-originate */
1212 if (CHECK_FLAG (peer->af_flags[afi][safi], PEER_FLAG_DEFAULT_ORIGINATE))
1213 {
1214 if (p->family == AF_INET && p->u.prefix4.s_addr == INADDR_ANY)
1215 return 0;
1216 #ifdef HAVE_IPV6
1217 else if (p->family == AF_INET6 && p->prefixlen == 0)
1218 return 0;
1219 #endif /* HAVE_IPV6 */
1220 }
1221
1222 /* Transparency check. */
1223 if (CHECK_FLAG (peer->af_flags[afi][safi], PEER_FLAG_RSERVER_CLIENT)
1224 && CHECK_FLAG (from->af_flags[afi][safi], PEER_FLAG_RSERVER_CLIENT))
1225 transparent = 1;
1226 else
1227 transparent = 0;
1228
1229 /* If community is not disabled check the no-export and local. */
1230 if (! transparent && bgp_community_filter (peer, riattr))
1231 {
1232 if (bgp_debug_update(NULL, p, subgrp->update_group, 0))
1233 zlog_debug ("subgrpannouncecheck: community filter check fail");
1234 return 0;
1235 }
1236
1237 /* If the attribute has originator-id and it is same as remote
1238 peer's id. */
1239 if (onlypeer &&
1240 riattr->flag & ATTR_FLAG_BIT (BGP_ATTR_ORIGINATOR_ID) &&
1241 (IPV4_ADDR_SAME (&onlypeer->remote_id, &riattr->extra->originator_id)))
1242 {
1243 if (bgp_debug_update(NULL, p, subgrp->update_group, 0))
1244 zlog_debug ("%s [Update:SEND] %s/%d originator-id is same as "
1245 "remote router-id",
1246 onlypeer->host,
1247 inet_ntop(p->family, &p->u.prefix, buf, SU_ADDRSTRLEN),
1248 p->prefixlen);
1249 return 0;
1250 }
1251
1252 /* ORF prefix-list filter check */
1253 if (CHECK_FLAG (peer->af_cap[afi][safi], PEER_CAP_ORF_PREFIX_RM_ADV)
1254 && (CHECK_FLAG (peer->af_cap[afi][safi], PEER_CAP_ORF_PREFIX_SM_RCV)
1255 || CHECK_FLAG (peer->af_cap[afi][safi],
1256 PEER_CAP_ORF_PREFIX_SM_OLD_RCV)))
1257 if (peer->orf_plist[afi][safi])
1258 {
1259 if (prefix_list_apply (peer->orf_plist[afi][safi], p) == PREFIX_DENY)
1260 {
1261 if (bgp_debug_update(NULL, p, subgrp->update_group, 0))
1262 zlog_debug ("%s [Update:SEND] %s/%d is filtered via ORF",
1263 peer->host,
1264 inet_ntop(p->family, &p->u.prefix, buf, SU_ADDRSTRLEN),
1265 p->prefixlen);
1266 return 0;
1267 }
1268 }
1269
1270 /* Output filter check. */
1271 if (bgp_output_filter (peer, p, riattr, afi, safi) == FILTER_DENY)
1272 {
1273 if (bgp_debug_update(NULL, p, subgrp->update_group, 0))
1274 zlog_debug ("%s [Update:SEND] %s/%d is filtered",
1275 peer->host,
1276 inet_ntop(p->family, &p->u.prefix, buf, SU_ADDRSTRLEN),
1277 p->prefixlen);
1278 return 0;
1279 }
1280
1281 #ifdef BGP_SEND_ASPATH_CHECK
1282 /* AS path loop check. */
1283 if (onlypeer && aspath_loop_check (riattr->aspath, onlypeer->as))
1284 {
1285 if (bgp_debug_update(NULL, p, subgrp->update_group, 0))
1286 zlog_debug ("%s [Update:SEND] suppress announcement to peer AS %u "
1287 "that is part of AS path.",
1288 onlypeer->host, onlypeer->as);
1289 return 0;
1290 }
1291 #endif /* BGP_SEND_ASPATH_CHECK */
1292
1293 /* If we're a CONFED we need to loop check the CONFED ID too */
1294 if (CHECK_FLAG(bgp->config, BGP_CONFIG_CONFEDERATION))
1295 {
1296 if (aspath_loop_check(riattr->aspath, bgp->confed_id))
1297 {
1298 if (bgp_debug_update(NULL, p, subgrp->update_group, 0))
1299 zlog_debug ("%s [Update:SEND] suppress announcement to peer AS %u"
1300 " is AS path.",
1301 peer->host,
1302 bgp->confed_id);
1303 return 0;
1304 }
1305 }
1306
1307 /* Route-Reflect check. */
1308 if (from->sort == BGP_PEER_IBGP && peer->sort == BGP_PEER_IBGP)
1309 reflect = 1;
1310 else
1311 reflect = 0;
1312
1313 /* IBGP reflection check. */
1314 if (reflect)
1315 {
1316 /* A route from a Client peer. */
1317 if (CHECK_FLAG (from->af_flags[afi][safi], PEER_FLAG_REFLECTOR_CLIENT))
1318 {
1319 /* Reflect to all the Non-Client peers and also to the
1320 Client peers other than the originator. Originator check
1321 is already done. So there is noting to do. */
1322 /* no bgp client-to-client reflection check. */
1323 if (bgp_flag_check (bgp, BGP_FLAG_NO_CLIENT_TO_CLIENT))
1324 if (CHECK_FLAG (peer->af_flags[afi][safi],
1325 PEER_FLAG_REFLECTOR_CLIENT))
1326 return 0;
1327 }
1328 else
1329 {
1330 /* A route from a Non-client peer. Reflect to all other
1331 clients. */
1332 if (! CHECK_FLAG (peer->af_flags[afi][safi],
1333 PEER_FLAG_REFLECTOR_CLIENT))
1334 return 0;
1335 }
1336 }
1337
1338 /* For modify attribute, copy it to temporary structure. */
1339 bgp_attr_dup (attr, riattr);
1340
1341 /* If local-preference is not set. */
1342 if ((peer->sort == BGP_PEER_IBGP
1343 || peer->sort == BGP_PEER_CONFED)
1344 && (! (attr->flag & ATTR_FLAG_BIT (BGP_ATTR_LOCAL_PREF))))
1345 {
1346 attr->flag |= ATTR_FLAG_BIT (BGP_ATTR_LOCAL_PREF);
1347 attr->local_pref = bgp->default_local_pref;
1348 }
1349
1350 /* If originator-id is not set and the route is to be reflected,
1351 set the originator id */
1352 if (reflect && (!(attr->flag & ATTR_FLAG_BIT(BGP_ATTR_ORIGINATOR_ID))))
1353 {
1354 attr->extra = bgp_attr_extra_get(attr);
1355 IPV4_ADDR_COPY(&(attr->extra->originator_id), &(from->remote_id));
1356 SET_FLAG(attr->flag, BGP_ATTR_ORIGINATOR_ID);
1357 }
1358
1359 /* Remove MED if its an EBGP peer - will get overwritten by route-maps */
1360 if (peer->sort == BGP_PEER_EBGP
1361 && attr->flag & ATTR_FLAG_BIT (BGP_ATTR_MULTI_EXIT_DISC))
1362 {
1363 if (from != bgp->peer_self && ! transparent
1364 && ! CHECK_FLAG (peer->af_flags[afi][safi], PEER_FLAG_MED_UNCHANGED))
1365 attr->flag &= ~(ATTR_FLAG_BIT (BGP_ATTR_MULTI_EXIT_DISC));
1366 }
1367
1368 /* Since the nexthop attribute can vary per peer, it is not explicitly set
1369 * in announce check, only certain flags and length (or number of nexthops
1370 * -- for IPv6/MP_REACH) are set here in order to guide the update formation
1371 * code in setting the nexthop(s) on a per peer basis in reformat_peer().
1372 * Typically, the source nexthop in the attribute is preserved but in the
1373 * scenarios where we know it will always be overwritten, we reset the
1374 * nexthop to "0" in an attempt to achieve better Update packing. An
1375 * example of this is when a prefix from each of 2 IBGP peers needs to be
1376 * announced to an EBGP peer (and they have the same attributes barring
1377 * their nexthop).
1378 */
1379 if (reflect)
1380 SET_FLAG(attr->rmap_change_flags, BATTR_REFLECTED);
1381
1382 #ifdef HAVE_IPV6
1383 #define NEXTHOP_IS_V6 (\
1384 (safi != SAFI_ENCAP && \
1385 (p->family == AF_INET6 || peer_cap_enhe(peer))) || \
1386 (safi == SAFI_ENCAP && attr->extra->mp_nexthop_len == 16))
1387
1388 /* IPv6/MP starts with 1 nexthop. The link-local address is passed only if
1389 * the peer (group) is configured to receive link-local nexthop unchanged
1390 * and it is available in the prefix OR we're not reflecting the route and
1391 * the peer (group) to whom we're going to announce is on a shared network
1392 * and this is either a self-originated route or the peer is EBGP.
1393 */
1394 if (NEXTHOP_IS_V6)
1395 {
1396 attr->extra->mp_nexthop_len = BGP_ATTR_NHLEN_IPV6_GLOBAL;
1397 if ((CHECK_FLAG (peer->af_flags[afi][safi],
1398 PEER_FLAG_NEXTHOP_LOCAL_UNCHANGED) &&
1399 IN6_IS_ADDR_LINKLOCAL (&attr->extra->mp_nexthop_local)) ||
1400 (!reflect && peer->shared_network &&
1401 (from == bgp->peer_self || peer->sort == BGP_PEER_EBGP)))
1402 {
1403 attr->extra->mp_nexthop_len = BGP_ATTR_NHLEN_IPV6_GLOBAL_AND_LL;
1404 }
1405
1406 /* Clear off link-local nexthop in source, whenever it is not needed to
1407 * ensure more prefixes share the same attribute for announcement.
1408 */
1409 if (!(CHECK_FLAG (peer->af_flags[afi][safi],
1410 PEER_FLAG_NEXTHOP_LOCAL_UNCHANGED)))
1411 memset (&attr->extra->mp_nexthop_local, 0, IPV6_MAX_BYTELEN);
1412 }
1413 #endif /* HAVE_IPV6 */
1414
1415 bgp_peer_remove_private_as(bgp, afi, safi, peer, attr);
1416 bgp_peer_as_override(bgp, afi, safi, peer, attr);
1417
1418 /* Route map & unsuppress-map apply. */
1419 if (ROUTE_MAP_OUT_NAME (filter)
1420 || (ri->extra && ri->extra->suppress) )
1421 {
1422 struct bgp_info info;
1423 struct attr dummy_attr;
1424 struct attr_extra dummy_extra;
1425
1426 dummy_attr.extra = &dummy_extra;
1427
1428 info.peer = peer;
1429 info.attr = attr;
1430 /* don't confuse inbound and outbound setting */
1431 RESET_FLAG(attr->rmap_change_flags);
1432
1433 /*
1434 * The route reflector is not allowed to modify the attributes
1435 * of the reflected IBGP routes unless explicitly allowed.
1436 */
1437 if ((from->sort == BGP_PEER_IBGP && peer->sort == BGP_PEER_IBGP)
1438 && !bgp_flag_check(bgp, BGP_FLAG_RR_ALLOW_OUTBOUND_POLICY))
1439 {
1440 bgp_attr_dup (&dummy_attr, attr);
1441 info.attr = &dummy_attr;
1442 }
1443
1444 SET_FLAG (peer->rmap_type, PEER_RMAP_TYPE_OUT);
1445
1446 if (ri->extra && ri->extra->suppress)
1447 ret = route_map_apply (UNSUPPRESS_MAP (filter), p, RMAP_BGP, &info);
1448 else
1449 ret = route_map_apply (ROUTE_MAP_OUT (filter), p, RMAP_BGP, &info);
1450
1451 peer->rmap_type = 0;
1452
1453 if (ret == RMAP_DENYMATCH)
1454 {
1455 bgp_attr_flush (attr);
1456 return 0;
1457 }
1458 }
1459
1460 /* After route-map has been applied, we check to see if the nexthop to
1461 * be carried in the attribute (that is used for the announcement) can
1462 * be cleared off or not. We do this in all cases where we would be
1463 * setting the nexthop to "ourselves". For IPv6, we only need to consider
1464 * the global nexthop here; the link-local nexthop would have been cleared
1465 * already, and if not, it is required by the update formation code.
1466 * Also see earlier comments in this function.
1467 */
1468 /*
1469 * If route-map has performed some operation on the nexthop or the peer
1470 * configuration says to pass it unchanged, we cannot reset the nexthop
1471 * here, so only attempt to do it if these aren't true. Note that the
1472 * route-map handler itself might have cleared the nexthop, if for example,
1473 * it is configured as 'peer-address'.
1474 */
1475 if (!bgp_rmap_nhop_changed(attr->rmap_change_flags,
1476 riattr->rmap_change_flags) &&
1477 !transparent &&
1478 !CHECK_FLAG (peer->af_flags[afi][safi], PEER_FLAG_NEXTHOP_UNCHANGED))
1479 {
1480 /* We can reset the nexthop, if setting (or forcing) it to 'self' */
1481 if (CHECK_FLAG (peer->af_flags[afi][safi], PEER_FLAG_NEXTHOP_SELF) ||
1482 CHECK_FLAG (peer->af_flags[afi][safi], PEER_FLAG_FORCE_NEXTHOP_SELF))
1483 {
1484 if (!reflect ||
1485 CHECK_FLAG (peer->af_flags[afi][safi],
1486 PEER_FLAG_FORCE_NEXTHOP_SELF))
1487 subgroup_announce_reset_nhop ((peer_cap_enhe(peer) ?
1488 AF_INET6 : p->family), attr);
1489 }
1490 else if (peer->sort == BGP_PEER_EBGP)
1491 {
1492 /* Can also reset the nexthop if announcing to EBGP, but only if
1493 * no peer in the subgroup is on a shared subnet.
1494 * Note: 3rd party nexthop currently implemented for IPv4 only.
1495 */
1496 SUBGRP_FOREACH_PEER (subgrp, paf)
1497 {
1498 if (bgp_multiaccess_check_v4 (riattr->nexthop, paf->peer))
1499 break;
1500 }
1501 if (!paf)
1502 subgroup_announce_reset_nhop ((peer_cap_enhe(peer) ? AF_INET6 : p->family), attr);
1503 }
1504 /* If IPv6/MP and nexthop does not have any override and happens to
1505 * be a link-local address, reset it so that we don't pass along the
1506 * source's link-local IPv6 address to recipients who may not be on
1507 * the same interface.
1508 */
1509 if (p->family == AF_INET6 || peer_cap_enhe(peer))
1510 {
1511 if (IN6_IS_ADDR_LINKLOCAL (&attr->extra->mp_nexthop_global))
1512 subgroup_announce_reset_nhop (AF_INET6, attr);
1513 }
1514 }
1515
1516 return 1;
1517 }
1518
1519 struct bgp_info_pair
1520 {
1521 struct bgp_info *old;
1522 struct bgp_info *new;
1523 };
1524
1525 static void
1526 bgp_best_selection (struct bgp *bgp, struct bgp_node *rn,
1527 struct bgp_maxpaths_cfg *mpath_cfg,
1528 struct bgp_info_pair *result)
1529 {
1530 struct bgp_info *new_select;
1531 struct bgp_info *old_select;
1532 struct bgp_info *ri;
1533 struct bgp_info *ri1;
1534 struct bgp_info *ri2;
1535 struct bgp_info *nextri = NULL;
1536 int paths_eq, do_mpath, debug;
1537 struct list mp_list;
1538 char pfx_buf[PREFIX2STR_BUFFER];
1539 char path_buf[PATH_ADDPATH_STR_BUFFER];
1540
1541 bgp_mp_list_init (&mp_list);
1542 do_mpath = (mpath_cfg->maxpaths_ebgp > 1 || mpath_cfg->maxpaths_ibgp > 1);
1543
1544 debug = bgp_debug_bestpath(&rn->p);
1545
1546 if (debug)
1547 prefix2str (&rn->p, pfx_buf, sizeof (pfx_buf));
1548
1549 /* bgp deterministic-med */
1550 new_select = NULL;
1551 if (bgp_flag_check (bgp, BGP_FLAG_DETERMINISTIC_MED))
1552 {
1553
1554 /* Clear BGP_INFO_DMED_SELECTED for all paths */
1555 for (ri1 = rn->info; ri1; ri1 = ri1->next)
1556 bgp_info_unset_flag (rn, ri1, BGP_INFO_DMED_SELECTED);
1557
1558 for (ri1 = rn->info; ri1; ri1 = ri1->next)
1559 {
1560 if (CHECK_FLAG (ri1->flags, BGP_INFO_DMED_CHECK))
1561 continue;
1562 if (BGP_INFO_HOLDDOWN (ri1))
1563 continue;
1564 if (ri1->peer && ri1->peer != bgp->peer_self)
1565 if (ri1->peer->status != Established)
1566 continue;
1567
1568 new_select = ri1;
1569 if (ri1->next)
1570 {
1571 for (ri2 = ri1->next; ri2; ri2 = ri2->next)
1572 {
1573 if (CHECK_FLAG (ri2->flags, BGP_INFO_DMED_CHECK))
1574 continue;
1575 if (BGP_INFO_HOLDDOWN (ri2))
1576 continue;
1577 if (ri2->peer &&
1578 ri2->peer != bgp->peer_self &&
1579 !CHECK_FLAG (ri2->peer->sflags, PEER_STATUS_NSF_WAIT))
1580 if (ri2->peer->status != Established)
1581 continue;
1582
1583 if (aspath_cmp_left (ri1->attr->aspath, ri2->attr->aspath)
1584 || aspath_cmp_left_confed (ri1->attr->aspath,
1585 ri2->attr->aspath))
1586 {
1587 if (bgp_info_cmp (bgp, ri2, new_select, &paths_eq,
1588 mpath_cfg, debug, pfx_buf))
1589 {
1590 bgp_info_unset_flag (rn, new_select, BGP_INFO_DMED_SELECTED);
1591 new_select = ri2;
1592 }
1593
1594 bgp_info_set_flag (rn, ri2, BGP_INFO_DMED_CHECK);
1595 }
1596 }
1597 }
1598 bgp_info_set_flag (rn, new_select, BGP_INFO_DMED_CHECK);
1599 bgp_info_set_flag (rn, new_select, BGP_INFO_DMED_SELECTED);
1600
1601 if (debug)
1602 {
1603 bgp_info_path_with_addpath_rx_str (new_select, path_buf);
1604 zlog_debug("%s: %s is the bestpath from AS %d",
1605 pfx_buf, path_buf, aspath_get_firstas(new_select->attr->aspath));
1606 }
1607 }
1608 }
1609
1610 /* Check old selected route and new selected route. */
1611 old_select = NULL;
1612 new_select = NULL;
1613 for (ri = rn->info; (ri != NULL) && (nextri = ri->next, 1); ri = nextri)
1614 {
1615 if (CHECK_FLAG (ri->flags, BGP_INFO_SELECTED))
1616 old_select = ri;
1617
1618 if (BGP_INFO_HOLDDOWN (ri))
1619 {
1620 /* reap REMOVED routes, if needs be
1621 * selected route must stay for a while longer though
1622 */
1623 if (CHECK_FLAG (ri->flags, BGP_INFO_REMOVED)
1624 && (ri != old_select))
1625 bgp_info_reap (rn, ri);
1626
1627 continue;
1628 }
1629
1630 if (ri->peer &&
1631 ri->peer != bgp->peer_self &&
1632 !CHECK_FLAG (ri->peer->sflags, PEER_STATUS_NSF_WAIT))
1633 if (ri->peer->status != Established)
1634 continue;
1635
1636 if (bgp_flag_check (bgp, BGP_FLAG_DETERMINISTIC_MED)
1637 && (! CHECK_FLAG (ri->flags, BGP_INFO_DMED_SELECTED)))
1638 {
1639 bgp_info_unset_flag (rn, ri, BGP_INFO_DMED_CHECK);
1640 continue;
1641 }
1642
1643 bgp_info_unset_flag (rn, ri, BGP_INFO_DMED_CHECK);
1644
1645 if (bgp_info_cmp (bgp, ri, new_select, &paths_eq, mpath_cfg, debug, pfx_buf))
1646 {
1647 new_select = ri;
1648 }
1649 }
1650
1651 /* Now that we know which path is the bestpath see if any of the other paths
1652 * qualify as multipaths
1653 */
1654 if (debug)
1655 {
1656 if (new_select)
1657 bgp_info_path_with_addpath_rx_str (new_select, path_buf);
1658 else
1659 sprintf (path_buf, "NONE");
1660 zlog_debug("%s: After path selection, newbest is %s oldbest was %s",
1661 pfx_buf, path_buf,
1662 old_select ? old_select->peer->host : "NONE");
1663 }
1664
1665 if (do_mpath && new_select)
1666 {
1667 for (ri = rn->info; (ri != NULL) && (nextri = ri->next, 1); ri = nextri)
1668 {
1669
1670 if (debug)
1671 bgp_info_path_with_addpath_rx_str (ri, path_buf);
1672
1673 if (ri == new_select)
1674 {
1675 if (debug)
1676 zlog_debug("%s: %s is the bestpath, add to the multipath list",
1677 pfx_buf, path_buf);
1678 bgp_mp_list_add (&mp_list, ri);
1679 continue;
1680 }
1681
1682 if (BGP_INFO_HOLDDOWN (ri))
1683 continue;
1684
1685 if (ri->peer &&
1686 ri->peer != bgp->peer_self &&
1687 !CHECK_FLAG (ri->peer->sflags, PEER_STATUS_NSF_WAIT))
1688 if (ri->peer->status != Established)
1689 continue;
1690
1691 if (!bgp_info_nexthop_cmp (ri, new_select))
1692 {
1693 if (debug)
1694 zlog_debug("%s: %s has the same nexthop as the bestpath, skip it",
1695 pfx_buf, path_buf);
1696 continue;
1697 }
1698
1699 bgp_info_cmp (bgp, ri, new_select, &paths_eq, mpath_cfg, debug, pfx_buf);
1700
1701 if (paths_eq)
1702 {
1703 if (debug)
1704 zlog_debug("%s: %s is equivalent to the bestpath, add to the multipath list",
1705 pfx_buf, path_buf);
1706 bgp_mp_list_add (&mp_list, ri);
1707 }
1708 }
1709 }
1710
1711 bgp_info_mpath_update (rn, new_select, old_select, &mp_list, mpath_cfg);
1712 bgp_info_mpath_aggregate_update (new_select, old_select);
1713 bgp_mp_list_clear (&mp_list);
1714
1715 result->old = old_select;
1716 result->new = new_select;
1717
1718 return;
1719 }
1720
1721 /*
1722 * A new route/change in bestpath of an existing route. Evaluate the path
1723 * for advertisement to the subgroup.
1724 */
1725 int
1726 subgroup_process_announce_selected (struct update_subgroup *subgrp,
1727 struct bgp_info *selected,
1728 struct bgp_node *rn,
1729 u_int32_t addpath_tx_id)
1730 {
1731 struct prefix *p;
1732 struct peer *onlypeer;
1733 struct attr attr;
1734 struct attr_extra extra;
1735 afi_t afi;
1736 safi_t safi;
1737
1738 p = &rn->p;
1739 afi = SUBGRP_AFI(subgrp);
1740 safi = SUBGRP_SAFI(subgrp);
1741 onlypeer = ((SUBGRP_PCOUNT(subgrp) == 1) ?
1742 (SUBGRP_PFIRST(subgrp))->peer : NULL);
1743
1744 /* First update is deferred until ORF or ROUTE-REFRESH is received */
1745 if (onlypeer && CHECK_FLAG (onlypeer->af_sflags[afi][safi],
1746 PEER_STATUS_ORF_WAIT_REFRESH))
1747 return 0;
1748
1749 /* It's initialized in bgp_announce_check() */
1750 attr.extra = &extra;
1751
1752 /* Announcement to the subgroup. If the route is filtered withdraw it. */
1753 if (selected)
1754 {
1755 if (subgroup_announce_check(selected, subgrp, p, &attr))
1756 bgp_adj_out_set_subgroup(rn, subgrp, &attr, selected);
1757 else
1758 bgp_adj_out_unset_subgroup(rn, subgrp, 1, selected->addpath_tx_id);
1759 }
1760
1761 /* If selected is NULL we must withdraw the path using addpath_tx_id */
1762 else
1763 {
1764 bgp_adj_out_unset_subgroup(rn, subgrp, 1, addpath_tx_id);
1765 }
1766
1767 return 0;
1768 }
1769
1770 /*
1771 * Clear IGP changed flag and attribute changed flag for a route (all paths).
1772 * This is called at the end of route processing.
1773 */
1774 static void
1775 bgp_zebra_clear_route_change_flags (struct bgp_node *rn)
1776 {
1777 struct bgp_info *ri;
1778
1779 for (ri = rn->info; ri; ri = ri->next)
1780 {
1781 if (BGP_INFO_HOLDDOWN (ri))
1782 continue;
1783 UNSET_FLAG (ri->flags, BGP_INFO_IGP_CHANGED);
1784 UNSET_FLAG (ri->flags, BGP_INFO_ATTR_CHANGED);
1785 }
1786 }
1787
1788 /*
1789 * Has the route changed from the RIB's perspective? This is invoked only
1790 * if the route selection returns the same best route as earlier - to
1791 * determine if we need to update zebra or not.
1792 */
1793 static int
1794 bgp_zebra_has_route_changed (struct bgp_node *rn, struct bgp_info *selected)
1795 {
1796 struct bgp_info *mpinfo;
1797
1798 /* If this is multipath, check all selected paths for any nexthop change or
1799 * attribute change. Some attribute changes (e.g., community) aren't of
1800 * relevance to the RIB, but we'll update zebra to ensure we handle the
1801 * case of BGP nexthop change. This is the behavior when the best path has
1802 * an attribute change anyway.
1803 */
1804 if (CHECK_FLAG (selected->flags, BGP_INFO_IGP_CHANGED) ||
1805 CHECK_FLAG (selected->flags, BGP_INFO_MULTIPATH_CHG))
1806 return 1;
1807
1808 /* If this is multipath, check all selected paths for any nexthop change */
1809 for (mpinfo = bgp_info_mpath_first (selected); mpinfo;
1810 mpinfo = bgp_info_mpath_next (mpinfo))
1811 {
1812 if (CHECK_FLAG (mpinfo->flags, BGP_INFO_IGP_CHANGED)
1813 || CHECK_FLAG (mpinfo->flags, BGP_INFO_ATTR_CHANGED))
1814 return 1;
1815 }
1816
1817 /* Nothing has changed from the RIB's perspective. */
1818 return 0;
1819 }
1820
1821 struct bgp_process_queue
1822 {
1823 struct bgp *bgp;
1824 struct bgp_node *rn;
1825 afi_t afi;
1826 safi_t safi;
1827 };
1828
1829 static wq_item_status
1830 bgp_process_main (struct work_queue *wq, void *data)
1831 {
1832 struct bgp_process_queue *pq = data;
1833 struct bgp *bgp = pq->bgp;
1834 struct bgp_node *rn = pq->rn;
1835 afi_t afi = pq->afi;
1836 safi_t safi = pq->safi;
1837 struct prefix *p = &rn->p;
1838 struct bgp_info *new_select;
1839 struct bgp_info *old_select;
1840 struct bgp_info_pair old_and_new;
1841
1842 /* Is it end of initial update? (after startup) */
1843 if (!rn)
1844 {
1845 quagga_timestamp(3, bgp->update_delay_zebra_resume_time,
1846 sizeof(bgp->update_delay_zebra_resume_time));
1847
1848 bgp->main_zebra_update_hold = 0;
1849 for (afi = AFI_IP; afi < AFI_MAX; afi++)
1850 for (safi = SAFI_UNICAST; safi < SAFI_MAX; safi++)
1851 {
1852 bgp_zebra_announce_table(bgp, afi, safi);
1853 }
1854 bgp->main_peers_update_hold = 0;
1855
1856 bgp_start_routeadv(bgp);
1857 return WQ_SUCCESS;
1858 }
1859
1860 /* Best path selection. */
1861 bgp_best_selection (bgp, rn, &bgp->maxpaths[afi][safi], &old_and_new);
1862 old_select = old_and_new.old;
1863 new_select = old_and_new.new;
1864
1865 /* Nothing to do. */
1866 if (old_select && old_select == new_select &&
1867 !CHECK_FLAG(rn->flags, BGP_NODE_USER_CLEAR) &&
1868 !CHECK_FLAG(old_select->flags, BGP_INFO_ATTR_CHANGED) &&
1869 !bgp->addpath_tx_used[afi][safi])
1870 {
1871 if (bgp_zebra_has_route_changed (rn, old_select))
1872 bgp_zebra_announce (p, old_select, bgp, afi, safi);
1873
1874 UNSET_FLAG (old_select->flags, BGP_INFO_MULTIPATH_CHG);
1875 bgp_zebra_clear_route_change_flags (rn);
1876 UNSET_FLAG (rn->flags, BGP_NODE_PROCESS_SCHEDULED);
1877 return WQ_SUCCESS;
1878 }
1879
1880 /* If the user did "clear ip bgp prefix x.x.x.x" this flag will be set */
1881 UNSET_FLAG(rn->flags, BGP_NODE_USER_CLEAR);
1882
1883 /* bestpath has changed; bump version */
1884 if (old_select || new_select)
1885 {
1886 bgp_bump_version(rn);
1887
1888 if (!bgp->t_rmap_def_originate_eval)
1889 {
1890 bgp_lock (bgp);
1891 THREAD_TIMER_ON(bm->master, bgp->t_rmap_def_originate_eval,
1892 update_group_refresh_default_originate_route_map,
1893 bgp, RMAP_DEFAULT_ORIGINATE_EVAL_TIMER);
1894 }
1895 }
1896
1897 if (old_select)
1898 bgp_info_unset_flag (rn, old_select, BGP_INFO_SELECTED);
1899 if (new_select)
1900 {
1901 bgp_info_set_flag (rn, new_select, BGP_INFO_SELECTED);
1902 bgp_info_unset_flag (rn, new_select, BGP_INFO_ATTR_CHANGED);
1903 UNSET_FLAG (new_select->flags, BGP_INFO_MULTIPATH_CHG);
1904 }
1905
1906 group_announce_route(bgp, afi, safi, rn, new_select);
1907
1908 /* FIB update. */
1909 if ((safi == SAFI_UNICAST || safi == SAFI_MULTICAST) &&
1910 (bgp->inst_type != BGP_INSTANCE_TYPE_VIEW) &&
1911 !bgp_option_check (BGP_OPT_NO_FIB))
1912 {
1913 if (new_select
1914 && new_select->type == ZEBRA_ROUTE_BGP
1915 && (new_select->sub_type == BGP_ROUTE_NORMAL ||
1916 new_select->sub_type == BGP_ROUTE_AGGREGATE))
1917 bgp_zebra_announce (p, new_select, bgp, afi, safi);
1918 else
1919 {
1920 /* Withdraw the route from the kernel. */
1921 if (old_select
1922 && old_select->type == ZEBRA_ROUTE_BGP
1923 && (old_select->sub_type == BGP_ROUTE_NORMAL ||
1924 old_select->sub_type == BGP_ROUTE_AGGREGATE))
1925 bgp_zebra_withdraw (p, old_select, safi);
1926 }
1927 }
1928
1929 /* Clear any route change flags. */
1930 bgp_zebra_clear_route_change_flags (rn);
1931
1932 /* Reap old select bgp_info, if it has been removed */
1933 if (old_select && CHECK_FLAG (old_select->flags, BGP_INFO_REMOVED))
1934 bgp_info_reap (rn, old_select);
1935
1936 UNSET_FLAG (rn->flags, BGP_NODE_PROCESS_SCHEDULED);
1937 return WQ_SUCCESS;
1938 }
1939
1940 static void
1941 bgp_processq_del (struct work_queue *wq, void *data)
1942 {
1943 struct bgp_process_queue *pq = data;
1944 struct bgp_table *table;
1945
1946 bgp_unlock (pq->bgp);
1947 if (pq->rn)
1948 {
1949 table = bgp_node_table (pq->rn);
1950 bgp_unlock_node (pq->rn);
1951 bgp_table_unlock (table);
1952 }
1953 XFREE (MTYPE_BGP_PROCESS_QUEUE, pq);
1954 }
1955
1956 void
1957 bgp_process_queue_init (void)
1958 {
1959 if (!bm->process_main_queue)
1960 {
1961 bm->process_main_queue
1962 = work_queue_new (bm->master, "process_main_queue");
1963
1964 if ( !bm->process_main_queue)
1965 {
1966 zlog_err ("%s: Failed to allocate work queue", __func__);
1967 exit (1);
1968 }
1969 }
1970
1971 bm->process_main_queue->spec.workfunc = &bgp_process_main;
1972 bm->process_main_queue->spec.del_item_data = &bgp_processq_del;
1973 bm->process_main_queue->spec.max_retries = 0;
1974 bm->process_main_queue->spec.hold = 50;
1975 /* Use a higher yield value of 50ms for main queue processing */
1976 bm->process_main_queue->spec.yield = 50 * 1000L;
1977 }
1978
1979 void
1980 bgp_process (struct bgp *bgp, struct bgp_node *rn, afi_t afi, safi_t safi)
1981 {
1982 struct bgp_process_queue *pqnode;
1983
1984 /* already scheduled for processing? */
1985 if (CHECK_FLAG (rn->flags, BGP_NODE_PROCESS_SCHEDULED))
1986 return;
1987
1988 if (bm->process_main_queue == NULL)
1989 bgp_process_queue_init ();
1990
1991 pqnode = XCALLOC (MTYPE_BGP_PROCESS_QUEUE,
1992 sizeof (struct bgp_process_queue));
1993 if (!pqnode)
1994 return;
1995
1996 /* all unlocked in bgp_processq_del */
1997 bgp_table_lock (bgp_node_table (rn));
1998 pqnode->rn = bgp_lock_node (rn);
1999 pqnode->bgp = bgp;
2000 bgp_lock (bgp);
2001 pqnode->afi = afi;
2002 pqnode->safi = safi;
2003 work_queue_add (bm->process_main_queue, pqnode);
2004 SET_FLAG (rn->flags, BGP_NODE_PROCESS_SCHEDULED);
2005 return;
2006 }
2007
2008 void
2009 bgp_add_eoiu_mark (struct bgp *bgp)
2010 {
2011 struct bgp_process_queue *pqnode;
2012
2013 if (bm->process_main_queue == NULL)
2014 bgp_process_queue_init ();
2015
2016 pqnode = XCALLOC (MTYPE_BGP_PROCESS_QUEUE,
2017 sizeof (struct bgp_process_queue));
2018 if (!pqnode)
2019 return;
2020
2021 pqnode->rn = NULL;
2022 pqnode->bgp = bgp;
2023 bgp_lock (bgp);
2024 work_queue_add (bm->process_main_queue, pqnode);
2025 }
2026
2027 static int
2028 bgp_maximum_prefix_restart_timer (struct thread *thread)
2029 {
2030 struct peer *peer;
2031
2032 peer = THREAD_ARG (thread);
2033 peer->t_pmax_restart = NULL;
2034
2035 if (bgp_debug_neighbor_events(peer))
2036 zlog_debug ("%s Maximum-prefix restart timer expired, restore peering",
2037 peer->host);
2038
2039 peer_clear (peer, NULL);
2040
2041 return 0;
2042 }
2043
2044 int
2045 bgp_maximum_prefix_overflow (struct peer *peer, afi_t afi,
2046 safi_t safi, int always)
2047 {
2048 if (!CHECK_FLAG (peer->af_flags[afi][safi], PEER_FLAG_MAX_PREFIX))
2049 return 0;
2050
2051 if (peer->pcount[afi][safi] > peer->pmax[afi][safi])
2052 {
2053 if (CHECK_FLAG (peer->af_sflags[afi][safi], PEER_STATUS_PREFIX_LIMIT)
2054 && ! always)
2055 return 0;
2056
2057 zlog_info ("%%MAXPFXEXCEED: No. of %s prefix received from %s %ld exceed, "
2058 "limit %ld", afi_safi_print (afi, safi), peer->host,
2059 peer->pcount[afi][safi], peer->pmax[afi][safi]);
2060 SET_FLAG (peer->af_sflags[afi][safi], PEER_STATUS_PREFIX_LIMIT);
2061
2062 if (CHECK_FLAG (peer->af_flags[afi][safi], PEER_FLAG_MAX_PREFIX_WARNING))
2063 return 0;
2064
2065 {
2066 u_int8_t ndata[7];
2067
2068 if (safi == SAFI_MPLS_VPN)
2069 safi = SAFI_MPLS_LABELED_VPN;
2070
2071 ndata[0] = (afi >> 8);
2072 ndata[1] = afi;
2073 ndata[2] = safi;
2074 ndata[3] = (peer->pmax[afi][safi] >> 24);
2075 ndata[4] = (peer->pmax[afi][safi] >> 16);
2076 ndata[5] = (peer->pmax[afi][safi] >> 8);
2077 ndata[6] = (peer->pmax[afi][safi]);
2078
2079 SET_FLAG (peer->sflags, PEER_STATUS_PREFIX_OVERFLOW);
2080 bgp_notify_send_with_data (peer, BGP_NOTIFY_CEASE,
2081 BGP_NOTIFY_CEASE_MAX_PREFIX, ndata, 7);
2082 }
2083
2084 /* Dynamic peers will just close their connection. */
2085 if (peer_dynamic_neighbor (peer))
2086 return 1;
2087
2088 /* restart timer start */
2089 if (peer->pmax_restart[afi][safi])
2090 {
2091 peer->v_pmax_restart = peer->pmax_restart[afi][safi] * 60;
2092
2093 if (bgp_debug_neighbor_events(peer))
2094 zlog_debug ("%s Maximum-prefix restart timer started for %d secs",
2095 peer->host, peer->v_pmax_restart);
2096
2097 BGP_TIMER_ON (peer->t_pmax_restart, bgp_maximum_prefix_restart_timer,
2098 peer->v_pmax_restart);
2099 }
2100
2101 return 1;
2102 }
2103 else
2104 UNSET_FLAG (peer->af_sflags[afi][safi], PEER_STATUS_PREFIX_LIMIT);
2105
2106 if (peer->pcount[afi][safi] > (peer->pmax[afi][safi] * peer->pmax_threshold[afi][safi] / 100))
2107 {
2108 if (CHECK_FLAG (peer->af_sflags[afi][safi], PEER_STATUS_PREFIX_THRESHOLD)
2109 && ! always)
2110 return 0;
2111
2112 zlog_info ("%%MAXPFX: No. of %s prefix received from %s reaches %ld, max %ld",
2113 afi_safi_print (afi, safi), peer->host, peer->pcount[afi][safi],
2114 peer->pmax[afi][safi]);
2115 SET_FLAG (peer->af_sflags[afi][safi], PEER_STATUS_PREFIX_THRESHOLD);
2116 }
2117 else
2118 UNSET_FLAG (peer->af_sflags[afi][safi], PEER_STATUS_PREFIX_THRESHOLD);
2119 return 0;
2120 }
2121
2122 /* Unconditionally remove the route from the RIB, without taking
2123 * damping into consideration (eg, because the session went down)
2124 */
2125 static void
2126 bgp_rib_remove (struct bgp_node *rn, struct bgp_info *ri, struct peer *peer,
2127 afi_t afi, safi_t safi)
2128 {
2129 bgp_aggregate_decrement (peer->bgp, &rn->p, ri, afi, safi);
2130
2131 if (!CHECK_FLAG (ri->flags, BGP_INFO_HISTORY))
2132 bgp_info_delete (rn, ri); /* keep historical info */
2133
2134 bgp_process (peer->bgp, rn, afi, safi);
2135 }
2136
2137 static void
2138 bgp_rib_withdraw (struct bgp_node *rn, struct bgp_info *ri, struct peer *peer,
2139 afi_t afi, safi_t safi)
2140 {
2141 int status = BGP_DAMP_NONE;
2142
2143 /* apply dampening, if result is suppressed, we'll be retaining
2144 * the bgp_info in the RIB for historical reference.
2145 */
2146 if (CHECK_FLAG (peer->bgp->af_flags[afi][safi], BGP_CONFIG_DAMPENING)
2147 && peer->sort == BGP_PEER_EBGP)
2148 if ( (status = bgp_damp_withdraw (ri, rn, afi, safi, 0))
2149 == BGP_DAMP_SUPPRESSED)
2150 {
2151 bgp_aggregate_decrement (peer->bgp, &rn->p, ri, afi, safi);
2152 return;
2153 }
2154
2155 bgp_rib_remove (rn, ri, peer, afi, safi);
2156 }
2157
2158 static struct bgp_info *
2159 info_make (int type, int sub_type, u_short instance, struct peer *peer, struct attr *attr,
2160 struct bgp_node *rn)
2161 {
2162 struct bgp_info *new;
2163
2164 /* Make new BGP info. */
2165 new = XCALLOC (MTYPE_BGP_ROUTE, sizeof (struct bgp_info));
2166 new->type = type;
2167 new->instance = instance;
2168 new->sub_type = sub_type;
2169 new->peer = peer;
2170 new->attr = attr;
2171 new->uptime = bgp_clock ();
2172 new->net = rn;
2173 new->addpath_tx_id = ++peer->bgp->addpath_tx_id;
2174 return new;
2175 }
2176
2177 static void
2178 bgp_info_addpath_rx_str(u_int32_t addpath_id, char *buf)
2179 {
2180 if (addpath_id)
2181 sprintf(buf, " with addpath ID %d", addpath_id);
2182 }
2183
2184
2185 /* Check if received nexthop is valid or not. */
2186 static int
2187 bgp_update_martian_nexthop (struct bgp *bgp, afi_t afi, safi_t safi, struct attr *attr)
2188 {
2189 struct attr_extra *attre = attr->extra;
2190 int ret = 0;
2191
2192 /* Only validated for unicast and multicast currently. */
2193 if (safi != SAFI_UNICAST && safi != SAFI_MULTICAST)
2194 return 0;
2195
2196 /* If NEXT_HOP is present, validate it. */
2197 if (attr->flag & ATTR_FLAG_BIT (BGP_ATTR_NEXT_HOP))
2198 {
2199 if (attr->nexthop.s_addr == 0 ||
2200 IPV4_CLASS_DE (ntohl (attr->nexthop.s_addr)) ||
2201 bgp_nexthop_self (bgp, attr))
2202 ret = 1;
2203 }
2204
2205 /* If MP_NEXTHOP is present, validate it. */
2206 /* Note: For IPv6 nexthops, we only validate the global (1st) nexthop;
2207 * there is code in bgp_attr.c to ignore the link-local (2nd) nexthop if
2208 * it is not an IPv6 link-local address.
2209 */
2210 if (attre && attre->mp_nexthop_len)
2211 {
2212 switch (attre->mp_nexthop_len)
2213 {
2214 case BGP_ATTR_NHLEN_IPV4:
2215 case BGP_ATTR_NHLEN_VPNV4:
2216 ret = (attre->mp_nexthop_global_in.s_addr == 0 ||
2217 IPV4_CLASS_DE (ntohl (attre->mp_nexthop_global_in.s_addr)));
2218 break;
2219
2220 #ifdef HAVE_IPV6
2221 case BGP_ATTR_NHLEN_IPV6_GLOBAL:
2222 case BGP_ATTR_NHLEN_IPV6_GLOBAL_AND_LL:
2223 ret = (IN6_IS_ADDR_UNSPECIFIED(&attre->mp_nexthop_global) ||
2224 IN6_IS_ADDR_LOOPBACK(&attre->mp_nexthop_global) ||
2225 IN6_IS_ADDR_MULTICAST(&attre->mp_nexthop_global));
2226 break;
2227 #endif /* HAVE_IPV6 */
2228
2229 default:
2230 ret = 1;
2231 break;
2232 }
2233 }
2234
2235 return ret;
2236 }
2237
2238 int
2239 bgp_update (struct peer *peer, struct prefix *p, u_int32_t addpath_id,
2240 struct attr *attr, afi_t afi, safi_t safi, int type,
2241 int sub_type, struct prefix_rd *prd, u_char *tag,
2242 int soft_reconfig)
2243 {
2244 int ret;
2245 int aspath_loop_count = 0;
2246 struct bgp_node *rn;
2247 struct bgp *bgp;
2248 struct attr new_attr;
2249 struct attr_extra new_extra;
2250 struct attr *attr_new;
2251 struct bgp_info *ri;
2252 struct bgp_info *new;
2253 const char *reason;
2254 char buf[SU_ADDRSTRLEN];
2255 char buf2[30];
2256 int connected = 0;
2257
2258 bgp = peer->bgp;
2259 rn = bgp_afi_node_get (bgp->rib[afi][safi], afi, safi, p, prd);
2260
2261 /* When peer's soft reconfiguration enabled. Record input packet in
2262 Adj-RIBs-In. */
2263 if (! soft_reconfig && CHECK_FLAG (peer->af_flags[afi][safi], PEER_FLAG_SOFT_RECONFIG)
2264 && peer != bgp->peer_self)
2265 bgp_adj_in_set (rn, peer, attr, addpath_id);
2266
2267 /* Check previously received route. */
2268 for (ri = rn->info; ri; ri = ri->next)
2269 if (ri->peer == peer && ri->type == type && ri->sub_type == sub_type &&
2270 ri->addpath_rx_id == addpath_id)
2271 break;
2272
2273 /* AS path local-as loop check. */
2274 if (peer->change_local_as)
2275 {
2276 if (! CHECK_FLAG (peer->flags, PEER_FLAG_LOCAL_AS_NO_PREPEND))
2277 aspath_loop_count = 1;
2278
2279 if (aspath_loop_check (attr->aspath, peer->change_local_as) > aspath_loop_count)
2280 {
2281 reason = "as-path contains our own AS;";
2282 goto filtered;
2283 }
2284 }
2285
2286 /* AS path loop check. */
2287 if (aspath_loop_check (attr->aspath, bgp->as) > peer->allowas_in[afi][safi]
2288 || (CHECK_FLAG(bgp->config, BGP_CONFIG_CONFEDERATION)
2289 && aspath_loop_check(attr->aspath, bgp->confed_id)
2290 > peer->allowas_in[afi][safi]))
2291 {
2292 reason = "as-path contains our own AS;";
2293 goto filtered;
2294 }
2295
2296 /* Route reflector originator ID check. */
2297 if (attr->flag & ATTR_FLAG_BIT (BGP_ATTR_ORIGINATOR_ID)
2298 && IPV4_ADDR_SAME (&bgp->router_id, &attr->extra->originator_id))
2299 {
2300 reason = "originator is us;";
2301 goto filtered;
2302 }
2303
2304 /* Route reflector cluster ID check. */
2305 if (bgp_cluster_filter (peer, attr))
2306 {
2307 reason = "reflected from the same cluster;";
2308 goto filtered;
2309 }
2310
2311 /* Apply incoming filter. */
2312 if (bgp_input_filter (peer, p, attr, afi, safi) == FILTER_DENY)
2313 {
2314 reason = "filter;";
2315 goto filtered;
2316 }
2317
2318 new_attr.extra = &new_extra;
2319 bgp_attr_dup (&new_attr, attr);
2320
2321 /* Apply incoming route-map.
2322 * NB: new_attr may now contain newly allocated values from route-map "set"
2323 * commands, so we need bgp_attr_flush in the error paths, until we intern
2324 * the attr (which takes over the memory references) */
2325 if (bgp_input_modifier (peer, p, &new_attr, afi, safi, NULL) == RMAP_DENY)
2326 {
2327 reason = "route-map;";
2328 bgp_attr_flush (&new_attr);
2329 goto filtered;
2330 }
2331
2332 /* next hop check. */
2333 if (bgp_update_martian_nexthop (bgp, afi, safi, &new_attr))
2334 {
2335 reason = "martian or self next-hop;";
2336 bgp_attr_flush (&new_attr);
2337 goto filtered;
2338 }
2339
2340 attr_new = bgp_attr_intern (&new_attr);
2341
2342 /* If the update is implicit withdraw. */
2343 if (ri)
2344 {
2345 ri->uptime = bgp_clock ();
2346
2347 /* Same attribute comes in. */
2348 if (!CHECK_FLAG (ri->flags, BGP_INFO_REMOVED)
2349 && attrhash_cmp (ri->attr, attr_new))
2350 {
2351 if (CHECK_FLAG (bgp->af_flags[afi][safi], BGP_CONFIG_DAMPENING)
2352 && peer->sort == BGP_PEER_EBGP
2353 && CHECK_FLAG (ri->flags, BGP_INFO_HISTORY))
2354 {
2355 if (bgp_debug_update(peer, p, NULL, 1))
2356 {
2357 bgp_info_addpath_rx_str(addpath_id, buf2);
2358 zlog_debug ("%s rcvd %s/%d%s",
2359 peer->host,
2360 inet_ntop(p->family, &p->u.prefix, buf, SU_ADDRSTRLEN),
2361 p->prefixlen, buf2);
2362 }
2363
2364 if (bgp_damp_update (ri, rn, afi, safi) != BGP_DAMP_SUPPRESSED)
2365 {
2366 bgp_aggregate_increment (bgp, p, ri, afi, safi);
2367 bgp_process (bgp, rn, afi, safi);
2368 }
2369 }
2370 else /* Duplicate - odd */
2371 {
2372 if (bgp_debug_update(peer, p, NULL, 1))
2373 {
2374 if (!peer->rcvd_attr_printed)
2375 {
2376 zlog_debug ("%s rcvd UPDATE w/ attr: %s", peer->host, peer->rcvd_attr_str);
2377 peer->rcvd_attr_printed = 1;
2378 }
2379
2380 bgp_info_addpath_rx_str(addpath_id, buf2);
2381 zlog_debug ("%s rcvd %s/%d%s...duplicate ignored",
2382 peer->host,
2383 inet_ntop(p->family, &p->u.prefix, buf, SU_ADDRSTRLEN),
2384 p->prefixlen, buf2);
2385 }
2386
2387 /* graceful restart STALE flag unset. */
2388 if (CHECK_FLAG (ri->flags, BGP_INFO_STALE))
2389 {
2390 bgp_info_unset_flag (rn, ri, BGP_INFO_STALE);
2391 bgp_process (bgp, rn, afi, safi);
2392 }
2393 }
2394
2395 bgp_unlock_node (rn);
2396 bgp_attr_unintern (&attr_new);
2397
2398 return 0;
2399 }
2400
2401 /* Withdraw/Announce before we fully processed the withdraw */
2402 if (CHECK_FLAG(ri->flags, BGP_INFO_REMOVED))
2403 {
2404 if (bgp_debug_update(peer, p, NULL, 1))
2405 {
2406 bgp_info_addpath_rx_str(addpath_id, buf2);
2407 zlog_debug ("%s rcvd %s/%d%s, flapped quicker than processing",
2408 peer->host,
2409 inet_ntop(p->family, &p->u.prefix, buf, SU_ADDRSTRLEN),
2410 p->prefixlen, buf2);
2411 }
2412 bgp_info_restore (rn, ri);
2413 }
2414
2415 /* Received Logging. */
2416 if (bgp_debug_update(peer, p, NULL, 1))
2417 {
2418 bgp_info_addpath_rx_str(addpath_id, buf2);
2419 zlog_debug ("%s rcvd %s/%d%s",
2420 peer->host,
2421 inet_ntop(p->family, &p->u.prefix, buf, SU_ADDRSTRLEN),
2422 p->prefixlen, buf2);
2423 }
2424
2425 /* graceful restart STALE flag unset. */
2426 if (CHECK_FLAG (ri->flags, BGP_INFO_STALE))
2427 bgp_info_unset_flag (rn, ri, BGP_INFO_STALE);
2428
2429 /* The attribute is changed. */
2430 bgp_info_set_flag (rn, ri, BGP_INFO_ATTR_CHANGED);
2431
2432 /* implicit withdraw, decrement aggregate and pcount here.
2433 * only if update is accepted, they'll increment below.
2434 */
2435 bgp_aggregate_decrement (bgp, p, ri, afi, safi);
2436
2437 /* Update bgp route dampening information. */
2438 if (CHECK_FLAG (bgp->af_flags[afi][safi], BGP_CONFIG_DAMPENING)
2439 && peer->sort == BGP_PEER_EBGP)
2440 {
2441 /* This is implicit withdraw so we should update dampening
2442 information. */
2443 if (! CHECK_FLAG (ri->flags, BGP_INFO_HISTORY))
2444 bgp_damp_withdraw (ri, rn, afi, safi, 1);
2445 }
2446
2447 /* Update to new attribute. */
2448 bgp_attr_unintern (&ri->attr);
2449 ri->attr = attr_new;
2450
2451 /* Update MPLS tag. */
2452 if (safi == SAFI_MPLS_VPN)
2453 memcpy ((bgp_info_extra_get (ri))->tag, tag, 3);
2454
2455 /* Update bgp route dampening information. */
2456 if (CHECK_FLAG (bgp->af_flags[afi][safi], BGP_CONFIG_DAMPENING)
2457 && peer->sort == BGP_PEER_EBGP)
2458 {
2459 /* Now we do normal update dampening. */
2460 ret = bgp_damp_update (ri, rn, afi, safi);
2461 if (ret == BGP_DAMP_SUPPRESSED)
2462 {
2463 bgp_unlock_node (rn);
2464 return 0;
2465 }
2466 }
2467
2468 /* Nexthop reachability check. */
2469 if ((afi == AFI_IP || afi == AFI_IP6) && safi == SAFI_UNICAST)
2470 {
2471 if (peer->sort == BGP_PEER_EBGP && peer->ttl == 1 &&
2472 ! CHECK_FLAG (peer->flags, PEER_FLAG_DISABLE_CONNECTED_CHECK)
2473 && ! bgp_flag_check(bgp, BGP_FLAG_DISABLE_NH_CONNECTED_CHK))
2474 connected = 1;
2475 else
2476 connected = 0;
2477
2478 if (bgp_find_or_add_nexthop (bgp, afi, ri, NULL, connected))
2479 bgp_info_set_flag (rn, ri, BGP_INFO_VALID);
2480 else
2481 {
2482 if (BGP_DEBUG(nht, NHT))
2483 {
2484 char buf1[INET6_ADDRSTRLEN];
2485 inet_ntop(AF_INET, (const void *)&attr_new->nexthop, buf1, INET6_ADDRSTRLEN);
2486 zlog_debug("%s(%s): NH unresolved", __FUNCTION__, buf1);
2487 }
2488 bgp_info_unset_flag (rn, ri, BGP_INFO_VALID);
2489 }
2490 }
2491 else
2492 bgp_info_set_flag (rn, ri, BGP_INFO_VALID);
2493
2494 /* Process change. */
2495 bgp_aggregate_increment (bgp, p, ri, afi, safi);
2496
2497 bgp_process (bgp, rn, afi, safi);
2498 bgp_unlock_node (rn);
2499
2500 return 0;
2501 } // End of implicit withdraw
2502
2503 /* Received Logging. */
2504 if (bgp_debug_update(peer, p, NULL, 1))
2505 {
2506 if (!peer->rcvd_attr_printed)
2507 {
2508 zlog_debug ("%s rcvd UPDATE w/ attr: %s", peer->host, peer->rcvd_attr_str);
2509 peer->rcvd_attr_printed = 1;
2510 }
2511
2512 bgp_info_addpath_rx_str(addpath_id, buf2);
2513 zlog_debug ("%s rcvd %s/%d%s",
2514 peer->host,
2515 inet_ntop(p->family, &p->u.prefix, buf, SU_ADDRSTRLEN),
2516 p->prefixlen, buf2);
2517 }
2518
2519 /* Make new BGP info. */
2520 new = info_make(type, sub_type, 0, peer, attr_new, rn);
2521
2522 /* Update MPLS tag. */
2523 if (safi == SAFI_MPLS_VPN)
2524 memcpy ((bgp_info_extra_get (new))->tag, tag, 3);
2525
2526 /* Nexthop reachability check. */
2527 if ((afi == AFI_IP || afi == AFI_IP6) && safi == SAFI_UNICAST)
2528 {
2529 if (peer->sort == BGP_PEER_EBGP && peer->ttl == 1 &&
2530 ! CHECK_FLAG (peer->flags, PEER_FLAG_DISABLE_CONNECTED_CHECK)
2531 && ! bgp_flag_check(bgp, BGP_FLAG_DISABLE_NH_CONNECTED_CHK))
2532 connected = 1;
2533 else
2534 connected = 0;
2535
2536 if (bgp_find_or_add_nexthop (bgp, afi, new, NULL, connected))
2537 bgp_info_set_flag (rn, new, BGP_INFO_VALID);
2538 else
2539 {
2540 if (BGP_DEBUG(nht, NHT))
2541 {
2542 char buf1[INET6_ADDRSTRLEN];
2543 inet_ntop(AF_INET, (const void *)&attr_new->nexthop, buf1, INET6_ADDRSTRLEN);
2544 zlog_debug("%s(%s): NH unresolved", __FUNCTION__, buf1);
2545 }
2546 bgp_info_unset_flag (rn, new, BGP_INFO_VALID);
2547 }
2548 }
2549 else
2550 bgp_info_set_flag (rn, new, BGP_INFO_VALID);
2551
2552 /* Addpath ID */
2553 new->addpath_rx_id = addpath_id;
2554
2555 /* Increment prefix */
2556 bgp_aggregate_increment (bgp, p, new, afi, safi);
2557
2558 /* Register new BGP information. */
2559 bgp_info_add (rn, new);
2560
2561 /* route_node_get lock */
2562 bgp_unlock_node (rn);
2563
2564 /* If maximum prefix count is configured and current prefix
2565 count exeed it. */
2566 if (bgp_maximum_prefix_overflow (peer, afi, safi, 0))
2567 return -1;
2568
2569 /* Process change. */
2570 bgp_process (bgp, rn, afi, safi);
2571
2572 return 0;
2573
2574 /* This BGP update is filtered. Log the reason then update BGP
2575 entry. */
2576 filtered:
2577 if (bgp_debug_update(peer, p, NULL, 1))
2578 {
2579 if (!peer->rcvd_attr_printed)
2580 {
2581 zlog_debug ("%s rcvd UPDATE w/ attr: %s", peer->host, peer->rcvd_attr_str);
2582 peer->rcvd_attr_printed = 1;
2583 }
2584
2585 bgp_info_addpath_rx_str(addpath_id, buf2);
2586 zlog_debug ("%s rcvd UPDATE about %s/%d%s -- DENIED due to: %s",
2587 peer->host,
2588 inet_ntop (p->family, &p->u.prefix, buf, SU_ADDRSTRLEN),
2589 p->prefixlen, buf2, reason);
2590 }
2591
2592 if (ri)
2593 bgp_rib_remove (rn, ri, peer, afi, safi);
2594
2595 bgp_unlock_node (rn);
2596
2597 return 0;
2598 }
2599
2600 int
2601 bgp_withdraw (struct peer *peer, struct prefix *p, u_int32_t addpath_id,
2602 struct attr *attr, afi_t afi, safi_t safi, int type, int sub_type,
2603 struct prefix_rd *prd, u_char *tag)
2604 {
2605 struct bgp *bgp;
2606 char buf[SU_ADDRSTRLEN];
2607 char buf2[30];
2608 struct bgp_node *rn;
2609 struct bgp_info *ri;
2610
2611 bgp = peer->bgp;
2612
2613 /* Lookup node. */
2614 rn = bgp_afi_node_get (bgp->rib[afi][safi], afi, safi, p, prd);
2615
2616 /* If peer is soft reconfiguration enabled. Record input packet for
2617 * further calculation.
2618 *
2619 * Cisco IOS 12.4(24)T4 on session establishment sends withdraws for all
2620 * routes that are filtered. This tanks out Quagga RS pretty badly due to
2621 * the iteration over all RS clients.
2622 * Since we need to remove the entry from adj_in anyway, do that first and
2623 * if there was no entry, we don't need to do anything more.
2624 */
2625 if (CHECK_FLAG (peer->af_flags[afi][safi], PEER_FLAG_SOFT_RECONFIG)
2626 && peer != bgp->peer_self)
2627 if (!bgp_adj_in_unset (rn, peer, addpath_id))
2628 {
2629 if (bgp_debug_update (peer, p, NULL, 1))
2630 zlog_debug ("%s withdrawing route %s/%d "
2631 "not in adj-in", peer->host,
2632 inet_ntop(p->family, &p->u.prefix, buf, SU_ADDRSTRLEN),
2633 p->prefixlen);
2634 bgp_unlock_node (rn);
2635 return 0;
2636 }
2637
2638 /* Lookup withdrawn route. */
2639 for (ri = rn->info; ri; ri = ri->next)
2640 if (ri->peer == peer && ri->type == type && ri->sub_type == sub_type &&
2641 ri->addpath_rx_id == addpath_id)
2642 break;
2643
2644 /* Logging. */
2645 if (bgp_debug_update(peer, p, NULL, 1))
2646 {
2647 bgp_info_addpath_rx_str(addpath_id, buf2);
2648 zlog_debug ("%s rcvd UPDATE about %s/%d%s -- withdrawn",
2649 peer->host,
2650 inet_ntop(p->family, &p->u.prefix, buf, SU_ADDRSTRLEN),
2651 p->prefixlen, buf2);
2652 }
2653
2654 /* Withdraw specified route from routing table. */
2655 if (ri && ! CHECK_FLAG (ri->flags, BGP_INFO_HISTORY))
2656 bgp_rib_withdraw (rn, ri, peer, afi, safi);
2657 else if (bgp_debug_update(peer, p, NULL, 1))
2658 zlog_debug ("%s Can't find the route %s/%d", peer->host,
2659 inet_ntop (p->family, &p->u.prefix, buf, SU_ADDRSTRLEN),
2660 p->prefixlen);
2661
2662 /* Unlock bgp_node_get() lock. */
2663 bgp_unlock_node (rn);
2664
2665 return 0;
2666 }
2667
2668 void
2669 bgp_default_originate (struct peer *peer, afi_t afi, safi_t safi, int withdraw)
2670 {
2671 struct update_subgroup *subgrp;
2672 subgrp = peer_subgroup(peer, afi, safi);
2673 subgroup_default_originate(subgrp, withdraw);
2674 }
2675
2676
2677 /*
2678 * bgp_stop_announce_route_timer
2679 */
2680 void
2681 bgp_stop_announce_route_timer (struct peer_af *paf)
2682 {
2683 if (!paf->t_announce_route)
2684 return;
2685
2686 THREAD_TIMER_OFF (paf->t_announce_route);
2687 }
2688
2689 /*
2690 * bgp_announce_route_timer_expired
2691 *
2692 * Callback that is invoked when the route announcement timer for a
2693 * peer_af expires.
2694 */
2695 static int
2696 bgp_announce_route_timer_expired (struct thread *t)
2697 {
2698 struct peer_af *paf;
2699 struct peer *peer;
2700
2701 paf = THREAD_ARG (t);
2702 peer = paf->peer;
2703
2704 assert (paf->t_announce_route);
2705 paf->t_announce_route = NULL;
2706
2707 if (peer->status != Established)
2708 return 0;
2709
2710 if (!peer->afc_nego[paf->afi][paf->safi])
2711 return 0;
2712
2713 peer_af_announce_route (paf, 1);
2714 return 0;
2715 }
2716
2717 /*
2718 * bgp_announce_route
2719 *
2720 * *Triggers* announcement of routes of a given AFI/SAFI to a peer.
2721 */
2722 void
2723 bgp_announce_route (struct peer *peer, afi_t afi, safi_t safi)
2724 {
2725 struct peer_af *paf;
2726 struct update_subgroup *subgrp;
2727
2728 paf = peer_af_find (peer, afi, safi);
2729 if (!paf)
2730 return;
2731 subgrp = PAF_SUBGRP(paf);
2732
2733 /*
2734 * Ignore if subgroup doesn't exist (implies AF is not negotiated)
2735 * or a refresh has already been triggered.
2736 */
2737 if (!subgrp || paf->t_announce_route)
2738 return;
2739
2740 /*
2741 * Start a timer to stagger/delay the announce. This serves
2742 * two purposes - announcement can potentially be combined for
2743 * multiple peers and the announcement doesn't happen in the
2744 * vty context.
2745 */
2746 THREAD_TIMER_MSEC_ON (bm->master, paf->t_announce_route,
2747 bgp_announce_route_timer_expired, paf,
2748 (subgrp->peer_count == 1) ?
2749 BGP_ANNOUNCE_ROUTE_SHORT_DELAY_MS :
2750 BGP_ANNOUNCE_ROUTE_DELAY_MS);
2751 }
2752
2753 /*
2754 * Announce routes from all AF tables to a peer.
2755 *
2756 * This should ONLY be called when there is a need to refresh the
2757 * routes to the peer based on a policy change for this peer alone
2758 * or a route refresh request received from the peer.
2759 * The operation will result in splitting the peer from its existing
2760 * subgroups and putting it in new subgroups.
2761 */
2762 void
2763 bgp_announce_route_all (struct peer *peer)
2764 {
2765 afi_t afi;
2766 safi_t safi;
2767
2768 for (afi = AFI_IP; afi < AFI_MAX; afi++)
2769 for (safi = SAFI_UNICAST; safi < SAFI_MAX; safi++)
2770 bgp_announce_route (peer, afi, safi);
2771 }
2772
2773 static void
2774 bgp_soft_reconfig_table (struct peer *peer, afi_t afi, safi_t safi,
2775 struct bgp_table *table, struct prefix_rd *prd)
2776 {
2777 int ret;
2778 struct bgp_node *rn;
2779 struct bgp_adj_in *ain;
2780
2781 if (! table)
2782 table = peer->bgp->rib[afi][safi];
2783
2784 for (rn = bgp_table_top (table); rn; rn = bgp_route_next (rn))
2785 for (ain = rn->adj_in; ain; ain = ain->next)
2786 {
2787 if (ain->peer == peer)
2788 {
2789 struct bgp_info *ri = rn->info;
2790 u_char *tag = (ri && ri->extra) ? ri->extra->tag : NULL;
2791
2792 ret = bgp_update (peer, &rn->p, ain->addpath_rx_id, ain->attr,
2793 afi, safi, ZEBRA_ROUTE_BGP, BGP_ROUTE_NORMAL,
2794 prd, tag, 1);
2795
2796 if (ret < 0)
2797 {
2798 bgp_unlock_node (rn);
2799 return;
2800 }
2801 }
2802 }
2803 }
2804
2805 void
2806 bgp_soft_reconfig_in (struct peer *peer, afi_t afi, safi_t safi)
2807 {
2808 struct bgp_node *rn;
2809 struct bgp_table *table;
2810
2811 if (peer->status != Established)
2812 return;
2813
2814 if ((safi != SAFI_MPLS_VPN) && (safi != SAFI_ENCAP))
2815 bgp_soft_reconfig_table (peer, afi, safi, NULL, NULL);
2816 else
2817 for (rn = bgp_table_top (peer->bgp->rib[afi][safi]); rn;
2818 rn = bgp_route_next (rn))
2819 if ((table = rn->info) != NULL)
2820 {
2821 struct prefix_rd prd;
2822 prd.family = AF_UNSPEC;
2823 prd.prefixlen = 64;
2824 memcpy(&prd.val, rn->p.u.val, 8);
2825
2826 bgp_soft_reconfig_table (peer, afi, safi, table, &prd);
2827 }
2828 }
2829
2830
2831 struct bgp_clear_node_queue
2832 {
2833 struct bgp_node *rn;
2834 };
2835
2836 static wq_item_status
2837 bgp_clear_route_node (struct work_queue *wq, void *data)
2838 {
2839 struct bgp_clear_node_queue *cnq = data;
2840 struct bgp_node *rn = cnq->rn;
2841 struct peer *peer = wq->spec.data;
2842 struct bgp_info *ri;
2843 afi_t afi = bgp_node_table (rn)->afi;
2844 safi_t safi = bgp_node_table (rn)->safi;
2845
2846 assert (rn && peer);
2847
2848 /* It is possible that we have multiple paths for a prefix from a peer
2849 * if that peer is using AddPath.
2850 */
2851 for (ri = rn->info; ri; ri = ri->next)
2852 if (ri->peer == peer)
2853 {
2854 /* graceful restart STALE flag set. */
2855 if (CHECK_FLAG (peer->sflags, PEER_STATUS_NSF_WAIT)
2856 && peer->nsf[afi][safi]
2857 && ! CHECK_FLAG (ri->flags, BGP_INFO_STALE)
2858 && ! CHECK_FLAG (ri->flags, BGP_INFO_UNUSEABLE))
2859 bgp_info_set_flag (rn, ri, BGP_INFO_STALE);
2860 else
2861 bgp_rib_remove (rn, ri, peer, afi, safi);
2862 }
2863 return WQ_SUCCESS;
2864 }
2865
2866 static void
2867 bgp_clear_node_queue_del (struct work_queue *wq, void *data)
2868 {
2869 struct bgp_clear_node_queue *cnq = data;
2870 struct bgp_node *rn = cnq->rn;
2871 struct bgp_table *table = bgp_node_table (rn);
2872
2873 bgp_unlock_node (rn);
2874 bgp_table_unlock (table);
2875 XFREE (MTYPE_BGP_CLEAR_NODE_QUEUE, cnq);
2876 }
2877
2878 static void
2879 bgp_clear_node_complete (struct work_queue *wq)
2880 {
2881 struct peer *peer = wq->spec.data;
2882
2883 /* Tickle FSM to start moving again */
2884 BGP_EVENT_ADD (peer, Clearing_Completed);
2885
2886 peer_unlock (peer); /* bgp_clear_route */
2887 }
2888
2889 static void
2890 bgp_clear_node_queue_init (struct peer *peer)
2891 {
2892 char wname[sizeof("clear xxxx:xxxx:xxxx:xxxx:xxxx:xxxx:xxxx:xxxx")];
2893
2894 snprintf (wname, sizeof(wname), "clear %s", peer->host);
2895 #undef CLEAR_QUEUE_NAME_LEN
2896
2897 if ( (peer->clear_node_queue = work_queue_new (bm->master, wname)) == NULL)
2898 {
2899 zlog_err ("%s: Failed to allocate work queue", __func__);
2900 exit (1);
2901 }
2902 peer->clear_node_queue->spec.hold = 10;
2903 peer->clear_node_queue->spec.workfunc = &bgp_clear_route_node;
2904 peer->clear_node_queue->spec.del_item_data = &bgp_clear_node_queue_del;
2905 peer->clear_node_queue->spec.completion_func = &bgp_clear_node_complete;
2906 peer->clear_node_queue->spec.max_retries = 0;
2907
2908 /* we only 'lock' this peer reference when the queue is actually active */
2909 peer->clear_node_queue->spec.data = peer;
2910 }
2911
2912 static void
2913 bgp_clear_route_table (struct peer *peer, afi_t afi, safi_t safi,
2914 struct bgp_table *table)
2915 {
2916 struct bgp_node *rn;
2917
2918
2919 if (! table)
2920 table = peer->bgp->rib[afi][safi];
2921
2922 /* If still no table => afi/safi isn't configured at all or smth. */
2923 if (! table)
2924 return;
2925
2926 for (rn = bgp_table_top (table); rn; rn = bgp_route_next (rn))
2927 {
2928 struct bgp_info *ri;
2929 struct bgp_adj_in *ain;
2930 struct bgp_adj_in *ain_next;
2931
2932 /* XXX:TODO: This is suboptimal, every non-empty route_node is
2933 * queued for every clearing peer, regardless of whether it is
2934 * relevant to the peer at hand.
2935 *
2936 * Overview: There are 3 different indices which need to be
2937 * scrubbed, potentially, when a peer is removed:
2938 *
2939 * 1 peer's routes visible via the RIB (ie accepted routes)
2940 * 2 peer's routes visible by the (optional) peer's adj-in index
2941 * 3 other routes visible by the peer's adj-out index
2942 *
2943 * 3 there is no hurry in scrubbing, once the struct peer is
2944 * removed from bgp->peer, we could just GC such deleted peer's
2945 * adj-outs at our leisure.
2946 *
2947 * 1 and 2 must be 'scrubbed' in some way, at least made
2948 * invisible via RIB index before peer session is allowed to be
2949 * brought back up. So one needs to know when such a 'search' is
2950 * complete.
2951 *
2952 * Ideally:
2953 *
2954 * - there'd be a single global queue or a single RIB walker
2955 * - rather than tracking which route_nodes still need to be
2956 * examined on a peer basis, we'd track which peers still
2957 * aren't cleared
2958 *
2959 * Given that our per-peer prefix-counts now should be reliable,
2960 * this may actually be achievable. It doesn't seem to be a huge
2961 * problem at this time,
2962 *
2963 * It is possible that we have multiple paths for a prefix from a peer
2964 * if that peer is using AddPath.
2965 */
2966 ain = rn->adj_in;
2967 while (ain)
2968 {
2969 ain_next = ain->next;
2970
2971 if (ain->peer == peer)
2972 {
2973 bgp_adj_in_remove (rn, ain);
2974 bgp_unlock_node (rn);
2975 }
2976
2977 ain = ain_next;
2978 }
2979
2980 for (ri = rn->info; ri; ri = ri->next)
2981 if (ri->peer == peer)
2982 {
2983 struct bgp_clear_node_queue *cnq;
2984
2985 /* both unlocked in bgp_clear_node_queue_del */
2986 bgp_table_lock (bgp_node_table (rn));
2987 bgp_lock_node (rn);
2988 cnq = XCALLOC (MTYPE_BGP_CLEAR_NODE_QUEUE,
2989 sizeof (struct bgp_clear_node_queue));
2990 cnq->rn = rn;
2991 work_queue_add (peer->clear_node_queue, cnq);
2992 break;
2993 }
2994 }
2995 return;
2996 }
2997
2998 void
2999 bgp_clear_route (struct peer *peer, afi_t afi, safi_t safi)
3000 {
3001 struct bgp_node *rn;
3002 struct bgp_table *table;
3003
3004 if (peer->clear_node_queue == NULL)
3005 bgp_clear_node_queue_init (peer);
3006
3007 /* bgp_fsm.c keeps sessions in state Clearing, not transitioning to
3008 * Idle until it receives a Clearing_Completed event. This protects
3009 * against peers which flap faster than we can we clear, which could
3010 * lead to:
3011 *
3012 * a) race with routes from the new session being installed before
3013 * clear_route_node visits the node (to delete the route of that
3014 * peer)
3015 * b) resource exhaustion, clear_route_node likely leads to an entry
3016 * on the process_main queue. Fast-flapping could cause that queue
3017 * to grow and grow.
3018 */
3019
3020 /* lock peer in assumption that clear-node-queue will get nodes; if so,
3021 * the unlock will happen upon work-queue completion; other wise, the
3022 * unlock happens at the end of this function.
3023 */
3024 if (!peer->clear_node_queue->thread)
3025 peer_lock (peer);
3026
3027 if (safi != SAFI_MPLS_VPN && safi != SAFI_ENCAP)
3028 bgp_clear_route_table (peer, afi, safi, NULL);
3029 else
3030 for (rn = bgp_table_top (peer->bgp->rib[afi][safi]); rn;
3031 rn = bgp_route_next (rn))
3032 if ((table = rn->info) != NULL)
3033 bgp_clear_route_table (peer, afi, safi, table);
3034
3035 /* unlock if no nodes got added to the clear-node-queue. */
3036 if (!peer->clear_node_queue->thread)
3037 peer_unlock (peer);
3038
3039 }
3040
3041 void
3042 bgp_clear_route_all (struct peer *peer)
3043 {
3044 afi_t afi;
3045 safi_t safi;
3046
3047 for (afi = AFI_IP; afi < AFI_MAX; afi++)
3048 for (safi = SAFI_UNICAST; safi < SAFI_MAX; safi++)
3049 bgp_clear_route (peer, afi, safi);
3050 }
3051
3052 void
3053 bgp_clear_adj_in (struct peer *peer, afi_t afi, safi_t safi)
3054 {
3055 struct bgp_table *table;
3056 struct bgp_node *rn;
3057 struct bgp_adj_in *ain;
3058 struct bgp_adj_in *ain_next;
3059
3060 table = peer->bgp->rib[afi][safi];
3061
3062 /* It is possible that we have multiple paths for a prefix from a peer
3063 * if that peer is using AddPath.
3064 */
3065 for (rn = bgp_table_top (table); rn; rn = bgp_route_next (rn))
3066 {
3067 ain = rn->adj_in;
3068
3069 while (ain)
3070 {
3071 ain_next = ain->next;
3072
3073 if (ain->peer == peer)
3074 {
3075 bgp_adj_in_remove (rn, ain);
3076 bgp_unlock_node (rn);
3077 }
3078
3079 ain = ain_next;
3080 }
3081 }
3082 }
3083
3084 void
3085 bgp_clear_stale_route (struct peer *peer, afi_t afi, safi_t safi)
3086 {
3087 struct bgp_node *rn;
3088 struct bgp_info *ri;
3089 struct bgp_table *table;
3090
3091 table = peer->bgp->rib[afi][safi];
3092
3093 for (rn = bgp_table_top (table); rn; rn = bgp_route_next (rn))
3094 {
3095 for (ri = rn->info; ri; ri = ri->next)
3096 if (ri->peer == peer)
3097 {
3098 if (CHECK_FLAG (ri->flags, BGP_INFO_STALE))
3099 bgp_rib_remove (rn, ri, peer, afi, safi);
3100 break;
3101 }
3102 }
3103 }
3104
3105 static void
3106 bgp_cleanup_table(struct bgp_table *table, safi_t safi)
3107 {
3108 struct bgp_node *rn;
3109 struct bgp_info *ri;
3110 struct bgp_info *next;
3111
3112 for (rn = bgp_table_top (table); rn; rn = bgp_route_next (rn))
3113 for (ri = rn->info; ri; ri = next)
3114 {
3115 next = ri->next;
3116 if (CHECK_FLAG (ri->flags, BGP_INFO_SELECTED)
3117 && ri->type == ZEBRA_ROUTE_BGP
3118 && (ri->sub_type == BGP_ROUTE_NORMAL ||
3119 ri->sub_type == BGP_ROUTE_AGGREGATE))
3120 bgp_zebra_withdraw (&rn->p, ri, safi);
3121 }
3122 }
3123
3124 /* Delete all kernel routes. */
3125 void
3126 bgp_cleanup_routes (void)
3127 {
3128 struct bgp *bgp;
3129 struct listnode *node, *nnode;
3130 afi_t afi;
3131
3132 for (ALL_LIST_ELEMENTS (bm->bgp, node, nnode, bgp))
3133 {
3134 for (afi = AFI_IP; afi < AFI_MAX; ++afi)
3135 {
3136 struct bgp_node *rn;
3137
3138 bgp_cleanup_table(bgp->rib[afi][SAFI_UNICAST], SAFI_UNICAST);
3139
3140 /*
3141 * VPN and ENCAP tables are two-level (RD is top level)
3142 */
3143 for (rn = bgp_table_top(bgp->rib[afi][SAFI_MPLS_VPN]); rn;
3144 rn = bgp_route_next (rn))
3145 {
3146 if (rn->info)
3147 {
3148 bgp_cleanup_table((struct bgp_table *)(rn->info), SAFI_MPLS_VPN);
3149 bgp_table_finish ((struct bgp_table **)&(rn->info));
3150 rn->info = NULL;
3151 bgp_unlock_node(rn);
3152 }
3153 }
3154
3155 for (rn = bgp_table_top(bgp->rib[afi][SAFI_ENCAP]); rn;
3156 rn = bgp_route_next (rn))
3157 {
3158 if (rn->info)
3159 {
3160 bgp_cleanup_table((struct bgp_table *)(rn->info), SAFI_ENCAP);
3161 bgp_table_finish ((struct bgp_table **)&(rn->info));
3162 rn->info = NULL;
3163 bgp_unlock_node(rn);
3164 }
3165 }
3166 }
3167 }
3168 }
3169
3170 void
3171 bgp_reset (void)
3172 {
3173 vty_reset ();
3174 bgp_zclient_reset ();
3175 access_list_reset ();
3176 prefix_list_reset ();
3177 }
3178
3179 static int
3180 bgp_addpath_encode_rx (struct peer *peer, afi_t afi, safi_t safi)
3181 {
3182 return (CHECK_FLAG (peer->af_cap[afi][safi], PEER_CAP_ADDPATH_AF_RX_ADV) &&
3183 CHECK_FLAG (peer->af_cap[afi][safi], PEER_CAP_ADDPATH_AF_TX_RCV));
3184 }
3185
3186 /* Parse NLRI stream. Withdraw NLRI is recognized by NULL attr
3187 value. */
3188 int
3189 bgp_nlri_parse (struct peer *peer, struct attr *attr, struct bgp_nlri *packet)
3190 {
3191 u_char *pnt;
3192 u_char *lim;
3193 struct prefix p;
3194 int psize;
3195 int ret;
3196 afi_t afi;
3197 safi_t safi;
3198 int addpath_encoded;
3199 u_int32_t addpath_id;
3200
3201 /* Check peer status. */
3202 if (peer->status != Established)
3203 return 0;
3204
3205 pnt = packet->nlri;
3206 lim = pnt + packet->length;
3207 afi = packet->afi;
3208 safi = packet->safi;
3209 addpath_id = 0;
3210 addpath_encoded = bgp_addpath_encode_rx (peer, afi, safi);
3211
3212 for (; pnt < lim; pnt += psize)
3213 {
3214 /* Clear prefix structure. */
3215 memset (&p, 0, sizeof (struct prefix));
3216
3217 if (addpath_encoded)
3218 {
3219
3220 /* When packet overflow occurs return immediately. */
3221 if (pnt + BGP_ADDPATH_ID_LEN > lim)
3222 return -1;
3223
3224 addpath_id = ntohl(*((uint32_t*) pnt));
3225 pnt += BGP_ADDPATH_ID_LEN;
3226 }
3227
3228 /* Fetch prefix length. */
3229 p.prefixlen = *pnt++;
3230 p.family = afi2family (afi);
3231
3232 /* Already checked in nlri_sanity_check(). We do double check
3233 here. */
3234 if ((afi == AFI_IP && p.prefixlen > 32)
3235 || (afi == AFI_IP6 && p.prefixlen > 128))
3236 return -1;
3237
3238 /* Packet size overflow check. */
3239 psize = PSIZE (p.prefixlen);
3240
3241 /* When packet overflow occur return immediately. */
3242 if (pnt + psize > lim)
3243 return -1;
3244
3245 /* Fetch prefix from NLRI packet. */
3246 memcpy (&p.u.prefix, pnt, psize);
3247
3248 /* Check address. */
3249 if (afi == AFI_IP && safi == SAFI_UNICAST)
3250 {
3251 if (IN_CLASSD (ntohl (p.u.prefix4.s_addr)))
3252 {
3253 /*
3254 * From draft-ietf-idr-bgp4-22, Section 6.3:
3255 * If a BGP router receives an UPDATE message with a
3256 * semantically incorrect NLRI field, in which a prefix is
3257 * semantically incorrect (eg. an unexpected multicast IP
3258 * address), it should ignore the prefix.
3259 */
3260 zlog_err ("IPv4 unicast NLRI is multicast address %s",
3261 inet_ntoa (p.u.prefix4));
3262
3263 return -1;
3264 }
3265 }
3266
3267 #ifdef HAVE_IPV6
3268 /* Check address. */
3269 if (afi == AFI_IP6 && safi == SAFI_UNICAST)
3270 {
3271 if (IN6_IS_ADDR_LINKLOCAL (&p.u.prefix6))
3272 {
3273 char buf[BUFSIZ];
3274
3275 zlog_warn ("IPv6 link-local NLRI received %s ignore this NLRI",
3276 inet_ntop (AF_INET6, &p.u.prefix6, buf, BUFSIZ));
3277
3278 continue;
3279 }
3280 }
3281 #endif /* HAVE_IPV6 */
3282
3283 /* Normal process. */
3284 if (attr)
3285 ret = bgp_update (peer, &p, addpath_id, attr, afi, safi,
3286 ZEBRA_ROUTE_BGP, BGP_ROUTE_NORMAL, NULL, NULL, 0);
3287 else
3288 ret = bgp_withdraw (peer, &p, addpath_id, attr, afi, safi,
3289 ZEBRA_ROUTE_BGP, BGP_ROUTE_NORMAL, NULL, NULL);
3290
3291 /* Address family configuration mismatch or maximum-prefix count
3292 overflow. */
3293 if (ret < 0)
3294 return -1;
3295 }
3296
3297 /* Packet length consistency check. */
3298 if (pnt != lim)
3299 return -1;
3300
3301 return 0;
3302 }
3303
3304 /* NLRI encode syntax check routine. */
3305 int
3306 bgp_nlri_sanity_check (struct peer *peer, int afi, safi_t safi, u_char *pnt,
3307 bgp_size_t length, int *numpfx)
3308 {
3309 u_char *end;
3310 u_char prefixlen;
3311 int psize;
3312 int addpath_encoded;
3313
3314 *numpfx = 0;
3315 end = pnt + length;
3316 addpath_encoded = bgp_addpath_encode_rx (peer, afi, safi);
3317
3318 /* RFC1771 6.3 The NLRI field in the UPDATE message is checked for
3319 syntactic validity. If the field is syntactically incorrect,
3320 then the Error Subcode is set to Invalid Network Field. */
3321
3322 while (pnt < end)
3323 {
3324 int badlength;
3325
3326 /* If the NLRI is encoded using addpath then the first 4 bytes are
3327 * the addpath ID. */
3328 if (addpath_encoded)
3329 {
3330 if (pnt + BGP_ADDPATH_ID_LEN > end)
3331 {
3332 zlog_err ("%s [Error] Update packet error"
3333 " (prefix data addpath overflow)",
3334 peer->host);
3335 bgp_notify_send (peer, BGP_NOTIFY_UPDATE_ERR,
3336 BGP_NOTIFY_UPDATE_INVAL_NETWORK);
3337 return -1;
3338 }
3339 pnt += BGP_ADDPATH_ID_LEN;
3340 }
3341
3342 prefixlen = *pnt++;
3343
3344 /* Prefix length check. */
3345 badlength = 0;
3346 if (safi == SAFI_ENCAP) {
3347 if (prefixlen > 128)
3348 badlength = 1;
3349 } else {
3350 if ((afi == AFI_IP && prefixlen > 32) ||
3351 (afi == AFI_IP6 && prefixlen > 128)) {
3352
3353 badlength = 1;
3354 }
3355 }
3356 if (badlength)
3357 {
3358 zlog_err ("%s [Error] Update packet error (wrong prefix length %d)",
3359 peer->host, prefixlen);
3360 bgp_notify_send (peer, BGP_NOTIFY_UPDATE_ERR,
3361 BGP_NOTIFY_UPDATE_INVAL_NETWORK);
3362 return -1;
3363 }
3364
3365 /* Packet size overflow check. */
3366 psize = PSIZE (prefixlen);
3367
3368 if (pnt + psize > end)
3369 {
3370 zlog_err ("%s [Error] Update packet error"
3371 " (prefix data overflow prefix size is %d)",
3372 peer->host, psize);
3373 bgp_notify_send (peer, BGP_NOTIFY_UPDATE_ERR,
3374 BGP_NOTIFY_UPDATE_INVAL_NETWORK);
3375 return -1;
3376 }
3377
3378 pnt += psize;
3379 (*numpfx)++;
3380 }
3381
3382 /* Packet length consistency check. */
3383 if (pnt != end)
3384 {
3385 zlog_err ("%s [Error] Update packet error"
3386 " (prefix length mismatch with total length)",
3387 peer->host);
3388 bgp_notify_send (peer, BGP_NOTIFY_UPDATE_ERR,
3389 BGP_NOTIFY_UPDATE_INVAL_NETWORK);
3390 return -1;
3391 }
3392 return 0;
3393 }
3394
3395 static struct bgp_static *
3396 bgp_static_new (void)
3397 {
3398 return XCALLOC (MTYPE_BGP_STATIC, sizeof (struct bgp_static));
3399 }
3400
3401 static void
3402 bgp_static_free (struct bgp_static *bgp_static)
3403 {
3404 if (bgp_static->rmap.name)
3405 XFREE(MTYPE_ROUTE_MAP_NAME, bgp_static->rmap.name);
3406 XFREE (MTYPE_BGP_STATIC, bgp_static);
3407 }
3408
3409 static void
3410 bgp_static_update_main (struct bgp *bgp, struct prefix *p,
3411 struct bgp_static *bgp_static, afi_t afi, safi_t safi)
3412 {
3413 struct bgp_node *rn;
3414 struct bgp_info *ri;
3415 struct bgp_info *new;
3416 struct bgp_info info;
3417 struct attr attr;
3418 struct attr *attr_new;
3419 int ret;
3420
3421 assert (bgp_static);
3422 if (!bgp_static)
3423 return;
3424
3425 rn = bgp_afi_node_get (bgp->rib[afi][safi], afi, safi, p, NULL);
3426
3427 bgp_attr_default_set (&attr, BGP_ORIGIN_IGP);
3428
3429 attr.nexthop = bgp_static->igpnexthop;
3430 attr.med = bgp_static->igpmetric;
3431 attr.flag |= ATTR_FLAG_BIT (BGP_ATTR_MULTI_EXIT_DISC);
3432
3433 if (bgp_static->atomic)
3434 attr.flag |= ATTR_FLAG_BIT (BGP_ATTR_ATOMIC_AGGREGATE);
3435
3436 /* Apply route-map. */
3437 if (bgp_static->rmap.name)
3438 {
3439 struct attr attr_tmp = attr;
3440 info.peer = bgp->peer_self;
3441 info.attr = &attr_tmp;
3442
3443 SET_FLAG (bgp->peer_self->rmap_type, PEER_RMAP_TYPE_NETWORK);
3444
3445 ret = route_map_apply (bgp_static->rmap.map, p, RMAP_BGP, &info);
3446
3447 bgp->peer_self->rmap_type = 0;
3448
3449 if (ret == RMAP_DENYMATCH)
3450 {
3451 /* Free uninterned attribute. */
3452 bgp_attr_flush (&attr_tmp);
3453
3454 /* Unintern original. */
3455 aspath_unintern (&attr.aspath);
3456 bgp_attr_extra_free (&attr);
3457 bgp_static_withdraw (bgp, p, afi, safi);
3458 return;
3459 }
3460 attr_new = bgp_attr_intern (&attr_tmp);
3461 }
3462 else
3463 attr_new = bgp_attr_intern (&attr);
3464
3465 for (ri = rn->info; ri; ri = ri->next)
3466 if (ri->peer == bgp->peer_self && ri->type == ZEBRA_ROUTE_BGP
3467 && ri->sub_type == BGP_ROUTE_STATIC)
3468 break;
3469
3470 if (ri)
3471 {
3472 if (attrhash_cmp (ri->attr, attr_new) &&
3473 !CHECK_FLAG(ri->flags, BGP_INFO_REMOVED) &&
3474 !bgp_flag_check(bgp, BGP_FLAG_FORCE_STATIC_PROCESS))
3475 {
3476 bgp_unlock_node (rn);
3477 bgp_attr_unintern (&attr_new);
3478 aspath_unintern (&attr.aspath);
3479 bgp_attr_extra_free (&attr);
3480 return;
3481 }
3482 else
3483 {
3484 /* The attribute is changed. */
3485 bgp_info_set_flag (rn, ri, BGP_INFO_ATTR_CHANGED);
3486
3487 /* Rewrite BGP route information. */
3488 if (CHECK_FLAG(ri->flags, BGP_INFO_REMOVED))
3489 bgp_info_restore(rn, ri);
3490 else
3491 bgp_aggregate_decrement (bgp, p, ri, afi, safi);
3492 bgp_attr_unintern (&ri->attr);
3493 ri->attr = attr_new;
3494 ri->uptime = bgp_clock ();
3495
3496 /* Nexthop reachability check. */
3497 if (bgp_flag_check (bgp, BGP_FLAG_IMPORT_CHECK))
3498 {
3499 if (bgp_find_or_add_nexthop (bgp, afi, ri, NULL, 0))
3500 bgp_info_set_flag (rn, ri, BGP_INFO_VALID);
3501 else
3502 {
3503 if (BGP_DEBUG(nht, NHT))
3504 {
3505 char buf1[INET6_ADDRSTRLEN];
3506 inet_ntop(p->family, &p->u.prefix, buf1,
3507 INET6_ADDRSTRLEN);
3508 zlog_debug("%s(%s): Route not in table, not advertising",
3509 __FUNCTION__, buf1);
3510 }
3511 bgp_info_unset_flag (rn, ri, BGP_INFO_VALID);
3512 }
3513 }
3514 else
3515 {
3516 /* Delete the NHT structure if any, if we're toggling between
3517 * enabling/disabling import check. We deregister the route
3518 * from NHT to avoid overloading NHT and the process interaction
3519 */
3520 bgp_unlink_nexthop(ri);
3521 bgp_info_set_flag (rn, ri, BGP_INFO_VALID);
3522 }
3523 /* Process change. */
3524 bgp_aggregate_increment (bgp, p, ri, afi, safi);
3525 bgp_process (bgp, rn, afi, safi);
3526 bgp_unlock_node (rn);
3527 aspath_unintern (&attr.aspath);
3528 bgp_attr_extra_free (&attr);
3529 return;
3530 }
3531 }
3532
3533 /* Make new BGP info. */
3534 new = info_make(ZEBRA_ROUTE_BGP, BGP_ROUTE_STATIC, 0, bgp->peer_self, attr_new,
3535 rn);
3536 /* Nexthop reachability check. */
3537 if (bgp_flag_check (bgp, BGP_FLAG_IMPORT_CHECK))
3538 {
3539 if (bgp_find_or_add_nexthop (bgp, afi, new, NULL, 0))
3540 bgp_info_set_flag (rn, new, BGP_INFO_VALID);
3541 else
3542 {
3543 if (BGP_DEBUG(nht, NHT))
3544 {
3545 char buf1[INET6_ADDRSTRLEN];
3546 inet_ntop(p->family, &p->u.prefix, buf1,
3547 INET6_ADDRSTRLEN);
3548 zlog_debug("%s(%s): Route not in table, not advertising",
3549 __FUNCTION__, buf1);
3550 }
3551 bgp_info_unset_flag (rn, new, BGP_INFO_VALID);
3552 }
3553 }
3554 else
3555 {
3556 /* Delete the NHT structure if any, if we're toggling between
3557 * enabling/disabling import check. We deregister the route
3558 * from NHT to avoid overloading NHT and the process interaction
3559 */
3560 bgp_unlink_nexthop(new);
3561
3562 bgp_info_set_flag (rn, new, BGP_INFO_VALID);
3563 }
3564
3565 /* Aggregate address increment. */
3566 bgp_aggregate_increment (bgp, p, new, afi, safi);
3567
3568 /* Register new BGP information. */
3569 bgp_info_add (rn, new);
3570
3571 /* route_node_get lock */
3572 bgp_unlock_node (rn);
3573
3574 /* Process change. */
3575 bgp_process (bgp, rn, afi, safi);
3576
3577 /* Unintern original. */
3578 aspath_unintern (&attr.aspath);
3579 bgp_attr_extra_free (&attr);
3580 }
3581
3582 void
3583 bgp_static_update (struct bgp *bgp, struct prefix *p,
3584 struct bgp_static *bgp_static, afi_t afi, safi_t safi)
3585 {
3586 bgp_static_update_main (bgp, p, bgp_static, afi, safi);
3587 }
3588
3589 void
3590 bgp_static_withdraw (struct bgp *bgp, struct prefix *p, afi_t afi,
3591 safi_t safi)
3592 {
3593 struct bgp_node *rn;
3594 struct bgp_info *ri;
3595
3596 rn = bgp_afi_node_get (bgp->rib[afi][safi], afi, safi, p, NULL);
3597
3598 /* Check selected route and self inserted route. */
3599 for (ri = rn->info; ri; ri = ri->next)
3600 if (ri->peer == bgp->peer_self
3601 && ri->type == ZEBRA_ROUTE_BGP
3602 && ri->sub_type == BGP_ROUTE_STATIC)
3603 break;
3604
3605 /* Withdraw static BGP route from routing table. */
3606 if (ri)
3607 {
3608 bgp_aggregate_decrement (bgp, p, ri, afi, safi);
3609 bgp_unlink_nexthop(ri);
3610 bgp_info_delete (rn, ri);
3611 bgp_process (bgp, rn, afi, safi);
3612 }
3613
3614 /* Unlock bgp_node_lookup. */
3615 bgp_unlock_node (rn);
3616 }
3617
3618 /*
3619 * Used for SAFI_MPLS_VPN and SAFI_ENCAP
3620 */
3621 static void
3622 bgp_static_withdraw_safi (struct bgp *bgp, struct prefix *p, afi_t afi,
3623 safi_t safi, struct prefix_rd *prd, u_char *tag)
3624 {
3625 struct bgp_node *rn;
3626 struct bgp_info *ri;
3627
3628 rn = bgp_afi_node_get (bgp->rib[afi][safi], afi, safi, p, prd);
3629
3630 /* Check selected route and self inserted route. */
3631 for (ri = rn->info; ri; ri = ri->next)
3632 if (ri->peer == bgp->peer_self
3633 && ri->type == ZEBRA_ROUTE_BGP
3634 && ri->sub_type == BGP_ROUTE_STATIC)
3635 break;
3636
3637 /* Withdraw static BGP route from routing table. */
3638 if (ri)
3639 {
3640 bgp_aggregate_decrement (bgp, p, ri, afi, safi);
3641 bgp_info_delete (rn, ri);
3642 bgp_process (bgp, rn, afi, safi);
3643 }
3644
3645 /* Unlock bgp_node_lookup. */
3646 bgp_unlock_node (rn);
3647 }
3648
3649 static void
3650 bgp_static_update_safi (struct bgp *bgp, struct prefix *p,
3651 struct bgp_static *bgp_static, afi_t afi, safi_t safi)
3652 {
3653 struct bgp_node *rn;
3654 struct bgp_info *new;
3655 struct attr *attr_new;
3656 struct attr attr = { 0 };
3657 struct bgp_info *ri;
3658
3659 assert (bgp_static);
3660
3661 rn = bgp_afi_node_get (bgp->rib[afi][safi], afi, safi, p, &bgp_static->prd);
3662
3663 bgp_attr_default_set (&attr, BGP_ORIGIN_IGP);
3664
3665 attr.nexthop = bgp_static->igpnexthop;
3666 attr.med = bgp_static->igpmetric;
3667 attr.flag |= ATTR_FLAG_BIT (BGP_ATTR_MULTI_EXIT_DISC);
3668
3669 /* Apply route-map. */
3670 if (bgp_static->rmap.name)
3671 {
3672 struct attr attr_tmp = attr;
3673 struct bgp_info info;
3674 int ret;
3675
3676 info.peer = bgp->peer_self;
3677 info.attr = &attr_tmp;
3678
3679 SET_FLAG (bgp->peer_self->rmap_type, PEER_RMAP_TYPE_NETWORK);
3680
3681 ret = route_map_apply (bgp_static->rmap.map, p, RMAP_BGP, &info);
3682
3683 bgp->peer_self->rmap_type = 0;
3684
3685 if (ret == RMAP_DENYMATCH)
3686 {
3687 /* Free uninterned attribute. */
3688 bgp_attr_flush (&attr_tmp);
3689
3690 /* Unintern original. */
3691 aspath_unintern (&attr.aspath);
3692 bgp_attr_extra_free (&attr);
3693 bgp_static_withdraw_safi (bgp, p, afi, safi, &bgp_static->prd,
3694 bgp_static->tag);
3695 return;
3696 }
3697
3698 attr_new = bgp_attr_intern (&attr_tmp);
3699 }
3700 else
3701 {
3702 attr_new = bgp_attr_intern (&attr);
3703 }
3704
3705 for (ri = rn->info; ri; ri = ri->next)
3706 if (ri->peer == bgp->peer_self && ri->type == ZEBRA_ROUTE_BGP
3707 && ri->sub_type == BGP_ROUTE_STATIC)
3708 break;
3709
3710 if (ri)
3711 {
3712 if (attrhash_cmp (ri->attr, attr_new) &&
3713 !CHECK_FLAG(ri->flags, BGP_INFO_REMOVED))
3714 {
3715 bgp_unlock_node (rn);
3716 bgp_attr_unintern (&attr_new);
3717 aspath_unintern (&attr.aspath);
3718 bgp_attr_extra_free (&attr);
3719 return;
3720 }
3721 else
3722 {
3723 /* The attribute is changed. */
3724 bgp_info_set_flag (rn, ri, BGP_INFO_ATTR_CHANGED);
3725
3726 /* Rewrite BGP route information. */
3727 if (CHECK_FLAG(ri->flags, BGP_INFO_REMOVED))
3728 bgp_info_restore(rn, ri);
3729 else
3730 bgp_aggregate_decrement (bgp, p, ri, afi, safi);
3731 bgp_attr_unintern (&ri->attr);
3732 ri->attr = attr_new;
3733 ri->uptime = bgp_clock ();
3734
3735 /* Process change. */
3736 bgp_aggregate_increment (bgp, p, ri, afi, safi);
3737 bgp_process (bgp, rn, afi, safi);
3738 bgp_unlock_node (rn);
3739 aspath_unintern (&attr.aspath);
3740 bgp_attr_extra_free (&attr);
3741 return;
3742 }
3743 }
3744
3745
3746 /* Make new BGP info. */
3747 new = info_make(ZEBRA_ROUTE_BGP, BGP_ROUTE_STATIC, 0, bgp->peer_self, attr_new,
3748 rn);
3749 SET_FLAG (new->flags, BGP_INFO_VALID);
3750 new->extra = bgp_info_extra_new();
3751 memcpy (new->extra->tag, bgp_static->tag, 3);
3752
3753 /* Aggregate address increment. */
3754 bgp_aggregate_increment (bgp, p, new, afi, safi);
3755
3756 /* Register new BGP information. */
3757 bgp_info_add (rn, new);
3758
3759 /* route_node_get lock */
3760 bgp_unlock_node (rn);
3761
3762 /* Process change. */
3763 bgp_process (bgp, rn, afi, safi);
3764
3765 /* Unintern original. */
3766 aspath_unintern (&attr.aspath);
3767 bgp_attr_extra_free (&attr);
3768 }
3769
3770 /* Configure static BGP network. When user don't run zebra, static
3771 route should be installed as valid. */
3772 static int
3773 bgp_static_set (struct vty *vty, struct bgp *bgp, const char *ip_str,
3774 afi_t afi, safi_t safi, const char *rmap, int backdoor)
3775 {
3776 int ret;
3777 struct prefix p;
3778 struct bgp_static *bgp_static;
3779 struct bgp_node *rn;
3780 u_char need_update = 0;
3781
3782 /* Convert IP prefix string to struct prefix. */
3783 ret = str2prefix (ip_str, &p);
3784 if (! ret)
3785 {
3786 vty_out (vty, "%% Malformed prefix%s", VTY_NEWLINE);
3787 return CMD_WARNING;
3788 }
3789 #ifdef HAVE_IPV6
3790 if (afi == AFI_IP6 && IN6_IS_ADDR_LINKLOCAL (&p.u.prefix6))
3791 {
3792 vty_out (vty, "%% Malformed prefix (link-local address)%s",
3793 VTY_NEWLINE);
3794 return CMD_WARNING;
3795 }
3796 #endif /* HAVE_IPV6 */
3797
3798 apply_mask (&p);
3799
3800 /* Set BGP static route configuration. */
3801 rn = bgp_node_get (bgp->route[afi][safi], &p);
3802
3803 if (rn->info)
3804 {
3805 /* Configuration change. */
3806 bgp_static = rn->info;
3807
3808 /* Check previous routes are installed into BGP. */
3809 if (bgp_static->valid && bgp_static->backdoor != backdoor)
3810 need_update = 1;
3811
3812 bgp_static->backdoor = backdoor;
3813
3814 if (rmap)
3815 {
3816 if (bgp_static->rmap.name)
3817 XFREE(MTYPE_ROUTE_MAP_NAME, bgp_static->rmap.name);
3818 bgp_static->rmap.name = XSTRDUP(MTYPE_ROUTE_MAP_NAME, rmap);
3819 bgp_static->rmap.map = route_map_lookup_by_name (rmap);
3820 }
3821 else
3822 {
3823 if (bgp_static->rmap.name)
3824 XFREE(MTYPE_ROUTE_MAP_NAME, bgp_static->rmap.name);
3825 bgp_static->rmap.name = NULL;
3826 bgp_static->rmap.map = NULL;
3827 bgp_static->valid = 0;
3828 }
3829 bgp_unlock_node (rn);
3830 }
3831 else
3832 {
3833 /* New configuration. */
3834 bgp_static = bgp_static_new ();
3835 bgp_static->backdoor = backdoor;
3836 bgp_static->valid = 0;
3837 bgp_static->igpmetric = 0;
3838 bgp_static->igpnexthop.s_addr = 0;
3839
3840 if (rmap)
3841 {
3842 if (bgp_static->rmap.name)
3843 XFREE(MTYPE_ROUTE_MAP_NAME, bgp_static->rmap.name);
3844 bgp_static->rmap.name = XSTRDUP(MTYPE_ROUTE_MAP_NAME, rmap);
3845 bgp_static->rmap.map = route_map_lookup_by_name (rmap);
3846 }
3847 rn->info = bgp_static;
3848 }
3849
3850 bgp_static->valid = 1;
3851 if (need_update)
3852 bgp_static_withdraw (bgp, &p, afi, safi);
3853
3854 if (! bgp_static->backdoor)
3855 bgp_static_update (bgp, &p, bgp_static, afi, safi);
3856
3857 return CMD_SUCCESS;
3858 }
3859
3860 /* Configure static BGP network. */
3861 static int
3862 bgp_static_unset (struct vty *vty, struct bgp *bgp, const char *ip_str,
3863 afi_t afi, safi_t safi)
3864 {
3865 int ret;
3866 struct prefix p;
3867 struct bgp_static *bgp_static;
3868 struct bgp_node *rn;
3869
3870 /* Convert IP prefix string to struct prefix. */
3871 ret = str2prefix (ip_str, &p);
3872 if (! ret)
3873 {
3874 vty_out (vty, "%% Malformed prefix%s", VTY_NEWLINE);
3875 return CMD_WARNING;
3876 }
3877 #ifdef HAVE_IPV6
3878 if (afi == AFI_IP6 && IN6_IS_ADDR_LINKLOCAL (&p.u.prefix6))
3879 {
3880 vty_out (vty, "%% Malformed prefix (link-local address)%s",
3881 VTY_NEWLINE);
3882 return CMD_WARNING;
3883 }
3884 #endif /* HAVE_IPV6 */
3885
3886 apply_mask (&p);
3887
3888 rn = bgp_node_lookup (bgp->route[afi][safi], &p);
3889 if (! rn)
3890 {
3891 vty_out (vty, "%% Can't find specified static route configuration.%s",
3892 VTY_NEWLINE);
3893 return CMD_WARNING;
3894 }
3895
3896 bgp_static = rn->info;
3897
3898 /* Update BGP RIB. */
3899 if (! bgp_static->backdoor)
3900 bgp_static_withdraw (bgp, &p, afi, safi);
3901
3902 /* Clear configuration. */
3903 bgp_static_free (bgp_static);
3904 rn->info = NULL;
3905 bgp_unlock_node (rn);
3906 bgp_unlock_node (rn);
3907
3908 return CMD_SUCCESS;
3909 }
3910
3911 void
3912 bgp_static_add (struct bgp *bgp)
3913 {
3914 afi_t afi;
3915 safi_t safi;
3916 struct bgp_node *rn;
3917 struct bgp_node *rm;
3918 struct bgp_table *table;
3919 struct bgp_static *bgp_static;
3920
3921 for (afi = AFI_IP; afi < AFI_MAX; afi++)
3922 for (safi = SAFI_UNICAST; safi < SAFI_MAX; safi++)
3923 for (rn = bgp_table_top (bgp->route[afi][safi]); rn; rn = bgp_route_next (rn))
3924 if (rn->info != NULL)
3925 {
3926 if (safi == SAFI_MPLS_VPN)
3927 {
3928 table = rn->info;
3929
3930 for (rm = bgp_table_top (table); rm; rm = bgp_route_next (rm))
3931 {
3932 bgp_static = rn->info;
3933 bgp_static_update_safi (bgp, &rm->p, bgp_static, afi, safi);
3934 }
3935 }
3936 else
3937 {
3938 bgp_static_update (bgp, &rn->p, rn->info, afi, safi);
3939 }
3940 }
3941 }
3942
3943 /* Called from bgp_delete(). Delete all static routes from the BGP
3944 instance. */
3945 void
3946 bgp_static_delete (struct bgp *bgp)
3947 {
3948 afi_t afi;
3949 safi_t safi;
3950 struct bgp_node *rn;
3951 struct bgp_node *rm;
3952 struct bgp_table *table;
3953 struct bgp_static *bgp_static;
3954
3955 for (afi = AFI_IP; afi < AFI_MAX; afi++)
3956 for (safi = SAFI_UNICAST; safi < SAFI_MAX; safi++)
3957 for (rn = bgp_table_top (bgp->route[afi][safi]); rn; rn = bgp_route_next (rn))
3958 if (rn->info != NULL)
3959 {
3960 if ((safi == SAFI_MPLS_VPN) || (safi == SAFI_ENCAP))
3961 {
3962 table = rn->info;
3963
3964 for (rm = bgp_table_top (table); rm; rm = bgp_route_next (rm))
3965 {
3966 bgp_static = rn->info;
3967 bgp_static_withdraw_safi (bgp, &rm->p,
3968 AFI_IP, safi,
3969 (struct prefix_rd *)&rn->p,
3970 bgp_static->tag);
3971 bgp_static_free (bgp_static);
3972 rn->info = NULL;
3973 bgp_unlock_node (rn);
3974 }
3975 }
3976 else
3977 {
3978 bgp_static = rn->info;
3979 bgp_static_withdraw (bgp, &rn->p, afi, safi);
3980 bgp_static_free (bgp_static);
3981 rn->info = NULL;
3982 bgp_unlock_node (rn);
3983 }
3984 }
3985 }
3986
3987 void
3988 bgp_static_redo_import_check (struct bgp *bgp)
3989 {
3990 afi_t afi;
3991 safi_t safi;
3992 struct bgp_node *rn;
3993 struct bgp_static *bgp_static;
3994
3995 /* Use this flag to force reprocessing of the route */
3996 bgp_flag_set(bgp, BGP_FLAG_FORCE_STATIC_PROCESS);
3997 for (afi = AFI_IP; afi < AFI_MAX; afi++)
3998 for (safi = SAFI_UNICAST; safi < SAFI_MAX; safi++)
3999 for (rn = bgp_table_top (bgp->route[afi][safi]); rn; rn = bgp_route_next (rn))
4000 if (rn->info != NULL)
4001 {
4002 bgp_static = rn->info;
4003 bgp_static_update (bgp, &rn->p, bgp_static, afi, safi);
4004 }
4005 bgp_flag_unset(bgp, BGP_FLAG_FORCE_STATIC_PROCESS);
4006 }
4007
4008 static void
4009 bgp_purge_af_static_redist_routes (struct bgp *bgp, afi_t afi, safi_t safi)
4010 {
4011 struct bgp_table *table;
4012 struct bgp_node *rn;
4013 struct bgp_info *ri;
4014
4015 table = bgp->rib[afi][safi];
4016 for (rn = bgp_table_top (table); rn; rn = bgp_route_next (rn))
4017 {
4018 for (ri = rn->info; ri; ri = ri->next)
4019 {
4020 if (ri->peer == bgp->peer_self &&
4021 ((ri->type == ZEBRA_ROUTE_BGP &&
4022 ri->sub_type == BGP_ROUTE_STATIC) ||
4023 (ri->type != ZEBRA_ROUTE_BGP &&
4024 ri->sub_type == BGP_ROUTE_REDISTRIBUTE)))
4025 {
4026 bgp_aggregate_decrement (bgp, &rn->p, ri, afi, safi);
4027 bgp_unlink_nexthop(ri);
4028 bgp_info_delete (rn, ri);
4029 bgp_process (bgp, rn, afi, safi);
4030 }
4031 }
4032 }
4033 }
4034
4035 /*
4036 * Purge all networks and redistributed routes from routing table.
4037 * Invoked upon the instance going down.
4038 */
4039 void
4040 bgp_purge_static_redist_routes (struct bgp *bgp)
4041 {
4042 afi_t afi;
4043 safi_t safi;
4044
4045 for (afi = AFI_IP; afi < AFI_MAX; afi++)
4046 for (safi = SAFI_UNICAST; safi < SAFI_MAX; safi++)
4047 bgp_purge_af_static_redist_routes (bgp, afi, safi);
4048 }
4049
4050 /*
4051 * gpz 110624
4052 * Currently this is used to set static routes for VPN and ENCAP.
4053 * I think it can probably be factored with bgp_static_set.
4054 */
4055 int
4056 bgp_static_set_safi (safi_t safi, struct vty *vty, const char *ip_str,
4057 const char *rd_str, const char *tag_str,
4058 const char *rmap_str)
4059 {
4060 int ret;
4061 struct prefix p;
4062 struct prefix_rd prd;
4063 struct bgp *bgp;
4064 struct bgp_node *prn;
4065 struct bgp_node *rn;
4066 struct bgp_table *table;
4067 struct bgp_static *bgp_static;
4068 u_char tag[3];
4069
4070 bgp = vty->index;
4071
4072 ret = str2prefix (ip_str, &p);
4073 if (! ret)
4074 {
4075 vty_out (vty, "%% Malformed prefix%s", VTY_NEWLINE);
4076 return CMD_WARNING;
4077 }
4078 apply_mask (&p);
4079
4080 ret = str2prefix_rd (rd_str, &prd);
4081 if (! ret)
4082 {
4083 vty_out (vty, "%% Malformed rd%s", VTY_NEWLINE);
4084 return CMD_WARNING;
4085 }
4086
4087 ret = str2tag (tag_str, tag);
4088 if (! ret)
4089 {
4090 vty_out (vty, "%% Malformed tag%s", VTY_NEWLINE);
4091 return CMD_WARNING;
4092 }
4093
4094 prn = bgp_node_get (bgp->route[AFI_IP][safi],
4095 (struct prefix *)&prd);
4096 if (prn->info == NULL)
4097 prn->info = bgp_table_init (AFI_IP, safi);
4098 else
4099 bgp_unlock_node (prn);
4100 table = prn->info;
4101
4102 rn = bgp_node_get (table, &p);
4103
4104 if (rn->info)
4105 {
4106 vty_out (vty, "%% Same network configuration exists%s", VTY_NEWLINE);
4107 bgp_unlock_node (rn);
4108 }
4109 else
4110 {
4111 /* New configuration. */
4112 bgp_static = bgp_static_new ();
4113 bgp_static->backdoor = 0;
4114 bgp_static->valid = 0;
4115 bgp_static->igpmetric = 0;
4116 bgp_static->igpnexthop.s_addr = 0;
4117 memcpy(bgp_static->tag, tag, 3);
4118 bgp_static->prd = prd;
4119
4120 if (rmap_str)
4121 {
4122 if (bgp_static->rmap.name)
4123 free (bgp_static->rmap.name);
4124 bgp_static->rmap.name = strdup (rmap_str);
4125 bgp_static->rmap.map = route_map_lookup_by_name (rmap_str);
4126 }
4127 rn->info = bgp_static;
4128
4129 bgp_static->valid = 1;
4130 bgp_static_update_safi (bgp, &p, bgp_static, AFI_IP, safi);
4131 }
4132
4133 return CMD_SUCCESS;
4134 }
4135
4136 /* Configure static BGP network. */
4137 int
4138 bgp_static_unset_safi(safi_t safi, struct vty *vty, const char *ip_str,
4139 const char *rd_str, const char *tag_str)
4140 {
4141 int ret;
4142 struct bgp *bgp;
4143 struct prefix p;
4144 struct prefix_rd prd;
4145 struct bgp_node *prn;
4146 struct bgp_node *rn;
4147 struct bgp_table *table;
4148 struct bgp_static *bgp_static;
4149 u_char tag[3];
4150
4151 bgp = vty->index;
4152
4153 /* Convert IP prefix string to struct prefix. */
4154 ret = str2prefix (ip_str, &p);
4155 if (! ret)
4156 {
4157 vty_out (vty, "%% Malformed prefix%s", VTY_NEWLINE);
4158 return CMD_WARNING;
4159 }
4160 apply_mask (&p);
4161
4162 ret = str2prefix_rd (rd_str, &prd);
4163 if (! ret)
4164 {
4165 vty_out (vty, "%% Malformed rd%s", VTY_NEWLINE);
4166 return CMD_WARNING;
4167 }
4168
4169 ret = str2tag (tag_str, tag);
4170 if (! ret)
4171 {
4172 vty_out (vty, "%% Malformed tag%s", VTY_NEWLINE);
4173 return CMD_WARNING;
4174 }
4175
4176 prn = bgp_node_get (bgp->route[AFI_IP][safi],
4177 (struct prefix *)&prd);
4178 if (prn->info == NULL)
4179 prn->info = bgp_table_init (AFI_IP, safi);
4180 else
4181 bgp_unlock_node (prn);
4182 table = prn->info;
4183
4184 rn = bgp_node_lookup (table, &p);
4185
4186 if (rn)
4187 {
4188 bgp_static_withdraw_safi (bgp, &p, AFI_IP, safi, &prd, tag);
4189
4190 bgp_static = rn->info;
4191 bgp_static_free (bgp_static);
4192 rn->info = NULL;
4193 bgp_unlock_node (rn);
4194 bgp_unlock_node (rn);
4195 }
4196 else
4197 vty_out (vty, "%% Can't find the route%s", VTY_NEWLINE);
4198
4199 return CMD_SUCCESS;
4200 }
4201
4202 static int
4203 bgp_table_map_set (struct vty *vty, struct bgp *bgp, afi_t afi, safi_t safi,
4204 const char *rmap_name)
4205 {
4206 struct bgp_rmap *rmap;
4207
4208 rmap = &bgp->table_map[afi][safi];
4209 if (rmap_name)
4210 {
4211 if (rmap->name)
4212 XFREE(MTYPE_ROUTE_MAP_NAME, rmap->name);
4213 rmap->name = XSTRDUP(MTYPE_ROUTE_MAP_NAME, rmap_name);
4214 rmap->map = route_map_lookup_by_name (rmap_name);
4215 }
4216 else
4217 {
4218 if (rmap->name)
4219 XFREE(MTYPE_ROUTE_MAP_NAME, rmap->name);
4220 rmap->name = NULL;
4221 rmap->map = NULL;
4222 }
4223
4224 bgp_zebra_announce_table(bgp, afi, safi);
4225
4226 return CMD_SUCCESS;
4227 }
4228
4229 static int
4230 bgp_table_map_unset (struct vty *vty, struct bgp *bgp, afi_t afi, safi_t safi,
4231 const char *rmap_name)
4232 {
4233 struct bgp_rmap *rmap;
4234
4235 rmap = &bgp->table_map[afi][safi];
4236 if (rmap->name)
4237 XFREE(MTYPE_ROUTE_MAP_NAME, rmap->name);
4238 rmap->name = NULL;
4239 rmap->map = NULL;
4240
4241 bgp_zebra_announce_table(bgp, afi, safi);
4242
4243 return CMD_SUCCESS;
4244 }
4245
4246 int
4247 bgp_config_write_table_map (struct vty *vty, struct bgp *bgp, afi_t afi,
4248 safi_t safi, int *write)
4249 {
4250 if (bgp->table_map[afi][safi].name)
4251 {
4252 bgp_config_write_family_header (vty, afi, safi, write);
4253 vty_out (vty, " table-map %s%s",
4254 bgp->table_map[afi][safi].name, VTY_NEWLINE);
4255 }
4256
4257 return 0;
4258 }
4259
4260
4261 DEFUN (bgp_table_map,
4262 bgp_table_map_cmd,
4263 "table-map WORD",
4264 "BGP table to RIB route download filter\n"
4265 "Name of the route map\n")
4266 {
4267 int idx_word = 1;
4268 return bgp_table_map_set (vty, vty->index,
4269 bgp_node_afi (vty), bgp_node_safi (vty), argv[idx_word]->arg);
4270 }
4271 DEFUN (no_bgp_table_map,
4272 no_bgp_table_map_cmd,
4273 "no table-map WORD",
4274 "BGP table to RIB route download filter\n"
4275 "Name of the route map\n")
4276 {
4277 int idx_word = 2;
4278 return bgp_table_map_unset (vty, vty->index,
4279 bgp_node_afi (vty), bgp_node_safi (vty), argv[idx_word]->arg);
4280 }
4281
4282 DEFUN (bgp_network,
4283 bgp_network_cmd,
4284 "network A.B.C.D/M",
4285 "Specify a network to announce via BGP\n"
4286 "IP prefix <network>/<length>, e.g., 35.0.0.0/8\n")
4287 {
4288 int idx_ipv4_prefixlen = 1;
4289 return bgp_static_set (vty, vty->index, argv[idx_ipv4_prefixlen]->arg,
4290 AFI_IP, bgp_node_safi (vty), NULL, 0);
4291 }
4292
4293 DEFUN (bgp_network_route_map,
4294 bgp_network_route_map_cmd,
4295 "network A.B.C.D/M route-map WORD",
4296 "Specify a network to announce via BGP\n"
4297 "IP prefix <network>/<length>, e.g., 35.0.0.0/8\n"
4298 "Route-map to modify the attributes\n"
4299 "Name of the route map\n")
4300 {
4301 int idx_ipv4_prefixlen = 1;
4302 int idx_word = 3;
4303 return bgp_static_set (vty, vty->index, argv[idx_ipv4_prefixlen]->arg,
4304 AFI_IP, bgp_node_safi (vty), argv[idx_word]->arg, 0);
4305 }
4306
4307 DEFUN (bgp_network_backdoor,
4308 bgp_network_backdoor_cmd,
4309 "network A.B.C.D/M backdoor",
4310 "Specify a network to announce via BGP\n"
4311 "IP prefix <network>/<length>, e.g., 35.0.0.0/8\n"
4312 "Specify a BGP backdoor route\n")
4313 {
4314 int idx_ipv4_prefixlen = 1;
4315 return bgp_static_set (vty, vty->index, argv[idx_ipv4_prefixlen]->arg, AFI_IP, SAFI_UNICAST,
4316 NULL, 1);
4317 }
4318
4319 DEFUN (bgp_network_mask,
4320 bgp_network_mask_cmd,
4321 "network A.B.C.D mask A.B.C.D",
4322 "Specify a network to announce via BGP\n"
4323 "Network number\n"
4324 "Network mask\n"
4325 "Network mask\n")
4326 {
4327 int idx_ipv4 = 1;
4328 int idx_ipv4_2 = 3;
4329 int ret;
4330 char prefix_str[BUFSIZ];
4331
4332 ret = netmask_str2prefix_str (argv[idx_ipv4]->arg, argv[idx_ipv4_2]->arg, prefix_str);
4333 if (! ret)
4334 {
4335 vty_out (vty, "%% Inconsistent address and mask%s", VTY_NEWLINE);
4336 return CMD_WARNING;
4337 }
4338
4339 return bgp_static_set (vty, vty->index, prefix_str,
4340 AFI_IP, bgp_node_safi (vty), NULL, 0);
4341 }
4342
4343 DEFUN (bgp_network_mask_route_map,
4344 bgp_network_mask_route_map_cmd,
4345 "network A.B.C.D mask A.B.C.D route-map WORD",
4346 "Specify a network to announce via BGP\n"
4347 "Network number\n"
4348 "Network mask\n"
4349 "Network mask\n"
4350 "Route-map to modify the attributes\n"
4351 "Name of the route map\n")
4352 {
4353 int idx_ipv4 = 1;
4354 int idx_ipv4_2 = 3;
4355 int idx_word = 5;
4356 int ret;
4357 char prefix_str[BUFSIZ];
4358
4359 ret = netmask_str2prefix_str (argv[idx_ipv4]->arg, argv[idx_ipv4_2]->arg, prefix_str);
4360 if (! ret)
4361 {
4362 vty_out (vty, "%% Inconsistent address and mask%s", VTY_NEWLINE);
4363 return CMD_WARNING;
4364 }
4365
4366 return bgp_static_set (vty, vty->index, prefix_str,
4367 AFI_IP, bgp_node_safi (vty), argv[idx_word]->arg, 0);
4368 }
4369
4370 DEFUN (bgp_network_mask_backdoor,
4371 bgp_network_mask_backdoor_cmd,
4372 "network A.B.C.D mask A.B.C.D backdoor",
4373 "Specify a network to announce via BGP\n"
4374 "Network number\n"
4375 "Network mask\n"
4376 "Network mask\n"
4377 "Specify a BGP backdoor route\n")
4378 {
4379 int idx_ipv4 = 1;
4380 int idx_ipv4_2 = 3;
4381 int ret;
4382 char prefix_str[BUFSIZ];
4383
4384 ret = netmask_str2prefix_str (argv[idx_ipv4]->arg, argv[idx_ipv4_2]->arg, prefix_str);
4385 if (! ret)
4386 {
4387 vty_out (vty, "%% Inconsistent address and mask%s", VTY_NEWLINE);
4388 return CMD_WARNING;
4389 }
4390
4391 return bgp_static_set (vty, vty->index, prefix_str, AFI_IP, SAFI_UNICAST,
4392 NULL, 1);
4393 }
4394
4395 DEFUN (bgp_network_mask_natural,
4396 bgp_network_mask_natural_cmd,
4397 "network A.B.C.D",
4398 "Specify a network to announce via BGP\n"
4399 "Network number\n")
4400 {
4401 int idx_ipv4 = 1;
4402 int ret;
4403 char prefix_str[BUFSIZ];
4404
4405 ret = netmask_str2prefix_str (argv[idx_ipv4]->arg, NULL, prefix_str);
4406 if (! ret)
4407 {
4408 vty_out (vty, "%% Inconsistent address and mask%s", VTY_NEWLINE);
4409 return CMD_WARNING;
4410 }
4411
4412 return bgp_static_set (vty, vty->index, prefix_str,
4413 AFI_IP, bgp_node_safi (vty), NULL, 0);
4414 }
4415
4416 DEFUN (bgp_network_mask_natural_route_map,
4417 bgp_network_mask_natural_route_map_cmd,
4418 "network A.B.C.D route-map WORD",
4419 "Specify a network to announce via BGP\n"
4420 "Network number\n"
4421 "Route-map to modify the attributes\n"
4422 "Name of the route map\n")
4423 {
4424 int idx_ipv4 = 1;
4425 int idx_word = 3;
4426 int ret;
4427 char prefix_str[BUFSIZ];
4428
4429 ret = netmask_str2prefix_str (argv[idx_ipv4]->arg, NULL, prefix_str);
4430 if (! ret)
4431 {
4432 vty_out (vty, "%% Inconsistent address and mask%s", VTY_NEWLINE);
4433 return CMD_WARNING;
4434 }
4435
4436 return bgp_static_set (vty, vty->index, prefix_str,
4437 AFI_IP, bgp_node_safi (vty), argv[idx_word]->arg, 0);
4438 }
4439
4440 DEFUN (bgp_network_mask_natural_backdoor,
4441 bgp_network_mask_natural_backdoor_cmd,
4442 "network A.B.C.D backdoor",
4443 "Specify a network to announce via BGP\n"
4444 "Network number\n"
4445 "Specify a BGP backdoor route\n")
4446 {
4447 int idx_ipv4 = 1;
4448 int ret;
4449 char prefix_str[BUFSIZ];
4450
4451 ret = netmask_str2prefix_str (argv[idx_ipv4]->arg, NULL, prefix_str);
4452 if (! ret)
4453 {
4454 vty_out (vty, "%% Inconsistent address and mask%s", VTY_NEWLINE);
4455 return CMD_WARNING;
4456 }
4457
4458 return bgp_static_set (vty, vty->index, prefix_str, AFI_IP, SAFI_UNICAST,
4459 NULL, 1);
4460 }
4461
4462 /*
4463 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
4464 * "no network A.B.C.D/M route-map WORD",
4465 * NO_STR
4466 * "Specify a network to announce via BGP\n"
4467 * "IP prefix <network>/<length>, e.g., 35.0.0.0/8\n"
4468 * "Route-map to modify the attributes\n"
4469 * "Name of the route map\n"
4470 *
4471 * "no network A.B.C.D/M backdoor",
4472 * NO_STR
4473 * "Specify a network to announce via BGP\n"
4474 * "IP prefix <network>/<length>, e.g., 35.0.0.0/8\n"
4475 * "Specify a BGP backdoor route\n"
4476 *
4477 */
4478 DEFUN (no_bgp_network,
4479 no_bgp_network_cmd,
4480 "no network A.B.C.D/M",
4481 NO_STR
4482 "Specify a network to announce via BGP\n"
4483 "IP prefix <network>/<length>, e.g., 35.0.0.0/8\n")
4484 {
4485 int idx_ipv4_prefixlen = 2;
4486 return bgp_static_unset (vty, vty->index, argv[idx_ipv4_prefixlen]->arg, AFI_IP,
4487 bgp_node_safi (vty));
4488 }
4489
4490
4491
4492 /*
4493 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
4494 * "no network A.B.C.D mask A.B.C.D backdoor",
4495 * NO_STR
4496 * "Specify a network to announce via BGP\n"
4497 * "Network number\n"
4498 * "Network mask\n"
4499 * "Network mask\n"
4500 * "Specify a BGP backdoor route\n"
4501 *
4502 * "no network A.B.C.D mask A.B.C.D route-map WORD",
4503 * NO_STR
4504 * "Specify a network to announce via BGP\n"
4505 * "Network number\n"
4506 * "Network mask\n"
4507 * "Network mask\n"
4508 * "Route-map to modify the attributes\n"
4509 * "Name of the route map\n"
4510 *
4511 */
4512 DEFUN (no_bgp_network_mask,
4513 no_bgp_network_mask_cmd,
4514 "no network A.B.C.D mask A.B.C.D",
4515 NO_STR
4516 "Specify a network to announce via BGP\n"
4517 "Network number\n"
4518 "Network mask\n"
4519 "Network mask\n")
4520 {
4521 int idx_ipv4 = 2;
4522 int idx_ipv4_2 = 4;
4523 int ret;
4524 char prefix_str[BUFSIZ];
4525
4526 ret = netmask_str2prefix_str (argv[idx_ipv4]->arg, argv[idx_ipv4_2]->arg, prefix_str);
4527 if (! ret)
4528 {
4529 vty_out (vty, "%% Inconsistent address and mask%s", VTY_NEWLINE);
4530 return CMD_WARNING;
4531 }
4532
4533 return bgp_static_unset (vty, vty->index, prefix_str, AFI_IP,
4534 bgp_node_safi (vty));
4535 }
4536
4537
4538
4539 /*
4540 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
4541 * "no network A.B.C.D backdoor",
4542 * NO_STR
4543 * "Specify a network to announce via BGP\n"
4544 * "Network number\n"
4545 * "Specify a BGP backdoor route\n"
4546 *
4547 * "no network A.B.C.D route-map WORD",
4548 * NO_STR
4549 * "Specify a network to announce via BGP\n"
4550 * "Network number\n"
4551 * "Route-map to modify the attributes\n"
4552 * "Name of the route map\n"
4553 *
4554 */
4555 DEFUN (no_bgp_network_mask_natural,
4556 no_bgp_network_mask_natural_cmd,
4557 "no network A.B.C.D",
4558 NO_STR
4559 "Specify a network to announce via BGP\n"
4560 "Network number\n")
4561 {
4562 int idx_ipv4 = 2;
4563 int ret;
4564 char prefix_str[BUFSIZ];
4565
4566 ret = netmask_str2prefix_str (argv[idx_ipv4]->arg, NULL, prefix_str);
4567 if (! ret)
4568 {
4569 vty_out (vty, "%% Inconsistent address and mask%s", VTY_NEWLINE);
4570 return CMD_WARNING;
4571 }
4572
4573 return bgp_static_unset (vty, vty->index, prefix_str, AFI_IP,
4574 bgp_node_safi (vty));
4575 }
4576
4577
4578
4579 #ifdef HAVE_IPV6
4580 /*
4581 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
4582 * "ipv6 bgp network X:X::X:X/M",
4583 * IPV6_STR
4584 * BGP_STR
4585 * "Specify a network to announce via BGP\n"
4586 * "IPv6 prefix <network>/<length>, e.g., 3ffe::/16\n"
4587 *
4588 */
4589 DEFUN (ipv6_bgp_network,
4590 ipv6_bgp_network_cmd,
4591 "network X:X::X:X/M",
4592 "Specify a network to announce via BGP\n"
4593 "IPv6 prefix <network>/<length>\n")
4594 {
4595 int idx_ipv6_prefixlen = 1;
4596 return bgp_static_set (vty, vty->index, argv[idx_ipv6_prefixlen]->arg, AFI_IP6, bgp_node_safi(vty),
4597 NULL, 0);
4598 }
4599
4600 DEFUN (ipv6_bgp_network_route_map,
4601 ipv6_bgp_network_route_map_cmd,
4602 "network X:X::X:X/M route-map WORD",
4603 "Specify a network to announce via BGP\n"
4604 "IPv6 prefix <network>/<length>\n"
4605 "Route-map to modify the attributes\n"
4606 "Name of the route map\n")
4607 {
4608 int idx_ipv6_prefixlen = 1;
4609 int idx_word = 3;
4610 return bgp_static_set (vty, vty->index, argv[idx_ipv6_prefixlen]->arg, AFI_IP6,
4611 bgp_node_safi (vty), argv[idx_word]->arg, 0);
4612 }
4613
4614 /*
4615 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
4616 * "no network X:X::X:X/M route-map WORD",
4617 * NO_STR
4618 * "Specify a network to announce via BGP\n"
4619 * "IPv6 prefix <network>/<length>\n"
4620 * "Route-map to modify the attributes\n"
4621 * "Name of the route map\n"
4622 *
4623 * "no ipv6 bgp network X:X::X:X/M",
4624 * NO_STR
4625 * IPV6_STR
4626 * BGP_STR
4627 * "Specify a network to announce via BGP\n"
4628 * "IPv6 prefix <network>/<length>, e.g., 3ffe::/16\n"
4629 *
4630 */
4631 DEFUN (no_ipv6_bgp_network,
4632 no_ipv6_bgp_network_cmd,
4633 "no network X:X::X:X/M",
4634 NO_STR
4635 "Specify a network to announce via BGP\n"
4636 "IPv6 prefix <network>/<length>\n")
4637 {
4638 int idx_ipv6_prefixlen = 2;
4639 return bgp_static_unset (vty, vty->index, argv[idx_ipv6_prefixlen]->arg, AFI_IP6, bgp_node_safi(vty));
4640 }
4641
4642
4643
4644 #endif /* HAVE_IPV6 */
4645
4646 /* Aggreagete address:
4647
4648 advertise-map Set condition to advertise attribute
4649 as-set Generate AS set path information
4650 attribute-map Set attributes of aggregate
4651 route-map Set parameters of aggregate
4652 summary-only Filter more specific routes from updates
4653 suppress-map Conditionally filter more specific routes from updates
4654 <cr>
4655 */
4656 struct bgp_aggregate
4657 {
4658 /* Summary-only flag. */
4659 u_char summary_only;
4660
4661 /* AS set generation. */
4662 u_char as_set;
4663
4664 /* Route-map for aggregated route. */
4665 struct route_map *map;
4666
4667 /* Suppress-count. */
4668 unsigned long count;
4669
4670 /* SAFI configuration. */
4671 safi_t safi;
4672 };
4673
4674 static struct bgp_aggregate *
4675 bgp_aggregate_new (void)
4676 {
4677 return XCALLOC (MTYPE_BGP_AGGREGATE, sizeof (struct bgp_aggregate));
4678 }
4679
4680 static void
4681 bgp_aggregate_free (struct bgp_aggregate *aggregate)
4682 {
4683 XFREE (MTYPE_BGP_AGGREGATE, aggregate);
4684 }
4685
4686 /* Update an aggregate as routes are added/removed from the BGP table */
4687 static void
4688 bgp_aggregate_route (struct bgp *bgp, struct prefix *p, struct bgp_info *rinew,
4689 afi_t afi, safi_t safi, struct bgp_info *del,
4690 struct bgp_aggregate *aggregate)
4691 {
4692 struct bgp_table *table;
4693 struct bgp_node *top;
4694 struct bgp_node *rn;
4695 u_char origin;
4696 struct aspath *aspath = NULL;
4697 struct aspath *asmerge = NULL;
4698 struct community *community = NULL;
4699 struct community *commerge = NULL;
4700 #if defined(AGGREGATE_NEXTHOP_CHECK)
4701 struct in_addr nexthop;
4702 u_int32_t med = 0;
4703 #endif
4704 struct bgp_info *ri;
4705 struct bgp_info *new;
4706 int first = 1;
4707 unsigned long match = 0;
4708 u_char atomic_aggregate = 0;
4709
4710 /* Record adding route's nexthop and med. */
4711 if (rinew)
4712 {
4713 #if defined(AGGREGATE_NEXTHOP_CHECK)
4714 nexthop = rinew->attr->nexthop;
4715 med = rinew->attr->med;
4716 #endif
4717 }
4718
4719 /* ORIGIN attribute: If at least one route among routes that are
4720 aggregated has ORIGIN with the value INCOMPLETE, then the
4721 aggregated route must have the ORIGIN attribute with the value
4722 INCOMPLETE. Otherwise, if at least one route among routes that
4723 are aggregated has ORIGIN with the value EGP, then the aggregated
4724 route must have the origin attribute with the value EGP. In all
4725 other case the value of the ORIGIN attribute of the aggregated
4726 route is INTERNAL. */
4727 origin = BGP_ORIGIN_IGP;
4728
4729 table = bgp->rib[afi][safi];
4730
4731 top = bgp_node_get (table, p);
4732 for (rn = bgp_node_get (table, p); rn; rn = bgp_route_next_until (rn, top))
4733 if (rn->p.prefixlen > p->prefixlen)
4734 {
4735 match = 0;
4736
4737 for (ri = rn->info; ri; ri = ri->next)
4738 {
4739 if (BGP_INFO_HOLDDOWN (ri))
4740 continue;
4741
4742 if (del && ri == del)
4743 continue;
4744
4745 if (! rinew && first)
4746 {
4747 #if defined(AGGREGATE_NEXTHOP_CHECK)
4748 nexthop = ri->attr->nexthop;
4749 med = ri->attr->med;
4750 #endif
4751 first = 0;
4752 }
4753
4754 #ifdef AGGREGATE_NEXTHOP_CHECK
4755 if (! IPV4_ADDR_SAME (&ri->attr->nexthop, &nexthop)
4756 || ri->attr->med != med)
4757 {
4758 if (aspath)
4759 aspath_free (aspath);
4760 if (community)
4761 community_free (community);
4762 bgp_unlock_node (rn);
4763 bgp_unlock_node (top);
4764 return;
4765 }
4766 #endif /* AGGREGATE_NEXTHOP_CHECK */
4767
4768 if (ri->attr->flag & ATTR_FLAG_BIT(BGP_ATTR_ATOMIC_AGGREGATE))
4769 atomic_aggregate = 1;
4770
4771 if (ri->sub_type != BGP_ROUTE_AGGREGATE)
4772 {
4773 if (aggregate->summary_only)
4774 {
4775 (bgp_info_extra_get (ri))->suppress++;
4776 bgp_info_set_flag (rn, ri, BGP_INFO_ATTR_CHANGED);
4777 match++;
4778 }
4779
4780 aggregate->count++;
4781
4782 if (origin < ri->attr->origin)
4783 origin = ri->attr->origin;
4784
4785 if (aggregate->as_set)
4786 {
4787 if (aspath)
4788 {
4789 asmerge = aspath_aggregate (aspath, ri->attr->aspath);
4790 aspath_free (aspath);
4791 aspath = asmerge;
4792 }
4793 else
4794 aspath = aspath_dup (ri->attr->aspath);
4795
4796 if (ri->attr->community)
4797 {
4798 if (community)
4799 {
4800 commerge = community_merge (community,
4801 ri->attr->community);
4802 community = community_uniq_sort (commerge);
4803 community_free (commerge);
4804 }
4805 else
4806 community = community_dup (ri->attr->community);
4807 }
4808 }
4809 }
4810 }
4811 if (match)
4812 bgp_process (bgp, rn, afi, safi);
4813 }
4814 bgp_unlock_node (top);
4815
4816 if (rinew)
4817 {
4818 aggregate->count++;
4819
4820 if (aggregate->summary_only)
4821 (bgp_info_extra_get (rinew))->suppress++;
4822
4823 if (origin < rinew->attr->origin)
4824 origin = rinew->attr->origin;
4825
4826 if (aggregate->as_set)
4827 {
4828 if (aspath)
4829 {
4830 asmerge = aspath_aggregate (aspath, rinew->attr->aspath);
4831 aspath_free (aspath);
4832 aspath = asmerge;
4833 }
4834 else
4835 aspath = aspath_dup (rinew->attr->aspath);
4836
4837 if (rinew->attr->community)
4838 {
4839 if (community)
4840 {
4841 commerge = community_merge (community,
4842 rinew->attr->community);
4843 community = community_uniq_sort (commerge);
4844 community_free (commerge);
4845 }
4846 else
4847 community = community_dup (rinew->attr->community);
4848 }
4849 }
4850 }
4851
4852 if (aggregate->count > 0)
4853 {
4854 rn = bgp_node_get (table, p);
4855 new = info_make(ZEBRA_ROUTE_BGP, BGP_ROUTE_AGGREGATE, 0, bgp->peer_self,
4856 bgp_attr_aggregate_intern(bgp, origin, aspath, community,
4857 aggregate->as_set,
4858 atomic_aggregate), rn);
4859 SET_FLAG (new->flags, BGP_INFO_VALID);
4860
4861 bgp_info_add (rn, new);
4862 bgp_unlock_node (rn);
4863 bgp_process (bgp, rn, afi, safi);
4864 }
4865 else
4866 {
4867 if (aspath)
4868 aspath_free (aspath);
4869 if (community)
4870 community_free (community);
4871 }
4872 }
4873
4874 void bgp_aggregate_delete (struct bgp *, struct prefix *, afi_t, safi_t,
4875 struct bgp_aggregate *);
4876
4877 void
4878 bgp_aggregate_increment (struct bgp *bgp, struct prefix *p,
4879 struct bgp_info *ri, afi_t afi, safi_t safi)
4880 {
4881 struct bgp_node *child;
4882 struct bgp_node *rn;
4883 struct bgp_aggregate *aggregate;
4884 struct bgp_table *table;
4885
4886 /* MPLS-VPN aggregation is not yet supported. */
4887 if ((safi == SAFI_MPLS_VPN) || (safi == SAFI_ENCAP))
4888 return;
4889
4890 table = bgp->aggregate[afi][safi];
4891
4892 /* No aggregates configured. */
4893 if (bgp_table_top_nolock (table) == NULL)
4894 return;
4895
4896 if (p->prefixlen == 0)
4897 return;
4898
4899 if (BGP_INFO_HOLDDOWN (ri))
4900 return;
4901
4902 child = bgp_node_get (table, p);
4903
4904 /* Aggregate address configuration check. */
4905 for (rn = child; rn; rn = bgp_node_parent_nolock (rn))
4906 if ((aggregate = rn->info) != NULL && rn->p.prefixlen < p->prefixlen)
4907 {
4908 bgp_aggregate_delete (bgp, &rn->p, afi, safi, aggregate);
4909 bgp_aggregate_route (bgp, &rn->p, ri, afi, safi, NULL, aggregate);
4910 }
4911 bgp_unlock_node (child);
4912 }
4913
4914 void
4915 bgp_aggregate_decrement (struct bgp *bgp, struct prefix *p,
4916 struct bgp_info *del, afi_t afi, safi_t safi)
4917 {
4918 struct bgp_node *child;
4919 struct bgp_node *rn;
4920 struct bgp_aggregate *aggregate;
4921 struct bgp_table *table;
4922
4923 /* MPLS-VPN aggregation is not yet supported. */
4924 if ((safi == SAFI_MPLS_VPN) || (safi == SAFI_ENCAP))
4925 return;
4926
4927 table = bgp->aggregate[afi][safi];
4928
4929 /* No aggregates configured. */
4930 if (bgp_table_top_nolock (table) == NULL)
4931 return;
4932
4933 if (p->prefixlen == 0)
4934 return;
4935
4936 child = bgp_node_get (table, p);
4937
4938 /* Aggregate address configuration check. */
4939 for (rn = child; rn; rn = bgp_node_parent_nolock (rn))
4940 if ((aggregate = rn->info) != NULL && rn->p.prefixlen < p->prefixlen)
4941 {
4942 bgp_aggregate_delete (bgp, &rn->p, afi, safi, aggregate);
4943 bgp_aggregate_route (bgp, &rn->p, NULL, afi, safi, del, aggregate);
4944 }
4945 bgp_unlock_node (child);
4946 }
4947
4948 /* Called via bgp_aggregate_set when the user configures aggregate-address */
4949 static void
4950 bgp_aggregate_add (struct bgp *bgp, struct prefix *p, afi_t afi, safi_t safi,
4951 struct bgp_aggregate *aggregate)
4952 {
4953 struct bgp_table *table;
4954 struct bgp_node *top;
4955 struct bgp_node *rn;
4956 struct bgp_info *new;
4957 struct bgp_info *ri;
4958 unsigned long match;
4959 u_char origin = BGP_ORIGIN_IGP;
4960 struct aspath *aspath = NULL;
4961 struct aspath *asmerge = NULL;
4962 struct community *community = NULL;
4963 struct community *commerge = NULL;
4964 u_char atomic_aggregate = 0;
4965
4966 table = bgp->rib[afi][safi];
4967
4968 /* Sanity check. */
4969 if (afi == AFI_IP && p->prefixlen == IPV4_MAX_BITLEN)
4970 return;
4971 if (afi == AFI_IP6 && p->prefixlen == IPV6_MAX_BITLEN)
4972 return;
4973
4974 /* If routes exists below this node, generate aggregate routes. */
4975 top = bgp_node_get (table, p);
4976 for (rn = bgp_node_get (table, p); rn; rn = bgp_route_next_until (rn, top))
4977 if (rn->p.prefixlen > p->prefixlen)
4978 {
4979 match = 0;
4980
4981 for (ri = rn->info; ri; ri = ri->next)
4982 {
4983 if (BGP_INFO_HOLDDOWN (ri))
4984 continue;
4985
4986 if (ri->attr->flag & ATTR_FLAG_BIT(BGP_ATTR_ATOMIC_AGGREGATE))
4987 atomic_aggregate = 1;
4988
4989 if (ri->sub_type != BGP_ROUTE_AGGREGATE)
4990 {
4991 /* summary-only aggregate route suppress aggregated
4992 route announcement. */
4993 if (aggregate->summary_only)
4994 {
4995 (bgp_info_extra_get (ri))->suppress++;
4996 bgp_info_set_flag (rn, ri, BGP_INFO_ATTR_CHANGED);
4997 match++;
4998 }
4999
5000 /* If at least one route among routes that are aggregated has
5001 * ORIGIN with the value INCOMPLETE, then the aggregated route
5002 * MUST have the ORIGIN attribute with the value INCOMPLETE.
5003 * Otherwise, if at least one route among routes that are
5004 * aggregated has ORIGIN with the value EGP, then the aggregated
5005 * route MUST have the ORIGIN attribute with the value EGP.
5006 */
5007 if (origin < ri->attr->origin)
5008 origin = ri->attr->origin;
5009
5010 /* as-set aggregate route generate origin, as path,
5011 community aggregation. */
5012 if (aggregate->as_set)
5013 {
5014 if (aspath)
5015 {
5016 asmerge = aspath_aggregate (aspath, ri->attr->aspath);
5017 aspath_free (aspath);
5018 aspath = asmerge;
5019 }
5020 else
5021 aspath = aspath_dup (ri->attr->aspath);
5022
5023 if (ri->attr->community)
5024 {
5025 if (community)
5026 {
5027 commerge = community_merge (community,
5028 ri->attr->community);
5029 community = community_uniq_sort (commerge);
5030 community_free (commerge);
5031 }
5032 else
5033 community = community_dup (ri->attr->community);
5034 }
5035 }
5036 aggregate->count++;
5037 }
5038 }
5039
5040 /* If this node is suppressed, process the change. */
5041 if (match)
5042 bgp_process (bgp, rn, afi, safi);
5043 }
5044 bgp_unlock_node (top);
5045
5046 /* Add aggregate route to BGP table. */
5047 if (aggregate->count)
5048 {
5049 rn = bgp_node_get (table, p);
5050 new = info_make(ZEBRA_ROUTE_BGP, BGP_ROUTE_AGGREGATE, 0, bgp->peer_self,
5051 bgp_attr_aggregate_intern(bgp, origin, aspath, community,
5052 aggregate->as_set,
5053 atomic_aggregate), rn);
5054 SET_FLAG (new->flags, BGP_INFO_VALID);
5055
5056 bgp_info_add (rn, new);
5057 bgp_unlock_node (rn);
5058
5059 /* Process change. */
5060 bgp_process (bgp, rn, afi, safi);
5061 }
5062 else
5063 {
5064 if (aspath)
5065 aspath_free (aspath);
5066 if (community)
5067 community_free (community);
5068 }
5069 }
5070
5071 void
5072 bgp_aggregate_delete (struct bgp *bgp, struct prefix *p, afi_t afi,
5073 safi_t safi, struct bgp_aggregate *aggregate)
5074 {
5075 struct bgp_table *table;
5076 struct bgp_node *top;
5077 struct bgp_node *rn;
5078 struct bgp_info *ri;
5079 unsigned long match;
5080
5081 table = bgp->rib[afi][safi];
5082
5083 if (afi == AFI_IP && p->prefixlen == IPV4_MAX_BITLEN)
5084 return;
5085 if (afi == AFI_IP6 && p->prefixlen == IPV6_MAX_BITLEN)
5086 return;
5087
5088 /* If routes exists below this node, generate aggregate routes. */
5089 top = bgp_node_get (table, p);
5090 for (rn = bgp_node_get (table, p); rn; rn = bgp_route_next_until (rn, top))
5091 if (rn->p.prefixlen > p->prefixlen)
5092 {
5093 match = 0;
5094
5095 for (ri = rn->info; ri; ri = ri->next)
5096 {
5097 if (BGP_INFO_HOLDDOWN (ri))
5098 continue;
5099
5100 if (ri->sub_type != BGP_ROUTE_AGGREGATE)
5101 {
5102 if (aggregate->summary_only && ri->extra)
5103 {
5104 ri->extra->suppress--;
5105
5106 if (ri->extra->suppress == 0)
5107 {
5108 bgp_info_set_flag (rn, ri, BGP_INFO_ATTR_CHANGED);
5109 match++;
5110 }
5111 }
5112 aggregate->count--;
5113 }
5114 }
5115
5116 /* If this node was suppressed, process the change. */
5117 if (match)
5118 bgp_process (bgp, rn, afi, safi);
5119 }
5120 bgp_unlock_node (top);
5121
5122 /* Delete aggregate route from BGP table. */
5123 rn = bgp_node_get (table, p);
5124
5125 for (ri = rn->info; ri; ri = ri->next)
5126 if (ri->peer == bgp->peer_self
5127 && ri->type == ZEBRA_ROUTE_BGP
5128 && ri->sub_type == BGP_ROUTE_AGGREGATE)
5129 break;
5130
5131 /* Withdraw static BGP route from routing table. */
5132 if (ri)
5133 {
5134 bgp_info_delete (rn, ri);
5135 bgp_process (bgp, rn, afi, safi);
5136 }
5137
5138 /* Unlock bgp_node_lookup. */
5139 bgp_unlock_node (rn);
5140 }
5141
5142 /* Aggregate route attribute. */
5143 #define AGGREGATE_SUMMARY_ONLY 1
5144 #define AGGREGATE_AS_SET 1
5145
5146 static int
5147 bgp_aggregate_unset (struct vty *vty, const char *prefix_str,
5148 afi_t afi, safi_t safi)
5149 {
5150 int ret;
5151 struct prefix p;
5152 struct bgp_node *rn;
5153 struct bgp *bgp;
5154 struct bgp_aggregate *aggregate;
5155
5156 /* Convert string to prefix structure. */
5157 ret = str2prefix (prefix_str, &p);
5158 if (!ret)
5159 {
5160 vty_out (vty, "Malformed prefix%s", VTY_NEWLINE);
5161 return CMD_WARNING;
5162 }
5163 apply_mask (&p);
5164
5165 /* Get BGP structure. */
5166 bgp = vty->index;
5167
5168 /* Old configuration check. */
5169 rn = bgp_node_lookup (bgp->aggregate[afi][safi], &p);
5170 if (! rn)
5171 {
5172 vty_out (vty, "%% There is no aggregate-address configuration.%s",
5173 VTY_NEWLINE);
5174 return CMD_WARNING;
5175 }
5176
5177 aggregate = rn->info;
5178 if (aggregate->safi & SAFI_UNICAST)
5179 bgp_aggregate_delete (bgp, &p, afi, SAFI_UNICAST, aggregate);
5180 if (aggregate->safi & SAFI_MULTICAST)
5181 bgp_aggregate_delete (bgp, &p, afi, SAFI_MULTICAST, aggregate);
5182
5183 /* Unlock aggregate address configuration. */
5184 rn->info = NULL;
5185 bgp_aggregate_free (aggregate);
5186 bgp_unlock_node (rn);
5187 bgp_unlock_node (rn);
5188
5189 return CMD_SUCCESS;
5190 }
5191
5192 static int
5193 bgp_aggregate_set (struct vty *vty, const char *prefix_str,
5194 afi_t afi, safi_t safi,
5195 u_char summary_only, u_char as_set)
5196 {
5197 int ret;
5198 struct prefix p;
5199 struct bgp_node *rn;
5200 struct bgp *bgp;
5201 struct bgp_aggregate *aggregate;
5202
5203 /* Convert string to prefix structure. */
5204 ret = str2prefix (prefix_str, &p);
5205 if (!ret)
5206 {
5207 vty_out (vty, "Malformed prefix%s", VTY_NEWLINE);
5208 return CMD_WARNING;
5209 }
5210 apply_mask (&p);
5211
5212 /* Get BGP structure. */
5213 bgp = vty->index;
5214
5215 /* Old configuration check. */
5216 rn = bgp_node_get (bgp->aggregate[afi][safi], &p);
5217
5218 if (rn->info)
5219 {
5220 vty_out (vty, "There is already same aggregate network.%s", VTY_NEWLINE);
5221 /* try to remove the old entry */
5222 ret = bgp_aggregate_unset (vty, prefix_str, afi, safi);
5223 if (ret)
5224 {
5225 vty_out (vty, "Error deleting aggregate.%s", VTY_NEWLINE);
5226 bgp_unlock_node (rn);
5227 return CMD_WARNING;
5228 }
5229 }
5230
5231 /* Make aggregate address structure. */
5232 aggregate = bgp_aggregate_new ();
5233 aggregate->summary_only = summary_only;
5234 aggregate->as_set = as_set;
5235 aggregate->safi = safi;
5236 rn->info = aggregate;
5237
5238 /* Aggregate address insert into BGP routing table. */
5239 if (safi & SAFI_UNICAST)
5240 bgp_aggregate_add (bgp, &p, afi, SAFI_UNICAST, aggregate);
5241 if (safi & SAFI_MULTICAST)
5242 bgp_aggregate_add (bgp, &p, afi, SAFI_MULTICAST, aggregate);
5243
5244 return CMD_SUCCESS;
5245 }
5246
5247 DEFUN (aggregate_address,
5248 aggregate_address_cmd,
5249 "aggregate-address A.B.C.D/M",
5250 "Configure BGP aggregate entries\n"
5251 "Aggregate prefix\n")
5252 {
5253 int idx_ipv4_prefixlen = 1;
5254 return bgp_aggregate_set (vty, argv[idx_ipv4_prefixlen]->arg, AFI_IP, bgp_node_safi (vty), 0, 0);
5255 }
5256
5257 DEFUN (aggregate_address_mask,
5258 aggregate_address_mask_cmd,
5259 "aggregate-address A.B.C.D A.B.C.D",
5260 "Configure BGP aggregate entries\n"
5261 "Aggregate address\n"
5262 "Aggregate mask\n")
5263 {
5264 int idx_ipv4 = 1;
5265 int idx_ipv4_2 = 2;
5266 int ret;
5267 char prefix_str[BUFSIZ];
5268
5269 ret = netmask_str2prefix_str (argv[idx_ipv4]->arg, argv[idx_ipv4_2]->arg, prefix_str);
5270
5271 if (! ret)
5272 {
5273 vty_out (vty, "%% Inconsistent address and mask%s", VTY_NEWLINE);
5274 return CMD_WARNING;
5275 }
5276
5277 return bgp_aggregate_set (vty, prefix_str, AFI_IP, bgp_node_safi (vty),
5278 0, 0);
5279 }
5280
5281 DEFUN (aggregate_address_summary_only,
5282 aggregate_address_summary_only_cmd,
5283 "aggregate-address A.B.C.D/M summary-only",
5284 "Configure BGP aggregate entries\n"
5285 "Aggregate prefix\n"
5286 "Filter more specific routes from updates\n")
5287 {
5288 int idx_ipv4_prefixlen = 1;
5289 return bgp_aggregate_set (vty, argv[idx_ipv4_prefixlen]->arg, AFI_IP, bgp_node_safi (vty),
5290 AGGREGATE_SUMMARY_ONLY, 0);
5291 }
5292
5293 DEFUN (aggregate_address_mask_summary_only,
5294 aggregate_address_mask_summary_only_cmd,
5295 "aggregate-address A.B.C.D A.B.C.D summary-only",
5296 "Configure BGP aggregate entries\n"
5297 "Aggregate address\n"
5298 "Aggregate mask\n"
5299 "Filter more specific routes from updates\n")
5300 {
5301 int idx_ipv4 = 1;
5302 int idx_ipv4_2 = 2;
5303 int ret;
5304 char prefix_str[BUFSIZ];
5305
5306 ret = netmask_str2prefix_str (argv[idx_ipv4]->arg, argv[idx_ipv4_2]->arg, prefix_str);
5307
5308 if (! ret)
5309 {
5310 vty_out (vty, "%% Inconsistent address and mask%s", VTY_NEWLINE);
5311 return CMD_WARNING;
5312 }
5313
5314 return bgp_aggregate_set (vty, prefix_str, AFI_IP, bgp_node_safi (vty),
5315 AGGREGATE_SUMMARY_ONLY, 0);
5316 }
5317
5318 DEFUN (aggregate_address_as_set,
5319 aggregate_address_as_set_cmd,
5320 "aggregate-address A.B.C.D/M as-set",
5321 "Configure BGP aggregate entries\n"
5322 "Aggregate prefix\n"
5323 "Generate AS set path information\n")
5324 {
5325 int idx_ipv4_prefixlen = 1;
5326 return bgp_aggregate_set (vty, argv[idx_ipv4_prefixlen]->arg, AFI_IP, bgp_node_safi (vty),
5327 0, AGGREGATE_AS_SET);
5328 }
5329
5330 DEFUN (aggregate_address_mask_as_set,
5331 aggregate_address_mask_as_set_cmd,
5332 "aggregate-address A.B.C.D A.B.C.D as-set",
5333 "Configure BGP aggregate entries\n"
5334 "Aggregate address\n"
5335 "Aggregate mask\n"
5336 "Generate AS set path information\n")
5337 {
5338 int idx_ipv4 = 1;
5339 int idx_ipv4_2 = 2;
5340 int ret;
5341 char prefix_str[BUFSIZ];
5342
5343 ret = netmask_str2prefix_str (argv[idx_ipv4]->arg, argv[idx_ipv4_2]->arg, prefix_str);
5344
5345 if (! ret)
5346 {
5347 vty_out (vty, "%% Inconsistent address and mask%s", VTY_NEWLINE);
5348 return CMD_WARNING;
5349 }
5350
5351 return bgp_aggregate_set (vty, prefix_str, AFI_IP, bgp_node_safi (vty),
5352 0, AGGREGATE_AS_SET);
5353 }
5354
5355
5356 /*
5357 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
5358 * "aggregate-address A.B.C.D/M summary-only as-set",
5359 * "Configure BGP aggregate entries\n"
5360 * "Aggregate prefix\n"
5361 * "Filter more specific routes from updates\n"
5362 * "Generate AS set path information\n"
5363 *
5364 */
5365 DEFUN (aggregate_address_as_set_summary,
5366 aggregate_address_as_set_summary_cmd,
5367 "aggregate-address A.B.C.D/M as-set summary-only",
5368 "Configure BGP aggregate entries\n"
5369 "Aggregate prefix\n"
5370 "Generate AS set path information\n"
5371 "Filter more specific routes from updates\n")
5372 {
5373 int idx_ipv4_prefixlen = 1;
5374 return bgp_aggregate_set (vty, argv[idx_ipv4_prefixlen]->arg, AFI_IP, bgp_node_safi (vty),
5375 AGGREGATE_SUMMARY_ONLY, AGGREGATE_AS_SET);
5376 }
5377
5378
5379 /*
5380 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
5381 * "aggregate-address A.B.C.D A.B.C.D summary-only as-set",
5382 * "Configure BGP aggregate entries\n"
5383 * "Aggregate address\n"
5384 * "Aggregate mask\n"
5385 * "Filter more specific routes from updates\n"
5386 * "Generate AS set path information\n"
5387 *
5388 */
5389 DEFUN (aggregate_address_mask_as_set_summary,
5390 aggregate_address_mask_as_set_summary_cmd,
5391 "aggregate-address A.B.C.D A.B.C.D as-set summary-only",
5392 "Configure BGP aggregate entries\n"
5393 "Aggregate address\n"
5394 "Aggregate mask\n"
5395 "Generate AS set path information\n"
5396 "Filter more specific routes from updates\n")
5397 {
5398 int idx_ipv4 = 1;
5399 int idx_ipv4_2 = 2;
5400 int ret;
5401 char prefix_str[BUFSIZ];
5402
5403 ret = netmask_str2prefix_str (argv[idx_ipv4]->arg, argv[idx_ipv4_2]->arg, prefix_str);
5404
5405 if (! ret)
5406 {
5407 vty_out (vty, "%% Inconsistent address and mask%s", VTY_NEWLINE);
5408 return CMD_WARNING;
5409 }
5410
5411 return bgp_aggregate_set (vty, prefix_str, AFI_IP, bgp_node_safi (vty),
5412 AGGREGATE_SUMMARY_ONLY, AGGREGATE_AS_SET);
5413 }
5414
5415
5416 /*
5417 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
5418 * "no aggregate-address A.B.C.D/M summary-only",
5419 * NO_STR
5420 * "Configure BGP aggregate entries\n"
5421 * "Aggregate prefix\n"
5422 * "Filter more specific routes from updates\n"
5423 *
5424 * "no aggregate-address A.B.C.D/M as-set summary-only",
5425 * NO_STR
5426 * "Configure BGP aggregate entries\n"
5427 * "Aggregate prefix\n"
5428 * "Generate AS set path information\n"
5429 * "Filter more specific routes from updates\n"
5430 *
5431 * "no aggregate-address A.B.C.D/M summary-only as-set",
5432 * NO_STR
5433 * "Configure BGP aggregate entries\n"
5434 * "Aggregate prefix\n"
5435 * "Filter more specific routes from updates\n"
5436 * "Generate AS set path information\n"
5437 *
5438 * "no aggregate-address A.B.C.D/M as-set",
5439 * NO_STR
5440 * "Configure BGP aggregate entries\n"
5441 * "Aggregate prefix\n"
5442 * "Generate AS set path information\n"
5443 *
5444 */
5445 DEFUN (no_aggregate_address,
5446 no_aggregate_address_cmd,
5447 "no aggregate-address A.B.C.D/M",
5448 NO_STR
5449 "Configure BGP aggregate entries\n"
5450 "Aggregate prefix\n")
5451 {
5452 int idx_ipv4_prefixlen = 2;
5453 return bgp_aggregate_unset (vty, argv[idx_ipv4_prefixlen]->arg, AFI_IP, bgp_node_safi (vty));
5454 }
5455
5456
5457
5458
5459
5460 /*
5461 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
5462 * "no aggregate-address A.B.C.D A.B.C.D summary-only as-set",
5463 * NO_STR
5464 * "Configure BGP aggregate entries\n"
5465 * "Aggregate address\n"
5466 * "Aggregate mask\n"
5467 * "Filter more specific routes from updates\n"
5468 * "Generate AS set path information\n"
5469 *
5470 * "no aggregate-address A.B.C.D A.B.C.D as-set summary-only",
5471 * NO_STR
5472 * "Configure BGP aggregate entries\n"
5473 * "Aggregate address\n"
5474 * "Aggregate mask\n"
5475 * "Generate AS set path information\n"
5476 * "Filter more specific routes from updates\n"
5477 *
5478 * "no aggregate-address A.B.C.D A.B.C.D summary-only",
5479 * NO_STR
5480 * "Configure BGP aggregate entries\n"
5481 * "Aggregate address\n"
5482 * "Aggregate mask\n"
5483 * "Filter more specific routes from updates\n"
5484 *
5485 * "no aggregate-address A.B.C.D A.B.C.D as-set",
5486 * NO_STR
5487 * "Configure BGP aggregate entries\n"
5488 * "Aggregate address\n"
5489 * "Aggregate mask\n"
5490 * "Generate AS set path information\n"
5491 *
5492 */
5493 DEFUN (no_aggregate_address_mask,
5494 no_aggregate_address_mask_cmd,
5495 "no aggregate-address A.B.C.D A.B.C.D",
5496 NO_STR
5497 "Configure BGP aggregate entries\n"
5498 "Aggregate address\n"
5499 "Aggregate mask\n")
5500 {
5501 int idx_ipv4 = 2;
5502 int idx_ipv4_2 = 3;
5503 int ret;
5504 char prefix_str[BUFSIZ];
5505
5506 ret = netmask_str2prefix_str (argv[idx_ipv4]->arg, argv[idx_ipv4_2]->arg, prefix_str);
5507
5508 if (! ret)
5509 {
5510 vty_out (vty, "%% Inconsistent address and mask%s", VTY_NEWLINE);
5511 return CMD_WARNING;
5512 }
5513
5514 return bgp_aggregate_unset (vty, prefix_str, AFI_IP, bgp_node_safi (vty));
5515 }
5516
5517
5518
5519
5520
5521 #ifdef HAVE_IPV6
5522 /*
5523 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
5524 * "ipv6 bgp aggregate-address X:X::X:X/M",
5525 * IPV6_STR
5526 * BGP_STR
5527 * "Configure BGP aggregate entries\n"
5528 * "Aggregate prefix\n"
5529 *
5530 */
5531 DEFUN (ipv6_aggregate_address,
5532 ipv6_aggregate_address_cmd,
5533 "aggregate-address X:X::X:X/M",
5534 "Configure BGP aggregate entries\n"
5535 "Aggregate prefix\n")
5536 {
5537 int idx_ipv6_prefixlen = 1;
5538 return bgp_aggregate_set (vty, argv[idx_ipv6_prefixlen]->arg, AFI_IP6, SAFI_UNICAST, 0, 0);
5539 }
5540
5541 /*
5542 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
5543 * "ipv6 bgp aggregate-address X:X::X:X/M summary-only",
5544 * IPV6_STR
5545 * BGP_STR
5546 * "Configure BGP aggregate entries\n"
5547 * "Aggregate prefix\n"
5548 * "Filter more specific routes from updates\n"
5549 *
5550 */
5551 DEFUN (ipv6_aggregate_address_summary_only,
5552 ipv6_aggregate_address_summary_only_cmd,
5553 "aggregate-address X:X::X:X/M summary-only",
5554 "Configure BGP aggregate entries\n"
5555 "Aggregate prefix\n"
5556 "Filter more specific routes from updates\n")
5557 {
5558 int idx_ipv6_prefixlen = 1;
5559 return bgp_aggregate_set (vty, argv[idx_ipv6_prefixlen]->arg, AFI_IP6, SAFI_UNICAST,
5560 AGGREGATE_SUMMARY_ONLY, 0);
5561 }
5562
5563 /*
5564 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
5565 * "no ipv6 bgp aggregate-address X:X::X:X/M",
5566 * NO_STR
5567 * IPV6_STR
5568 * BGP_STR
5569 * "Configure BGP aggregate entries\n"
5570 * "Aggregate prefix\n"
5571 *
5572 */
5573 DEFUN (no_ipv6_aggregate_address,
5574 no_ipv6_aggregate_address_cmd,
5575 "no aggregate-address X:X::X:X/M",
5576 NO_STR
5577 "Configure BGP aggregate entries\n"
5578 "Aggregate prefix\n")
5579 {
5580 int idx_ipv6_prefixlen = 2;
5581 return bgp_aggregate_unset (vty, argv[idx_ipv6_prefixlen]->arg, AFI_IP6, SAFI_UNICAST);
5582 }
5583
5584 /*
5585 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
5586 * "no ipv6 bgp aggregate-address X:X::X:X/M summary-only",
5587 * NO_STR
5588 * IPV6_STR
5589 * BGP_STR
5590 * "Configure BGP aggregate entries\n"
5591 * "Aggregate prefix\n"
5592 * "Filter more specific routes from updates\n"
5593 *
5594 */
5595 DEFUN (no_ipv6_aggregate_address_summary_only,
5596 no_ipv6_aggregate_address_summary_only_cmd,
5597 "no aggregate-address X:X::X:X/M summary-only",
5598 NO_STR
5599 "Configure BGP aggregate entries\n"
5600 "Aggregate prefix\n"
5601 "Filter more specific routes from updates\n")
5602 {
5603 int idx_ipv6_prefixlen = 2;
5604 return bgp_aggregate_unset (vty, argv[idx_ipv6_prefixlen]->arg, AFI_IP6, SAFI_UNICAST);
5605 }
5606
5607
5608
5609
5610 #endif /* HAVE_IPV6 */
5611
5612 /* Redistribute route treatment. */
5613 void
5614 bgp_redistribute_add (struct bgp *bgp, struct prefix *p, const struct in_addr *nexthop,
5615 const struct in6_addr *nexthop6, unsigned int ifindex,
5616 u_int32_t metric, u_char type, u_short instance, u_short tag)
5617 {
5618 struct bgp_info *new;
5619 struct bgp_info *bi;
5620 struct bgp_info info;
5621 struct bgp_node *bn;
5622 struct attr attr;
5623 struct attr *new_attr;
5624 afi_t afi;
5625 int ret;
5626 struct bgp_redist *red;
5627
5628 /* Make default attribute. */
5629 bgp_attr_default_set (&attr, BGP_ORIGIN_INCOMPLETE);
5630 if (nexthop)
5631 attr.nexthop = *nexthop;
5632 attr.nh_ifindex = ifindex;
5633
5634 #ifdef HAVE_IPV6
5635 if (nexthop6)
5636 {
5637 struct attr_extra *extra = bgp_attr_extra_get(&attr);
5638 extra->mp_nexthop_global = *nexthop6;
5639 extra->mp_nexthop_len = BGP_ATTR_NHLEN_IPV6_GLOBAL;
5640 }
5641 #endif
5642
5643 attr.med = metric;
5644 attr.flag |= ATTR_FLAG_BIT (BGP_ATTR_MULTI_EXIT_DISC);
5645 attr.extra->tag = tag;
5646
5647 afi = family2afi (p->family);
5648
5649 red = bgp_redist_lookup(bgp, afi, type, instance);
5650 if (red)
5651 {
5652 struct attr attr_new;
5653 struct attr_extra extra_new;
5654
5655 /* Copy attribute for modification. */
5656 attr_new.extra = &extra_new;
5657 bgp_attr_dup (&attr_new, &attr);
5658
5659 if (red->redist_metric_flag)
5660 attr_new.med = red->redist_metric;
5661
5662 /* Apply route-map. */
5663 if (red->rmap.name)
5664 {
5665 info.peer = bgp->peer_self;
5666 info.attr = &attr_new;
5667
5668 SET_FLAG (bgp->peer_self->rmap_type, PEER_RMAP_TYPE_REDISTRIBUTE);
5669
5670 ret = route_map_apply (red->rmap.map, p, RMAP_BGP, &info);
5671
5672 bgp->peer_self->rmap_type = 0;
5673
5674 if (ret == RMAP_DENYMATCH)
5675 {
5676 /* Free uninterned attribute. */
5677 bgp_attr_flush (&attr_new);
5678
5679 /* Unintern original. */
5680 aspath_unintern (&attr.aspath);
5681 bgp_attr_extra_free (&attr);
5682 bgp_redistribute_delete (bgp, p, type, instance);
5683 return;
5684 }
5685 }
5686
5687 bn = bgp_afi_node_get (bgp->rib[afi][SAFI_UNICAST],
5688 afi, SAFI_UNICAST, p, NULL);
5689
5690 new_attr = bgp_attr_intern (&attr_new);
5691
5692 for (bi = bn->info; bi; bi = bi->next)
5693 if (bi->peer == bgp->peer_self
5694 && bi->sub_type == BGP_ROUTE_REDISTRIBUTE)
5695 break;
5696
5697 if (bi)
5698 {
5699 /* Ensure the (source route) type is updated. */
5700 bi->type = type;
5701 if (attrhash_cmp (bi->attr, new_attr) &&
5702 !CHECK_FLAG(bi->flags, BGP_INFO_REMOVED))
5703 {
5704 bgp_attr_unintern (&new_attr);
5705 aspath_unintern (&attr.aspath);
5706 bgp_attr_extra_free (&attr);
5707 bgp_unlock_node (bn);
5708 return;
5709 }
5710 else
5711 {
5712 /* The attribute is changed. */
5713 bgp_info_set_flag (bn, bi, BGP_INFO_ATTR_CHANGED);
5714
5715 /* Rewrite BGP route information. */
5716 if (CHECK_FLAG(bi->flags, BGP_INFO_REMOVED))
5717 bgp_info_restore(bn, bi);
5718 else
5719 bgp_aggregate_decrement (bgp, p, bi, afi, SAFI_UNICAST);
5720 bgp_attr_unintern (&bi->attr);
5721 bi->attr = new_attr;
5722 bi->uptime = bgp_clock ();
5723
5724 /* Process change. */
5725 bgp_aggregate_increment (bgp, p, bi, afi, SAFI_UNICAST);
5726 bgp_process (bgp, bn, afi, SAFI_UNICAST);
5727 bgp_unlock_node (bn);
5728 aspath_unintern (&attr.aspath);
5729 bgp_attr_extra_free (&attr);
5730 return;
5731 }
5732 }
5733
5734 new = info_make(type, BGP_ROUTE_REDISTRIBUTE, instance, bgp->peer_self,
5735 new_attr, bn);
5736 SET_FLAG (new->flags, BGP_INFO_VALID);
5737
5738 bgp_aggregate_increment (bgp, p, new, afi, SAFI_UNICAST);
5739 bgp_info_add (bn, new);
5740 bgp_unlock_node (bn);
5741 bgp_process (bgp, bn, afi, SAFI_UNICAST);
5742 }
5743
5744 /* Unintern original. */
5745 aspath_unintern (&attr.aspath);
5746 bgp_attr_extra_free (&attr);
5747 }
5748
5749 void
5750 bgp_redistribute_delete (struct bgp *bgp, struct prefix *p, u_char type, u_short instance)
5751 {
5752 afi_t afi;
5753 struct bgp_node *rn;
5754 struct bgp_info *ri;
5755 struct bgp_redist *red;
5756
5757 afi = family2afi (p->family);
5758
5759 red = bgp_redist_lookup(bgp, afi, type, instance);
5760 if (red)
5761 {
5762 rn = bgp_afi_node_get (bgp->rib[afi][SAFI_UNICAST], afi, SAFI_UNICAST, p, NULL);
5763
5764 for (ri = rn->info; ri; ri = ri->next)
5765 if (ri->peer == bgp->peer_self
5766 && ri->type == type)
5767 break;
5768
5769 if (ri)
5770 {
5771 bgp_aggregate_decrement (bgp, p, ri, afi, SAFI_UNICAST);
5772 bgp_info_delete (rn, ri);
5773 bgp_process (bgp, rn, afi, SAFI_UNICAST);
5774 }
5775 bgp_unlock_node (rn);
5776 }
5777 }
5778
5779 /* Withdraw specified route type's route. */
5780 void
5781 bgp_redistribute_withdraw (struct bgp *bgp, afi_t afi, int type, u_short instance)
5782 {
5783 struct bgp_node *rn;
5784 struct bgp_info *ri;
5785 struct bgp_table *table;
5786
5787 table = bgp->rib[afi][SAFI_UNICAST];
5788
5789 for (rn = bgp_table_top (table); rn; rn = bgp_route_next (rn))
5790 {
5791 for (ri = rn->info; ri; ri = ri->next)
5792 if (ri->peer == bgp->peer_self
5793 && ri->type == type
5794 && ri->instance == instance)
5795 break;
5796
5797 if (ri)
5798 {
5799 bgp_aggregate_decrement (bgp, &rn->p, ri, afi, SAFI_UNICAST);
5800 bgp_info_delete (rn, ri);
5801 bgp_process (bgp, rn, afi, SAFI_UNICAST);
5802 }
5803 }
5804 }
5805
5806 /* Static function to display route. */
5807 static void
5808 route_vty_out_route (struct prefix *p, struct vty *vty)
5809 {
5810 int len;
5811 u_int32_t destination;
5812 char buf[BUFSIZ];
5813
5814 if (p->family == AF_INET)
5815 {
5816 len = vty_out (vty, "%s", inet_ntop (p->family, &p->u.prefix, buf, BUFSIZ));
5817 destination = ntohl (p->u.prefix4.s_addr);
5818
5819 if ((IN_CLASSC (destination) && p->prefixlen == 24)
5820 || (IN_CLASSB (destination) && p->prefixlen == 16)
5821 || (IN_CLASSA (destination) && p->prefixlen == 8)
5822 || p->u.prefix4.s_addr == 0)
5823 {
5824 /* When mask is natural, mask is not displayed. */
5825 }
5826 else
5827 len += vty_out (vty, "/%d", p->prefixlen);
5828 }
5829 else
5830 len = vty_out (vty, "%s/%d", inet_ntop (p->family, &p->u.prefix, buf, BUFSIZ),
5831 p->prefixlen);
5832
5833 len = 17 - len;
5834 if (len < 1)
5835 vty_out (vty, "%s%*s", VTY_NEWLINE, 20, " ");
5836 else
5837 vty_out (vty, "%*s", len, " ");
5838 }
5839
5840 enum bgp_display_type
5841 {
5842 normal_list,
5843 };
5844
5845 /* Print the short form route status for a bgp_info */
5846 static void
5847 route_vty_short_status_out (struct vty *vty, struct bgp_info *binfo,
5848 json_object *json_path)
5849 {
5850 if (json_path)
5851 {
5852
5853 /* Route status display. */
5854 if (CHECK_FLAG (binfo->flags, BGP_INFO_REMOVED))
5855 json_object_boolean_true_add(json_path, "removed");
5856
5857 if (CHECK_FLAG (binfo->flags, BGP_INFO_STALE))
5858 json_object_boolean_true_add(json_path, "stale");
5859
5860 if (binfo->extra && binfo->extra->suppress)
5861 json_object_boolean_true_add(json_path, "suppressed");
5862
5863 if (CHECK_FLAG (binfo->flags, BGP_INFO_VALID) &&
5864 ! CHECK_FLAG (binfo->flags, BGP_INFO_HISTORY))
5865 json_object_boolean_true_add(json_path, "valid");
5866
5867 /* Selected */
5868 if (CHECK_FLAG (binfo->flags, BGP_INFO_HISTORY))
5869 json_object_boolean_true_add(json_path, "history");
5870
5871 if (CHECK_FLAG (binfo->flags, BGP_INFO_DAMPED))
5872 json_object_boolean_true_add(json_path, "damped");
5873
5874 if (CHECK_FLAG (binfo->flags, BGP_INFO_SELECTED))
5875 json_object_boolean_true_add(json_path, "bestpath");
5876
5877 if (CHECK_FLAG (binfo->flags, BGP_INFO_MULTIPATH))
5878 json_object_boolean_true_add(json_path, "multipath");
5879
5880 /* Internal route. */
5881 if ((binfo->peer->as) && (binfo->peer->as == binfo->peer->local_as))
5882 json_object_string_add(json_path, "pathFrom", "internal");
5883 else
5884 json_object_string_add(json_path, "pathFrom", "external");
5885
5886 return;
5887 }
5888
5889 /* Route status display. */
5890 if (CHECK_FLAG (binfo->flags, BGP_INFO_REMOVED))
5891 vty_out (vty, "R");
5892 else if (CHECK_FLAG (binfo->flags, BGP_INFO_STALE))
5893 vty_out (vty, "S");
5894 else if (binfo->extra && binfo->extra->suppress)
5895 vty_out (vty, "s");
5896 else if (CHECK_FLAG (binfo->flags, BGP_INFO_VALID) &&
5897 ! CHECK_FLAG (binfo->flags, BGP_INFO_HISTORY))
5898 vty_out (vty, "*");
5899 else
5900 vty_out (vty, " ");
5901
5902 /* Selected */
5903 if (CHECK_FLAG (binfo->flags, BGP_INFO_HISTORY))
5904 vty_out (vty, "h");
5905 else if (CHECK_FLAG (binfo->flags, BGP_INFO_DAMPED))
5906 vty_out (vty, "d");
5907 else if (CHECK_FLAG (binfo->flags, BGP_INFO_SELECTED))
5908 vty_out (vty, ">");
5909 else if (CHECK_FLAG (binfo->flags, BGP_INFO_MULTIPATH))
5910 vty_out (vty, "=");
5911 else
5912 vty_out (vty, " ");
5913
5914 /* Internal route. */
5915 if ((binfo->peer->as) && (binfo->peer->as == binfo->peer->local_as))
5916 vty_out (vty, "i");
5917 else
5918 vty_out (vty, " ");
5919 }
5920
5921 /* called from terminal list command */
5922 void
5923 route_vty_out (struct vty *vty, struct prefix *p,
5924 struct bgp_info *binfo, int display, safi_t safi,
5925 json_object *json_paths)
5926 {
5927 struct attr *attr;
5928 json_object *json_path = NULL;
5929 json_object *json_nexthops = NULL;
5930 json_object *json_nexthop_global = NULL;
5931 json_object *json_nexthop_ll = NULL;
5932
5933 if (json_paths)
5934 json_path = json_object_new_object();
5935
5936 /* short status lead text */
5937 route_vty_short_status_out (vty, binfo, json_path);
5938
5939 if (!json_paths)
5940 {
5941 /* print prefix and mask */
5942 if (! display)
5943 route_vty_out_route (p, vty);
5944 else
5945 vty_out (vty, "%*s", 17, " ");
5946 }
5947
5948 /* Print attribute */
5949 attr = binfo->attr;
5950 if (attr)
5951 {
5952 /*
5953 * For ENCAP routes, nexthop address family is not
5954 * neccessarily the same as the prefix address family.
5955 * Both SAFI_MPLS_VPN and SAFI_ENCAP use the MP nexthop field
5956 */
5957 if ((safi == SAFI_ENCAP) || (safi == SAFI_MPLS_VPN))
5958 {
5959 if (attr->extra)
5960 {
5961 char buf[BUFSIZ];
5962 int af = NEXTHOP_FAMILY(attr->extra->mp_nexthop_len);
5963
5964 switch (af)
5965 {
5966 case AF_INET:
5967 vty_out (vty, "%s", inet_ntop(af,
5968 &attr->extra->mp_nexthop_global_in, buf, BUFSIZ));
5969 break;
5970 #if HAVE_IPV6
5971 case AF_INET6:
5972 vty_out (vty, "%s", inet_ntop(af,
5973 &attr->extra->mp_nexthop_global, buf, BUFSIZ));
5974 break;
5975 #endif
5976 default:
5977 vty_out(vty, "?");
5978 break;
5979 }
5980 }
5981 else
5982 vty_out(vty, "?");
5983 }
5984 /* IPv4 Next Hop */
5985 else if (p->family == AF_INET || !BGP_ATTR_NEXTHOP_AFI_IP6(attr))
5986 {
5987 if (json_paths)
5988 {
5989 json_nexthop_global = json_object_new_object();
5990
5991 if (safi == SAFI_MPLS_VPN)
5992 json_object_string_add(json_nexthop_global, "ip", inet_ntoa (attr->extra->mp_nexthop_global_in));
5993 else
5994 json_object_string_add(json_nexthop_global, "ip", inet_ntoa (attr->nexthop));
5995
5996 json_object_string_add(json_nexthop_global, "afi", "ipv4");
5997 json_object_boolean_true_add(json_nexthop_global, "used");
5998 }
5999 else
6000 {
6001 if (safi == SAFI_MPLS_VPN)
6002 vty_out (vty, "%-16s",
6003 inet_ntoa (attr->extra->mp_nexthop_global_in));
6004 else
6005 vty_out (vty, "%-16s", inet_ntoa (attr->nexthop));
6006 }
6007 }
6008
6009 /* IPv6 Next Hop */
6010 else if (p->family == AF_INET6 || BGP_ATTR_NEXTHOP_AFI_IP6(attr))
6011 {
6012 int len;
6013 char buf[BUFSIZ];
6014
6015 if (json_paths)
6016 {
6017 json_nexthop_global = json_object_new_object();
6018 json_object_string_add(json_nexthop_global, "ip",
6019 inet_ntop (AF_INET6,
6020 &attr->extra->mp_nexthop_global,
6021 buf, BUFSIZ));
6022 json_object_string_add(json_nexthop_global, "afi", "ipv6");
6023 json_object_string_add(json_nexthop_global, "scope", "global");
6024
6025 /* We display both LL & GL if both have been received */
6026 if ((attr->extra->mp_nexthop_len == 32) || (binfo->peer->conf_if))
6027 {
6028 json_nexthop_ll = json_object_new_object();
6029 json_object_string_add(json_nexthop_ll, "ip",
6030 inet_ntop (AF_INET6,
6031 &attr->extra->mp_nexthop_local,
6032 buf, BUFSIZ));
6033 json_object_string_add(json_nexthop_ll, "afi", "ipv6");
6034 json_object_string_add(json_nexthop_ll, "scope", "link-local");
6035
6036 if ((IPV6_ADDR_CMP (&attr->extra->mp_nexthop_global,
6037 &attr->extra->mp_nexthop_local) != 0) &&
6038 !attr->extra->mp_nexthop_prefer_global)
6039 json_object_boolean_true_add(json_nexthop_ll, "used");
6040 else
6041 json_object_boolean_true_add(json_nexthop_global, "used");
6042 }
6043 else
6044 json_object_boolean_true_add(json_nexthop_global, "used");
6045 }
6046 else
6047 {
6048 /* Display LL if LL/Global both in table unless prefer-global is set */
6049 if (((attr->extra->mp_nexthop_len == 32) &&
6050 !attr->extra->mp_nexthop_prefer_global) ||
6051 (binfo->peer->conf_if))
6052 {
6053 if (binfo->peer->conf_if)
6054 {
6055 len = vty_out (vty, "%s",
6056 binfo->peer->conf_if);
6057 len = 7 - len; /* len of IPv6 addr + max len of def ifname */
6058
6059 if (len < 1)
6060 vty_out (vty, "%s%*s", VTY_NEWLINE, 45, " ");
6061 else
6062 vty_out (vty, "%*s", len, " ");
6063 }
6064 else
6065 {
6066 len = vty_out (vty, "%s",
6067 inet_ntop (AF_INET6,
6068 &attr->extra->mp_nexthop_local,
6069 buf, BUFSIZ));
6070 len = 16 - len;
6071
6072 if (len < 1)
6073 vty_out (vty, "%s%*s", VTY_NEWLINE, 36, " ");
6074 else
6075 vty_out (vty, "%*s", len, " ");
6076 }
6077 }
6078 else
6079 {
6080 len = vty_out (vty, "%s",
6081 inet_ntop (AF_INET6,
6082 &attr->extra->mp_nexthop_global,
6083 buf, BUFSIZ));
6084 len = 16 - len;
6085
6086 if (len < 1)
6087 vty_out (vty, "%s%*s", VTY_NEWLINE, 36, " ");
6088 else
6089 vty_out (vty, "%*s", len, " ");
6090 }
6091 }
6092 }
6093
6094 /* MED/Metric */
6095 if (attr->flag & ATTR_FLAG_BIT (BGP_ATTR_MULTI_EXIT_DISC))
6096 if (json_paths)
6097 json_object_int_add(json_path, "med", attr->med);
6098 else
6099 vty_out (vty, "%10u", attr->med);
6100 else
6101 if (!json_paths)
6102 vty_out (vty, " ");
6103
6104 /* Local Pref */
6105 if (attr->flag & ATTR_FLAG_BIT (BGP_ATTR_LOCAL_PREF))
6106 if (json_paths)
6107 json_object_int_add(json_path, "localpref", attr->local_pref);
6108 else
6109 vty_out (vty, "%7u", attr->local_pref);
6110 else
6111 if (!json_paths)
6112 vty_out (vty, " ");
6113
6114 if (json_paths)
6115 {
6116 if (attr->extra)
6117 json_object_int_add(json_path, "weight", attr->extra->weight);
6118 else
6119 json_object_int_add(json_path, "weight", 0);
6120 }
6121 else
6122 vty_out (vty, "%7u ", (attr->extra ? attr->extra->weight : 0));
6123
6124 if (json_paths) {
6125 char buf[BUFSIZ];
6126 json_object_string_add(json_path, "peerId", sockunion2str (&binfo->peer->su, buf, SU_ADDRSTRLEN));
6127 }
6128
6129 /* Print aspath */
6130 if (attr->aspath)
6131 {
6132 if (json_paths)
6133 json_object_string_add(json_path, "aspath", attr->aspath->str);
6134 else
6135 aspath_print_vty (vty, "%s", attr->aspath, " ");
6136 }
6137
6138 /* Print origin */
6139 if (json_paths)
6140 json_object_string_add(json_path, "origin", bgp_origin_long_str[attr->origin]);
6141 else
6142 vty_out (vty, "%s", bgp_origin_str[attr->origin]);
6143 }
6144 else
6145 {
6146 if (json_paths)
6147 json_object_string_add(json_path, "alert", "No attributes");
6148 else
6149 vty_out (vty, "No attributes to print%s", VTY_NEWLINE);
6150 }
6151
6152 if (json_paths)
6153 {
6154 if (json_nexthop_global || json_nexthop_ll)
6155 {
6156 json_nexthops = json_object_new_array();
6157
6158 if (json_nexthop_global)
6159 json_object_array_add(json_nexthops, json_nexthop_global);
6160
6161 if (json_nexthop_ll)
6162 json_object_array_add(json_nexthops, json_nexthop_ll);
6163
6164 json_object_object_add(json_path, "nexthops", json_nexthops);
6165 }
6166
6167 json_object_array_add(json_paths, json_path);
6168 }
6169 else
6170 vty_out (vty, "%s", VTY_NEWLINE);
6171 }
6172
6173 /* called from terminal list command */
6174 void
6175 route_vty_out_tmp (struct vty *vty, struct prefix *p, struct attr *attr, safi_t safi,
6176 u_char use_json, json_object *json_ar)
6177 {
6178 json_object *json_status = NULL;
6179 json_object *json_net = NULL;
6180 char buff[BUFSIZ];
6181 /* Route status display. */
6182 if (use_json)
6183 {
6184 json_status = json_object_new_object();
6185 json_net = json_object_new_object();
6186 }
6187 else
6188 {
6189 vty_out (vty, "*");
6190 vty_out (vty, ">");
6191 vty_out (vty, " ");
6192 }
6193
6194 /* print prefix and mask */
6195 if (use_json)
6196 json_object_string_add(json_net, "addrPrefix", inet_ntop (p->family, &p->u.prefix, buff, BUFSIZ));
6197 else
6198 route_vty_out_route (p, vty);
6199
6200 /* Print attribute */
6201 if (attr)
6202 {
6203 if (use_json)
6204 {
6205 if (p->family == AF_INET &&
6206 (safi == SAFI_MPLS_VPN ||
6207 safi == SAFI_ENCAP ||
6208 !BGP_ATTR_NEXTHOP_AFI_IP6(attr)))
6209 {
6210 if (safi == SAFI_MPLS_VPN || safi == SAFI_ENCAP)
6211 json_object_string_add(json_net, "nextHop", inet_ntoa (attr->extra->mp_nexthop_global_in));
6212 else
6213 json_object_string_add(json_net, "nextHop", inet_ntoa (attr->nexthop));
6214 }
6215 #ifdef HAVE_IPV6
6216 else if (p->family == AF_INET6 || BGP_ATTR_NEXTHOP_AFI_IP6(attr))
6217 {
6218 char buf[BUFSIZ];
6219
6220 json_object_string_add(json_net, "netHopGloabal", inet_ntop (AF_INET6, &attr->extra->mp_nexthop_global,
6221 buf, BUFSIZ));
6222 }
6223 #endif /* HAVE_IPV6 */
6224
6225 if (attr->flag & ATTR_FLAG_BIT (BGP_ATTR_MULTI_EXIT_DISC))
6226 json_object_int_add(json_net, "metric", attr->med);
6227
6228 if (attr->flag & ATTR_FLAG_BIT (BGP_ATTR_LOCAL_PREF))
6229 json_object_int_add(json_net, "localPref", attr->local_pref);
6230
6231 if (attr->extra)
6232 json_object_int_add(json_net, "weight", attr->extra->weight);
6233 else
6234 json_object_int_add(json_net, "weight", 0);
6235
6236 /* Print aspath */
6237 if (attr->aspath)
6238 json_object_string_add(json_net, "asPath", attr->aspath->str);
6239
6240 /* Print origin */
6241 json_object_string_add(json_net, "bgpOriginCode", bgp_origin_str[attr->origin]);
6242 }
6243 else
6244 {
6245 if (p->family == AF_INET &&
6246 (safi == SAFI_MPLS_VPN ||
6247 safi == SAFI_ENCAP ||
6248 !BGP_ATTR_NEXTHOP_AFI_IP6(attr)))
6249 {
6250 if (safi == SAFI_MPLS_VPN || safi == SAFI_ENCAP)
6251 vty_out (vty, "%-16s",
6252 inet_ntoa (attr->extra->mp_nexthop_global_in));
6253 else
6254 vty_out (vty, "%-16s", inet_ntoa (attr->nexthop));
6255 }
6256 #ifdef HAVE_IPV6
6257 else if (p->family == AF_INET6 || BGP_ATTR_NEXTHOP_AFI_IP6(attr))
6258 {
6259 int len;
6260 char buf[BUFSIZ];
6261
6262 assert (attr->extra);
6263
6264 len = vty_out (vty, "%s",
6265 inet_ntop (AF_INET6, &attr->extra->mp_nexthop_global,
6266 buf, BUFSIZ));
6267 len = 16 - len;
6268 if (len < 1)
6269 vty_out (vty, "%s%*s", VTY_NEWLINE, 36, " ");
6270 else
6271 vty_out (vty, "%*s", len, " ");
6272 }
6273 #endif /* HAVE_IPV6 */
6274 if (attr->flag & ATTR_FLAG_BIT (BGP_ATTR_MULTI_EXIT_DISC))
6275 vty_out (vty, "%10u", attr->med);
6276 else
6277 vty_out (vty, " ");
6278
6279 if (attr->flag & ATTR_FLAG_BIT (BGP_ATTR_LOCAL_PREF))
6280 vty_out (vty, "%7u", attr->local_pref);
6281 else
6282 vty_out (vty, " ");
6283
6284 vty_out (vty, "%7u ", (attr->extra ? attr->extra->weight : 0));
6285
6286 /* Print aspath */
6287 if (attr->aspath)
6288 aspath_print_vty (vty, "%s", attr->aspath, " ");
6289
6290 /* Print origin */
6291 vty_out (vty, "%s", bgp_origin_str[attr->origin]);
6292 }
6293 }
6294 if (use_json)
6295 {
6296 json_object_boolean_true_add(json_status, "*");
6297 json_object_boolean_true_add(json_status, ">");
6298 json_object_object_add(json_net, "appliedStatusSymbols", json_status);
6299 char buf_cut[BUFSIZ];
6300 json_object_object_add(json_ar, inet_ntop (p->family, &p->u.prefix, buf_cut, BUFSIZ), json_net);
6301 }
6302 else
6303 vty_out (vty, "%s", VTY_NEWLINE);
6304 }
6305
6306 void
6307 route_vty_out_tag (struct vty *vty, struct prefix *p,
6308 struct bgp_info *binfo, int display, safi_t safi, json_object *json)
6309 {
6310 json_object *json_out = NULL;
6311 struct attr *attr;
6312 u_int32_t label = 0;
6313
6314 if (!binfo->extra)
6315 return;
6316
6317 if (json)
6318 json_out = json_object_new_object();
6319
6320 /* short status lead text */
6321 route_vty_short_status_out (vty, binfo, json_out);
6322
6323 /* print prefix and mask */
6324 if (json == NULL)
6325 {
6326 if (! display)
6327 route_vty_out_route (p, vty);
6328 else
6329 vty_out (vty, "%*s", 17, " ");
6330 }
6331
6332 /* Print attribute */
6333 attr = binfo->attr;
6334 if (attr)
6335 {
6336 if (p->family == AF_INET
6337 && (safi == SAFI_MPLS_VPN || !BGP_ATTR_NEXTHOP_AFI_IP6(attr)))
6338 {
6339 if (safi == SAFI_MPLS_VPN || safi == SAFI_ENCAP)
6340 {
6341 if (json)
6342 json_object_string_add(json_out, "mpNexthopGlobalIn", inet_ntoa (attr->extra->mp_nexthop_global_in));
6343 else
6344 vty_out (vty, "%-16s", inet_ntoa (attr->extra->mp_nexthop_global_in));
6345 }
6346 else
6347 {
6348 if (json)
6349 json_object_string_add(json_out, "nexthop", inet_ntoa (attr->nexthop));
6350 else
6351 vty_out (vty, "%-16s", inet_ntoa (attr->nexthop));
6352 }
6353 }
6354 #ifdef HAVE_IPV6
6355 else if (p->family == AF_INET6 || BGP_ATTR_NEXTHOP_AFI_IP6(attr))
6356 {
6357 assert (attr->extra);
6358 char buf_a[BUFSIZ];
6359 char buf_b[BUFSIZ];
6360 char buf_c[BUFSIZ];
6361 if (attr->extra->mp_nexthop_len == BGP_ATTR_NHLEN_IPV6_GLOBAL)
6362 {
6363 if (json)
6364 json_object_string_add(json_out, "mpNexthopGlobalIn",
6365 inet_ntop (AF_INET6, &attr->extra->mp_nexthop_global, buf_a, BUFSIZ));
6366 else
6367 vty_out (vty, "%s",
6368 inet_ntop (AF_INET6, &attr->extra->mp_nexthop_global,
6369 buf_a, BUFSIZ));
6370 }
6371 else if (attr->extra->mp_nexthop_len == BGP_ATTR_NHLEN_IPV6_GLOBAL_AND_LL)
6372 {
6373 if (json)
6374 {
6375 inet_ntop (AF_INET6, &attr->extra->mp_nexthop_global,
6376 buf_a, BUFSIZ);
6377 inet_ntop (AF_INET6, &attr->extra->mp_nexthop_local,
6378 buf_b, BUFSIZ);
6379 sprintf(buf_c, "%s(%s)", buf_a, buf_b);
6380 json_object_string_add(json_out, "mpNexthopGlobalLocal", buf_c);
6381 }
6382 else
6383 vty_out (vty, "%s(%s)",
6384 inet_ntop (AF_INET6, &attr->extra->mp_nexthop_global,
6385 buf_a, BUFSIZ),
6386 inet_ntop (AF_INET6, &attr->extra->mp_nexthop_local,
6387 buf_b, BUFSIZ));
6388 }
6389
6390 }
6391 #endif /* HAVE_IPV6 */
6392 }
6393
6394 label = decode_label (binfo->extra->tag);
6395
6396 if (json)
6397 {
6398 if (label)
6399 json_object_int_add(json_out, "notag", label);
6400 json_object_array_add(json, json_out);
6401 }
6402 else
6403 {
6404 vty_out (vty, "notag/%d", label);
6405 vty_out (vty, "%s", VTY_NEWLINE);
6406 }
6407 }
6408
6409 /* dampening route */
6410 static void
6411 damp_route_vty_out (struct vty *vty, struct prefix *p, struct bgp_info *binfo,
6412 int display, safi_t safi, u_char use_json, json_object *json)
6413 {
6414 struct attr *attr;
6415 int len;
6416 char timebuf[BGP_UPTIME_LEN];
6417
6418 /* short status lead text */
6419 route_vty_short_status_out (vty, binfo, json);
6420
6421 /* print prefix and mask */
6422 if (!use_json)
6423 {
6424 if (! display)
6425 route_vty_out_route (p, vty);
6426 else
6427 vty_out (vty, "%*s", 17, " ");
6428 }
6429
6430 len = vty_out (vty, "%s", binfo->peer->host);
6431 len = 17 - len;
6432 if (len < 1)
6433 {
6434 if (!use_json)
6435 vty_out (vty, "%s%*s", VTY_NEWLINE, 34, " ");
6436 }
6437 else
6438 {
6439 if (use_json)
6440 json_object_int_add(json, "peerHost", len);
6441 else
6442 vty_out (vty, "%*s", len, " ");
6443 }
6444
6445 if (use_json)
6446 bgp_damp_reuse_time_vty (vty, binfo, timebuf, BGP_UPTIME_LEN, use_json, json);
6447 else
6448 vty_out (vty, "%s ", bgp_damp_reuse_time_vty (vty, binfo, timebuf, BGP_UPTIME_LEN, use_json, json));
6449
6450 /* Print attribute */
6451 attr = binfo->attr;
6452 if (attr)
6453 {
6454 /* Print aspath */
6455 if (attr->aspath)
6456 {
6457 if (use_json)
6458 json_object_string_add(json, "asPath", attr->aspath->str);
6459 else
6460 aspath_print_vty (vty, "%s", attr->aspath, " ");
6461 }
6462
6463 /* Print origin */
6464 if (use_json)
6465 json_object_string_add(json, "origin", bgp_origin_str[attr->origin]);
6466 else
6467 vty_out (vty, "%s", bgp_origin_str[attr->origin]);
6468 }
6469 if (!use_json)
6470 vty_out (vty, "%s", VTY_NEWLINE);
6471 }
6472
6473 /* flap route */
6474 static void
6475 flap_route_vty_out (struct vty *vty, struct prefix *p, struct bgp_info *binfo,
6476 int display, safi_t safi, u_char use_json, json_object *json)
6477 {
6478 struct attr *attr;
6479 struct bgp_damp_info *bdi;
6480 char timebuf[BGP_UPTIME_LEN];
6481 int len;
6482
6483 if (!binfo->extra)
6484 return;
6485
6486 bdi = binfo->extra->damp_info;
6487
6488 /* short status lead text */
6489 route_vty_short_status_out (vty, binfo, json);
6490
6491 /* print prefix and mask */
6492 if (!use_json)
6493 {
6494 if (! display)
6495 route_vty_out_route (p, vty);
6496 else
6497 vty_out (vty, "%*s", 17, " ");
6498 }
6499
6500 len = vty_out (vty, "%s", binfo->peer->host);
6501 len = 16 - len;
6502 if (len < 1)
6503 {
6504 if (!use_json)
6505 vty_out (vty, "%s%*s", VTY_NEWLINE, 33, " ");
6506 }
6507 else
6508 {
6509 if (use_json)
6510 json_object_int_add(json, "peerHost", len);
6511 else
6512 vty_out (vty, "%*s", len, " ");
6513 }
6514
6515 len = vty_out (vty, "%d", bdi->flap);
6516 len = 5 - len;
6517 if (len < 1)
6518 {
6519 if (!use_json)
6520 vty_out (vty, " ");
6521 }
6522 else
6523 {
6524 if (use_json)
6525 json_object_int_add(json, "bdiFlap", len);
6526 else
6527 vty_out (vty, "%*s", len, " ");
6528 }
6529
6530 if (use_json)
6531 peer_uptime (bdi->start_time, timebuf, BGP_UPTIME_LEN, use_json, json);
6532 else
6533 vty_out (vty, "%s ", peer_uptime (bdi->start_time,
6534 timebuf, BGP_UPTIME_LEN, 0, NULL));
6535
6536 if (CHECK_FLAG (binfo->flags, BGP_INFO_DAMPED)
6537 && ! CHECK_FLAG (binfo->flags, BGP_INFO_HISTORY))
6538 {
6539 if (use_json)
6540 bgp_damp_reuse_time_vty (vty, binfo, timebuf, BGP_UPTIME_LEN, use_json, json);
6541 else
6542 vty_out (vty, "%s ", bgp_damp_reuse_time_vty (vty, binfo, timebuf, BGP_UPTIME_LEN, use_json, json));
6543 }
6544 else
6545 {
6546 if (!use_json)
6547 vty_out (vty, "%*s ", 8, " ");
6548 }
6549
6550 /* Print attribute */
6551 attr = binfo->attr;
6552 if (attr)
6553 {
6554 /* Print aspath */
6555 if (attr->aspath)
6556 {
6557 if (use_json)
6558 json_object_string_add(json, "asPath", attr->aspath->str);
6559 else
6560 aspath_print_vty (vty, "%s", attr->aspath, " ");
6561 }
6562
6563 /* Print origin */
6564 if (use_json)
6565 json_object_string_add(json, "origin", bgp_origin_str[attr->origin]);
6566 else
6567 vty_out (vty, "%s", bgp_origin_str[attr->origin]);
6568 }
6569 if (!use_json)
6570 vty_out (vty, "%s", VTY_NEWLINE);
6571 }
6572
6573 static void
6574 route_vty_out_advertised_to (struct vty *vty, struct peer *peer, int *first,
6575 const char *header, json_object *json_adv_to)
6576 {
6577 char buf1[INET6_ADDRSTRLEN];
6578 json_object *json_peer = NULL;
6579
6580 if (json_adv_to)
6581 {
6582 /* 'advertised-to' is a dictionary of peers we have advertised this
6583 * prefix too. The key is the peer's IP or swpX, the value is the
6584 * hostname if we know it and "" if not.
6585 */
6586 json_peer = json_object_new_object();
6587
6588 if (peer->hostname)
6589 json_object_string_add(json_peer, "hostname", peer->hostname);
6590
6591 if (peer->conf_if)
6592 json_object_object_add(json_adv_to, peer->conf_if, json_peer);
6593 else
6594 json_object_object_add(json_adv_to,
6595 sockunion2str (&peer->su, buf1, SU_ADDRSTRLEN),
6596 json_peer);
6597 }
6598 else
6599 {
6600 if (*first)
6601 {
6602 vty_out (vty, "%s", header);
6603 *first = 0;
6604 }
6605
6606 if (peer->hostname && bgp_flag_check(peer->bgp, BGP_FLAG_SHOW_HOSTNAME))
6607 {
6608 if (peer->conf_if)
6609 vty_out (vty, " %s(%s)", peer->hostname, peer->conf_if);
6610 else
6611 vty_out (vty, " %s(%s)", peer->hostname,
6612 sockunion2str (&peer->su, buf1, SU_ADDRSTRLEN));
6613 }
6614 else
6615 {
6616 if (peer->conf_if)
6617 vty_out (vty, " %s", peer->conf_if);
6618 else
6619 vty_out (vty, " %s", sockunion2str (&peer->su, buf1, SU_ADDRSTRLEN));
6620 }
6621 }
6622 }
6623
6624 static void
6625 route_vty_out_detail (struct vty *vty, struct bgp *bgp, struct prefix *p,
6626 struct bgp_info *binfo, afi_t afi, safi_t safi,
6627 json_object *json_paths)
6628 {
6629 char buf[INET6_ADDRSTRLEN];
6630 char buf1[BUFSIZ];
6631 struct attr *attr;
6632 int sockunion_vty_out (struct vty *, union sockunion *);
6633 #ifdef HAVE_CLOCK_MONOTONIC
6634 time_t tbuf;
6635 #endif
6636 json_object *json_bestpath = NULL;
6637 json_object *json_cluster_list = NULL;
6638 json_object *json_cluster_list_list = NULL;
6639 json_object *json_ext_community = NULL;
6640 json_object *json_last_update = NULL;
6641 json_object *json_nexthop_global = NULL;
6642 json_object *json_nexthop_ll = NULL;
6643 json_object *json_nexthops = NULL;
6644 json_object *json_path = NULL;
6645 json_object *json_peer = NULL;
6646 json_object *json_string = NULL;
6647 json_object *json_adv_to = NULL;
6648 int first = 0;
6649 struct listnode *node, *nnode;
6650 struct peer *peer;
6651 int addpath_capable;
6652 int has_adj;
6653 int first_as;
6654
6655 if (json_paths)
6656 {
6657 json_path = json_object_new_object();
6658 json_peer = json_object_new_object();
6659 json_nexthop_global = json_object_new_object();
6660 }
6661
6662 attr = binfo->attr;
6663
6664 if (attr)
6665 {
6666 /* Line1 display AS-path, Aggregator */
6667 if (attr->aspath)
6668 {
6669 if (json_paths)
6670 {
6671 json_object_lock(attr->aspath->json);
6672 json_object_object_add(json_path, "aspath", attr->aspath->json);
6673 }
6674 else
6675 {
6676 if (attr->aspath->segments)
6677 aspath_print_vty (vty, " %s", attr->aspath, "");
6678 else
6679 vty_out (vty, " Local");
6680 }
6681 }
6682
6683 if (CHECK_FLAG (binfo->flags, BGP_INFO_REMOVED))
6684 {
6685 if (json_paths)
6686 json_object_boolean_true_add(json_path, "removed");
6687 else
6688 vty_out (vty, ", (removed)");
6689 }
6690
6691 if (CHECK_FLAG (binfo->flags, BGP_INFO_STALE))
6692 {
6693 if (json_paths)
6694 json_object_boolean_true_add(json_path, "stale");
6695 else
6696 vty_out (vty, ", (stale)");
6697 }
6698
6699 if (CHECK_FLAG (attr->flag, ATTR_FLAG_BIT (BGP_ATTR_AGGREGATOR)))
6700 {
6701 if (json_paths)
6702 {
6703 json_object_int_add(json_path, "aggregatorAs", attr->extra->aggregator_as);
6704 json_object_string_add(json_path, "aggregatorId", inet_ntoa (attr->extra->aggregator_addr));
6705 }
6706 else
6707 {
6708 vty_out (vty, ", (aggregated by %u %s)",
6709 attr->extra->aggregator_as,
6710 inet_ntoa (attr->extra->aggregator_addr));
6711 }
6712 }
6713
6714 if (CHECK_FLAG (binfo->peer->af_flags[afi][safi], PEER_FLAG_REFLECTOR_CLIENT))
6715 {
6716 if (json_paths)
6717 json_object_boolean_true_add(json_path, "rxedFromRrClient");
6718 else
6719 vty_out (vty, ", (Received from a RR-client)");
6720 }
6721
6722 if (CHECK_FLAG (binfo->peer->af_flags[afi][safi], PEER_FLAG_RSERVER_CLIENT))
6723 {
6724 if (json_paths)
6725 json_object_boolean_true_add(json_path, "rxedFromRsClient");
6726 else
6727 vty_out (vty, ", (Received from a RS-client)");
6728 }
6729
6730 if (CHECK_FLAG (binfo->flags, BGP_INFO_HISTORY))
6731 {
6732 if (json_paths)
6733 json_object_boolean_true_add(json_path, "dampeningHistoryEntry");
6734 else
6735 vty_out (vty, ", (history entry)");
6736 }
6737 else if (CHECK_FLAG (binfo->flags, BGP_INFO_DAMPED))
6738 {
6739 if (json_paths)
6740 json_object_boolean_true_add(json_path, "dampeningSuppressed");
6741 else
6742 vty_out (vty, ", (suppressed due to dampening)");
6743 }
6744
6745 if (!json_paths)
6746 vty_out (vty, "%s", VTY_NEWLINE);
6747
6748 /* Line2 display Next-hop, Neighbor, Router-id */
6749 /* Display the nexthop */
6750 if (p->family == AF_INET &&
6751 (safi == SAFI_MPLS_VPN ||
6752 safi == SAFI_ENCAP ||
6753 !BGP_ATTR_NEXTHOP_AFI_IP6(attr)))
6754 {
6755 if (safi == SAFI_MPLS_VPN || safi == SAFI_ENCAP)
6756 {
6757 if (json_paths)
6758 json_object_string_add(json_nexthop_global, "ip", inet_ntoa (attr->extra->mp_nexthop_global_in));
6759 else
6760 vty_out (vty, " %s", inet_ntoa (attr->extra->mp_nexthop_global_in));
6761 }
6762 else
6763 {
6764 if (json_paths)
6765 json_object_string_add(json_nexthop_global, "ip", inet_ntoa (attr->nexthop));
6766 else
6767 vty_out (vty, " %s", inet_ntoa (attr->nexthop));
6768 }
6769
6770 if (json_paths)
6771 json_object_string_add(json_nexthop_global, "afi", "ipv4");
6772 }
6773 else
6774 {
6775 assert (attr->extra);
6776 if (json_paths)
6777 {
6778 json_object_string_add(json_nexthop_global, "ip",
6779 inet_ntop (AF_INET6, &attr->extra->mp_nexthop_global,
6780 buf, INET6_ADDRSTRLEN));
6781 json_object_string_add(json_nexthop_global, "afi", "ipv6");
6782 json_object_string_add(json_nexthop_global, "scope", "global");
6783 }
6784 else
6785 {
6786 vty_out (vty, " %s",
6787 inet_ntop (AF_INET6, &attr->extra->mp_nexthop_global,
6788 buf, INET6_ADDRSTRLEN));
6789 }
6790 }
6791
6792 /* Display the IGP cost or 'inaccessible' */
6793 if (! CHECK_FLAG (binfo->flags, BGP_INFO_VALID))
6794 {
6795 if (json_paths)
6796 json_object_boolean_false_add(json_nexthop_global, "accessible");
6797 else
6798 vty_out (vty, " (inaccessible)");
6799 }
6800 else
6801 {
6802 if (binfo->extra && binfo->extra->igpmetric)
6803 {
6804 if (json_paths)
6805 json_object_int_add(json_nexthop_global, "metric", binfo->extra->igpmetric);
6806 else
6807 vty_out (vty, " (metric %u)", binfo->extra->igpmetric);
6808 }
6809
6810 /* IGP cost is 0, display this only for json */
6811 else
6812 {
6813 if (json_paths)
6814 json_object_int_add(json_nexthop_global, "metric", 0);
6815 }
6816
6817 if (json_paths)
6818 json_object_boolean_true_add(json_nexthop_global, "accessible");
6819 }
6820
6821 /* Display peer "from" output */
6822 /* This path was originated locally */
6823 if (binfo->peer == bgp->peer_self)
6824 {
6825
6826 if (p->family == AF_INET && !BGP_ATTR_NEXTHOP_AFI_IP6(attr))
6827 {
6828 if (json_paths)
6829 json_object_string_add(json_peer, "peerId", "0.0.0.0");
6830 else
6831 vty_out (vty, " from 0.0.0.0 ");
6832 }
6833 else
6834 {
6835 if (json_paths)
6836 json_object_string_add(json_peer, "peerId", "::");
6837 else
6838 vty_out (vty, " from :: ");
6839 }
6840
6841 if (json_paths)
6842 json_object_string_add(json_peer, "routerId", inet_ntoa(bgp->router_id));
6843 else
6844 vty_out (vty, "(%s)", inet_ntoa(bgp->router_id));
6845 }
6846
6847 /* We RXed this path from one of our peers */
6848 else
6849 {
6850
6851 if (json_paths)
6852 {
6853 json_object_string_add(json_peer, "peerId", sockunion2str (&binfo->peer->su, buf, SU_ADDRSTRLEN));
6854 json_object_string_add(json_peer, "routerId", inet_ntop (AF_INET, &binfo->peer->remote_id, buf1, BUFSIZ));
6855
6856 if (binfo->peer->hostname)
6857 json_object_string_add(json_peer, "hostname", binfo->peer->hostname);
6858
6859 if (binfo->peer->domainname)
6860 json_object_string_add(json_peer, "domainname", binfo->peer->domainname);
6861
6862 if (binfo->peer->conf_if)
6863 json_object_string_add(json_peer, "interface", binfo->peer->conf_if);
6864 }
6865 else
6866 {
6867 if (binfo->peer->conf_if)
6868 {
6869 if (binfo->peer->hostname &&
6870 bgp_flag_check(binfo->peer->bgp, BGP_FLAG_SHOW_HOSTNAME))
6871 vty_out (vty, " from %s(%s)", binfo->peer->hostname,
6872 binfo->peer->conf_if);
6873 else
6874 vty_out (vty, " from %s", binfo->peer->conf_if);
6875 }
6876 else
6877 {
6878 if (binfo->peer->hostname &&
6879 bgp_flag_check(binfo->peer->bgp, BGP_FLAG_SHOW_HOSTNAME))
6880 vty_out (vty, " from %s(%s)", binfo->peer->hostname,
6881 binfo->peer->host);
6882 else
6883 vty_out (vty, " from %s", sockunion2str (&binfo->peer->su, buf, SU_ADDRSTRLEN));
6884 }
6885
6886 if (attr->flag & ATTR_FLAG_BIT(BGP_ATTR_ORIGINATOR_ID))
6887 vty_out (vty, " (%s)", inet_ntoa (attr->extra->originator_id));
6888 else
6889 vty_out (vty, " (%s)", inet_ntop (AF_INET, &binfo->peer->remote_id, buf1, BUFSIZ));
6890 }
6891 }
6892
6893 if (!json_paths)
6894 vty_out (vty, "%s", VTY_NEWLINE);
6895
6896 /* display the link-local nexthop */
6897 if (attr->extra && attr->extra->mp_nexthop_len == BGP_ATTR_NHLEN_IPV6_GLOBAL_AND_LL)
6898 {
6899 if (json_paths)
6900 {
6901 json_nexthop_ll = json_object_new_object();
6902 json_object_string_add(json_nexthop_ll, "ip",
6903 inet_ntop (AF_INET6, &attr->extra->mp_nexthop_local,
6904 buf, INET6_ADDRSTRLEN));
6905 json_object_string_add(json_nexthop_ll, "afi", "ipv6");
6906 json_object_string_add(json_nexthop_ll, "scope", "link-local");
6907
6908 json_object_boolean_true_add(json_nexthop_ll, "accessible");
6909
6910 if (!attr->extra->mp_nexthop_prefer_global)
6911 json_object_boolean_true_add(json_nexthop_ll, "used");
6912 else
6913 json_object_boolean_true_add(json_nexthop_global, "used");
6914 }
6915 else
6916 {
6917 vty_out (vty, " (%s) %s%s",
6918 inet_ntop (AF_INET6, &attr->extra->mp_nexthop_local,
6919 buf, INET6_ADDRSTRLEN),
6920 attr->extra->mp_nexthop_prefer_global ?
6921 "(prefer-global)" : "(used)",
6922 VTY_NEWLINE);
6923 }
6924 }
6925 /* If we do not have a link-local nexthop then we must flag the global as "used" */
6926 else
6927 {
6928 if (json_paths)
6929 json_object_boolean_true_add(json_nexthop_global, "used");
6930 }
6931
6932 /* Line 3 display Origin, Med, Locpref, Weight, Tag, valid, Int/Ext/Local, Atomic, best */
6933 if (json_paths)
6934 json_object_string_add(json_path, "origin", bgp_origin_long_str[attr->origin]);
6935 else
6936 vty_out (vty, " Origin %s", bgp_origin_long_str[attr->origin]);
6937
6938 if (attr->flag & ATTR_FLAG_BIT(BGP_ATTR_MULTI_EXIT_DISC))
6939 {
6940 if (json_paths)
6941 json_object_int_add(json_path, "med", attr->med);
6942 else
6943 vty_out (vty, ", metric %u", attr->med);
6944 }
6945
6946 if (attr->flag & ATTR_FLAG_BIT(BGP_ATTR_LOCAL_PREF))
6947 {
6948 if (json_paths)
6949 json_object_int_add(json_path, "localpref", attr->local_pref);
6950 else
6951 vty_out (vty, ", localpref %u", attr->local_pref);
6952 }
6953 else
6954 {
6955 if (json_paths)
6956 json_object_int_add(json_path, "localpref", bgp->default_local_pref);
6957 else
6958 vty_out (vty, ", localpref %u", bgp->default_local_pref);
6959 }
6960
6961 if (attr->extra && attr->extra->weight != 0)
6962 {
6963 if (json_paths)
6964 json_object_int_add(json_path, "weight", attr->extra->weight);
6965 else
6966 vty_out (vty, ", weight %u", attr->extra->weight);
6967 }
6968
6969 if (attr->extra && attr->extra->tag != 0)
6970 {
6971 if (json_paths)
6972 json_object_int_add(json_path, "tag", attr->extra->tag);
6973 else
6974 vty_out (vty, ", tag %d", attr->extra->tag);
6975 }
6976
6977 if (! CHECK_FLAG (binfo->flags, BGP_INFO_VALID))
6978 {
6979 if (json_paths)
6980 json_object_boolean_false_add(json_path, "valid");
6981 else
6982 vty_out (vty, ", invalid");
6983 }
6984 else if (! CHECK_FLAG (binfo->flags, BGP_INFO_HISTORY))
6985 {
6986 if (json_paths)
6987 json_object_boolean_true_add(json_path, "valid");
6988 else
6989 vty_out (vty, ", valid");
6990 }
6991
6992 if (binfo->peer != bgp->peer_self)
6993 {
6994 if (binfo->peer->as == binfo->peer->local_as)
6995 {
6996 if (CHECK_FLAG(bgp->config, BGP_CONFIG_CONFEDERATION))
6997 {
6998 if (json_paths)
6999 json_object_string_add(json_peer, "type", "confed-internal");
7000 else
7001 vty_out (vty, ", confed-internal");
7002 }
7003 else
7004 {
7005 if (json_paths)
7006 json_object_string_add(json_peer, "type", "internal");
7007 else
7008 vty_out (vty, ", internal");
7009 }
7010 }
7011 else
7012 {
7013 if (bgp_confederation_peers_check(bgp, binfo->peer->as))
7014 {
7015 if (json_paths)
7016 json_object_string_add(json_peer, "type", "confed-external");
7017 else
7018 vty_out (vty, ", confed-external");
7019 }
7020 else
7021 {
7022 if (json_paths)
7023 json_object_string_add(json_peer, "type", "external");
7024 else
7025 vty_out (vty, ", external");
7026 }
7027 }
7028 }
7029 else if (binfo->sub_type == BGP_ROUTE_AGGREGATE)
7030 {
7031 if (json_paths)
7032 {
7033 json_object_boolean_true_add(json_path, "aggregated");
7034 json_object_boolean_true_add(json_path, "local");
7035 }
7036 else
7037 {
7038 vty_out (vty, ", aggregated, local");
7039 }
7040 }
7041 else if (binfo->type != ZEBRA_ROUTE_BGP)
7042 {
7043 if (json_paths)
7044 json_object_boolean_true_add(json_path, "sourced");
7045 else
7046 vty_out (vty, ", sourced");
7047 }
7048 else
7049 {
7050 if (json_paths)
7051 {
7052 json_object_boolean_true_add(json_path, "sourced");
7053 json_object_boolean_true_add(json_path, "local");
7054 }
7055 else
7056 {
7057 vty_out (vty, ", sourced, local");
7058 }
7059 }
7060
7061 if (attr->flag & ATTR_FLAG_BIT(BGP_ATTR_ATOMIC_AGGREGATE))
7062 {
7063 if (json_paths)
7064 json_object_boolean_true_add(json_path, "atomicAggregate");
7065 else
7066 vty_out (vty, ", atomic-aggregate");
7067 }
7068
7069 if (CHECK_FLAG (binfo->flags, BGP_INFO_MULTIPATH) ||
7070 (CHECK_FLAG (binfo->flags, BGP_INFO_SELECTED) &&
7071 bgp_info_mpath_count (binfo)))
7072 {
7073 if (json_paths)
7074 json_object_boolean_true_add(json_path, "multipath");
7075 else
7076 vty_out (vty, ", multipath");
7077 }
7078
7079 // Mark the bestpath(s)
7080 if (CHECK_FLAG (binfo->flags, BGP_INFO_DMED_SELECTED))
7081 {
7082 first_as = aspath_get_firstas(attr->aspath);
7083
7084 if (json_paths)
7085 {
7086 if (!json_bestpath)
7087 json_bestpath = json_object_new_object();
7088 json_object_int_add(json_bestpath, "bestpathFromAs", first_as);
7089 }
7090 else
7091 {
7092 if (first_as)
7093 vty_out (vty, ", bestpath-from-AS %d", first_as);
7094 else
7095 vty_out (vty, ", bestpath-from-AS Local");
7096 }
7097 }
7098
7099 if (CHECK_FLAG (binfo->flags, BGP_INFO_SELECTED))
7100 {
7101 if (json_paths)
7102 {
7103 if (!json_bestpath)
7104 json_bestpath = json_object_new_object();
7105 json_object_boolean_true_add(json_bestpath, "overall");
7106 }
7107 else
7108 vty_out (vty, ", best");
7109 }
7110
7111 if (json_bestpath)
7112 json_object_object_add(json_path, "bestpath", json_bestpath);
7113
7114 if (!json_paths)
7115 vty_out (vty, "%s", VTY_NEWLINE);
7116
7117 /* Line 4 display Community */
7118 if (attr->community)
7119 {
7120 if (json_paths)
7121 {
7122 json_object_lock(attr->community->json);
7123 json_object_object_add(json_path, "community", attr->community->json);
7124 }
7125 else
7126 {
7127 vty_out (vty, " Community: %s%s", attr->community->str,
7128 VTY_NEWLINE);
7129 }
7130 }
7131
7132 /* Line 5 display Extended-community */
7133 if (attr->flag & ATTR_FLAG_BIT(BGP_ATTR_EXT_COMMUNITIES))
7134 {
7135 if (json_paths)
7136 {
7137 json_ext_community = json_object_new_object();
7138 json_object_string_add(json_ext_community, "string", attr->extra->ecommunity->str);
7139 json_object_object_add(json_path, "extendedCommunity", json_ext_community);
7140 }
7141 else
7142 {
7143 vty_out (vty, " Extended Community: %s%s",
7144 attr->extra->ecommunity->str, VTY_NEWLINE);
7145 }
7146 }
7147
7148 /* Line 6 display Originator, Cluster-id */
7149 if ((attr->flag & ATTR_FLAG_BIT(BGP_ATTR_ORIGINATOR_ID)) ||
7150 (attr->flag & ATTR_FLAG_BIT(BGP_ATTR_CLUSTER_LIST)))
7151 {
7152 assert (attr->extra);
7153 if (attr->flag & ATTR_FLAG_BIT(BGP_ATTR_ORIGINATOR_ID))
7154 {
7155 if (json_paths)
7156 json_object_string_add(json_path, "originatorId", inet_ntoa (attr->extra->originator_id));
7157 else
7158 vty_out (vty, " Originator: %s",
7159 inet_ntoa (attr->extra->originator_id));
7160 }
7161
7162 if (attr->flag & ATTR_FLAG_BIT(BGP_ATTR_CLUSTER_LIST))
7163 {
7164 int i;
7165
7166 if (json_paths)
7167 {
7168 json_cluster_list = json_object_new_object();
7169 json_cluster_list_list = json_object_new_array();
7170
7171 for (i = 0; i < attr->extra->cluster->length / 4; i++)
7172 {
7173 json_string = json_object_new_string(inet_ntoa (attr->extra->cluster->list[i]));
7174 json_object_array_add(json_cluster_list_list, json_string);
7175 }
7176
7177 /* struct cluster_list does not have "str" variable like
7178 * aspath and community do. Add this someday if someone
7179 * asks for it.
7180 json_object_string_add(json_cluster_list, "string", attr->extra->cluster->str);
7181 */
7182 json_object_object_add(json_cluster_list, "list", json_cluster_list_list);
7183 json_object_object_add(json_path, "clusterList", json_cluster_list);
7184 }
7185 else
7186 {
7187 vty_out (vty, ", Cluster list: ");
7188
7189 for (i = 0; i < attr->extra->cluster->length / 4; i++)
7190 {
7191 vty_out (vty, "%s ",
7192 inet_ntoa (attr->extra->cluster->list[i]));
7193 }
7194 }
7195 }
7196
7197 if (!json_paths)
7198 vty_out (vty, "%s", VTY_NEWLINE);
7199 }
7200
7201 if (binfo->extra && binfo->extra->damp_info)
7202 bgp_damp_info_vty (vty, binfo, json_path);
7203
7204 /* Line 7 display Addpath IDs */
7205 if (binfo->addpath_rx_id || binfo->addpath_tx_id)
7206 {
7207 if (json_paths)
7208 {
7209 json_object_int_add(json_path, "addpathRxId", binfo->addpath_rx_id);
7210 json_object_int_add(json_path, "addpathTxId", binfo->addpath_tx_id);
7211 }
7212 else
7213 {
7214 vty_out (vty, " AddPath ID: RX %u, TX %u%s",
7215 binfo->addpath_rx_id, binfo->addpath_tx_id,
7216 VTY_NEWLINE);
7217 }
7218 }
7219
7220 /* If we used addpath to TX a non-bestpath we need to display
7221 * "Advertised to" on a path-by-path basis */
7222 if (bgp->addpath_tx_used[afi][safi])
7223 {
7224 first = 1;
7225
7226 for (ALL_LIST_ELEMENTS (bgp->peer, node, nnode, peer))
7227 {
7228 addpath_capable = bgp_addpath_encode_tx (peer, afi, safi);
7229 has_adj = bgp_adj_out_lookup (peer, binfo->net, binfo->addpath_tx_id);
7230
7231 if ((addpath_capable && has_adj) ||
7232 (!addpath_capable && has_adj && CHECK_FLAG (binfo->flags, BGP_INFO_SELECTED)))
7233 {
7234 if (json_path && !json_adv_to)
7235 json_adv_to = json_object_new_object();
7236
7237 route_vty_out_advertised_to(vty, peer, &first,
7238 " Advertised to:",
7239 json_adv_to);
7240 }
7241 }
7242
7243 if (json_path)
7244 {
7245 if (json_adv_to)
7246 {
7247 json_object_object_add(json_path, "advertisedTo", json_adv_to);
7248 }
7249 }
7250 else
7251 {
7252 if (!first)
7253 {
7254 vty_out (vty, "%s", VTY_NEWLINE);
7255 }
7256 }
7257 }
7258
7259 /* Line 8 display Uptime */
7260 #ifdef HAVE_CLOCK_MONOTONIC
7261 tbuf = time(NULL) - (bgp_clock() - binfo->uptime);
7262 if (json_paths)
7263 {
7264 json_last_update = json_object_new_object();
7265 json_object_int_add(json_last_update, "epoch", tbuf);
7266 json_object_string_add(json_last_update, "string", ctime(&tbuf));
7267 json_object_object_add(json_path, "lastUpdate", json_last_update);
7268 }
7269 else
7270 vty_out (vty, " Last update: %s", ctime(&tbuf));
7271 #else
7272 if (json_paths)
7273 {
7274 json_last_update = json_object_new_object();
7275 json_object_int_add(json_last_update, "epoch", tbuf);
7276 json_object_string_add(json_last_update, "string", ctime(&binfo->uptime));
7277 json_object_object_add(json_path, "lastUpdate", json_last_update);
7278 }
7279 else
7280 vty_out (vty, " Last update: %s", ctime(&binfo->uptime));
7281 #endif /* HAVE_CLOCK_MONOTONIC */
7282 }
7283
7284 /* We've constructed the json object for this path, add it to the json
7285 * array of paths
7286 */
7287 if (json_paths)
7288 {
7289 if (json_nexthop_global || json_nexthop_ll)
7290 {
7291 json_nexthops = json_object_new_array();
7292
7293 if (json_nexthop_global)
7294 json_object_array_add(json_nexthops, json_nexthop_global);
7295
7296 if (json_nexthop_ll)
7297 json_object_array_add(json_nexthops, json_nexthop_ll);
7298
7299 json_object_object_add(json_path, "nexthops", json_nexthops);
7300 }
7301
7302 json_object_object_add(json_path, "peer", json_peer);
7303 json_object_array_add(json_paths, json_path);
7304 }
7305 else
7306 vty_out (vty, "%s", VTY_NEWLINE);
7307 }
7308
7309 #define BGP_SHOW_HEADER_CSV "Flags, Network, Next Hop, Metric, LocPrf, Weight, Path%s"
7310 #define BGP_SHOW_DAMP_HEADER " Network From Reuse Path%s"
7311 #define BGP_SHOW_FLAP_HEADER " Network From Flaps Duration Reuse Path%s"
7312
7313 enum bgp_show_type
7314 {
7315 bgp_show_type_normal,
7316 bgp_show_type_regexp,
7317 bgp_show_type_prefix_list,
7318 bgp_show_type_filter_list,
7319 bgp_show_type_route_map,
7320 bgp_show_type_neighbor,
7321 bgp_show_type_cidr_only,
7322 bgp_show_type_prefix_longer,
7323 bgp_show_type_community_all,
7324 bgp_show_type_community,
7325 bgp_show_type_community_exact,
7326 bgp_show_type_community_list,
7327 bgp_show_type_community_list_exact,
7328 bgp_show_type_flap_statistics,
7329 bgp_show_type_flap_address,
7330 bgp_show_type_flap_prefix,
7331 bgp_show_type_flap_cidr_only,
7332 bgp_show_type_flap_regexp,
7333 bgp_show_type_flap_filter_list,
7334 bgp_show_type_flap_prefix_list,
7335 bgp_show_type_flap_prefix_longer,
7336 bgp_show_type_flap_route_map,
7337 bgp_show_type_flap_neighbor,
7338 bgp_show_type_dampend_paths,
7339 bgp_show_type_damp_neighbor
7340 };
7341
7342 static int
7343 bgp_show_prefix_list (struct vty *vty, const char *name,
7344 const char *prefix_list_str, afi_t afi,
7345 safi_t safi, enum bgp_show_type type);
7346 static int
7347 bgp_show_filter_list (struct vty *vty, const char *name,
7348 const char *filter, afi_t afi,
7349 safi_t safi, enum bgp_show_type type);
7350 static int
7351 bgp_show_route_map (struct vty *vty, const char *name,
7352 const char *rmap_str, afi_t afi,
7353 safi_t safi, enum bgp_show_type type);
7354 static int
7355 bgp_show_community_list (struct vty *vty, const char *name,
7356 const char *com, int exact,
7357 afi_t afi, safi_t safi);
7358 static int
7359 bgp_show_prefix_longer (struct vty *vty, const char *name,
7360 const char *prefix, afi_t afi,
7361 safi_t safi, enum bgp_show_type type);
7362
7363 static int
7364 bgp_show_table (struct vty *vty, struct bgp_table *table,
7365 struct in_addr *router_id, enum bgp_show_type type,
7366 void *output_arg, u_char use_json, json_object *json)
7367 {
7368 struct bgp_info *ri;
7369 struct bgp_node *rn;
7370 int header = 1;
7371 int display;
7372 unsigned long output_count;
7373 struct prefix *p;
7374 char buf[BUFSIZ];
7375 char buf2[BUFSIZ];
7376 json_object *json_paths = NULL;
7377 json_object *json_routes = NULL;
7378
7379 if (use_json)
7380 {
7381 if (json == NULL)
7382 json = json_object_new_object();
7383
7384 json_object_int_add(json, "tableVersion", table->version);
7385 json_object_string_add(json, "routerId", inet_ntoa (*router_id));
7386 json_routes = json_object_new_object();
7387 }
7388
7389 /* This is first entry point, so reset total line. */
7390 output_count = 0;
7391
7392 /* Start processing of routes. */
7393 for (rn = bgp_table_top (table); rn; rn = bgp_route_next (rn))
7394 if (rn->info != NULL)
7395 {
7396 display = 0;
7397
7398 if (use_json)
7399 json_paths = json_object_new_array();
7400 else
7401 json_paths = NULL;
7402
7403 for (ri = rn->info; ri; ri = ri->next)
7404 {
7405 if (type == bgp_show_type_flap_statistics
7406 || type == bgp_show_type_flap_address
7407 || type == bgp_show_type_flap_prefix
7408 || type == bgp_show_type_flap_cidr_only
7409 || type == bgp_show_type_flap_regexp
7410 || type == bgp_show_type_flap_filter_list
7411 || type == bgp_show_type_flap_prefix_list
7412 || type == bgp_show_type_flap_prefix_longer
7413 || type == bgp_show_type_flap_route_map
7414 || type == bgp_show_type_flap_neighbor
7415 || type == bgp_show_type_dampend_paths
7416 || type == bgp_show_type_damp_neighbor)
7417 {
7418 if (!(ri->extra && ri->extra->damp_info))
7419 continue;
7420 }
7421 if (type == bgp_show_type_regexp
7422 || type == bgp_show_type_flap_regexp)
7423 {
7424 regex_t *regex = output_arg;
7425
7426 if (bgp_regexec (regex, ri->attr->aspath) == REG_NOMATCH)
7427 continue;
7428 }
7429 if (type == bgp_show_type_prefix_list
7430 || type == bgp_show_type_flap_prefix_list)
7431 {
7432 struct prefix_list *plist = output_arg;
7433
7434 if (prefix_list_apply (plist, &rn->p) != PREFIX_PERMIT)
7435 continue;
7436 }
7437 if (type == bgp_show_type_filter_list
7438 || type == bgp_show_type_flap_filter_list)
7439 {
7440 struct as_list *as_list = output_arg;
7441
7442 if (as_list_apply (as_list, ri->attr->aspath) != AS_FILTER_PERMIT)
7443 continue;
7444 }
7445 if (type == bgp_show_type_route_map
7446 || type == bgp_show_type_flap_route_map)
7447 {
7448 struct route_map *rmap = output_arg;
7449 struct bgp_info binfo;
7450 struct attr dummy_attr;
7451 struct attr_extra dummy_extra;
7452 int ret;
7453
7454 dummy_attr.extra = &dummy_extra;
7455 bgp_attr_dup (&dummy_attr, ri->attr);
7456
7457 binfo.peer = ri->peer;
7458 binfo.attr = &dummy_attr;
7459
7460 ret = route_map_apply (rmap, &rn->p, RMAP_BGP, &binfo);
7461 if (ret == RMAP_DENYMATCH)
7462 continue;
7463 }
7464 if (type == bgp_show_type_neighbor
7465 || type == bgp_show_type_flap_neighbor
7466 || type == bgp_show_type_damp_neighbor)
7467 {
7468 union sockunion *su = output_arg;
7469
7470 if (ri->peer->su_remote == NULL || ! sockunion_same(ri->peer->su_remote, su))
7471 continue;
7472 }
7473 if (type == bgp_show_type_cidr_only
7474 || type == bgp_show_type_flap_cidr_only)
7475 {
7476 u_int32_t destination;
7477
7478 destination = ntohl (rn->p.u.prefix4.s_addr);
7479 if (IN_CLASSC (destination) && rn->p.prefixlen == 24)
7480 continue;
7481 if (IN_CLASSB (destination) && rn->p.prefixlen == 16)
7482 continue;
7483 if (IN_CLASSA (destination) && rn->p.prefixlen == 8)
7484 continue;
7485 }
7486 if (type == bgp_show_type_prefix_longer
7487 || type == bgp_show_type_flap_prefix_longer)
7488 {
7489 struct prefix *p = output_arg;
7490
7491 if (! prefix_match (p, &rn->p))
7492 continue;
7493 }
7494 if (type == bgp_show_type_community_all)
7495 {
7496 if (! ri->attr->community)
7497 continue;
7498 }
7499 if (type == bgp_show_type_community)
7500 {
7501 struct community *com = output_arg;
7502
7503 if (! ri->attr->community ||
7504 ! community_match (ri->attr->community, com))
7505 continue;
7506 }
7507 if (type == bgp_show_type_community_exact)
7508 {
7509 struct community *com = output_arg;
7510
7511 if (! ri->attr->community ||
7512 ! community_cmp (ri->attr->community, com))
7513 continue;
7514 }
7515 if (type == bgp_show_type_community_list)
7516 {
7517 struct community_list *list = output_arg;
7518
7519 if (! community_list_match (ri->attr->community, list))
7520 continue;
7521 }
7522 if (type == bgp_show_type_community_list_exact)
7523 {
7524 struct community_list *list = output_arg;
7525
7526 if (! community_list_exact_match (ri->attr->community, list))
7527 continue;
7528 }
7529 if (type == bgp_show_type_flap_address
7530 || type == bgp_show_type_flap_prefix)
7531 {
7532 struct prefix *p = output_arg;
7533
7534 if (! prefix_match (&rn->p, p))
7535 continue;
7536
7537 if (type == bgp_show_type_flap_prefix)
7538 if (p->prefixlen != rn->p.prefixlen)
7539 continue;
7540 }
7541 if (type == bgp_show_type_dampend_paths
7542 || type == bgp_show_type_damp_neighbor)
7543 {
7544 if (! CHECK_FLAG (ri->flags, BGP_INFO_DAMPED)
7545 || CHECK_FLAG (ri->flags, BGP_INFO_HISTORY))
7546 continue;
7547 }
7548
7549 if (!use_json && header)
7550 {
7551 vty_out (vty, "BGP table version is %" PRIu64 ", local router ID is %s%s", table->version, inet_ntoa (*router_id), VTY_NEWLINE);
7552 vty_out (vty, BGP_SHOW_SCODE_HEADER, VTY_NEWLINE, VTY_NEWLINE);
7553 vty_out (vty, BGP_SHOW_OCODE_HEADER, VTY_NEWLINE, VTY_NEWLINE);
7554 if (type == bgp_show_type_dampend_paths
7555 || type == bgp_show_type_damp_neighbor)
7556 vty_out (vty, BGP_SHOW_DAMP_HEADER, VTY_NEWLINE);
7557 else if (type == bgp_show_type_flap_statistics
7558 || type == bgp_show_type_flap_address
7559 || type == bgp_show_type_flap_prefix
7560 || type == bgp_show_type_flap_cidr_only
7561 || type == bgp_show_type_flap_regexp
7562 || type == bgp_show_type_flap_filter_list
7563 || type == bgp_show_type_flap_prefix_list
7564 || type == bgp_show_type_flap_prefix_longer
7565 || type == bgp_show_type_flap_route_map
7566 || type == bgp_show_type_flap_neighbor)
7567 vty_out (vty, BGP_SHOW_FLAP_HEADER, VTY_NEWLINE);
7568 else
7569 vty_out (vty, BGP_SHOW_HEADER, VTY_NEWLINE);
7570 header = 0;
7571 }
7572
7573 if (type == bgp_show_type_dampend_paths
7574 || type == bgp_show_type_damp_neighbor)
7575 damp_route_vty_out (vty, &rn->p, ri, display, SAFI_UNICAST, use_json, json_paths);
7576 else if (type == bgp_show_type_flap_statistics
7577 || type == bgp_show_type_flap_address
7578 || type == bgp_show_type_flap_prefix
7579 || type == bgp_show_type_flap_cidr_only
7580 || type == bgp_show_type_flap_regexp
7581 || type == bgp_show_type_flap_filter_list
7582 || type == bgp_show_type_flap_prefix_list
7583 || type == bgp_show_type_flap_prefix_longer
7584 || type == bgp_show_type_flap_route_map
7585 || type == bgp_show_type_flap_neighbor)
7586 flap_route_vty_out (vty, &rn->p, ri, display, SAFI_UNICAST, use_json, json_paths);
7587 else
7588 route_vty_out (vty, &rn->p, ri, display, SAFI_UNICAST, json_paths);
7589 display++;
7590 }
7591
7592 if (display)
7593 {
7594 output_count++;
7595 if (use_json)
7596 {
7597 p = &rn->p;
7598 sprintf(buf2, "%s/%d", inet_ntop (p->family, &p->u.prefix, buf, BUFSIZ), p->prefixlen);
7599 json_object_object_add(json_routes, buf2, json_paths);
7600 }
7601 }
7602 }
7603
7604 if (use_json)
7605 {
7606 json_object_object_add(json, "routes", json_routes);
7607 vty_out (vty, "%s%s", json_object_to_json_string(json), VTY_NEWLINE);
7608 json_object_free(json);
7609 }
7610 else
7611 {
7612 /* No route is displayed */
7613 if (output_count == 0)
7614 {
7615 if (type == bgp_show_type_normal)
7616 vty_out (vty, "No BGP network exists%s", VTY_NEWLINE);
7617 }
7618 else
7619 vty_out (vty, "%sTotal number of prefixes %ld%s",
7620 VTY_NEWLINE, output_count, VTY_NEWLINE);
7621 }
7622
7623 return CMD_SUCCESS;
7624 }
7625
7626 static int
7627 bgp_show (struct vty *vty, struct bgp *bgp, afi_t afi, safi_t safi,
7628 enum bgp_show_type type, void *output_arg, u_char use_json)
7629 {
7630 struct bgp_table *table;
7631
7632 if (bgp == NULL)
7633 {
7634 bgp = bgp_get_default ();
7635 }
7636
7637 if (bgp == NULL)
7638 {
7639 if (!use_json)
7640 vty_out (vty, "No BGP process is configured%s", VTY_NEWLINE);
7641 return CMD_WARNING;
7642 }
7643
7644 table = bgp->rib[afi][safi];
7645
7646 return bgp_show_table (vty, table, &bgp->router_id, type, output_arg,
7647 use_json, NULL);
7648 }
7649
7650 static void
7651 bgp_show_all_instances_routes_vty (struct vty *vty, afi_t afi, safi_t safi,
7652 u_char use_json)
7653 {
7654 struct listnode *node, *nnode;
7655 struct bgp *bgp;
7656 struct bgp_table *table;
7657 json_object *json = NULL;
7658 int is_first = 1;
7659
7660 if (use_json)
7661 vty_out (vty, "{%s", VTY_NEWLINE);
7662
7663 for (ALL_LIST_ELEMENTS (bm->bgp, node, nnode, bgp))
7664 {
7665 if (use_json)
7666 {
7667 if (!(json = json_object_new_object()))
7668 {
7669 zlog_err("Unable to allocate memory for JSON object");
7670 vty_out (vty,
7671 "{\"error\": {\"message:\": \"Unable to allocate memory for JSON object\"}}}%s",
7672 VTY_NEWLINE);
7673 return;
7674 }
7675 json_object_int_add(json, "vrfId",
7676 (bgp->vrf_id == VRF_UNKNOWN)
7677 ? -1 : bgp->vrf_id);
7678 json_object_string_add(json, "vrfName",
7679 (bgp->inst_type == BGP_INSTANCE_TYPE_DEFAULT)
7680 ? "Default" : bgp->name);
7681 if (! is_first)
7682 vty_out (vty, ",%s", VTY_NEWLINE);
7683 else
7684 is_first = 0;
7685
7686 vty_out(vty, "\"%s\":", (bgp->inst_type == BGP_INSTANCE_TYPE_DEFAULT)
7687 ? "Default" : bgp->name);
7688 }
7689 else
7690 {
7691 vty_out (vty, "%sInstance %s:%s",
7692 VTY_NEWLINE,
7693 (bgp->inst_type == BGP_INSTANCE_TYPE_DEFAULT)
7694 ? "Default" : bgp->name,
7695 VTY_NEWLINE);
7696 }
7697 table = bgp->rib[afi][safi];
7698 bgp_show_table (vty, table, &bgp->router_id,
7699 bgp_show_type_normal, NULL, use_json, json);
7700
7701 }
7702
7703 if (use_json)
7704 vty_out (vty, "}%s", VTY_NEWLINE);
7705 }
7706
7707 /* Header of detailed BGP route information */
7708 static void
7709 route_vty_out_detail_header (struct vty *vty, struct bgp *bgp,
7710 struct bgp_node *rn,
7711 struct prefix_rd *prd, afi_t afi, safi_t safi,
7712 json_object *json)
7713 {
7714 struct bgp_info *ri;
7715 struct prefix *p;
7716 struct peer *peer;
7717 struct listnode *node, *nnode;
7718 char buf1[INET6_ADDRSTRLEN];
7719 char buf2[INET6_ADDRSTRLEN];
7720 int count = 0;
7721 int best = 0;
7722 int suppress = 0;
7723 int no_export = 0;
7724 int no_advertise = 0;
7725 int local_as = 0;
7726 int first = 1;
7727 json_object *json_adv_to = NULL;
7728
7729 p = &rn->p;
7730
7731 if (json)
7732 {
7733 json_object_string_add(json, "prefix", inet_ntop (p->family, &p->u.prefix, buf2, INET6_ADDRSTRLEN));
7734 json_object_int_add(json, "prefixlen", p->prefixlen);
7735 }
7736 else
7737 {
7738 vty_out (vty, "BGP routing table entry for %s%s%s/%d%s",
7739 ((safi == SAFI_MPLS_VPN || safi == SAFI_ENCAP) ?
7740 prefix_rd2str (prd, buf1, RD_ADDRSTRLEN) : ""),
7741 safi == SAFI_MPLS_VPN ? ":" : "",
7742 inet_ntop (p->family, &p->u.prefix, buf2, INET6_ADDRSTRLEN),
7743 p->prefixlen, VTY_NEWLINE);
7744 }
7745
7746 for (ri = rn->info; ri; ri = ri->next)
7747 {
7748 count++;
7749 if (CHECK_FLAG (ri->flags, BGP_INFO_SELECTED))
7750 {
7751 best = count;
7752 if (ri->extra && ri->extra->suppress)
7753 suppress = 1;
7754 if (ri->attr->community != NULL)
7755 {
7756 if (community_include (ri->attr->community, COMMUNITY_NO_ADVERTISE))
7757 no_advertise = 1;
7758 if (community_include (ri->attr->community, COMMUNITY_NO_EXPORT))
7759 no_export = 1;
7760 if (community_include (ri->attr->community, COMMUNITY_LOCAL_AS))
7761 local_as = 1;
7762 }
7763 }
7764 }
7765
7766 if (!json)
7767 {
7768 vty_out (vty, "Paths: (%d available", count);
7769 if (best)
7770 {
7771 vty_out (vty, ", best #%d", best);
7772 if (safi == SAFI_UNICAST)
7773 vty_out (vty, ", table %s",
7774 (bgp->inst_type == BGP_INSTANCE_TYPE_DEFAULT)
7775 ? "Default-IP-Routing-Table" : bgp->name);
7776 }
7777 else
7778 vty_out (vty, ", no best path");
7779
7780 if (no_advertise)
7781 vty_out (vty, ", not advertised to any peer");
7782 else if (no_export)
7783 vty_out (vty, ", not advertised to EBGP peer");
7784 else if (local_as)
7785 vty_out (vty, ", not advertised outside local AS");
7786
7787 if (suppress)
7788 vty_out (vty, ", Advertisements suppressed by an aggregate.");
7789 vty_out (vty, ")%s", VTY_NEWLINE);
7790 }
7791
7792 /* If we are not using addpath then we can display Advertised to and that will
7793 * show what peers we advertised the bestpath to. If we are using addpath
7794 * though then we must display Advertised to on a path-by-path basis. */
7795 if (!bgp->addpath_tx_used[afi][safi])
7796 {
7797 for (ALL_LIST_ELEMENTS (bgp->peer, node, nnode, peer))
7798 {
7799 if (bgp_adj_out_lookup (peer, rn, 0))
7800 {
7801 if (json && !json_adv_to)
7802 json_adv_to = json_object_new_object();
7803
7804 route_vty_out_advertised_to(vty, peer, &first,
7805 " Advertised to non peer-group peers:\n ",
7806 json_adv_to);
7807 }
7808 }
7809
7810 if (json)
7811 {
7812 if (json_adv_to)
7813 {
7814 json_object_object_add(json, "advertisedTo", json_adv_to);
7815 }
7816 }
7817 else
7818 {
7819 if (first)
7820 vty_out (vty, " Not advertised to any peer");
7821 vty_out (vty, "%s", VTY_NEWLINE);
7822 }
7823 }
7824 }
7825
7826 /* Display specified route of BGP table. */
7827 static int
7828 bgp_show_route_in_table (struct vty *vty, struct bgp *bgp,
7829 struct bgp_table *rib, const char *ip_str,
7830 afi_t afi, safi_t safi, struct prefix_rd *prd,
7831 int prefix_check, enum bgp_path_type pathtype,
7832 u_char use_json)
7833 {
7834 int ret;
7835 int header;
7836 int display = 0;
7837 struct prefix match;
7838 struct bgp_node *rn;
7839 struct bgp_node *rm;
7840 struct bgp_info *ri;
7841 struct bgp_table *table;
7842 json_object *json = NULL;
7843 json_object *json_paths = NULL;
7844
7845 /* Check IP address argument. */
7846 ret = str2prefix (ip_str, &match);
7847 if (! ret)
7848 {
7849 vty_out (vty, "address is malformed%s", VTY_NEWLINE);
7850 return CMD_WARNING;
7851 }
7852
7853 match.family = afi2family (afi);
7854
7855 if (use_json)
7856 {
7857 json = json_object_new_object();
7858 json_paths = json_object_new_array();
7859 }
7860
7861 if (safi == SAFI_MPLS_VPN || safi == SAFI_ENCAP)
7862 {
7863 for (rn = bgp_table_top (rib); rn; rn = bgp_route_next (rn))
7864 {
7865 if (prd && memcmp (rn->p.u.val, prd->val, 8) != 0)
7866 continue;
7867
7868 if ((table = rn->info) != NULL)
7869 {
7870 header = 1;
7871
7872 if ((rm = bgp_node_match (table, &match)) != NULL)
7873 {
7874 if (prefix_check && rm->p.prefixlen != match.prefixlen)
7875 {
7876 bgp_unlock_node (rm);
7877 continue;
7878 }
7879
7880 for (ri = rm->info; ri; ri = ri->next)
7881 {
7882 if (header)
7883 {
7884 route_vty_out_detail_header (vty, bgp, rm, (struct prefix_rd *)&rn->p,
7885 AFI_IP, safi, json);
7886 header = 0;
7887 }
7888 display++;
7889
7890 if (pathtype == BGP_PATH_ALL ||
7891 (pathtype == BGP_PATH_BESTPATH && CHECK_FLAG (ri->flags, BGP_INFO_SELECTED)) ||
7892 (pathtype == BGP_PATH_MULTIPATH &&
7893 (CHECK_FLAG (ri->flags, BGP_INFO_MULTIPATH) || CHECK_FLAG (ri->flags, BGP_INFO_SELECTED))))
7894 route_vty_out_detail (vty, bgp, &rm->p, ri, AFI_IP, safi, json_paths);
7895 }
7896
7897 bgp_unlock_node (rm);
7898 }
7899 }
7900 }
7901 }
7902 else
7903 {
7904 header = 1;
7905
7906 if ((rn = bgp_node_match (rib, &match)) != NULL)
7907 {
7908 if (! prefix_check || rn->p.prefixlen == match.prefixlen)
7909 {
7910 for (ri = rn->info; ri; ri = ri->next)
7911 {
7912 if (header)
7913 {
7914 route_vty_out_detail_header (vty, bgp, rn, NULL, afi, safi, json);
7915 header = 0;
7916 }
7917 display++;
7918
7919 if (pathtype == BGP_PATH_ALL ||
7920 (pathtype == BGP_PATH_BESTPATH && CHECK_FLAG (ri->flags, BGP_INFO_SELECTED)) ||
7921 (pathtype == BGP_PATH_MULTIPATH &&
7922 (CHECK_FLAG (ri->flags, BGP_INFO_MULTIPATH) || CHECK_FLAG (ri->flags, BGP_INFO_SELECTED))))
7923 route_vty_out_detail (vty, bgp, &rn->p, ri, afi, safi, json_paths);
7924 }
7925 }
7926
7927 bgp_unlock_node (rn);
7928 }
7929 }
7930
7931 if (use_json)
7932 {
7933 if (display)
7934 json_object_object_add(json, "paths", json_paths);
7935
7936 vty_out (vty, "%s%s", json_object_to_json_string(json), VTY_NEWLINE);
7937 json_object_free(json);
7938 }
7939 else
7940 {
7941 if (!display)
7942 {
7943 vty_out (vty, "%% Network not in table%s", VTY_NEWLINE);
7944 return CMD_WARNING;
7945 }
7946 }
7947
7948 return CMD_SUCCESS;
7949 }
7950
7951 /* Display specified route of Main RIB */
7952 static int
7953 bgp_show_route (struct vty *vty, const char *view_name, const char *ip_str,
7954 afi_t afi, safi_t safi, struct prefix_rd *prd,
7955 int prefix_check, enum bgp_path_type pathtype,
7956 u_char use_json)
7957 {
7958 struct bgp *bgp;
7959
7960 /* BGP structure lookup. */
7961 if (view_name)
7962 {
7963 bgp = bgp_lookup_by_name (view_name);
7964 if (bgp == NULL)
7965 {
7966 vty_out (vty, "Can't find BGP instance %s%s", view_name, VTY_NEWLINE);
7967 return CMD_WARNING;
7968 }
7969 }
7970 else
7971 {
7972 bgp = bgp_get_default ();
7973 if (bgp == NULL)
7974 {
7975 vty_out (vty, "No BGP process is configured%s", VTY_NEWLINE);
7976 return CMD_WARNING;
7977 }
7978 }
7979
7980 return bgp_show_route_in_table (vty, bgp, bgp->rib[afi][safi], ip_str,
7981 afi, safi, prd, prefix_check, pathtype,
7982 use_json);
7983 }
7984
7985 /* BGP route print out function. */
7986 DEFUN (show_ip_bgp,
7987 show_ip_bgp_cmd,
7988 "show ip bgp [json]",
7989 SHOW_STR
7990 IP_STR
7991 BGP_STR
7992 "JavaScript Object Notation\n")
7993 {
7994 return bgp_show (vty, NULL, AFI_IP, SAFI_UNICAST, bgp_show_type_normal, NULL, use_json(argc, argv));
7995 }
7996
7997 /*
7998 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
7999 * "show bgp ipv4 (unicast|multicast) [json]",
8000 * SHOW_STR
8001 * BGP_STR
8002 * "Address family\n"
8003 * "Address Family modifier\n"
8004 * "Address Family modifier\n"
8005 * "JavaScript Object Notation\n"
8006 *
8007 */
8008 DEFUN (show_ip_bgp_ipv4,
8009 show_ip_bgp_ipv4_cmd,
8010 "show ip bgp ipv4 <unicast|multicast> [json]",
8011 SHOW_STR
8012 IP_STR
8013 BGP_STR
8014 "Address family\n"
8015 "Address Family modifier\n"
8016 "Address Family modifier\n"
8017 "JavaScript Object Notation\n")
8018 {
8019 int idx_safi = 4;
8020 u_char uj = use_json(argc, argv);
8021
8022 if (strncmp (argv[idx_safi]->arg, "m", 1) == 0)
8023 return bgp_show (vty, NULL, AFI_IP, SAFI_MULTICAST, bgp_show_type_normal,
8024 NULL, uj);
8025
8026 return bgp_show (vty, NULL, AFI_IP, SAFI_UNICAST, bgp_show_type_normal, NULL, uj);
8027 }
8028
8029
8030 DEFUN (show_ip_bgp_route,
8031 show_ip_bgp_route_cmd,
8032 "show ip bgp A.B.C.D [json]",
8033 SHOW_STR
8034 IP_STR
8035 BGP_STR
8036 "Network in the BGP routing table to display\n"
8037 "JavaScript Object Notation\n")
8038 {
8039 int idx_ipv4 = 3;
8040 return bgp_show_route (vty, NULL, argv[idx_ipv4]->arg, AFI_IP, SAFI_UNICAST, NULL, 0, BGP_PATH_ALL, use_json(argc, argv));
8041 }
8042
8043 DEFUN (show_ip_bgp_route_pathtype,
8044 show_ip_bgp_route_pathtype_cmd,
8045 "show ip bgp A.B.C.D <bestpath|multipath> [json]",
8046 SHOW_STR
8047 IP_STR
8048 BGP_STR
8049 "IP prefix <network>/<length>, e.g., 35.0.0.0/8\n"
8050 "Display only the bestpath\n"
8051 "Display only multipaths\n"
8052 "JavaScript Object Notation\n")
8053 {
8054 int idx_ipv4 = 3;
8055 int idx_bestpath = 4;
8056 u_char uj = use_json(argc, argv);
8057
8058 if (strncmp (argv[idx_bestpath]->arg, "b", 1) == 0)
8059 return bgp_show_route (vty, NULL, argv[idx_ipv4]->arg, AFI_IP, SAFI_UNICAST, NULL, 0, BGP_PATH_BESTPATH, uj);
8060 else
8061 return bgp_show_route (vty, NULL, argv[idx_ipv4]->arg, AFI_IP, SAFI_UNICAST, NULL, 0, BGP_PATH_MULTIPATH, uj);
8062 }
8063
8064 DEFUN (show_bgp_ipv4_safi_route_pathtype,
8065 show_bgp_ipv4_safi_route_pathtype_cmd,
8066 "show bgp ipv4 <unicast|multicast> A.B.C.D <bestpath|multipath> [json]",
8067 SHOW_STR
8068 BGP_STR
8069 "Address family\n"
8070 "Address Family modifier\n"
8071 "Address Family modifier\n"
8072 "IP prefix <network>/<length>, e.g., 35.0.0.0/8\n"
8073 "Display only the bestpath\n"
8074 "Display only multipaths\n"
8075 "JavaScript Object Notation\n")
8076 {
8077 int idx_safi = 3;
8078 int idx_ipv4 = 4;
8079 int idx_bestpath = 5;
8080 u_char uj = use_json(argc, argv);
8081
8082 if (strncmp (argv[idx_safi]->arg, "m", 1) == 0)
8083 if (strncmp (argv[idx_bestpath]->arg, "b", 1) == 0)
8084 return bgp_show_route (vty, NULL, argv[idx_ipv4]->arg, AFI_IP, SAFI_MULTICAST, NULL, 0, BGP_PATH_BESTPATH, uj);
8085 else
8086 return bgp_show_route (vty, NULL, argv[idx_ipv4]->arg, AFI_IP, SAFI_MULTICAST, NULL, 0, BGP_PATH_MULTIPATH, uj);
8087 else
8088 if (strncmp (argv[idx_bestpath]->arg, "b", 1) == 0)
8089 return bgp_show_route (vty, NULL, argv[idx_ipv4]->arg, AFI_IP, SAFI_UNICAST, NULL, 0, BGP_PATH_BESTPATH, uj);
8090 else
8091 return bgp_show_route (vty, NULL, argv[idx_ipv4]->arg, AFI_IP, SAFI_UNICAST, NULL, 0, BGP_PATH_MULTIPATH, uj);
8092 }
8093
8094 DEFUN (show_bgp_ipv4_prefix,
8095 show_bgp_ipv4_prefix_cmd,
8096 "show bgp ipv4 A.B.C.D/M [json]",
8097 SHOW_STR
8098 BGP_STR
8099 IP_STR
8100 "IP prefix <network>/<length>, e.g., 35.0.0.0/8\n"
8101 JSON_STR)
8102 {
8103 int idx_ipv4_prefixlen = 3;
8104 return bgp_show_route (vty, NULL, argv[idx_ipv4_prefixlen]->arg, AFI_IP, SAFI_UNICAST, NULL, 1, BGP_PATH_ALL, use_json (argc, argv));
8105 }
8106
8107 DEFUN (show_bgp_ipv6_route,
8108 show_bgp_ipv6_route_cmd,
8109 "show bgp ipv6 X:X::X:X [json]",
8110 SHOW_STR
8111 BGP_STR
8112 "Address family\n"
8113 "Network in the BGP routing table to display\n"
8114 JSON_STR)
8115 {
8116 int idx_ipv6 = 3;
8117 return bgp_show_route (vty, NULL, argv[idx_ipv6]->arg, AFI_IP6, SAFI_UNICAST, NULL, 0, BGP_PATH_ALL, use_json (argc, argv));
8118 }
8119
8120 DEFUN (show_bgp_ipv6_prefix,
8121 show_bgp_ipv6_prefix_cmd,
8122 "show bgp ipv6 X:X::X:X/M [json]",
8123 SHOW_STR
8124 BGP_STR
8125 IP_STR
8126 "IPv6 prefix <network>/<length>\n"
8127 JSON_STR)
8128 {
8129 int idx_ipv6_prefixlen = 3;
8130 return bgp_show_route (vty, NULL, argv[idx_ipv6_prefixlen]->arg, AFI_IP6, SAFI_UNICAST, NULL, 1, BGP_PATH_ALL, use_json (argc,argv));
8131 }
8132
8133 /*
8134 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
8135 * "show bgp ipv4 (unicast|multicast) A.B.C.D [json]",
8136 * SHOW_STR
8137 * BGP_STR
8138 * "Address family\n"
8139 * "Address Family modifier\n"
8140 * "Address Family modifier\n"
8141 * "Network in the BGP routing table to display\n"
8142 * "JavaScript Object Notation\n"
8143 *
8144 */
8145 DEFUN (show_ip_bgp_ipv4_route,
8146 show_ip_bgp_ipv4_route_cmd,
8147 "show ip bgp ipv4 <unicast|multicast> A.B.C.D [json]",
8148 SHOW_STR
8149 IP_STR
8150 BGP_STR
8151 "Address family\n"
8152 "Address Family modifier\n"
8153 "Address Family modifier\n"
8154 "Network in the BGP routing table to display\n"
8155 "JavaScript Object Notation\n")
8156 {
8157 int idx_safi = 4;
8158 int idx_ipv4 = 5;
8159 u_char uj = use_json(argc, argv);
8160
8161 if (strncmp (argv[idx_safi]->arg, "m", 1) == 0)
8162 return bgp_show_route (vty, NULL, argv[idx_ipv4]->arg, AFI_IP, SAFI_MULTICAST, NULL, 0, BGP_PATH_ALL, uj);
8163
8164 return bgp_show_route (vty, NULL, argv[idx_ipv4]->arg, AFI_IP, SAFI_UNICAST, NULL, 0, BGP_PATH_ALL, uj);
8165 }
8166
8167
8168 DEFUN (show_ip_bgp_vpnv4_all_route,
8169 show_ip_bgp_vpnv4_all_route_cmd,
8170 "show ip bgp vpnv4 all A.B.C.D [json]",
8171 SHOW_STR
8172 IP_STR
8173 BGP_STR
8174 "Display VPNv4 NLRI specific information\n"
8175 "Display information about all VPNv4 NLRIs\n"
8176 "Network in the BGP routing table to display\n"
8177 "JavaScript Object Notation\n")
8178 {
8179 int idx_ipv4 = 5;
8180 return bgp_show_route (vty, NULL, argv[idx_ipv4]->arg, AFI_IP, SAFI_MPLS_VPN, NULL, 0, BGP_PATH_ALL, use_json(argc, argv));
8181 }
8182
8183 DEFUN (show_bgp_ipv4_vpn_route,
8184 show_bgp_ipv4_vpn_route_cmd,
8185 "show bgp ipv4 vpn A.B.C.D [json]",
8186 SHOW_STR
8187 BGP_STR
8188 "Address Family\n"
8189 "Display VPN NLRI specific information\n"
8190 "Network in the BGP routing table to display\n"
8191 JSON_STR)
8192 {
8193 int idx_ipv4 = 4;
8194 return bgp_show_route (vty, NULL, argv[idx_ipv4]->arg, AFI_IP, SAFI_MPLS_VPN, NULL, 0, BGP_PATH_ALL, use_json (argc, argv));
8195 }
8196
8197 DEFUN (show_bgp_ipv6_vpn_route,
8198 show_bgp_ipv6_vpn_route_cmd,
8199 "show bgp ipv6 vpn X:X::X:X [json]",
8200 SHOW_STR
8201 BGP_STR
8202 "Address Family\n"
8203 "Display VPN NLRI specific information\n"
8204 "Network in the BGP routing table to display\n"
8205 JSON_STR)
8206 {
8207 int idx_ipv6 = 4;
8208 return bgp_show_route (vty, NULL, argv[idx_ipv6]->arg, AFI_IP6, SAFI_MPLS_VPN, NULL, 0, BGP_PATH_ALL, use_json (argc, argv));
8209 }
8210
8211 DEFUN (show_bgp_ipv4_vpn_rd_route,
8212 show_bgp_ipv4_vpn_rd_route_cmd,
8213 "show bgp ipv4 vpn rd ASN:nn_or_IP-address:nn A.B.C.D [json]",
8214 SHOW_STR
8215 BGP_STR
8216 IP_STR
8217 "Display VPN NLRI specific information\n"
8218 "Display information for a route distinguisher\n"
8219 "VPN Route Distinguisher\n"
8220 "Network in the BGP routing table to display\n"
8221 JSON_STR)
8222 {
8223 int idx_ext_community = 5;
8224 int idx_ipv4 = 6;
8225 int ret;
8226 struct prefix_rd prd;
8227
8228 ret = str2prefix_rd (argv[idx_ext_community]->arg, &prd);
8229 if (! ret)
8230 {
8231 vty_out (vty, "%% Malformed Route Distinguisher%s", VTY_NEWLINE);
8232 return CMD_WARNING;
8233 }
8234 return bgp_show_route (vty, NULL, argv[idx_ipv4]->arg, AFI_IP, SAFI_MPLS_VPN, &prd, 0, BGP_PATH_ALL, use_json (argc, argv));
8235 }
8236
8237 DEFUN (show_bgp_ipv6_vpn_rd_route,
8238 show_bgp_ipv6_vpn_rd_route_cmd,
8239 "show bgp ipv6 vpn rd ASN:nn_or_IP-address:nn X:X::X:X [json]",
8240 SHOW_STR
8241 BGP_STR
8242 "Address Family\n"
8243 "Display VPN NLRI specific information\n"
8244 "Display information for a route distinguisher\n"
8245 "VPN Route Distinguisher\n"
8246 "Network in the BGP routing table to display\n"
8247 JSON_STR)
8248 {
8249 int idx_ext_community = 5;
8250 int idx_ipv6 = 6;
8251 int ret;
8252 struct prefix_rd prd;
8253
8254 ret = str2prefix_rd (argv[idx_ext_community]->arg, &prd);
8255 if (! ret)
8256 {
8257 vty_out (vty, "%% Malformed Route Distinguisher%s", VTY_NEWLINE);
8258 return CMD_WARNING;
8259 }
8260 return bgp_show_route (vty, NULL, argv[idx_ipv6]->arg, AFI_IP6, SAFI_MPLS_VPN, &prd, 0, BGP_PATH_ALL, use_json (argc, argv));
8261 }
8262
8263 DEFUN (show_ip_bgp_vpnv4_rd_route,
8264 show_ip_bgp_vpnv4_rd_route_cmd,
8265 "show ip bgp vpnv4 rd ASN:nn_or_IP-address:nn A.B.C.D [json]",
8266 SHOW_STR
8267 IP_STR
8268 BGP_STR
8269 "Display VPNv4 NLRI specific information\n"
8270 "Display information for a route distinguisher\n"
8271 "VPN Route Distinguisher\n"
8272 "Network in the BGP routing table to display\n"
8273 "JavaScript Object Notation\n")
8274 {
8275 int idx_ext_community = 5;
8276 int idx_ipv4 = 6;
8277 int ret;
8278 struct prefix_rd prd;
8279 u_char uj= use_json(argc, argv);
8280
8281 ret = str2prefix_rd (argv[idx_ext_community]->arg, &prd);
8282 if (! ret)
8283 {
8284 vty_out (vty, "%% Malformed Route Distinguisher%s", VTY_NEWLINE);
8285 return CMD_WARNING;
8286 }
8287 return bgp_show_route (vty, NULL, argv[idx_ipv4]->arg, AFI_IP, SAFI_MPLS_VPN, &prd, 0, BGP_PATH_ALL, uj);
8288 }
8289
8290 DEFUN (show_ip_bgp_prefix,
8291 show_ip_bgp_prefix_cmd,
8292 "show ip bgp A.B.C.D/M [json]",
8293 SHOW_STR
8294 IP_STR
8295 BGP_STR
8296 "IP prefix <network>/<length>, e.g., 35.0.0.0/8\n"
8297 "JavaScript Object Notation\n")
8298 {
8299 int idx_ipv4_prefixlen = 3;
8300 return bgp_show_route (vty, NULL, argv[idx_ipv4_prefixlen]->arg, AFI_IP, SAFI_UNICAST, NULL, 1, BGP_PATH_ALL, use_json(argc, argv));
8301 }
8302
8303 DEFUN (show_ip_bgp_prefix_pathtype,
8304 show_ip_bgp_prefix_pathtype_cmd,
8305 "show ip bgp A.B.C.D/M <bestpath|multipath> [json]",
8306 SHOW_STR
8307 IP_STR
8308 BGP_STR
8309 "IP prefix <network>/<length>, e.g., 35.0.0.0/8\n"
8310 "Display only the bestpath\n"
8311 "Display only multipaths\n"
8312 "JavaScript Object Notation\n")
8313 {
8314 int idx_ipv4_prefixlen = 3;
8315 int idx_bestpath = 4;
8316 u_char uj = use_json(argc, argv);
8317 if (strncmp (argv[idx_bestpath]->arg, "b", 1) == 0)
8318 return bgp_show_route (vty, NULL, argv[idx_ipv4_prefixlen]->arg, AFI_IP, SAFI_UNICAST, NULL, 1, BGP_PATH_BESTPATH, uj);
8319 else
8320 return bgp_show_route (vty, NULL, argv[idx_ipv4_prefixlen]->arg, AFI_IP, SAFI_UNICAST, NULL, 1, BGP_PATH_MULTIPATH, uj);
8321 }
8322
8323 /*
8324 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
8325 * "show bgp ipv4 (unicast|multicast) A.B.C.D/M [json]",
8326 * SHOW_STR
8327 * BGP_STR
8328 * "Address family\n"
8329 * "Address Family modifier\n"
8330 * "Address Family modifier\n"
8331 * "IP prefix <network>/<length>, e.g., 35.0.0.0/8\n"
8332 * "JavaScript Object Notation\n"
8333 *
8334 */
8335 DEFUN (show_ip_bgp_ipv4_prefix,
8336 show_ip_bgp_ipv4_prefix_cmd,
8337 "show ip bgp ipv4 <unicast|multicast> A.B.C.D/M [json]",
8338 SHOW_STR
8339 IP_STR
8340 BGP_STR
8341 "Address family\n"
8342 "Address Family modifier\n"
8343 "Address Family modifier\n"
8344 "IP prefix <network>/<length>, e.g., 35.0.0.0/8\n"
8345 "JavaScript Object Notation\n")
8346 {
8347 int idx_safi = 4;
8348 int idx_ipv4_prefixlen = 5;
8349 u_char uj = use_json(argc, argv);
8350
8351 if (strncmp (argv[idx_safi]->arg, "m", 1) == 0)
8352 return bgp_show_route (vty, NULL, argv[idx_ipv4_prefixlen]->arg, AFI_IP, SAFI_MULTICAST, NULL, 1, BGP_PATH_ALL, uj);
8353
8354 return bgp_show_route (vty, NULL, argv[idx_ipv4_prefixlen]->arg, AFI_IP, SAFI_UNICAST, NULL, 1, BGP_PATH_ALL, uj);
8355 }
8356
8357
8358 /*
8359 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
8360 * "show bgp ipv4 (unicast|multicast) A.B.C.D/M (bestpath|multipath) [json]",
8361 * SHOW_STR
8362 * BGP_STR
8363 * "Address family\n"
8364 * "Address Family modifier\n"
8365 * "Address Family modifier\n"
8366 * "IP prefix <network>/<length>, e.g., 35.0.0.0/8\n"
8367 * "Display only the bestpath\n"
8368 * "Display only multipaths\n"
8369 * "JavaScript Object Notation\n"
8370 *
8371 */
8372 DEFUN (show_ip_bgp_ipv4_prefix_pathtype,
8373 show_ip_bgp_ipv4_prefix_pathtype_cmd,
8374 "show ip bgp ipv4 <unicast|multicast> A.B.C.D/M <bestpath|multipath> [json]",
8375 SHOW_STR
8376 IP_STR
8377 BGP_STR
8378 "Address family\n"
8379 "Address Family modifier\n"
8380 "Address Family modifier\n"
8381 "IP prefix <network>/<length>, e.g., 35.0.0.0/8\n"
8382 "Display only the bestpath\n"
8383 "Display only multipaths\n"
8384 "JavaScript Object Notation\n")
8385 {
8386 int idx_safi = 4;
8387 int idx_ipv4_prefixlen = 5;
8388 int idx_bestpath = 6;
8389 u_char uj = use_json(argc, argv);
8390
8391 if (strncmp (argv[idx_safi]->arg, "m", 1) == 0)
8392 if (strncmp (argv[idx_bestpath]->arg, "b", 1) == 0)
8393 return bgp_show_route (vty, NULL, argv[idx_ipv4_prefixlen]->arg, AFI_IP, SAFI_MULTICAST, NULL, 1, BGP_PATH_BESTPATH, uj);
8394 else
8395 return bgp_show_route (vty, NULL, argv[idx_ipv4_prefixlen]->arg, AFI_IP, SAFI_MULTICAST, NULL, 1, BGP_PATH_MULTIPATH, uj);
8396 else
8397 if (strncmp (argv[idx_bestpath]->arg, "b", 1) == 0)
8398 return bgp_show_route (vty, NULL, argv[idx_ipv4_prefixlen]->arg, AFI_IP, SAFI_UNICAST, NULL, 1, BGP_PATH_BESTPATH, uj);
8399 else
8400 return bgp_show_route (vty, NULL, argv[idx_ipv4_prefixlen]->arg, AFI_IP, SAFI_UNICAST, NULL, 1, BGP_PATH_MULTIPATH, uj);
8401 }
8402
8403
8404 DEFUN (show_ip_bgp_vpnv4_all_prefix,
8405 show_ip_bgp_vpnv4_all_prefix_cmd,
8406 "show ip bgp vpnv4 all A.B.C.D/M [json]",
8407 SHOW_STR
8408 IP_STR
8409 BGP_STR
8410 "Display VPNv4 NLRI specific information\n"
8411 "Display information about all VPNv4 NLRIs\n"
8412 "IP prefix <network>/<length>, e.g., 35.0.0.0/8\n"
8413 "JavaScript Object Notation\n")
8414 {
8415 int idx_ipv4_prefixlen = 5;
8416 return bgp_show_route (vty, NULL, argv[idx_ipv4_prefixlen]->arg, AFI_IP, SAFI_MPLS_VPN, NULL, 1, BGP_PATH_ALL, use_json(argc, argv));
8417 }
8418
8419 DEFUN (show_ip_bgp_vpnv4_rd_prefix,
8420 show_ip_bgp_vpnv4_rd_prefix_cmd,
8421 "show ip bgp vpnv4 rd ASN:nn_or_IP-address:nn A.B.C.D/M [json]",
8422 SHOW_STR
8423 IP_STR
8424 BGP_STR
8425 "Display VPNv4 NLRI specific information\n"
8426 "Display information for a route distinguisher\n"
8427 "VPN Route Distinguisher\n"
8428 "IP prefix <network>/<length>, e.g., 35.0.0.0/8\n"
8429 "JavaScript Object Notation\n")
8430 {
8431 int idx_ext_community = 5;
8432 int idx_ipv4_prefixlen = 6;
8433 int ret;
8434 struct prefix_rd prd;
8435
8436 ret = str2prefix_rd (argv[idx_ext_community]->arg, &prd);
8437 if (! ret)
8438 {
8439 vty_out (vty, "%% Malformed Route Distinguisher%s", VTY_NEWLINE);
8440 return CMD_WARNING;
8441 }
8442 return bgp_show_route (vty, NULL, argv[idx_ipv4_prefixlen]->arg, AFI_IP, SAFI_MPLS_VPN, &prd, 0, BGP_PATH_ALL, use_json(argc, argv));
8443 }
8444
8445 DEFUN (show_ip_bgp_view,
8446 show_ip_bgp_instance_cmd,
8447 "show ip bgp <view|vrf> WORD [json]",
8448 SHOW_STR
8449 IP_STR
8450 BGP_STR
8451 BGP_INSTANCE_HELP_STR
8452 "JavaScript Object Notation\n")
8453 {
8454 int idx_word = 4;
8455 struct bgp *bgp;
8456
8457 /* BGP structure lookup. */
8458 bgp = bgp_lookup_by_name (argv[idx_word]->arg);
8459 if (bgp == NULL)
8460 {
8461 vty_out (vty, "Can't find BGP instance %s%s", argv[idx_word]->arg, VTY_NEWLINE);
8462 return CMD_WARNING;
8463 }
8464
8465 return bgp_show (vty, bgp, AFI_IP, SAFI_UNICAST, bgp_show_type_normal, NULL, use_json(argc, argv));
8466 }
8467
8468 DEFUN (show_ip_bgp_instance_all,
8469 show_ip_bgp_instance_all_cmd,
8470 "show ip bgp <view|vrf> all [json]",
8471 SHOW_STR
8472 IP_STR
8473 BGP_STR
8474 BGP_INSTANCE_ALL_HELP_STR
8475 "JavaScript Object Notation\n")
8476 {
8477 u_char uj = use_json(argc, argv);
8478
8479 bgp_show_all_instances_routes_vty (vty, AFI_IP, SAFI_UNICAST, uj);
8480 return CMD_SUCCESS;
8481 }
8482
8483 DEFUN (show_ip_bgp_instance_route,
8484 show_ip_bgp_instance_route_cmd,
8485 "show ip bgp <view|vrf> WORD A.B.C.D [json]",
8486 SHOW_STR
8487 IP_STR
8488 BGP_STR
8489 BGP_INSTANCE_HELP_STR
8490 "Network in the BGP routing table to display\n"
8491 "JavaScript Object Notation\n")
8492 {
8493 int idx_word = 4;
8494 int idx_ipv4 = 5;
8495 return bgp_show_route (vty, argv[idx_word]->arg, argv[idx_ipv4]->arg, AFI_IP, SAFI_UNICAST, NULL, 0, BGP_PATH_ALL, use_json(argc, argv));
8496 }
8497
8498 DEFUN (show_ip_bgp_instance_route_pathtype,
8499 show_ip_bgp_instance_route_pathtype_cmd,
8500 "show ip bgp <view|vrf> WORD A.B.C.D <bestpath|multipath> [json]",
8501 SHOW_STR
8502 IP_STR
8503 BGP_STR
8504 BGP_INSTANCE_HELP_STR
8505 "Network in the BGP routing table to display\n"
8506 "Display only the bestpath\n"
8507 "Display only multipaths\n"
8508 "JavaScript Object Notation\n")
8509 {
8510 int idx_word = 4;
8511 int idx_ipv4 = 5;
8512 int idx_bestpath = 6;
8513 u_char uj = use_json(argc, argv);
8514
8515 if (strncmp (argv[idx_bestpath]->arg, "b", 1) == 0)
8516 return bgp_show_route (vty, argv[idx_word]->arg, argv[idx_ipv4]->arg, AFI_IP, SAFI_UNICAST, NULL, 0, BGP_PATH_BESTPATH, uj);
8517 else
8518 return bgp_show_route (vty, argv[idx_word]->arg, argv[idx_ipv4]->arg, AFI_IP, SAFI_UNICAST, NULL, 0, BGP_PATH_MULTIPATH, uj);
8519 }
8520
8521 DEFUN (show_ip_bgp_instance_prefix,
8522 show_ip_bgp_instance_prefix_cmd,
8523 "show ip bgp <view|vrf> WORD A.B.C.D/M [json]",
8524 SHOW_STR
8525 IP_STR
8526 BGP_STR
8527 BGP_INSTANCE_HELP_STR
8528 "IP prefix <network>/<length>, e.g., 35.0.0.0/8\n"
8529 "JavaScript Object Notation\n")
8530 {
8531 int idx_word = 4;
8532 int idx_ipv4_prefixlen = 5;
8533 return bgp_show_route (vty, argv[idx_word]->arg, argv[idx_ipv4_prefixlen]->arg, AFI_IP, SAFI_UNICAST, NULL, 1, BGP_PATH_ALL, use_json(argc, argv));
8534 }
8535
8536 DEFUN (show_ip_bgp_instance_prefix_pathtype,
8537 show_ip_bgp_instance_prefix_pathtype_cmd,
8538 "show ip bgp <view|vrf> WORD A.B.C.D/M <bestpath|multipath> [json]",
8539 SHOW_STR
8540 IP_STR
8541 BGP_STR
8542 BGP_INSTANCE_HELP_STR
8543 "IP prefix <network>/<length>, e.g., 35.0.0.0/8\n"
8544 "Display only the bestpath\n"
8545 "Display only multipaths\n"
8546 "JavaScript Object Notation\n")
8547 {
8548 int idx_word = 4;
8549 int idx_ipv4_prefixlen = 5;
8550 int idx_bestpath = 6;
8551 u_char uj = use_json(argc, argv);
8552 if (strncmp (argv[idx_bestpath]->arg, "b", 1) == 0)
8553 return bgp_show_route (vty, argv[idx_word]->arg, argv[idx_ipv4_prefixlen]->arg, AFI_IP, SAFI_UNICAST, NULL, 1, BGP_PATH_BESTPATH, uj);
8554 else
8555 return bgp_show_route (vty, argv[idx_word]->arg, argv[idx_ipv4_prefixlen]->arg, AFI_IP, SAFI_UNICAST, NULL, 1, BGP_PATH_MULTIPATH, uj);
8556 }
8557
8558 #ifdef HAVE_IPV6
8559 /*
8560 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
8561 * "show bgp ipv6 [json]",
8562 * SHOW_STR
8563 * BGP_STR
8564 * "Address family\n"
8565 * "JavaScript Object Notation\n"
8566 *
8567 */
8568 DEFUN (show_bgp,
8569 show_bgp_cmd,
8570 "show bgp [json]",
8571 SHOW_STR
8572 BGP_STR
8573 "JavaScript Object Notation\n")
8574 {
8575 return bgp_show (vty, NULL, AFI_IP6, SAFI_UNICAST, bgp_show_type_normal,
8576 NULL, use_json(argc, argv));
8577 }
8578
8579
8580 DEFUN (show_bgp_ipv6_safi,
8581 show_bgp_ipv6_safi_cmd,
8582 "show bgp ipv6 <unicast|multicast> [json]",
8583 SHOW_STR
8584 BGP_STR
8585 "Address family\n"
8586 "Address Family modifier\n"
8587 "Address Family modifier\n"
8588 "JavaScript Object Notation\n")
8589 {
8590 int idx_safi = 3;
8591 u_char uj = use_json(argc, argv);
8592 if (strncmp (argv[idx_safi]->arg, "m", 1) == 0)
8593 return bgp_show (vty, NULL, AFI_IP6, SAFI_MULTICAST, bgp_show_type_normal,
8594 NULL, uj);
8595
8596 return bgp_show (vty, NULL, AFI_IP6, SAFI_UNICAST, bgp_show_type_normal, NULL, uj);
8597 }
8598
8599 static void
8600 bgp_show_ipv6_bgp_deprecate_warning (struct vty *vty)
8601 {
8602 vty_out (vty, "WARNING: The 'show ipv6 bgp' parse tree will be deprecated in our"
8603 " next release%sPlese use 'show bgp ipv6' instead%s%s",
8604 VTY_NEWLINE, VTY_NEWLINE, VTY_NEWLINE);
8605 }
8606
8607 /* old command */
8608 DEFUN (show_ipv6_bgp,
8609 show_ipv6_bgp_cmd,
8610 "show ipv6 bgp [json]",
8611 SHOW_STR
8612 IP_STR
8613 BGP_STR
8614 "JavaScript Object Notation\n")
8615 {
8616 bgp_show_ipv6_bgp_deprecate_warning(vty);
8617 return bgp_show (vty, NULL, AFI_IP6, SAFI_UNICAST, bgp_show_type_normal,
8618 NULL, use_json(argc, argv));
8619 }
8620
8621 DEFUN (show_bgp_route,
8622 show_bgp_route_cmd,
8623 "show bgp X:X::X:X [json]",
8624 SHOW_STR
8625 BGP_STR
8626 "Network in the BGP routing table to display\n"
8627 "JavaScript Object Notation\n")
8628 {
8629 int idx_ipv6 = 2;
8630 return bgp_show_route (vty, NULL, argv[idx_ipv6]->arg, AFI_IP6, SAFI_UNICAST, NULL, 0, BGP_PATH_ALL, use_json(argc, argv));
8631 }
8632
8633 DEFUN (show_bgp_ipv6_safi_route,
8634 show_bgp_ipv6_safi_route_cmd,
8635 "show bgp ipv6 <unicast|multicast> X:X::X:X [json]",
8636 SHOW_STR
8637 BGP_STR
8638 "Address family\n"
8639 "Address Family modifier\n"
8640 "Address Family modifier\n"
8641 "Network in the BGP routing table to display\n"
8642 "JavaScript Object Notation\n")
8643 {
8644 int idx_safi = 3;
8645 int idx_ipv6 = 4;
8646 u_char uj = use_json(argc, argv);
8647 if (strncmp (argv[idx_safi]->arg, "m", 1) == 0)
8648 return bgp_show_route (vty, NULL, argv[idx_ipv6]->arg, AFI_IP6, SAFI_MULTICAST, NULL, 0, BGP_PATH_ALL, uj);
8649
8650 return bgp_show_route (vty, NULL, argv[idx_ipv6]->arg, AFI_IP6, SAFI_UNICAST, NULL, 0, BGP_PATH_ALL, uj);
8651 }
8652
8653 /*
8654 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
8655 * "show bgp ipv6 X:X::X:X (bestpath|multipath) [json]",
8656 * SHOW_STR
8657 * BGP_STR
8658 * "Address family\n"
8659 * "Network in the BGP routing table to display\n"
8660 * "Display only the bestpath\n"
8661 * "Display only multipaths\n"
8662 * "JavaScript Object Notation\n"
8663 *
8664 */
8665 DEFUN (show_bgp_route_pathtype,
8666 show_bgp_route_pathtype_cmd,
8667 "show bgp X:X::X:X <bestpath|multipath> [json]",
8668 SHOW_STR
8669 BGP_STR
8670 "Network in the BGP routing table to display\n"
8671 "Display only the bestpath\n"
8672 "Display only multipaths\n"
8673 "JavaScript Object Notation\n")
8674 {
8675 int idx_ipv6 = 2;
8676 int idx_bestpath = 3;
8677 u_char uj = use_json(argc, argv);
8678 if (strncmp (argv[idx_bestpath]->arg, "b", 1) == 0)
8679 return bgp_show_route (vty, NULL, argv[idx_ipv6]->arg, AFI_IP6, SAFI_UNICAST, NULL, 0, BGP_PATH_BESTPATH, uj);
8680 else
8681 return bgp_show_route (vty, NULL, argv[idx_ipv6]->arg, AFI_IP6, SAFI_UNICAST, NULL, 0, BGP_PATH_MULTIPATH, uj);
8682 }
8683
8684
8685 DEFUN (show_bgp_ipv6_safi_route_pathtype,
8686 show_bgp_ipv6_safi_route_pathtype_cmd,
8687 "show bgp ipv6 <unicast|multicast> X:X::X:X <bestpath|multipath> [json]",
8688 SHOW_STR
8689 BGP_STR
8690 "Address family\n"
8691 "Address Family modifier\n"
8692 "Address Family modifier\n"
8693 "Network in the BGP routing table to display\n"
8694 "Display only the bestpath\n"
8695 "Display only multipaths\n"
8696 "JavaScript Object Notation\n")
8697 {
8698 int idx_safi = 3;
8699 int idx_ipv6 = 4;
8700 int idx_bestpath = 5;
8701 u_char uj = use_json(argc, argv);
8702 if (strncmp (argv[idx_safi]->arg, "m", 1) == 0)
8703 if (strncmp (argv[idx_bestpath]->arg, "b", 1) == 0)
8704 return bgp_show_route (vty, NULL, argv[idx_ipv6]->arg, AFI_IP6, SAFI_MULTICAST, NULL, 0, BGP_PATH_BESTPATH, uj);
8705 else
8706 return bgp_show_route (vty, NULL, argv[idx_ipv6]->arg, AFI_IP6, SAFI_MULTICAST, NULL, 0, BGP_PATH_MULTIPATH, uj);
8707 else
8708 if (strncmp (argv[idx_bestpath]->arg, "b", 1) == 0)
8709 return bgp_show_route (vty, NULL, argv[idx_ipv6]->arg, AFI_IP6, SAFI_UNICAST, NULL, 0, BGP_PATH_BESTPATH, uj);
8710 else
8711 return bgp_show_route (vty, NULL, argv[idx_ipv6]->arg, AFI_IP6, SAFI_UNICAST, NULL, 0, BGP_PATH_MULTIPATH, uj);
8712 }
8713
8714 /* old command */
8715 DEFUN (show_ipv6_bgp_route,
8716 show_ipv6_bgp_route_cmd,
8717 "show ipv6 bgp X:X::X:X [json]",
8718 SHOW_STR
8719 IP_STR
8720 BGP_STR
8721 "Network in the BGP routing table to display\n"
8722 "JavaScript Object Notation\n")
8723 {
8724 int idx_ipv6 = 3;
8725 bgp_show_ipv6_bgp_deprecate_warning(vty);
8726 return bgp_show_route (vty, NULL, argv[idx_ipv6]->arg, AFI_IP6, SAFI_UNICAST, NULL, 0, BGP_PATH_ALL, use_json(argc, argv));
8727 }
8728
8729 DEFUN (show_bgp_prefix,
8730 show_bgp_prefix_cmd,
8731 "show bgp X:X::X:X/M [json]",
8732 SHOW_STR
8733 BGP_STR
8734 "IPv6 prefix <network>/<length>\n"
8735 "JavaScript Object Notation\n")
8736 {
8737 int idx_ipv6_prefixlen = 2;
8738 return bgp_show_route (vty, NULL, argv[idx_ipv6_prefixlen]->arg, AFI_IP6, SAFI_UNICAST, NULL, 1, BGP_PATH_ALL, use_json(argc, argv));
8739 }
8740
8741 DEFUN (show_bgp_ipv6_safi_prefix,
8742 show_bgp_ipv6_safi_prefix_cmd,
8743 "show bgp ipv6 <unicast|multicast> X:X::X:X/M [json]",
8744 SHOW_STR
8745 BGP_STR
8746 "Address family\n"
8747 "Address Family modifier\n"
8748 "Address Family modifier\n"
8749 "IPv6 prefix <network>/<length>, e.g., 3ffe::/16\n"
8750 "JavaScript Object Notation\n")
8751 {
8752 int idx_safi = 3;
8753 int idx_ipv6_prefixlen = 4;
8754 u_char uj = use_json(argc, argv);
8755 if (strncmp (argv[idx_safi]->arg, "m", 1) == 0)
8756 return bgp_show_route (vty, NULL, argv[idx_ipv6_prefixlen]->arg, AFI_IP6, SAFI_MULTICAST, NULL, 1, BGP_PATH_ALL, uj);
8757
8758 return bgp_show_route (vty, NULL, argv[idx_ipv6_prefixlen]->arg, AFI_IP6, SAFI_UNICAST, NULL, 1, BGP_PATH_ALL, uj);
8759 }
8760
8761 /*
8762 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
8763 * "show bgp ipv6 X:X::X:X/M (bestpath|multipath) [json]",
8764 * SHOW_STR
8765 * BGP_STR
8766 * "Address family\n"
8767 * "IPv6 prefix <network>/<length>\n"
8768 * "Display only the bestpath\n"
8769 * "Display only multipaths\n"
8770 * "JavaScript Object Notation\n"
8771 *
8772 */
8773 DEFUN (show_bgp_prefix_pathtype,
8774 show_bgp_prefix_pathtype_cmd,
8775 "show bgp X:X::X:X/M <bestpath|multipath> [json]",
8776 SHOW_STR
8777 BGP_STR
8778 "IPv6 prefix <network>/<length>\n"
8779 "Display only the bestpath\n"
8780 "Display only multipaths\n"
8781 "JavaScript Object Notation\n")
8782 {
8783 int idx_ipv6_prefixlen = 2;
8784 int idx_bestpath = 3;
8785 u_char uj = use_json(argc, argv);
8786 if (strncmp (argv[idx_bestpath]->arg, "b", 1) == 0)
8787 return bgp_show_route (vty, NULL, argv[idx_ipv6_prefixlen]->arg, AFI_IP6, SAFI_UNICAST, NULL, 1, BGP_PATH_BESTPATH, uj);
8788 else
8789 return bgp_show_route (vty, NULL, argv[idx_ipv6_prefixlen]->arg, AFI_IP6, SAFI_UNICAST, NULL, 1, BGP_PATH_MULTIPATH, uj);
8790 }
8791
8792
8793 DEFUN (show_bgp_ipv6_safi_prefix_pathtype,
8794 show_bgp_ipv6_safi_prefix_pathtype_cmd,
8795 "show bgp ipv6 <unicast|multicast> X:X::X:X/M <bestpath|multipath> [json]",
8796 SHOW_STR
8797 BGP_STR
8798 "Address family\n"
8799 "Address Family modifier\n"
8800 "Address Family modifier\n"
8801 "IPv6 prefix <network>/<length>, e.g., 3ffe::/16\n"
8802 "Display only the bestpath\n"
8803 "Display only multipaths\n"
8804 "JavaScript Object Notation\n")
8805 {
8806 int idx_safi = 3;
8807 int idx_ipv6_prefixlen = 4;
8808 int idx_bestpath = 5;
8809 u_char uj = use_json(argc, argv);
8810 if (strncmp (argv[idx_safi]->arg, "m", 1) == 0)
8811 if (strncmp (argv[idx_bestpath]->arg, "b", 1) == 0)
8812 return bgp_show_route (vty, NULL, argv[idx_ipv6_prefixlen]->arg, AFI_IP6, SAFI_MULTICAST, NULL, 1, BGP_PATH_BESTPATH, uj);
8813 else
8814 return bgp_show_route (vty, NULL, argv[idx_ipv6_prefixlen]->arg, AFI_IP6, SAFI_MULTICAST, NULL, 1, BGP_PATH_MULTIPATH, uj);
8815 else
8816 if (strncmp (argv[idx_bestpath]->arg, "b", 1) == 0)
8817 return bgp_show_route (vty, NULL, argv[idx_ipv6_prefixlen]->arg, AFI_IP6, SAFI_UNICAST, NULL, 1, BGP_PATH_BESTPATH, uj);
8818 else
8819 return bgp_show_route (vty, NULL, argv[idx_ipv6_prefixlen]->arg, AFI_IP6, SAFI_UNICAST, NULL, 1, BGP_PATH_MULTIPATH, uj);
8820 }
8821
8822 /* old command */
8823 DEFUN (show_ipv6_bgp_prefix,
8824 show_ipv6_bgp_prefix_cmd,
8825 "show ipv6 bgp X:X::X:X/M [json]",
8826 SHOW_STR
8827 IP_STR
8828 BGP_STR
8829 "IPv6 prefix <network>/<length>, e.g., 3ffe::/16\n"
8830 "JavaScript Object Notation\n")
8831 {
8832 int idx_ipv6_prefixlen = 3;
8833 bgp_show_ipv6_bgp_deprecate_warning(vty);
8834 return bgp_show_route (vty, NULL, argv[idx_ipv6_prefixlen]->arg, AFI_IP6, SAFI_UNICAST, NULL, 1, BGP_PATH_ALL, use_json(argc, argv));
8835 }
8836
8837 /*
8838 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
8839 * "show bgp <view|vrf> WORD ipv6 [json]",
8840 * SHOW_STR
8841 * BGP_STR
8842 * BGP_INSTANCE_HELP_STR
8843 * "Address family\n"
8844 * "JavaScript Object Notation\n"
8845 *
8846 */
8847 DEFUN (show_bgp_view,
8848 show_bgp_instance_cmd,
8849 "show bgp <view|vrf> WORD [json]",
8850 SHOW_STR
8851 BGP_STR
8852 BGP_INSTANCE_HELP_STR
8853 "JavaScript Object Notation\n")
8854 {
8855 int idx_word = 3;
8856 struct bgp *bgp;
8857
8858 /* BGP structure lookup. */
8859 bgp = bgp_lookup_by_name (argv[idx_word]->arg);
8860 if (bgp == NULL)
8861 {
8862 vty_out (vty, "Can't find BGP instance %s%s", argv[idx_word]->arg, VTY_NEWLINE);
8863 return CMD_WARNING;
8864 }
8865
8866 return bgp_show (vty, bgp, AFI_IP6, SAFI_UNICAST, bgp_show_type_normal, NULL, use_json(argc, argv));
8867 }
8868
8869 DEFUN (show_bgp_instance_all,
8870 show_bgp_instance_all_cmd,
8871 "show bgp <view|vrf> all [json]",
8872 SHOW_STR
8873 BGP_STR
8874 BGP_INSTANCE_ALL_HELP_STR
8875 "JavaScript Object Notation\n")
8876 {
8877 u_char uj = use_json(argc, argv);
8878
8879 bgp_show_all_instances_routes_vty (vty, AFI_IP6, SAFI_UNICAST, uj);
8880 return CMD_SUCCESS;
8881 }
8882
8883
8884 /*
8885 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
8886 * "show bgp <view|vrf> WORD ipv6 X:X::X:X [json]",
8887 * SHOW_STR
8888 * BGP_STR
8889 * BGP_INSTANCE_HELP_STR
8890 * "Address family\n"
8891 * "Network in the BGP routing table to display\n"
8892 * "JavaScript Object Notation\n"
8893 *
8894 */
8895 DEFUN (show_bgp_instance_route,
8896 show_bgp_instance_route_cmd,
8897 "show bgp <view|vrf> WORD X:X::X:X [json]",
8898 SHOW_STR
8899 BGP_STR
8900 BGP_INSTANCE_HELP_STR
8901 "Network in the BGP routing table to display\n"
8902 "JavaScript Object Notation\n")
8903 {
8904 int idx_word = 3;
8905 int idx_ipv6 = 4;
8906 return bgp_show_route (vty, argv[idx_word]->arg, argv[idx_ipv6]->arg, AFI_IP6, SAFI_UNICAST, NULL, 0, BGP_PATH_ALL, use_json(argc, argv));
8907 }
8908
8909
8910 /*
8911 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
8912 * "show bgp <view|vrf> WORD ipv6 X:X::X:X (bestpath|multipath) [json]",
8913 * SHOW_STR
8914 * BGP_STR
8915 * BGP_INSTANCE_HELP_STR
8916 * "Address family\n"
8917 * "Network in the BGP routing table to display\n"
8918 * "Display only the bestpath\n"
8919 * "Display only multipaths\n"
8920 * "JavaScript Object Notation\n"
8921 *
8922 */
8923 DEFUN (show_bgp_instance_route_pathtype,
8924 show_bgp_instance_route_pathtype_cmd,
8925 "show bgp <view|vrf> WORD X:X::X:X <bestpath|multipath> [json]",
8926 SHOW_STR
8927 BGP_STR
8928 BGP_INSTANCE_HELP_STR
8929 "Network in the BGP routing table to display\n"
8930 "Display only the bestpath\n"
8931 "Display only multipaths\n"
8932 "JavaScript Object Notation\n")
8933 {
8934 int idx_word = 3;
8935 int idx_ipv6 = 4;
8936 int idx_bestpath = 5;
8937 u_char uj = use_json(argc, argv);
8938 if (strncmp (argv[idx_bestpath]->arg, "b", 1) == 0)
8939 return bgp_show_route (vty, argv[idx_word]->arg, argv[idx_ipv6]->arg, AFI_IP6, SAFI_UNICAST, NULL, 0, BGP_PATH_BESTPATH, uj);
8940 else
8941 return bgp_show_route (vty, argv[idx_word]->arg, argv[idx_ipv6]->arg, AFI_IP6, SAFI_UNICAST, NULL, 0, BGP_PATH_MULTIPATH, uj);
8942 }
8943
8944
8945 /*
8946 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
8947 * "show bgp <view|vrf> WORD ipv6 X:X::X:X/M [json]",
8948 * SHOW_STR
8949 * BGP_STR
8950 * BGP_INSTANCE_HELP_STR
8951 * "Address family\n"
8952 * "IPv6 prefix <network>/<length>\n"
8953 * "JavaScript Object Notation\n"
8954 *
8955 */
8956 DEFUN (show_bgp_instance_prefix,
8957 show_bgp_instance_prefix_cmd,
8958 "show bgp <view|vrf> WORD X:X::X:X/M [json]",
8959 SHOW_STR
8960 BGP_STR
8961 BGP_INSTANCE_HELP_STR
8962 "IPv6 prefix <network>/<length>\n"
8963 "JavaScript Object Notation\n")
8964 {
8965 int idx_word = 3;
8966 int idx_ipv6_prefixlen = 4;
8967 return bgp_show_route (vty, argv[idx_word]->arg, argv[idx_ipv6_prefixlen]->arg, AFI_IP6, SAFI_UNICAST, NULL, 1, BGP_PATH_ALL, use_json(argc, argv));
8968 }
8969
8970
8971 /*
8972 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
8973 * "show bgp <view|vrf> WORD ipv6 X:X::X:X/M (bestpath|multipath) [json]",
8974 * SHOW_STR
8975 * BGP_STR
8976 * BGP_INSTANCE_HELP_STR
8977 * "Address family\n"
8978 * "IPv6 prefix <network>/<length>\n"
8979 * "Display only the bestpath\n"
8980 * "Display only multipaths\n"
8981 * "JavaScript Object Notation\n"
8982 *
8983 */
8984 DEFUN (show_bgp_instance_prefix_pathtype,
8985 show_bgp_instance_prefix_pathtype_cmd,
8986 "show bgp <view|vrf> WORD X:X::X:X/M <bestpath|multipath> [json]",
8987 SHOW_STR
8988 BGP_STR
8989 BGP_INSTANCE_HELP_STR
8990 "IPv6 prefix <network>/<length>\n"
8991 "Display only the bestpath\n"
8992 "Display only multipaths\n"
8993 "JavaScript Object Notation\n")
8994 {
8995 int idx_word = 3;
8996 int idx_ipv6_prefixlen = 4;
8997 int idx_bestpath = 5;
8998 u_char uj = use_json(argc, argv);
8999 if (strncmp (argv[idx_bestpath]->arg, "b", 1) == 0)
9000 return bgp_show_route (vty, argv[idx_word]->arg, argv[idx_ipv6_prefixlen]->arg, AFI_IP6, SAFI_UNICAST, NULL, 1, BGP_PATH_BESTPATH, uj);
9001 else
9002 return bgp_show_route (vty, argv[idx_word]->arg, argv[idx_ipv6_prefixlen]->arg, AFI_IP6, SAFI_UNICAST, NULL, 1, BGP_PATH_MULTIPATH, uj);
9003 }
9004
9005
9006 /*
9007 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
9008 * "show bgp <view|vrf> WORD ipv6 prefix-list WORD",
9009 * SHOW_STR
9010 * BGP_STR
9011 * BGP_INSTANCE_HELP_STR
9012 * "Address family\n"
9013 * "Display routes conforming to the prefix-list\n"
9014 * "IPv6 prefix-list name\n"
9015 *
9016 */
9017 DEFUN (show_bgp_instance_prefix_list,
9018 show_bgp_instance_prefix_list_cmd,
9019 "show bgp <view|vrf> WORD prefix-list WORD",
9020 SHOW_STR
9021 BGP_STR
9022 BGP_INSTANCE_HELP_STR
9023 "Display routes conforming to the prefix-list\n"
9024 "IPv6 prefix-list name\n")
9025 {
9026 int idx_word = 3;
9027 int idx_word_2 = 5;
9028 return bgp_show_prefix_list (vty, argv[idx_word]->arg, argv[idx_word_2]->arg, AFI_IP6, SAFI_UNICAST,
9029 bgp_show_type_prefix_list);
9030 }
9031
9032
9033 /*
9034 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
9035 * "show bgp <view|vrf> WORD ipv6 filter-list WORD",
9036 * SHOW_STR
9037 * BGP_STR
9038 * BGP_INSTANCE_HELP_STR
9039 * "Address family\n"
9040 * "Display routes conforming to the filter-list\n"
9041 * "Regular expression access list name\n"
9042 *
9043 */
9044 DEFUN (show_bgp_instance_filter_list,
9045 show_bgp_instance_filter_list_cmd,
9046 "show bgp <view|vrf> WORD filter-list WORD",
9047 SHOW_STR
9048 BGP_STR
9049 BGP_INSTANCE_HELP_STR
9050 "Display routes conforming to the filter-list\n"
9051 "Regular expression access list name\n")
9052 {
9053 int idx_word = 3;
9054 int idx_word_2 = 5;
9055 return bgp_show_filter_list (vty, argv[idx_word]->arg, argv[idx_word_2]->arg, AFI_IP6, SAFI_UNICAST,
9056 bgp_show_type_filter_list);
9057 }
9058
9059
9060 /*
9061 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
9062 * "show bgp <view|vrf> WORD ipv6 route-map WORD",
9063 * SHOW_STR
9064 * BGP_STR
9065 * BGP_INSTANCE_HELP_STR
9066 * "Address family\n"
9067 * "Display routes matching the route-map\n"
9068 * "A route-map to match on\n"
9069 *
9070 */
9071 DEFUN (show_bgp_instance_route_map,
9072 show_bgp_instance_route_map_cmd,
9073 "show bgp <view|vrf> WORD route-map WORD",
9074 SHOW_STR
9075 BGP_STR
9076 BGP_INSTANCE_HELP_STR
9077 "Display routes matching the route-map\n"
9078 "A route-map to match on\n")
9079 {
9080 int idx_word = 3;
9081 int idx_word_2 = 5;
9082 return bgp_show_route_map (vty, argv[idx_word]->arg, argv[idx_word_2]->arg, AFI_IP6, SAFI_UNICAST,
9083 bgp_show_type_route_map);
9084 }
9085
9086
9087 /*
9088 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
9089 * "show bgp <view|vrf> WORD ipv6 community-list (<1-500>|WORD)",
9090 * SHOW_STR
9091 * BGP_STR
9092 * BGP_INSTANCE_HELP_STR
9093 * "Address family\n"
9094 * "Display routes matching the community-list\n"
9095 * "community-list number\n"
9096 * "community-list name\n"
9097 *
9098 */
9099 DEFUN (show_bgp_instance_community_list,
9100 show_bgp_instance_community_list_cmd,
9101 "show bgp <view|vrf> WORD community-list <(1-500)|WORD>",
9102 SHOW_STR
9103 BGP_STR
9104 BGP_INSTANCE_HELP_STR
9105 "Display routes matching the community-list\n"
9106 "community-list number\n"
9107 "community-list name\n")
9108 {
9109 int idx_word = 3;
9110 int idx_comm_list = 5;
9111 return bgp_show_community_list (vty, argv[idx_word]->arg, argv[idx_comm_list]->arg, 0, AFI_IP6, SAFI_UNICAST);
9112 }
9113
9114
9115 /*
9116 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
9117 * "show bgp <view|vrf> WORD ipv6 X:X::X:X/M longer-prefixes",
9118 * SHOW_STR
9119 * BGP_STR
9120 * BGP_INSTANCE_HELP_STR
9121 * "Address family\n"
9122 * "IPv6 prefix <network>/<length>\n"
9123 * "Display route and more specific routes\n"
9124 *
9125 */
9126 DEFUN (show_bgp_instance_prefix_longer,
9127 show_bgp_instance_prefix_longer_cmd,
9128 "show bgp <view|vrf> WORD X:X::X:X/M longer-prefixes",
9129 SHOW_STR
9130 BGP_STR
9131 BGP_INSTANCE_HELP_STR
9132 "IPv6 prefix <network>/<length>\n"
9133 "Display route and more specific routes\n")
9134 {
9135 int idx_word = 3;
9136 int idx_ipv6_prefixlen = 4;
9137 return bgp_show_prefix_longer (vty, argv[idx_word]->arg, argv[idx_ipv6_prefixlen]->arg, AFI_IP6, SAFI_UNICAST,
9138 bgp_show_type_prefix_longer);
9139 }
9140
9141
9142 /* old command */
9143 DEFUN (show_ipv6_mbgp,
9144 show_ipv6_mbgp_cmd,
9145 "show ipv6 mbgp [json]",
9146 SHOW_STR
9147 IP_STR
9148 MBGP_STR
9149 "JavaScript Object Notation\n")
9150 {
9151 bgp_show_ipv6_bgp_deprecate_warning(vty);
9152 return bgp_show (vty, NULL, AFI_IP6, SAFI_MULTICAST, bgp_show_type_normal,
9153 NULL, use_json(argc, argv));
9154 }
9155
9156 /* old command */
9157 DEFUN (show_ipv6_mbgp_route,
9158 show_ipv6_mbgp_route_cmd,
9159 "show ipv6 mbgp X:X::X:X [json]",
9160 SHOW_STR
9161 IP_STR
9162 MBGP_STR
9163 "Network in the MBGP routing table to display\n"
9164 "JavaScript Object Notation\n")
9165 {
9166 int idx_ipv6 = 3;
9167 bgp_show_ipv6_bgp_deprecate_warning(vty);
9168 return bgp_show_route (vty, NULL, argv[idx_ipv6]->arg, AFI_IP6, SAFI_MULTICAST, NULL, 0, BGP_PATH_ALL, use_json(argc, argv));
9169 }
9170
9171 /* old command */
9172 DEFUN (show_ipv6_mbgp_prefix,
9173 show_ipv6_mbgp_prefix_cmd,
9174 "show ipv6 mbgp X:X::X:X/M [json]",
9175 SHOW_STR
9176 IP_STR
9177 MBGP_STR
9178 "IPv6 prefix <network>/<length>, e.g., 3ffe::/16\n"
9179 "JavaScript Object Notation\n")
9180 {
9181 int idx_ipv6_prefixlen = 3;
9182 bgp_show_ipv6_bgp_deprecate_warning(vty);
9183 return bgp_show_route (vty, NULL, argv[idx_ipv6_prefixlen]->arg, AFI_IP6, SAFI_MULTICAST, NULL, 1, BGP_PATH_ALL, use_json(argc, argv));
9184 }
9185 #endif
9186
9187
9188 static int
9189 bgp_show_regexp (struct vty *vty, int argc, struct cmd_token **argv, afi_t afi,
9190 safi_t safi, enum bgp_show_type type)
9191 {
9192 int i;
9193 struct buffer *b;
9194 char *regstr;
9195 int first;
9196 regex_t *regex;
9197 int rc;
9198
9199 first = 0;
9200 b = buffer_new (1024);
9201 for (i = 0; i < argc; i++)
9202 {
9203 if (first)
9204 buffer_putc (b, ' ');
9205 else
9206 {
9207 if ((strcmp (argv[i]->arg, "unicast") == 0) || (strcmp (argv[i]->arg, "multicast") == 0))
9208 continue;
9209 first = 1;
9210 }
9211
9212 buffer_putstr (b, argv[i]->arg);
9213 }
9214 buffer_putc (b, '\0');
9215
9216 regstr = buffer_getstr (b);
9217 buffer_free (b);
9218
9219 regex = bgp_regcomp (regstr);
9220 XFREE(MTYPE_TMP, regstr);
9221 if (! regex)
9222 {
9223 vty_out (vty, "Can't compile regexp %s%s", argv[0]->arg,
9224 VTY_NEWLINE);
9225 return CMD_WARNING;
9226 }
9227
9228 rc = bgp_show (vty, NULL, afi, safi, type, regex, 0);
9229 bgp_regex_free (regex);
9230 return rc;
9231 }
9232
9233 DEFUN (show_ip_bgp_regexp,
9234 show_ip_bgp_regexp_cmd,
9235 "show ip bgp regexp .LINE",
9236 SHOW_STR
9237 IP_STR
9238 BGP_STR
9239 "Display routes matching the AS path regular expression\n"
9240 "A regular-expression to match the BGP AS paths\n")
9241 {
9242 return bgp_show_regexp (vty, argc, argv, AFI_IP, SAFI_UNICAST,
9243 bgp_show_type_regexp);
9244 }
9245
9246 /*
9247 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
9248 * "show ip bgp dampening flap-statistics regexp .LINE",
9249 * SHOW_STR
9250 * IP_STR
9251 * BGP_STR
9252 * "Display detailed information about dampening\n"
9253 * "Display flap statistics of routes\n"
9254 * "Display routes matching the AS path regular expression\n"
9255 * "A regular-expression to match the BGP AS paths\n"
9256 *
9257 */
9258 DEFUN (show_ip_bgp_flap_regexp,
9259 show_ip_bgp_flap_regexp_cmd,
9260 "show ip bgp flap-statistics regexp .LINE",
9261 SHOW_STR
9262 IP_STR
9263 BGP_STR
9264 "Display flap statistics of routes\n"
9265 "Display routes matching the AS path regular expression\n"
9266 "A regular-expression to match the BGP AS paths\n")
9267 {
9268 return bgp_show_regexp (vty, argc, argv, AFI_IP, SAFI_UNICAST,
9269 bgp_show_type_flap_regexp);
9270 }
9271
9272
9273 DEFUN (show_ip_bgp_ipv4_regexp,
9274 show_ip_bgp_ipv4_regexp_cmd,
9275 "show ip bgp ipv4 <unicast|multicast> regexp .LINE",
9276 SHOW_STR
9277 IP_STR
9278 BGP_STR
9279 "Address family\n"
9280 "Address Family modifier\n"
9281 "Address Family modifier\n"
9282 "Display routes matching the AS path regular expression\n"
9283 "A regular-expression to match the BGP AS paths\n")
9284 {
9285 int idx_safi = 4;
9286 if (strncmp (argv[idx_safi]->arg, "m", 1) == 0)
9287 return bgp_show_regexp (vty, argc, argv, AFI_IP, SAFI_MULTICAST,
9288 bgp_show_type_regexp);
9289
9290 return bgp_show_regexp (vty, argc, argv, AFI_IP, SAFI_UNICAST,
9291 bgp_show_type_regexp);
9292 }
9293
9294 #ifdef HAVE_IPV6
9295 /*
9296 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
9297 * "show bgp ipv6 regexp .LINE",
9298 * SHOW_STR
9299 * BGP_STR
9300 * "Address family\n"
9301 * "Display routes matching the AS path regular expression\n"
9302 * "A regular-expression to match the BGP AS paths\n"
9303 *
9304 */
9305 DEFUN (show_bgp_regexp,
9306 show_bgp_regexp_cmd,
9307 "show bgp regexp .LINE",
9308 SHOW_STR
9309 BGP_STR
9310 "Display routes matching the AS path regular expression\n"
9311 "A regular-expression to match the BGP AS paths\n")
9312 {
9313 return bgp_show_regexp (vty, argc, argv, AFI_IP6, SAFI_UNICAST,
9314 bgp_show_type_regexp);
9315 }
9316
9317
9318 /* old command */
9319 DEFUN (show_ipv6_bgp_regexp,
9320 show_ipv6_bgp_regexp_cmd,
9321 "show ipv6 bgp regexp .LINE",
9322 SHOW_STR
9323 IP_STR
9324 BGP_STR
9325 "Display routes matching the AS path regular expression\n"
9326 "A regular-expression to match the BGP AS paths\n")
9327 {
9328 bgp_show_ipv6_bgp_deprecate_warning(vty);
9329 return bgp_show_regexp (vty, argc, argv, AFI_IP6, SAFI_UNICAST,
9330 bgp_show_type_regexp);
9331 }
9332
9333 /* old command */
9334 DEFUN (show_ipv6_mbgp_regexp,
9335 show_ipv6_mbgp_regexp_cmd,
9336 "show ipv6 mbgp regexp .LINE",
9337 SHOW_STR
9338 IP_STR
9339 BGP_STR
9340 "Display routes matching the AS path regular expression\n"
9341 "A regular-expression to match the MBGP AS paths\n")
9342 {
9343 bgp_show_ipv6_bgp_deprecate_warning(vty);
9344 return bgp_show_regexp (vty, argc, argv, AFI_IP6, SAFI_MULTICAST,
9345 bgp_show_type_regexp);
9346 }
9347 #endif /* HAVE_IPV6 */
9348
9349 static int
9350 bgp_show_prefix_list (struct vty *vty, const char *name,
9351 const char *prefix_list_str, afi_t afi,
9352 safi_t safi, enum bgp_show_type type)
9353 {
9354 struct prefix_list *plist;
9355 struct bgp *bgp = NULL;
9356
9357 if (name && !(bgp = bgp_lookup_by_name(name)))
9358 {
9359 vty_out (vty, "%% No such BGP instance exists%s", VTY_NEWLINE);
9360 return CMD_WARNING;
9361 }
9362
9363 plist = prefix_list_lookup (afi, prefix_list_str);
9364 if (plist == NULL)
9365 {
9366 vty_out (vty, "%% %s is not a valid prefix-list name%s",
9367 prefix_list_str, VTY_NEWLINE);
9368 return CMD_WARNING;
9369 }
9370
9371 return bgp_show (vty, bgp, afi, safi, type, plist, 0);
9372 }
9373
9374 DEFUN (show_ip_bgp_prefix_list,
9375 show_ip_bgp_prefix_list_cmd,
9376 "show ip bgp prefix-list WORD",
9377 SHOW_STR
9378 IP_STR
9379 BGP_STR
9380 "Display routes conforming to the prefix-list\n"
9381 "IP prefix-list name\n")
9382 {
9383 int idx_word = 4;
9384 return bgp_show_prefix_list (vty, NULL, argv[idx_word]->arg, AFI_IP, SAFI_UNICAST,
9385 bgp_show_type_prefix_list);
9386 }
9387
9388 DEFUN (show_ip_bgp_instance_prefix_list,
9389 show_ip_bgp_instance_prefix_list_cmd,
9390 "show ip bgp <view|vrf> WORD prefix-list WORD",
9391 SHOW_STR
9392 IP_STR
9393 BGP_STR
9394 BGP_INSTANCE_HELP_STR
9395 "Display routes conforming to the prefix-list\n"
9396 "IP prefix-list name\n")
9397 {
9398 int idx_word = 4;
9399 int idx_word_2 = 6;
9400 return bgp_show_prefix_list (vty, argv[idx_word]->arg, argv[idx_word_2]->arg, AFI_IP, SAFI_UNICAST,
9401 bgp_show_type_prefix_list);
9402 }
9403
9404 /*
9405 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
9406 * "show ip bgp dampening flap-statistics prefix-list WORD",
9407 * SHOW_STR
9408 * IP_STR
9409 * BGP_STR
9410 * "Display detailed information about dampening\n"
9411 * "Display flap statistics of routes\n"
9412 * "Display routes conforming to the prefix-list\n"
9413 * "IP prefix-list name\n"
9414 *
9415 */
9416 DEFUN (show_ip_bgp_flap_prefix_list,
9417 show_ip_bgp_flap_prefix_list_cmd,
9418 "show ip bgp flap-statistics prefix-list WORD",
9419 SHOW_STR
9420 IP_STR
9421 BGP_STR
9422 "Display flap statistics of routes\n"
9423 "Display routes conforming to the prefix-list\n"
9424 "IP prefix-list name\n")
9425 {
9426 int idx_word = 5;
9427 return bgp_show_prefix_list (vty, NULL, argv[idx_word]->arg, AFI_IP, SAFI_UNICAST,
9428 bgp_show_type_flap_prefix_list);
9429 }
9430
9431
9432 DEFUN (show_ip_bgp_ipv4_prefix_list,
9433 show_ip_bgp_ipv4_prefix_list_cmd,
9434 "show ip bgp ipv4 <unicast|multicast> prefix-list WORD",
9435 SHOW_STR
9436 IP_STR
9437 BGP_STR
9438 "Address family\n"
9439 "Address Family modifier\n"
9440 "Address Family modifier\n"
9441 "Display routes conforming to the prefix-list\n"
9442 "IP prefix-list name\n")
9443 {
9444 int idx_safi = 4;
9445 int idx_word = 6;
9446 if (strncmp (argv[idx_safi]->arg, "m", 1) == 0)
9447 return bgp_show_prefix_list (vty, NULL, argv[idx_word]->arg, AFI_IP, SAFI_MULTICAST,
9448 bgp_show_type_prefix_list);
9449
9450 return bgp_show_prefix_list (vty, NULL, argv[idx_word]->arg, AFI_IP, SAFI_UNICAST,
9451 bgp_show_type_prefix_list);
9452 }
9453
9454 #ifdef HAVE_IPV6
9455 /*
9456 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
9457 * "show bgp ipv6 prefix-list WORD",
9458 * SHOW_STR
9459 * BGP_STR
9460 * "Address family\n"
9461 * "Display routes conforming to the prefix-list\n"
9462 * "IPv6 prefix-list name\n"
9463 *
9464 */
9465 DEFUN (show_bgp_prefix_list,
9466 show_bgp_prefix_list_cmd,
9467 "show bgp prefix-list WORD",
9468 SHOW_STR
9469 BGP_STR
9470 "Display routes conforming to the prefix-list\n"
9471 "IPv6 prefix-list name\n")
9472 {
9473 int idx_word = 3;
9474 return bgp_show_prefix_list (vty, NULL, argv[idx_word]->arg, AFI_IP6, SAFI_UNICAST,
9475 bgp_show_type_prefix_list);
9476 }
9477
9478
9479 /* old command */
9480 DEFUN (show_ipv6_bgp_prefix_list,
9481 show_ipv6_bgp_prefix_list_cmd,
9482 "show ipv6 bgp prefix-list WORD",
9483 SHOW_STR
9484 IPV6_STR
9485 BGP_STR
9486 "Display routes matching the prefix-list\n"
9487 "IPv6 prefix-list name\n")
9488 {
9489 int idx_word = 4;
9490 bgp_show_ipv6_bgp_deprecate_warning(vty);
9491 return bgp_show_prefix_list (vty, NULL, argv[idx_word]->arg, AFI_IP6, SAFI_UNICAST,
9492 bgp_show_type_prefix_list);
9493 }
9494
9495 /* old command */
9496 DEFUN (show_ipv6_mbgp_prefix_list,
9497 show_ipv6_mbgp_prefix_list_cmd,
9498 "show ipv6 mbgp prefix-list WORD",
9499 SHOW_STR
9500 IPV6_STR
9501 MBGP_STR
9502 "Display routes matching the prefix-list\n"
9503 "IPv6 prefix-list name\n")
9504 {
9505 int idx_word = 4;
9506 bgp_show_ipv6_bgp_deprecate_warning(vty);
9507 return bgp_show_prefix_list (vty, NULL, argv[idx_word]->arg, AFI_IP6, SAFI_MULTICAST,
9508 bgp_show_type_prefix_list);
9509 }
9510 #endif /* HAVE_IPV6 */
9511
9512 static int
9513 bgp_show_filter_list (struct vty *vty, const char *name,
9514 const char *filter, afi_t afi,
9515 safi_t safi, enum bgp_show_type type)
9516 {
9517 struct as_list *as_list;
9518 struct bgp *bgp = NULL;
9519
9520 if (name && !(bgp = bgp_lookup_by_name(name)))
9521 {
9522 vty_out (vty, "%% No such BGP instance exists%s", VTY_NEWLINE);
9523 return CMD_WARNING;
9524 }
9525
9526 as_list = as_list_lookup (filter);
9527 if (as_list == NULL)
9528 {
9529 vty_out (vty, "%% %s is not a valid AS-path access-list name%s", filter, VTY_NEWLINE);
9530 return CMD_WARNING;
9531 }
9532
9533 return bgp_show (vty, bgp, afi, safi, type, as_list, 0);
9534 }
9535
9536 DEFUN (show_ip_bgp_filter_list,
9537 show_ip_bgp_filter_list_cmd,
9538 "show ip bgp filter-list WORD",
9539 SHOW_STR
9540 IP_STR
9541 BGP_STR
9542 "Display routes conforming to the filter-list\n"
9543 "Regular expression access list name\n")
9544 {
9545 int idx_word = 4;
9546 return bgp_show_filter_list (vty, NULL, argv[idx_word]->arg, AFI_IP, SAFI_UNICAST,
9547 bgp_show_type_filter_list);
9548 }
9549
9550 DEFUN (show_ip_bgp_instance_filter_list,
9551 show_ip_bgp_instance_filter_list_cmd,
9552 "show ip bgp <view|vrf> WORD filter-list WORD",
9553 SHOW_STR
9554 IP_STR
9555 BGP_STR
9556 BGP_INSTANCE_HELP_STR
9557 "Display routes conforming to the filter-list\n"
9558 "Regular expression access list name\n")
9559 {
9560 int idx_word = 4;
9561 int idx_word_2 = 6;
9562 return bgp_show_filter_list (vty, argv[idx_word]->arg, argv[idx_word_2]->arg, AFI_IP, SAFI_UNICAST,
9563 bgp_show_type_filter_list);
9564 }
9565
9566 /*
9567 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
9568 * "show ip bgp dampening flap-statistics filter-list WORD",
9569 * SHOW_STR
9570 * IP_STR
9571 * BGP_STR
9572 * "Display detailed information about dampening\n"
9573 * "Display flap statistics of routes\n"
9574 * "Display routes conforming to the filter-list\n"
9575 * "Regular expression access list name\n"
9576 *
9577 */
9578 DEFUN (show_ip_bgp_flap_filter_list,
9579 show_ip_bgp_flap_filter_list_cmd,
9580 "show ip bgp flap-statistics filter-list WORD",
9581 SHOW_STR
9582 IP_STR
9583 BGP_STR
9584 "Display flap statistics of routes\n"
9585 "Display routes conforming to the filter-list\n"
9586 "Regular expression access list name\n")
9587 {
9588 int idx_word = 5;
9589 return bgp_show_filter_list (vty, NULL, argv[idx_word]->arg, AFI_IP, SAFI_UNICAST,
9590 bgp_show_type_flap_filter_list);
9591 }
9592
9593
9594 DEFUN (show_ip_bgp_ipv4_filter_list,
9595 show_ip_bgp_ipv4_filter_list_cmd,
9596 "show ip bgp ipv4 <unicast|multicast> filter-list WORD",
9597 SHOW_STR
9598 IP_STR
9599 BGP_STR
9600 "Address family\n"
9601 "Address Family modifier\n"
9602 "Address Family modifier\n"
9603 "Display routes conforming to the filter-list\n"
9604 "Regular expression access list name\n")
9605 {
9606 int idx_safi = 4;
9607 int idx_word = 6;
9608 if (strncmp (argv[idx_safi]->arg, "m", 1) == 0)
9609 return bgp_show_filter_list (vty, NULL, argv[idx_word]->arg, AFI_IP, SAFI_MULTICAST,
9610 bgp_show_type_filter_list);
9611
9612 return bgp_show_filter_list (vty, NULL, argv[idx_word]->arg, AFI_IP, SAFI_UNICAST,
9613 bgp_show_type_filter_list);
9614 }
9615
9616 #ifdef HAVE_IPV6
9617 /*
9618 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
9619 * "show bgp ipv6 filter-list WORD",
9620 * SHOW_STR
9621 * BGP_STR
9622 * "Address family\n"
9623 * "Display routes conforming to the filter-list\n"
9624 * "Regular expression access list name\n"
9625 *
9626 */
9627 DEFUN (show_bgp_filter_list,
9628 show_bgp_filter_list_cmd,
9629 "show bgp filter-list WORD",
9630 SHOW_STR
9631 BGP_STR
9632 "Display routes conforming to the filter-list\n"
9633 "Regular expression access list name\n")
9634 {
9635 int idx_word = 3;
9636 return bgp_show_filter_list (vty, NULL, argv[idx_word]->arg, AFI_IP6, SAFI_UNICAST,
9637 bgp_show_type_filter_list);
9638 }
9639
9640
9641 /* old command */
9642 DEFUN (show_ipv6_bgp_filter_list,
9643 show_ipv6_bgp_filter_list_cmd,
9644 "show ipv6 bgp filter-list WORD",
9645 SHOW_STR
9646 IPV6_STR
9647 BGP_STR
9648 "Display routes conforming to the filter-list\n"
9649 "Regular expression access list name\n")
9650 {
9651 int idx_word = 4;
9652 bgp_show_ipv6_bgp_deprecate_warning(vty);
9653 return bgp_show_filter_list (vty, NULL, argv[idx_word]->arg, AFI_IP6, SAFI_UNICAST,
9654 bgp_show_type_filter_list);
9655 }
9656
9657 /* old command */
9658 DEFUN (show_ipv6_mbgp_filter_list,
9659 show_ipv6_mbgp_filter_list_cmd,
9660 "show ipv6 mbgp filter-list WORD",
9661 SHOW_STR
9662 IPV6_STR
9663 MBGP_STR
9664 "Display routes conforming to the filter-list\n"
9665 "Regular expression access list name\n")
9666 {
9667 int idx_word = 4;
9668 bgp_show_ipv6_bgp_deprecate_warning(vty);
9669 return bgp_show_filter_list (vty, NULL, argv[idx_word]->arg, AFI_IP6, SAFI_MULTICAST,
9670 bgp_show_type_filter_list);
9671 }
9672 #endif /* HAVE_IPV6 */
9673
9674 DEFUN (show_ip_bgp_dampening_info,
9675 show_ip_bgp_dampening_params_cmd,
9676 "show ip bgp dampening parameters",
9677 SHOW_STR
9678 IP_STR
9679 BGP_STR
9680 "Display detailed information about dampening\n"
9681 "Display detail of configured dampening parameters\n")
9682 {
9683 return bgp_show_dampening_parameters (vty, AFI_IP, SAFI_UNICAST);
9684 }
9685
9686
9687 DEFUN (show_ip_bgp_ipv4_dampening_parameters,
9688 show_ip_bgp_ipv4_dampening_parameters_cmd,
9689 "show ip bgp ipv4 <unicast|multicast> dampening parameters",
9690 SHOW_STR
9691 IP_STR
9692 BGP_STR
9693 "Address family\n"
9694 "Address Family modifier\n"
9695 "Address Family modifier\n"
9696 "Display detailed information about dampening\n"
9697 "Display detail of configured dampening parameters\n")
9698 {
9699 int idx_safi = 4;
9700 if (strncmp(argv[idx_safi]->arg, "m", 1) == 0)
9701 return bgp_show_dampening_parameters (vty, AFI_IP, SAFI_MULTICAST);
9702
9703 return bgp_show_dampening_parameters (vty, AFI_IP, SAFI_UNICAST);
9704 }
9705
9706
9707 DEFUN (show_ip_bgp_ipv4_dampening_flap_stats,
9708 show_ip_bgp_ipv4_dampening_flap_stats_cmd,
9709 "show ip bgp ipv4 <unicast|multicast> dampening flap-statistics",
9710 SHOW_STR
9711 IP_STR
9712 BGP_STR
9713 "Address family\n"
9714 "Address Family modifier\n"
9715 "Address Family modifier\n"
9716 "Display detailed information about dampening\n"
9717 "Display flap statistics of routes\n")
9718 {
9719 int idx_safi = 4;
9720 if (strncmp(argv[idx_safi]->arg, "m", 1) == 0)
9721 return bgp_show (vty, NULL, AFI_IP, SAFI_MULTICAST,
9722 bgp_show_type_flap_statistics, NULL, 0);
9723
9724 return bgp_show (vty, NULL, AFI_IP, SAFI_MULTICAST,
9725 bgp_show_type_flap_statistics, NULL, 0);
9726 }
9727
9728 DEFUN (show_ip_bgp_ipv4_dampening_dampd_paths,
9729 show_ip_bgp_ipv4_dampening_dampd_paths_cmd,
9730 "show ip bgp ipv4 <unicast|multicast> dampening dampened-paths",
9731 SHOW_STR
9732 IP_STR
9733 BGP_STR
9734 "Address family\n"
9735 "Address Family modifier\n"
9736 "Address Family modifier\n"
9737 "Display detailed information about dampening\n"
9738 "Display paths suppressed due to dampening\n")
9739 {
9740 int idx_safi = 4;
9741 if (strncmp(argv[idx_safi]->arg, "m", 1) == 0)
9742 return bgp_show (vty, NULL, AFI_IP, SAFI_MULTICAST,
9743 bgp_show_type_dampend_paths, NULL, 0);
9744
9745 return bgp_show (vty, NULL, AFI_IP, SAFI_MULTICAST,
9746 bgp_show_type_dampend_paths, NULL, 0);
9747 }
9748
9749 static int
9750 bgp_show_route_map (struct vty *vty, const char *name,
9751 const char *rmap_str, afi_t afi,
9752 safi_t safi, enum bgp_show_type type)
9753 {
9754 struct route_map *rmap;
9755 struct bgp *bgp = NULL;
9756
9757 if (name && !(bgp = bgp_lookup_by_name(name)))
9758 {
9759 vty_out (vty, "%% No such BGP instance exists%s", VTY_NEWLINE);
9760 return CMD_WARNING;
9761 }
9762
9763 rmap = route_map_lookup_by_name (rmap_str);
9764 if (! rmap)
9765 {
9766 vty_out (vty, "%% %s is not a valid route-map name%s",
9767 rmap_str, VTY_NEWLINE);
9768 return CMD_WARNING;
9769 }
9770
9771 return bgp_show (vty, bgp, afi, safi, type, rmap, 0);
9772 }
9773
9774 DEFUN (show_ip_bgp_route_map,
9775 show_ip_bgp_route_map_cmd,
9776 "show ip bgp route-map WORD",
9777 SHOW_STR
9778 IP_STR
9779 BGP_STR
9780 "Display routes matching the route-map\n"
9781 "A route-map to match on\n")
9782 {
9783 int idx_word = 4;
9784 return bgp_show_route_map (vty, NULL, argv[idx_word]->arg, AFI_IP, SAFI_UNICAST,
9785 bgp_show_type_route_map);
9786 }
9787
9788 DEFUN (show_ip_bgp_instance_route_map,
9789 show_ip_bgp_instance_route_map_cmd,
9790 "show ip bgp <view|vrf> WORD route-map WORD",
9791 SHOW_STR
9792 IP_STR
9793 BGP_STR
9794 BGP_INSTANCE_HELP_STR
9795 "Display routes matching the route-map\n"
9796 "A route-map to match on\n")
9797 {
9798 int idx_word = 4;
9799 int idx_word_2 = 6;
9800 return bgp_show_route_map (vty, argv[idx_word]->arg, argv[idx_word_2]->arg, AFI_IP, SAFI_UNICAST,
9801 bgp_show_type_route_map);
9802 }
9803
9804 /*
9805 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
9806 * "show ip bgp dampening flap-statistics route-map WORD",
9807 * SHOW_STR
9808 * IP_STR
9809 * BGP_STR
9810 * "Display detailed information about dampening\n"
9811 * "Display flap statistics of routes\n"
9812 * "Display routes matching the route-map\n"
9813 * "A route-map to match on\n"
9814 *
9815 */
9816 DEFUN (show_ip_bgp_flap_route_map,
9817 show_ip_bgp_flap_route_map_cmd,
9818 "show ip bgp flap-statistics route-map WORD",
9819 SHOW_STR
9820 IP_STR
9821 BGP_STR
9822 "Display flap statistics of routes\n"
9823 "Display routes matching the route-map\n"
9824 "A route-map to match on\n")
9825 {
9826 int idx_word = 5;
9827 return bgp_show_route_map (vty, NULL, argv[idx_word]->arg, AFI_IP, SAFI_UNICAST,
9828 bgp_show_type_flap_route_map);
9829 }
9830
9831
9832 DEFUN (show_ip_bgp_ipv4_route_map,
9833 show_ip_bgp_ipv4_route_map_cmd,
9834 "show ip bgp ipv4 <unicast|multicast> route-map WORD",
9835 SHOW_STR
9836 IP_STR
9837 BGP_STR
9838 "Address family\n"
9839 "Address Family modifier\n"
9840 "Address Family modifier\n"
9841 "Display routes matching the route-map\n"
9842 "A route-map to match on\n")
9843 {
9844 int idx_safi = 4;
9845 int idx_word = 6;
9846 if (strncmp (argv[idx_safi]->arg, "m", 1) == 0)
9847 return bgp_show_route_map (vty, NULL, argv[idx_word]->arg, AFI_IP, SAFI_MULTICAST,
9848 bgp_show_type_route_map);
9849
9850 return bgp_show_route_map (vty, NULL, argv[idx_word]->arg, AFI_IP, SAFI_UNICAST,
9851 bgp_show_type_route_map);
9852 }
9853
9854 /*
9855 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
9856 * "show bgp ipv6 route-map WORD",
9857 * SHOW_STR
9858 * BGP_STR
9859 * "Address family\n"
9860 * "Display routes matching the route-map\n"
9861 * "A route-map to match on\n"
9862 *
9863 */
9864 DEFUN (show_bgp_route_map,
9865 show_bgp_route_map_cmd,
9866 "show bgp route-map WORD",
9867 SHOW_STR
9868 BGP_STR
9869 "Display routes matching the route-map\n"
9870 "A route-map to match on\n")
9871 {
9872 int idx_word = 3;
9873 return bgp_show_route_map (vty, NULL, argv[idx_word]->arg, AFI_IP6, SAFI_UNICAST,
9874 bgp_show_type_route_map);
9875 }
9876
9877
9878 DEFUN (show_ip_bgp_cidr_only,
9879 show_ip_bgp_cidr_only_cmd,
9880 "show ip bgp cidr-only",
9881 SHOW_STR
9882 IP_STR
9883 BGP_STR
9884 "Display only routes with non-natural netmasks\n")
9885 {
9886 return bgp_show (vty, NULL, AFI_IP, SAFI_UNICAST,
9887 bgp_show_type_cidr_only, NULL, 0);
9888 }
9889
9890 /*
9891 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
9892 * "show ip bgp dampening flap-statistics cidr-only",
9893 * SHOW_STR
9894 * IP_STR
9895 * BGP_STR
9896 * "Display detailed information about dampening\n"
9897 * "Display flap statistics of routes\n"
9898 * "Display only routes with non-natural netmasks\n"
9899 *
9900 */
9901 DEFUN (show_ip_bgp_flap_cidr_only,
9902 show_ip_bgp_flap_cidr_only_cmd,
9903 "show ip bgp flap-statistics cidr-only",
9904 SHOW_STR
9905 IP_STR
9906 BGP_STR
9907 "Display flap statistics of routes\n"
9908 "Display only routes with non-natural netmasks\n")
9909 {
9910 return bgp_show (vty, NULL, AFI_IP, SAFI_UNICAST,
9911 bgp_show_type_flap_cidr_only, NULL, 0);
9912 }
9913
9914
9915 DEFUN (show_ip_bgp_ipv4_cidr_only,
9916 show_ip_bgp_ipv4_cidr_only_cmd,
9917 "show ip bgp ipv4 <unicast|multicast> cidr-only",
9918 SHOW_STR
9919 IP_STR
9920 BGP_STR
9921 "Address family\n"
9922 "Address Family modifier\n"
9923 "Address Family modifier\n"
9924 "Display only routes with non-natural netmasks\n")
9925 {
9926 int idx_safi = 4;
9927 if (strncmp (argv[idx_safi]->arg, "m", 1) == 0)
9928 return bgp_show (vty, NULL, AFI_IP, SAFI_MULTICAST,
9929 bgp_show_type_cidr_only, NULL, 0);
9930
9931 return bgp_show (vty, NULL, AFI_IP, SAFI_UNICAST,
9932 bgp_show_type_cidr_only, NULL, 0);
9933 }
9934
9935 DEFUN (show_ip_bgp_community_all,
9936 show_ip_bgp_community_all_cmd,
9937 "show ip bgp community",
9938 SHOW_STR
9939 IP_STR
9940 BGP_STR
9941 "Display routes matching the communities\n")
9942 {
9943 return bgp_show (vty, NULL, AFI_IP, SAFI_UNICAST,
9944 bgp_show_type_community_all, NULL, 0);
9945 }
9946
9947 DEFUN (show_ip_bgp_ipv4_community_all,
9948 show_ip_bgp_ipv4_community_all_cmd,
9949 "show ip bgp ipv4 <unicast|multicast> community",
9950 SHOW_STR
9951 IP_STR
9952 BGP_STR
9953 "Address family\n"
9954 "Address Family modifier\n"
9955 "Address Family modifier\n"
9956 "Display routes matching the communities\n")
9957 {
9958 int idx_safi = 4;
9959 if (strncmp (argv[idx_safi]->arg, "m", 1) == 0)
9960 return bgp_show (vty, NULL, AFI_IP, SAFI_MULTICAST,
9961 bgp_show_type_community_all, NULL, 0);
9962
9963 return bgp_show (vty, NULL, AFI_IP, SAFI_UNICAST,
9964 bgp_show_type_community_all, NULL, 0);
9965 }
9966
9967 #ifdef HAVE_IPV6
9968 /*
9969 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
9970 * "show bgp ipv6 community",
9971 * SHOW_STR
9972 * BGP_STR
9973 * "Address family\n"
9974 * "Display routes matching the communities\n"
9975 *
9976 */
9977 DEFUN (show_bgp_community_all,
9978 show_bgp_community_all_cmd,
9979 "show bgp community",
9980 SHOW_STR
9981 BGP_STR
9982 "Display routes matching the communities\n")
9983 {
9984 return bgp_show (vty, NULL, AFI_IP6, SAFI_UNICAST,
9985 bgp_show_type_community_all, NULL, 0);
9986 }
9987
9988
9989 /* old command */
9990 DEFUN (show_ipv6_bgp_community_all,
9991 show_ipv6_bgp_community_all_cmd,
9992 "show ipv6 bgp community",
9993 SHOW_STR
9994 IPV6_STR
9995 BGP_STR
9996 "Display routes matching the communities\n")
9997 {
9998 bgp_show_ipv6_bgp_deprecate_warning(vty);
9999 return bgp_show (vty, NULL, AFI_IP6, SAFI_UNICAST,
10000 bgp_show_type_community_all, NULL, 0);
10001 }
10002
10003 /* old command */
10004 DEFUN (show_ipv6_mbgp_community_all,
10005 show_ipv6_mbgp_community_all_cmd,
10006 "show ipv6 mbgp community",
10007 SHOW_STR
10008 IPV6_STR
10009 MBGP_STR
10010 "Display routes matching the communities\n")
10011 {
10012 bgp_show_ipv6_bgp_deprecate_warning(vty);
10013 return bgp_show (vty, NULL, AFI_IP6, SAFI_MULTICAST,
10014 bgp_show_type_community_all, NULL, 0);
10015 }
10016 #endif /* HAVE_IPV6 */
10017
10018 static int
10019 bgp_show_community (struct vty *vty, const char *view_name, int argc,
10020 struct cmd_token **argv, int exact, afi_t afi, safi_t safi)
10021 {
10022 struct community *com;
10023 struct buffer *b;
10024 struct bgp *bgp;
10025 int i;
10026 char *str;
10027 int first = 0;
10028
10029 /* BGP structure lookup */
10030 if (view_name)
10031 {
10032 bgp = bgp_lookup_by_name (view_name);
10033 if (bgp == NULL)
10034 {
10035 vty_out (vty, "Can't find BGP instance %s%s", view_name, VTY_NEWLINE);
10036 return CMD_WARNING;
10037 }
10038 }
10039 else
10040 {
10041 bgp = bgp_get_default ();
10042 if (bgp == NULL)
10043 {
10044 vty_out (vty, "No BGP process is configured%s", VTY_NEWLINE);
10045 return CMD_WARNING;
10046 }
10047 }
10048
10049 b = buffer_new (1024);
10050 for (i = 0; i < argc; i++)
10051 {
10052 if (first)
10053 buffer_putc (b, ' ');
10054 else
10055 {
10056 if ((strcmp (argv[i]->arg, "unicast") == 0) || (strcmp (argv[i]->arg, "multicast") == 0))
10057 continue;
10058 first = 1;
10059 }
10060
10061 buffer_putstr (b, argv[i]->arg);
10062 }
10063 buffer_putc (b, '\0');
10064
10065 str = buffer_getstr (b);
10066 buffer_free (b);
10067
10068 com = community_str2com (str);
10069 XFREE (MTYPE_TMP, str);
10070 if (! com)
10071 {
10072 vty_out (vty, "%% Community malformed: %s", VTY_NEWLINE);
10073 return CMD_WARNING;
10074 }
10075
10076 return bgp_show (vty, bgp, afi, safi,
10077 (exact ? bgp_show_type_community_exact :
10078 bgp_show_type_community), com, 0);
10079 }
10080
10081 /*
10082 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
10083 * "show ip bgp community (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export)",
10084 * SHOW_STR
10085 * IP_STR
10086 * BGP_STR
10087 * "Display routes matching the communities\n"
10088 * COMMUNITY_AANN_STR
10089 * "Do not send outside local AS (well-known community)\n"
10090 * "Do not advertise to any peer (well-known community)\n"
10091 * "Do not export to next AS (well-known community)\n"
10092 * COMMUNITY_AANN_STR
10093 * "Do not send outside local AS (well-known community)\n"
10094 * "Do not advertise to any peer (well-known community)\n"
10095 * "Do not export to next AS (well-known community)\n"
10096 * COMMUNITY_AANN_STR
10097 * "Do not send outside local AS (well-known community)\n"
10098 * "Do not advertise to any peer (well-known community)\n"
10099 * "Do not export to next AS (well-known community)\n"
10100 *
10101 * "show ip bgp community (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export)",
10102 * SHOW_STR
10103 * IP_STR
10104 * BGP_STR
10105 * "Display routes matching the communities\n"
10106 * COMMUNITY_AANN_STR
10107 * "Do not send outside local AS (well-known community)\n"
10108 * "Do not advertise to any peer (well-known community)\n"
10109 * "Do not export to next AS (well-known community)\n"
10110 * COMMUNITY_AANN_STR
10111 * "Do not send outside local AS (well-known community)\n"
10112 * "Do not advertise to any peer (well-known community)\n"
10113 * "Do not export to next AS (well-known community)\n"
10114 * COMMUNITY_AANN_STR
10115 * "Do not send outside local AS (well-known community)\n"
10116 * "Do not advertise to any peer (well-known community)\n"
10117 * "Do not export to next AS (well-known community)\n"
10118 * COMMUNITY_AANN_STR
10119 * "Do not send outside local AS (well-known community)\n"
10120 * "Do not advertise to any peer (well-known community)\n"
10121 * "Do not export to next AS (well-known community)\n"
10122 *
10123 * "show ip bgp community (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export)",
10124 * SHOW_STR
10125 * IP_STR
10126 * BGP_STR
10127 * "Display routes matching the communities\n"
10128 * COMMUNITY_AANN_STR
10129 * "Do not send outside local AS (well-known community)\n"
10130 * "Do not advertise to any peer (well-known community)\n"
10131 * "Do not export to next AS (well-known community)\n"
10132 * COMMUNITY_AANN_STR
10133 * "Do not send outside local AS (well-known community)\n"
10134 * "Do not advertise to any peer (well-known community)\n"
10135 * "Do not export to next AS (well-known community)\n"
10136 *
10137 */
10138 DEFUN (show_ip_bgp_community,
10139 show_ip_bgp_community_cmd,
10140 "show ip bgp community <AA:NN|local-AS|no-advertise|no-export>",
10141 SHOW_STR
10142 IP_STR
10143 BGP_STR
10144 "Display routes matching the communities\n"
10145 COMMUNITY_AANN_STR
10146 "Do not send outside local AS (well-known community)\n"
10147 "Do not advertise to any peer (well-known community)\n"
10148 "Do not export to next AS (well-known community)\n")
10149 {
10150 return bgp_show_community (vty, NULL, argc, argv, 0, AFI_IP, SAFI_UNICAST);
10151 }
10152
10153
10154
10155
10156 /*
10157 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
10158 * "show ip bgp ipv4 (unicast|multicast) community (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export)",
10159 * SHOW_STR
10160 * IP_STR
10161 * BGP_STR
10162 * "Address family\n"
10163 * "Address Family modifier\n"
10164 * "Address Family modifier\n"
10165 * "Display routes matching the communities\n"
10166 * COMMUNITY_AANN_STR
10167 * "Do not send outside local AS (well-known community)\n"
10168 * "Do not advertise to any peer (well-known community)\n"
10169 * "Do not export to next AS (well-known community)\n"
10170 * COMMUNITY_AANN_STR
10171 * "Do not send outside local AS (well-known community)\n"
10172 * "Do not advertise to any peer (well-known community)\n"
10173 * "Do not export to next AS (well-known community)\n"
10174 * COMMUNITY_AANN_STR
10175 * "Do not send outside local AS (well-known community)\n"
10176 * "Do not advertise to any peer (well-known community)\n"
10177 * "Do not export to next AS (well-known community)\n"
10178 *
10179 * "show ip bgp ipv4 (unicast|multicast) community (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export)",
10180 * SHOW_STR
10181 * IP_STR
10182 * BGP_STR
10183 * "Address family\n"
10184 * "Address Family modifier\n"
10185 * "Address Family modifier\n"
10186 * "Display routes matching the communities\n"
10187 * COMMUNITY_AANN_STR
10188 * "Do not send outside local AS (well-known community)\n"
10189 * "Do not advertise to any peer (well-known community)\n"
10190 * "Do not export to next AS (well-known community)\n"
10191 * COMMUNITY_AANN_STR
10192 * "Do not send outside local AS (well-known community)\n"
10193 * "Do not advertise to any peer (well-known community)\n"
10194 * "Do not export to next AS (well-known community)\n"
10195 *
10196 * "show ip bgp ipv4 (unicast|multicast) community (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export)",
10197 * SHOW_STR
10198 * IP_STR
10199 * BGP_STR
10200 * "Address family\n"
10201 * "Address Family modifier\n"
10202 * "Address Family modifier\n"
10203 * "Display routes matching the communities\n"
10204 * COMMUNITY_AANN_STR
10205 * "Do not send outside local AS (well-known community)\n"
10206 * "Do not advertise to any peer (well-known community)\n"
10207 * "Do not export to next AS (well-known community)\n"
10208 * COMMUNITY_AANN_STR
10209 * "Do not send outside local AS (well-known community)\n"
10210 * "Do not advertise to any peer (well-known community)\n"
10211 * "Do not export to next AS (well-known community)\n"
10212 * COMMUNITY_AANN_STR
10213 * "Do not send outside local AS (well-known community)\n"
10214 * "Do not advertise to any peer (well-known community)\n"
10215 * "Do not export to next AS (well-known community)\n"
10216 * COMMUNITY_AANN_STR
10217 * "Do not send outside local AS (well-known community)\n"
10218 * "Do not advertise to any peer (well-known community)\n"
10219 * "Do not export to next AS (well-known community)\n"
10220 *
10221 */
10222 DEFUN (show_ip_bgp_ipv4_community,
10223 show_ip_bgp_ipv4_community_cmd,
10224 "show ip bgp ipv4 <unicast|multicast> community <AA:NN|local-AS|no-advertise|no-export>",
10225 SHOW_STR
10226 IP_STR
10227 BGP_STR
10228 "Address family\n"
10229 "Address Family modifier\n"
10230 "Address Family modifier\n"
10231 "Display routes matching the communities\n"
10232 COMMUNITY_AANN_STR
10233 "Do not send outside local AS (well-known community)\n"
10234 "Do not advertise to any peer (well-known community)\n"
10235 "Do not export to next AS (well-known community)\n")
10236 {
10237 int idx_safi = 4;
10238 if (strncmp (argv[idx_safi]->arg, "m", 1) == 0)
10239 return bgp_show_community (vty, NULL, argc, argv, 0, AFI_IP, SAFI_MULTICAST);
10240
10241 return bgp_show_community (vty, NULL, argc, argv, 0, AFI_IP, SAFI_UNICAST);
10242 }
10243
10244
10245
10246
10247 DEFUN (show_bgp_instance_afi_safi_community_all,
10248 show_bgp_instance_afi_safi_community_all_cmd,
10249 "show bgp <view|vrf> WORD <ipv4|ipv6> <unicast|multicast> community",
10250 SHOW_STR
10251 BGP_STR
10252 BGP_INSTANCE_HELP_STR
10253 "Address family\n"
10254 "Address family\n"
10255 "Address Family modifier\n"
10256 "Address Family modifier\n"
10257 "Display routes matching the communities\n")
10258 {
10259 int idx_word = 3;
10260 int idx_afi = 4;
10261 int idx_safi = 5;
10262 int afi;
10263 int safi;
10264 struct bgp *bgp;
10265
10266 /* BGP structure lookup. */
10267 bgp = bgp_lookup_by_name (argv[idx_word]->arg);
10268 if (bgp == NULL)
10269 {
10270 vty_out (vty, "Can't find BGP instance %s%s", argv[idx_word]->arg, VTY_NEWLINE);
10271 return CMD_WARNING;
10272 }
10273
10274 afi = (strncmp (argv[idx_afi]->arg, "ipv6", 4) == 0) ? AFI_IP6 : AFI_IP;
10275 safi = (strncmp (argv[idx_safi]->arg, "m", 1) == 0) ? SAFI_MULTICAST : SAFI_UNICAST;
10276 return bgp_show (vty, bgp, afi, safi, bgp_show_type_community_all, NULL, 0);
10277 }
10278
10279 /*
10280 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
10281 * "show bgp <view|vrf> WORD (ipv4|ipv6) (unicast|multicast) community (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export)",
10282 * SHOW_STR
10283 * BGP_STR
10284 * BGP_INSTANCE_HELP_STR
10285 * "Address family\n"
10286 * "Address family\n"
10287 * "Address family modifier\n"
10288 * "Address family modifier\n"
10289 * "Display routes matching the communities\n"
10290 * COMMUNITY_AANN_STR
10291 * "Do not send outside local AS (well-known community)\n"
10292 * "Do not advertise to any peer (well-known community)\n"
10293 * "Do not export to next AS (well-known community)\n"
10294 * COMMUNITY_AANN_STR
10295 * "Do not send outside local AS (well-known community)\n"
10296 * "Do not advertise to any peer (well-known community)\n"
10297 * "Do not export to next AS (well-known community)\n"
10298 * COMMUNITY_AANN_STR
10299 * "Do not send outside local AS (well-known community)\n"
10300 * "Do not advertise to any peer (well-known community)\n"
10301 * "Do not export to next AS (well-known community)\n"
10302 *
10303 * "show bgp <view|vrf> WORD (ipv4|ipv6) (unicast|multicast) community (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export)",
10304 * SHOW_STR
10305 * BGP_STR
10306 * BGP_INSTANCE_HELP_STR
10307 * "Address family\n"
10308 * "Address family\n"
10309 * "Address family modifier\n"
10310 * "Address family modifier\n"
10311 * "Display routes matching the communities\n"
10312 * COMMUNITY_AANN_STR
10313 * "Do not send outside local AS (well-known community)\n"
10314 * "Do not advertise to any peer (well-known community)\n"
10315 * "Do not export to next AS (well-known community)\n"
10316 * COMMUNITY_AANN_STR
10317 * "Do not send outside local AS (well-known community)\n"
10318 * "Do not advertise to any peer (well-known community)\n"
10319 * "Do not export to next AS (well-known community)\n"
10320 * COMMUNITY_AANN_STR
10321 * "Do not send outside local AS (well-known community)\n"
10322 * "Do not advertise to any peer (well-known community)\n"
10323 * "Do not export to next AS (well-known community)\n"
10324 * COMMUNITY_AANN_STR
10325 * "Do not send outside local AS (well-known community)\n"
10326 * "Do not advertise to any peer (well-known community)\n"
10327 * "Do not export to next AS (well-known community)\n"
10328 *
10329 * "show bgp <view|vrf> WORD (ipv4|ipv6) (unicast|multicast) community (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export)",
10330 * SHOW_STR
10331 * BGP_STR
10332 * BGP_INSTANCE_HELP_STR
10333 * "Address family\n"
10334 * "Address family\n"
10335 * "Address family modifier\n"
10336 * "Address family modifier\n"
10337 * "Display routes matching the communities\n"
10338 * COMMUNITY_AANN_STR
10339 * "Do not send outside local AS (well-known community)\n"
10340 * "Do not advertise to any peer (well-known community)\n"
10341 * "Do not export to next AS (well-known community)\n"
10342 * COMMUNITY_AANN_STR
10343 * "Do not send outside local AS (well-known community)\n"
10344 * "Do not advertise to any peer (well-known community)\n"
10345 * "Do not export to next AS (well-known community)\n"
10346 *
10347 */
10348 DEFUN (show_bgp_instance_afi_safi_community,
10349 show_bgp_instance_afi_safi_community_cmd,
10350 "show bgp <view|vrf> WORD <ipv4|ipv6> <unicast|multicast> community <AA:NN|local-AS|no-advertise|no-export>",
10351 SHOW_STR
10352 BGP_STR
10353 BGP_INSTANCE_HELP_STR
10354 "Address family\n"
10355 "Address family\n"
10356 "Address family modifier\n"
10357 "Address family modifier\n"
10358 "Display routes matching the communities\n"
10359 COMMUNITY_AANN_STR
10360 "Do not send outside local AS (well-known community)\n"
10361 "Do not advertise to any peer (well-known community)\n"
10362 "Do not export to next AS (well-known community)\n")
10363 {
10364 int idx_word = 3;
10365 int idx_afi = 4;
10366 int idx_safi = 5;
10367 int afi;
10368 int safi;
10369
10370 afi = (strncmp (argv[idx_afi]->arg, "ipv6", 4) == 0) ? AFI_IP6 : AFI_IP;
10371 safi = (strncmp (argv[idx_safi]->arg, "m", 1) == 0) ? SAFI_MULTICAST : SAFI_UNICAST;
10372 return bgp_show_community (vty, argv[idx_word]->arg, argc, argv, 0, afi, safi);
10373 }
10374
10375
10376
10377
10378 /*
10379 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
10380 * "show ip bgp community (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) exact-match",
10381 * SHOW_STR
10382 * IP_STR
10383 * BGP_STR
10384 * "Display routes matching the communities\n"
10385 * COMMUNITY_AANN_STR
10386 * "Do not send outside local AS (well-known community)\n"
10387 * "Do not advertise to any peer (well-known community)\n"
10388 * "Do not export to next AS (well-known community)\n"
10389 * COMMUNITY_AANN_STR
10390 * "Do not send outside local AS (well-known community)\n"
10391 * "Do not advertise to any peer (well-known community)\n"
10392 * "Do not export to next AS (well-known community)\n"
10393 * COMMUNITY_AANN_STR
10394 * "Do not send outside local AS (well-known community)\n"
10395 * "Do not advertise to any peer (well-known community)\n"
10396 * "Do not export to next AS (well-known community)\n"
10397 * "Exact match of the communities"
10398 *
10399 * "show ip bgp community (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) exact-match",
10400 * SHOW_STR
10401 * IP_STR
10402 * BGP_STR
10403 * "Display routes matching the communities\n"
10404 * COMMUNITY_AANN_STR
10405 * "Do not send outside local AS (well-known community)\n"
10406 * "Do not advertise to any peer (well-known community)\n"
10407 * "Do not export to next AS (well-known community)\n"
10408 * COMMUNITY_AANN_STR
10409 * "Do not send outside local AS (well-known community)\n"
10410 * "Do not advertise to any peer (well-known community)\n"
10411 * "Do not export to next AS (well-known community)\n"
10412 * COMMUNITY_AANN_STR
10413 * "Do not send outside local AS (well-known community)\n"
10414 * "Do not advertise to any peer (well-known community)\n"
10415 * "Do not export to next AS (well-known community)\n"
10416 * COMMUNITY_AANN_STR
10417 * "Do not send outside local AS (well-known community)\n"
10418 * "Do not advertise to any peer (well-known community)\n"
10419 * "Do not export to next AS (well-known community)\n"
10420 * "Exact match of the communities"
10421 *
10422 * "show ip bgp community (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) exact-match",
10423 * SHOW_STR
10424 * IP_STR
10425 * BGP_STR
10426 * "Display routes matching the communities\n"
10427 * COMMUNITY_AANN_STR
10428 * "Do not send outside local AS (well-known community)\n"
10429 * "Do not advertise to any peer (well-known community)\n"
10430 * "Do not export to next AS (well-known community)\n"
10431 * COMMUNITY_AANN_STR
10432 * "Do not send outside local AS (well-known community)\n"
10433 * "Do not advertise to any peer (well-known community)\n"
10434 * "Do not export to next AS (well-known community)\n"
10435 * "Exact match of the communities"
10436 *
10437 */
10438 DEFUN (show_ip_bgp_community_exact,
10439 show_ip_bgp_community_exact_cmd,
10440 "show ip bgp community <AA:NN|local-AS|no-advertise|no-export> exact-match",
10441 SHOW_STR
10442 IP_STR
10443 BGP_STR
10444 "Display routes matching the communities\n"
10445 COMMUNITY_AANN_STR
10446 "Do not send outside local AS (well-known community)\n"
10447 "Do not advertise to any peer (well-known community)\n"
10448 "Do not export to next AS (well-known community)\n"
10449 "Exact match of the communities")
10450 {
10451 return bgp_show_community (vty, NULL, argc, argv, 1, AFI_IP, SAFI_UNICAST);
10452 }
10453
10454
10455
10456
10457 /*
10458 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
10459 * "show ip bgp ipv4 (unicast|multicast) community (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) exact-match",
10460 * SHOW_STR
10461 * IP_STR
10462 * BGP_STR
10463 * "Address family\n"
10464 * "Address Family modifier\n"
10465 * "Address Family modifier\n"
10466 * "Display routes matching the communities\n"
10467 * COMMUNITY_AANN_STR
10468 * "Do not send outside local AS (well-known community)\n"
10469 * "Do not advertise to any peer (well-known community)\n"
10470 * "Do not export to next AS (well-known community)\n"
10471 * COMMUNITY_AANN_STR
10472 * "Do not send outside local AS (well-known community)\n"
10473 * "Do not advertise to any peer (well-known community)\n"
10474 * "Do not export to next AS (well-known community)\n"
10475 * COMMUNITY_AANN_STR
10476 * "Do not send outside local AS (well-known community)\n"
10477 * "Do not advertise to any peer (well-known community)\n"
10478 * "Do not export to next AS (well-known community)\n"
10479 * "Exact match of the communities"
10480 *
10481 * "show ip bgp ipv4 (unicast|multicast) community (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) exact-match",
10482 * SHOW_STR
10483 * IP_STR
10484 * BGP_STR
10485 * "Address family\n"
10486 * "Address Family modifier\n"
10487 * "Address Family modifier\n"
10488 * "Display routes matching the communities\n"
10489 * COMMUNITY_AANN_STR
10490 * "Do not send outside local AS (well-known community)\n"
10491 * "Do not advertise to any peer (well-known community)\n"
10492 * "Do not export to next AS (well-known community)\n"
10493 * COMMUNITY_AANN_STR
10494 * "Do not send outside local AS (well-known community)\n"
10495 * "Do not advertise to any peer (well-known community)\n"
10496 * "Do not export to next AS (well-known community)\n"
10497 * "Exact match of the communities"
10498 *
10499 * "show ip bgp ipv4 (unicast|multicast) community (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) exact-match",
10500 * SHOW_STR
10501 * IP_STR
10502 * BGP_STR
10503 * "Address family\n"
10504 * "Address Family modifier\n"
10505 * "Address Family modifier\n"
10506 * "Display routes matching the communities\n"
10507 * COMMUNITY_AANN_STR
10508 * "Do not send outside local AS (well-known community)\n"
10509 * "Do not advertise to any peer (well-known community)\n"
10510 * "Do not export to next AS (well-known community)\n"
10511 * COMMUNITY_AANN_STR
10512 * "Do not send outside local AS (well-known community)\n"
10513 * "Do not advertise to any peer (well-known community)\n"
10514 * "Do not export to next AS (well-known community)\n"
10515 * COMMUNITY_AANN_STR
10516 * "Do not send outside local AS (well-known community)\n"
10517 * "Do not advertise to any peer (well-known community)\n"
10518 * "Do not export to next AS (well-known community)\n"
10519 * COMMUNITY_AANN_STR
10520 * "Do not send outside local AS (well-known community)\n"
10521 * "Do not advertise to any peer (well-known community)\n"
10522 * "Do not export to next AS (well-known community)\n"
10523 * "Exact match of the communities"
10524 *
10525 */
10526 DEFUN (show_ip_bgp_ipv4_community_exact,
10527 show_ip_bgp_ipv4_community_exact_cmd,
10528 "show ip bgp ipv4 <unicast|multicast> community <AA:NN|local-AS|no-advertise|no-export> exact-match",
10529 SHOW_STR
10530 IP_STR
10531 BGP_STR
10532 "Address family\n"
10533 "Address Family modifier\n"
10534 "Address Family modifier\n"
10535 "Display routes matching the communities\n"
10536 COMMUNITY_AANN_STR
10537 "Do not send outside local AS (well-known community)\n"
10538 "Do not advertise to any peer (well-known community)\n"
10539 "Do not export to next AS (well-known community)\n"
10540 "Exact match of the communities")
10541 {
10542 int idx_safi = 4;
10543 if (strncmp (argv[idx_safi]->arg, "m", 1) == 0)
10544 return bgp_show_community (vty, NULL, argc, argv, 1, AFI_IP, SAFI_MULTICAST);
10545
10546 return bgp_show_community (vty, NULL, argc, argv, 1, AFI_IP, SAFI_UNICAST);
10547 }
10548
10549
10550
10551
10552 #ifdef HAVE_IPV6
10553 /*
10554 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
10555 * "show bgp ipv6 community (AA:NN|local-AS|no-advertise|no-export)",
10556 * SHOW_STR
10557 * BGP_STR
10558 * "Address family\n"
10559 * "Display routes matching the communities\n"
10560 * COMMUNITY_AANN_STR
10561 * "Do not send outside local AS (well-known community)\n"
10562 * "Do not advertise to any peer (well-known community)\n"
10563 * "Do not export to next AS (well-known community)\n"
10564 *
10565 * "show bgp ipv6 community (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export)",
10566 * SHOW_STR
10567 * BGP_STR
10568 * "Address family\n"
10569 * "Display routes matching the communities\n"
10570 * COMMUNITY_AANN_STR
10571 * "Do not send outside local AS (well-known community)\n"
10572 * "Do not advertise to any peer (well-known community)\n"
10573 * "Do not export to next AS (well-known community)\n"
10574 * COMMUNITY_AANN_STR
10575 * "Do not send outside local AS (well-known community)\n"
10576 * "Do not advertise to any peer (well-known community)\n"
10577 * "Do not export to next AS (well-known community)\n"
10578 * COMMUNITY_AANN_STR
10579 * "Do not send outside local AS (well-known community)\n"
10580 * "Do not advertise to any peer (well-known community)\n"
10581 * "Do not export to next AS (well-known community)\n"
10582 * COMMUNITY_AANN_STR
10583 * "Do not send outside local AS (well-known community)\n"
10584 * "Do not advertise to any peer (well-known community)\n"
10585 * "Do not export to next AS (well-known community)\n"
10586 *
10587 * "show bgp ipv6 community (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export)",
10588 * SHOW_STR
10589 * BGP_STR
10590 * "Address family\n"
10591 * "Display routes matching the communities\n"
10592 * COMMUNITY_AANN_STR
10593 * "Do not send outside local AS (well-known community)\n"
10594 * "Do not advertise to any peer (well-known community)\n"
10595 * "Do not export to next AS (well-known community)\n"
10596 * COMMUNITY_AANN_STR
10597 * "Do not send outside local AS (well-known community)\n"
10598 * "Do not advertise to any peer (well-known community)\n"
10599 * "Do not export to next AS (well-known community)\n"
10600 *
10601 * "show bgp community (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export)",
10602 * SHOW_STR
10603 * BGP_STR
10604 * "Display routes matching the communities\n"
10605 * COMMUNITY_AANN_STR
10606 * "Do not send outside local AS (well-known community)\n"
10607 * "Do not advertise to any peer (well-known community)\n"
10608 * "Do not export to next AS (well-known community)\n"
10609 * COMMUNITY_AANN_STR
10610 * "Do not send outside local AS (well-known community)\n"
10611 * "Do not advertise to any peer (well-known community)\n"
10612 * "Do not export to next AS (well-known community)\n"
10613 * COMMUNITY_AANN_STR
10614 * "Do not send outside local AS (well-known community)\n"
10615 * "Do not advertise to any peer (well-known community)\n"
10616 * "Do not export to next AS (well-known community)\n"
10617 *
10618 * "show bgp community (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export)",
10619 * SHOW_STR
10620 * BGP_STR
10621 * "Display routes matching the communities\n"
10622 * COMMUNITY_AANN_STR
10623 * "Do not send outside local AS (well-known community)\n"
10624 * "Do not advertise to any peer (well-known community)\n"
10625 * "Do not export to next AS (well-known community)\n"
10626 * COMMUNITY_AANN_STR
10627 * "Do not send outside local AS (well-known community)\n"
10628 * "Do not advertise to any peer (well-known community)\n"
10629 * "Do not export to next AS (well-known community)\n"
10630 *
10631 * "show bgp ipv6 community (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export)",
10632 * SHOW_STR
10633 * BGP_STR
10634 * "Address family\n"
10635 * "Display routes matching the communities\n"
10636 * COMMUNITY_AANN_STR
10637 * "Do not send outside local AS (well-known community)\n"
10638 * "Do not advertise to any peer (well-known community)\n"
10639 * "Do not export to next AS (well-known community)\n"
10640 * COMMUNITY_AANN_STR
10641 * "Do not send outside local AS (well-known community)\n"
10642 * "Do not advertise to any peer (well-known community)\n"
10643 * "Do not export to next AS (well-known community)\n"
10644 * COMMUNITY_AANN_STR
10645 * "Do not send outside local AS (well-known community)\n"
10646 * "Do not advertise to any peer (well-known community)\n"
10647 * "Do not export to next AS (well-known community)\n"
10648 *
10649 * "show bgp community (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export)",
10650 * SHOW_STR
10651 * BGP_STR
10652 * "Display routes matching the communities\n"
10653 * COMMUNITY_AANN_STR
10654 * "Do not send outside local AS (well-known community)\n"
10655 * "Do not advertise to any peer (well-known community)\n"
10656 * "Do not export to next AS (well-known community)\n"
10657 * COMMUNITY_AANN_STR
10658 * "Do not send outside local AS (well-known community)\n"
10659 * "Do not advertise to any peer (well-known community)\n"
10660 * "Do not export to next AS (well-known community)\n"
10661 * COMMUNITY_AANN_STR
10662 * "Do not send outside local AS (well-known community)\n"
10663 * "Do not advertise to any peer (well-known community)\n"
10664 * "Do not export to next AS (well-known community)\n"
10665 * COMMUNITY_AANN_STR
10666 * "Do not send outside local AS (well-known community)\n"
10667 * "Do not advertise to any peer (well-known community)\n"
10668 * "Do not export to next AS (well-known community)\n"
10669 *
10670 */
10671 DEFUN (show_bgp_community,
10672 show_bgp_community_cmd,
10673 "show bgp community <AA:NN|local-AS|no-advertise|no-export>",
10674 SHOW_STR
10675 BGP_STR
10676 "Display routes matching the communities\n"
10677 COMMUNITY_AANN_STR
10678 "Do not send outside local AS (well-known community)\n"
10679 "Do not advertise to any peer (well-known community)\n"
10680 "Do not export to next AS (well-known community)\n")
10681 {
10682 return bgp_show_community (vty, NULL, argc, argv, 0, AFI_IP6, SAFI_UNICAST);
10683 }
10684
10685
10686
10687
10688
10689
10690
10691
10692 /* old command */
10693 /*
10694 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
10695 * "show ipv6 bgp community (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export)",
10696 * SHOW_STR
10697 * IPV6_STR
10698 * BGP_STR
10699 * "Display routes matching the communities\n"
10700 * COMMUNITY_AANN_STR
10701 * "Do not send outside local AS (well-known community)\n"
10702 * "Do not advertise to any peer (well-known community)\n"
10703 * "Do not export to next AS (well-known community)\n"
10704 * COMMUNITY_AANN_STR
10705 * "Do not send outside local AS (well-known community)\n"
10706 * "Do not advertise to any peer (well-known community)\n"
10707 * "Do not export to next AS (well-known community)\n"
10708 * COMMUNITY_AANN_STR
10709 * "Do not send outside local AS (well-known community)\n"
10710 * "Do not advertise to any peer (well-known community)\n"
10711 * "Do not export to next AS (well-known community)\n"
10712 *
10713 * "show ipv6 bgp community (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export)",
10714 * SHOW_STR
10715 * IPV6_STR
10716 * BGP_STR
10717 * "Display routes matching the communities\n"
10718 * COMMUNITY_AANN_STR
10719 * "Do not send outside local AS (well-known community)\n"
10720 * "Do not advertise to any peer (well-known community)\n"
10721 * "Do not export to next AS (well-known community)\n"
10722 * COMMUNITY_AANN_STR
10723 * "Do not send outside local AS (well-known community)\n"
10724 * "Do not advertise to any peer (well-known community)\n"
10725 * "Do not export to next AS (well-known community)\n"
10726 * COMMUNITY_AANN_STR
10727 * "Do not send outside local AS (well-known community)\n"
10728 * "Do not advertise to any peer (well-known community)\n"
10729 * "Do not export to next AS (well-known community)\n"
10730 * COMMUNITY_AANN_STR
10731 * "Do not send outside local AS (well-known community)\n"
10732 * "Do not advertise to any peer (well-known community)\n"
10733 * "Do not export to next AS (well-known community)\n"
10734 *
10735 * "show ipv6 bgp community (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export)",
10736 * SHOW_STR
10737 * IPV6_STR
10738 * BGP_STR
10739 * "Display routes matching the communities\n"
10740 * COMMUNITY_AANN_STR
10741 * "Do not send outside local AS (well-known community)\n"
10742 * "Do not advertise to any peer (well-known community)\n"
10743 * "Do not export to next AS (well-known community)\n"
10744 * COMMUNITY_AANN_STR
10745 * "Do not send outside local AS (well-known community)\n"
10746 * "Do not advertise to any peer (well-known community)\n"
10747 * "Do not export to next AS (well-known community)\n"
10748 *
10749 */
10750 DEFUN (show_ipv6_bgp_community,
10751 show_ipv6_bgp_community_cmd,
10752 "show ipv6 bgp community <AA:NN|local-AS|no-advertise|no-export>",
10753 SHOW_STR
10754 IPV6_STR
10755 BGP_STR
10756 "Display routes matching the communities\n"
10757 COMMUNITY_AANN_STR
10758 "Do not send outside local AS (well-known community)\n"
10759 "Do not advertise to any peer (well-known community)\n"
10760 "Do not export to next AS (well-known community)\n")
10761 {
10762 bgp_show_ipv6_bgp_deprecate_warning(vty);
10763 return bgp_show_community (vty, NULL, argc, argv, 0, AFI_IP6, SAFI_UNICAST);
10764 }
10765
10766 /* old command */
10767
10768 /* old command */
10769
10770 /* old command */
10771
10772 /*
10773 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
10774 * "show bgp community (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) exact-match",
10775 * SHOW_STR
10776 * BGP_STR
10777 * "Display routes matching the communities\n"
10778 * COMMUNITY_AANN_STR
10779 * "Do not send outside local AS (well-known community)\n"
10780 * "Do not advertise to any peer (well-known community)\n"
10781 * "Do not export to next AS (well-known community)\n"
10782 * COMMUNITY_AANN_STR
10783 * "Do not send outside local AS (well-known community)\n"
10784 * "Do not advertise to any peer (well-known community)\n"
10785 * "Do not export to next AS (well-known community)\n"
10786 * "Exact match of the communities"
10787 *
10788 * "show bgp ipv6 community (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) exact-match",
10789 * SHOW_STR
10790 * BGP_STR
10791 * "Address family\n"
10792 * "Display routes matching the communities\n"
10793 * COMMUNITY_AANN_STR
10794 * "Do not send outside local AS (well-known community)\n"
10795 * "Do not advertise to any peer (well-known community)\n"
10796 * "Do not export to next AS (well-known community)\n"
10797 * COMMUNITY_AANN_STR
10798 * "Do not send outside local AS (well-known community)\n"
10799 * "Do not advertise to any peer (well-known community)\n"
10800 * "Do not export to next AS (well-known community)\n"
10801 * COMMUNITY_AANN_STR
10802 * "Do not send outside local AS (well-known community)\n"
10803 * "Do not advertise to any peer (well-known community)\n"
10804 * "Do not export to next AS (well-known community)\n"
10805 * COMMUNITY_AANN_STR
10806 * "Do not send outside local AS (well-known community)\n"
10807 * "Do not advertise to any peer (well-known community)\n"
10808 * "Do not export to next AS (well-known community)\n"
10809 * "Exact match of the communities"
10810 *
10811 * "show bgp ipv6 community (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) exact-match",
10812 * SHOW_STR
10813 * BGP_STR
10814 * "Address family\n"
10815 * "Display routes matching the communities\n"
10816 * COMMUNITY_AANN_STR
10817 * "Do not send outside local AS (well-known community)\n"
10818 * "Do not advertise to any peer (well-known community)\n"
10819 * "Do not export to next AS (well-known community)\n"
10820 * COMMUNITY_AANN_STR
10821 * "Do not send outside local AS (well-known community)\n"
10822 * "Do not advertise to any peer (well-known community)\n"
10823 * "Do not export to next AS (well-known community)\n"
10824 * COMMUNITY_AANN_STR
10825 * "Do not send outside local AS (well-known community)\n"
10826 * "Do not advertise to any peer (well-known community)\n"
10827 * "Do not export to next AS (well-known community)\n"
10828 * "Exact match of the communities"
10829 *
10830 * "show bgp community (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) exact-match",
10831 * SHOW_STR
10832 * BGP_STR
10833 * "Display routes matching the communities\n"
10834 * COMMUNITY_AANN_STR
10835 * "Do not send outside local AS (well-known community)\n"
10836 * "Do not advertise to any peer (well-known community)\n"
10837 * "Do not export to next AS (well-known community)\n"
10838 * COMMUNITY_AANN_STR
10839 * "Do not send outside local AS (well-known community)\n"
10840 * "Do not advertise to any peer (well-known community)\n"
10841 * "Do not export to next AS (well-known community)\n"
10842 * COMMUNITY_AANN_STR
10843 * "Do not send outside local AS (well-known community)\n"
10844 * "Do not advertise to any peer (well-known community)\n"
10845 * "Do not export to next AS (well-known community)\n"
10846 * "Exact match of the communities"
10847 *
10848 * "show bgp community (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) exact-match",
10849 * SHOW_STR
10850 * BGP_STR
10851 * "Display routes matching the communities\n"
10852 * COMMUNITY_AANN_STR
10853 * "Do not send outside local AS (well-known community)\n"
10854 * "Do not advertise to any peer (well-known community)\n"
10855 * "Do not export to next AS (well-known community)\n"
10856 * COMMUNITY_AANN_STR
10857 * "Do not send outside local AS (well-known community)\n"
10858 * "Do not advertise to any peer (well-known community)\n"
10859 * "Do not export to next AS (well-known community)\n"
10860 * COMMUNITY_AANN_STR
10861 * "Do not send outside local AS (well-known community)\n"
10862 * "Do not advertise to any peer (well-known community)\n"
10863 * "Do not export to next AS (well-known community)\n"
10864 * COMMUNITY_AANN_STR
10865 * "Do not send outside local AS (well-known community)\n"
10866 * "Do not advertise to any peer (well-known community)\n"
10867 * "Do not export to next AS (well-known community)\n"
10868 * "Exact match of the communities"
10869 *
10870 * "show bgp ipv6 community (AA:NN|local-AS|no-advertise|no-export) exact-match",
10871 * SHOW_STR
10872 * BGP_STR
10873 * "Address family\n"
10874 * "Display routes matching the communities\n"
10875 * COMMUNITY_AANN_STR
10876 * "Do not send outside local AS (well-known community)\n"
10877 * "Do not advertise to any peer (well-known community)\n"
10878 * "Do not export to next AS (well-known community)\n"
10879 * "Exact match of the communities"
10880 *
10881 * "show bgp ipv6 community (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) exact-match",
10882 * SHOW_STR
10883 * BGP_STR
10884 * "Address family\n"
10885 * "Display routes matching the communities\n"
10886 * COMMUNITY_AANN_STR
10887 * "Do not send outside local AS (well-known community)\n"
10888 * "Do not advertise to any peer (well-known community)\n"
10889 * "Do not export to next AS (well-known community)\n"
10890 * COMMUNITY_AANN_STR
10891 * "Do not send outside local AS (well-known community)\n"
10892 * "Do not advertise to any peer (well-known community)\n"
10893 * "Do not export to next AS (well-known community)\n"
10894 * "Exact match of the communities"
10895 *
10896 */
10897 DEFUN (show_bgp_community_exact,
10898 show_bgp_community_exact_cmd,
10899 "show bgp community <AA:NN|local-AS|no-advertise|no-export> exact-match",
10900 SHOW_STR
10901 BGP_STR
10902 "Display routes matching the communities\n"
10903 COMMUNITY_AANN_STR
10904 "Do not send outside local AS (well-known community)\n"
10905 "Do not advertise to any peer (well-known community)\n"
10906 "Do not export to next AS (well-known community)\n"
10907 "Exact match of the communities")
10908 {
10909 return bgp_show_community (vty, NULL, argc, argv, 1, AFI_IP6, SAFI_UNICAST);
10910 }
10911
10912
10913
10914
10915
10916
10917
10918
10919 /* old command */
10920 /*
10921 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
10922 * "show ipv6 bgp community (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) exact-match",
10923 * SHOW_STR
10924 * IPV6_STR
10925 * BGP_STR
10926 * "Display routes matching the communities\n"
10927 * COMMUNITY_AANN_STR
10928 * "Do not send outside local AS (well-known community)\n"
10929 * "Do not advertise to any peer (well-known community)\n"
10930 * "Do not export to next AS (well-known community)\n"
10931 * COMMUNITY_AANN_STR
10932 * "Do not send outside local AS (well-known community)\n"
10933 * "Do not advertise to any peer (well-known community)\n"
10934 * "Do not export to next AS (well-known community)\n"
10935 * COMMUNITY_AANN_STR
10936 * "Do not send outside local AS (well-known community)\n"
10937 * "Do not advertise to any peer (well-known community)\n"
10938 * "Do not export to next AS (well-known community)\n"
10939 * COMMUNITY_AANN_STR
10940 * "Do not send outside local AS (well-known community)\n"
10941 * "Do not advertise to any peer (well-known community)\n"
10942 * "Do not export to next AS (well-known community)\n"
10943 * "Exact match of the communities"
10944 *
10945 * "show ipv6 bgp community (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) exact-match",
10946 * SHOW_STR
10947 * IPV6_STR
10948 * BGP_STR
10949 * "Display routes matching the communities\n"
10950 * COMMUNITY_AANN_STR
10951 * "Do not send outside local AS (well-known community)\n"
10952 * "Do not advertise to any peer (well-known community)\n"
10953 * "Do not export to next AS (well-known community)\n"
10954 * COMMUNITY_AANN_STR
10955 * "Do not send outside local AS (well-known community)\n"
10956 * "Do not advertise to any peer (well-known community)\n"
10957 * "Do not export to next AS (well-known community)\n"
10958 * "Exact match of the communities"
10959 *
10960 * "show ipv6 bgp community (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) exact-match",
10961 * SHOW_STR
10962 * IPV6_STR
10963 * BGP_STR
10964 * "Display routes matching the communities\n"
10965 * COMMUNITY_AANN_STR
10966 * "Do not send outside local AS (well-known community)\n"
10967 * "Do not advertise to any peer (well-known community)\n"
10968 * "Do not export to next AS (well-known community)\n"
10969 * COMMUNITY_AANN_STR
10970 * "Do not send outside local AS (well-known community)\n"
10971 * "Do not advertise to any peer (well-known community)\n"
10972 * "Do not export to next AS (well-known community)\n"
10973 * COMMUNITY_AANN_STR
10974 * "Do not send outside local AS (well-known community)\n"
10975 * "Do not advertise to any peer (well-known community)\n"
10976 * "Do not export to next AS (well-known community)\n"
10977 * "Exact match of the communities"
10978 *
10979 */
10980 DEFUN (show_ipv6_bgp_community_exact,
10981 show_ipv6_bgp_community_exact_cmd,
10982 "show ipv6 bgp community <AA:NN|local-AS|no-advertise|no-export> exact-match",
10983 SHOW_STR
10984 IPV6_STR
10985 BGP_STR
10986 "Display routes matching the communities\n"
10987 COMMUNITY_AANN_STR
10988 "Do not send outside local AS (well-known community)\n"
10989 "Do not advertise to any peer (well-known community)\n"
10990 "Do not export to next AS (well-known community)\n"
10991 "Exact match of the communities")
10992 {
10993 bgp_show_ipv6_bgp_deprecate_warning(vty);
10994 return bgp_show_community (vty, NULL, argc, argv, 1, AFI_IP6, SAFI_UNICAST);
10995 }
10996
10997 /* old command */
10998
10999 /* old command */
11000
11001 /* old command */
11002
11003 /* old command */
11004 /*
11005 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
11006 * "show ipv6 mbgp community (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export)",
11007 * SHOW_STR
11008 * IPV6_STR
11009 * MBGP_STR
11010 * "Display routes matching the communities\n"
11011 * COMMUNITY_AANN_STR
11012 * "Do not send outside local AS (well-known community)\n"
11013 * "Do not advertise to any peer (well-known community)\n"
11014 * "Do not export to next AS (well-known community)\n"
11015 * COMMUNITY_AANN_STR
11016 * "Do not send outside local AS (well-known community)\n"
11017 * "Do not advertise to any peer (well-known community)\n"
11018 * "Do not export to next AS (well-known community)\n"
11019 *
11020 * "show ipv6 mbgp community (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export)",
11021 * SHOW_STR
11022 * IPV6_STR
11023 * MBGP_STR
11024 * "Display routes matching the communities\n"
11025 * COMMUNITY_AANN_STR
11026 * "Do not send outside local AS (well-known community)\n"
11027 * "Do not advertise to any peer (well-known community)\n"
11028 * "Do not export to next AS (well-known community)\n"
11029 * COMMUNITY_AANN_STR
11030 * "Do not send outside local AS (well-known community)\n"
11031 * "Do not advertise to any peer (well-known community)\n"
11032 * "Do not export to next AS (well-known community)\n"
11033 * COMMUNITY_AANN_STR
11034 * "Do not send outside local AS (well-known community)\n"
11035 * "Do not advertise to any peer (well-known community)\n"
11036 * "Do not export to next AS (well-known community)\n"
11037 *
11038 * "show ipv6 mbgp community (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export)",
11039 * SHOW_STR
11040 * IPV6_STR
11041 * MBGP_STR
11042 * "Display routes matching the communities\n"
11043 * COMMUNITY_AANN_STR
11044 * "Do not send outside local AS (well-known community)\n"
11045 * "Do not advertise to any peer (well-known community)\n"
11046 * "Do not export to next AS (well-known community)\n"
11047 * COMMUNITY_AANN_STR
11048 * "Do not send outside local AS (well-known community)\n"
11049 * "Do not advertise to any peer (well-known community)\n"
11050 * "Do not export to next AS (well-known community)\n"
11051 * COMMUNITY_AANN_STR
11052 * "Do not send outside local AS (well-known community)\n"
11053 * "Do not advertise to any peer (well-known community)\n"
11054 * "Do not export to next AS (well-known community)\n"
11055 * COMMUNITY_AANN_STR
11056 * "Do not send outside local AS (well-known community)\n"
11057 * "Do not advertise to any peer (well-known community)\n"
11058 * "Do not export to next AS (well-known community)\n"
11059 *
11060 */
11061 DEFUN (show_ipv6_mbgp_community,
11062 show_ipv6_mbgp_community_cmd,
11063 "show ipv6 mbgp community <AA:NN|local-AS|no-advertise|no-export>",
11064 SHOW_STR
11065 IPV6_STR
11066 MBGP_STR
11067 "Display routes matching the communities\n"
11068 COMMUNITY_AANN_STR
11069 "Do not send outside local AS (well-known community)\n"
11070 "Do not advertise to any peer (well-known community)\n"
11071 "Do not export to next AS (well-known community)\n")
11072 {
11073 bgp_show_ipv6_bgp_deprecate_warning(vty);
11074 return bgp_show_community (vty, NULL, argc, argv, 0, AFI_IP6, SAFI_MULTICAST);
11075 }
11076
11077 /* old command */
11078
11079 /* old command */
11080
11081 /* old command */
11082
11083 /* old command */
11084 /*
11085 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
11086 * "show ipv6 mbgp community (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) exact-match",
11087 * SHOW_STR
11088 * IPV6_STR
11089 * MBGP_STR
11090 * "Display routes matching the communities\n"
11091 * COMMUNITY_AANN_STR
11092 * "Do not send outside local AS (well-known community)\n"
11093 * "Do not advertise to any peer (well-known community)\n"
11094 * "Do not export to next AS (well-known community)\n"
11095 * COMMUNITY_AANN_STR
11096 * "Do not send outside local AS (well-known community)\n"
11097 * "Do not advertise to any peer (well-known community)\n"
11098 * "Do not export to next AS (well-known community)\n"
11099 * COMMUNITY_AANN_STR
11100 * "Do not send outside local AS (well-known community)\n"
11101 * "Do not advertise to any peer (well-known community)\n"
11102 * "Do not export to next AS (well-known community)\n"
11103 * "Exact match of the communities"
11104 *
11105 * "show ipv6 mbgp community (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) exact-match",
11106 * SHOW_STR
11107 * IPV6_STR
11108 * MBGP_STR
11109 * "Display routes matching the communities\n"
11110 * COMMUNITY_AANN_STR
11111 * "Do not send outside local AS (well-known community)\n"
11112 * "Do not advertise to any peer (well-known community)\n"
11113 * "Do not export to next AS (well-known community)\n"
11114 * COMMUNITY_AANN_STR
11115 * "Do not send outside local AS (well-known community)\n"
11116 * "Do not advertise to any peer (well-known community)\n"
11117 * "Do not export to next AS (well-known community)\n"
11118 * COMMUNITY_AANN_STR
11119 * "Do not send outside local AS (well-known community)\n"
11120 * "Do not advertise to any peer (well-known community)\n"
11121 * "Do not export to next AS (well-known community)\n"
11122 * COMMUNITY_AANN_STR
11123 * "Do not send outside local AS (well-known community)\n"
11124 * "Do not advertise to any peer (well-known community)\n"
11125 * "Do not export to next AS (well-known community)\n"
11126 * "Exact match of the communities"
11127 *
11128 * "show ipv6 mbgp community (AA:NN|local-AS|no-advertise|no-export) (AA:NN|local-AS|no-advertise|no-export) exact-match",
11129 * SHOW_STR
11130 * IPV6_STR
11131 * MBGP_STR
11132 * "Display routes matching the communities\n"
11133 * COMMUNITY_AANN_STR
11134 * "Do not send outside local AS (well-known community)\n"
11135 * "Do not advertise to any peer (well-known community)\n"
11136 * "Do not export to next AS (well-known community)\n"
11137 * COMMUNITY_AANN_STR
11138 * "Do not send outside local AS (well-known community)\n"
11139 * "Do not advertise to any peer (well-known community)\n"
11140 * "Do not export to next AS (well-known community)\n"
11141 * "Exact match of the communities"
11142 *
11143 */
11144 DEFUN (show_ipv6_mbgp_community_exact,
11145 show_ipv6_mbgp_community_exact_cmd,
11146 "show ipv6 mbgp community <AA:NN|local-AS|no-advertise|no-export> exact-match",
11147 SHOW_STR
11148 IPV6_STR
11149 MBGP_STR
11150 "Display routes matching the communities\n"
11151 COMMUNITY_AANN_STR
11152 "Do not send outside local AS (well-known community)\n"
11153 "Do not advertise to any peer (well-known community)\n"
11154 "Do not export to next AS (well-known community)\n"
11155 "Exact match of the communities")
11156 {
11157 bgp_show_ipv6_bgp_deprecate_warning(vty);
11158 return bgp_show_community (vty, NULL, argc, argv, 1, AFI_IP6, SAFI_MULTICAST);
11159 }
11160
11161 /* old command */
11162
11163 /* old command */
11164
11165 /* old command */
11166 #endif /* HAVE_IPV6 */
11167
11168 static int
11169 bgp_show_community_list (struct vty *vty, const char *name,
11170 const char *com, int exact,
11171 afi_t afi, safi_t safi)
11172 {
11173 struct community_list *list;
11174 struct bgp *bgp = NULL;
11175
11176 if (name && !(bgp = bgp_lookup_by_name(name)))
11177 {
11178 vty_out (vty, "%% No such BGP instance exists%s", VTY_NEWLINE);
11179 return CMD_WARNING;
11180 }
11181
11182 list = community_list_lookup (bgp_clist, com, COMMUNITY_LIST_MASTER);
11183 if (list == NULL)
11184 {
11185 vty_out (vty, "%% %s is not a valid community-list name%s", com,
11186 VTY_NEWLINE);
11187 return CMD_WARNING;
11188 }
11189
11190 return bgp_show (vty, bgp, afi, safi,
11191 (exact ? bgp_show_type_community_list_exact :
11192 bgp_show_type_community_list), list, 0);
11193 }
11194
11195 DEFUN (show_ip_bgp_community_list,
11196 show_ip_bgp_community_list_cmd,
11197 "show ip bgp community-list <(1-500)|WORD>",
11198 SHOW_STR
11199 IP_STR
11200 BGP_STR
11201 "Display routes matching the community-list\n"
11202 "community-list number\n"
11203 "community-list name\n")
11204 {
11205 int idx_comm_list = 4;
11206 return bgp_show_community_list (vty, NULL, argv[idx_comm_list]->arg, 0, AFI_IP, SAFI_UNICAST);
11207 }
11208
11209 DEFUN (show_ip_bgp_instance_community_list,
11210 show_ip_bgp_instance_community_list_cmd,
11211 "show ip bgp <view|vrf> WORD community-list <(1-500)|WORD>",
11212 SHOW_STR
11213 IP_STR
11214 BGP_STR
11215 BGP_INSTANCE_HELP_STR
11216 "Display routes matching the community-list\n"
11217 "community-list number\n"
11218 "community-list name\n")
11219 {
11220 int idx_word = 4;
11221 int idx_comm_list = 6;
11222 return bgp_show_community_list (vty, argv[idx_word]->arg, argv[idx_comm_list]->arg, 0, AFI_IP, SAFI_UNICAST);
11223 }
11224
11225 DEFUN (show_ip_bgp_ipv4_community_list,
11226 show_ip_bgp_ipv4_community_list_cmd,
11227 "show ip bgp ipv4 <unicast|multicast> community-list <(1-500)|WORD>",
11228 SHOW_STR
11229 IP_STR
11230 BGP_STR
11231 "Address family\n"
11232 "Address Family modifier\n"
11233 "Address Family modifier\n"
11234 "Display routes matching the community-list\n"
11235 "community-list number\n"
11236 "community-list name\n")
11237 {
11238 int idx_safi = 4;
11239 int idx_comm_list = 6;
11240 if (strncmp (argv[idx_safi]->arg, "m", 1) == 0)
11241 return bgp_show_community_list (vty, NULL, argv[idx_comm_list]->arg, 0, AFI_IP, SAFI_MULTICAST);
11242
11243 return bgp_show_community_list (vty, NULL, argv[idx_comm_list]->arg, 0, AFI_IP, SAFI_UNICAST);
11244 }
11245
11246 DEFUN (show_ip_bgp_community_list_exact,
11247 show_ip_bgp_community_list_exact_cmd,
11248 "show ip bgp community-list <(1-500)|WORD> exact-match",
11249 SHOW_STR
11250 IP_STR
11251 BGP_STR
11252 "Display routes matching the community-list\n"
11253 "community-list number\n"
11254 "community-list name\n"
11255 "Exact match of the communities\n")
11256 {
11257 int idx_comm_list = 4;
11258 return bgp_show_community_list (vty, NULL, argv[idx_comm_list]->arg, 1, AFI_IP, SAFI_UNICAST);
11259 }
11260
11261 DEFUN (show_ip_bgp_ipv4_community_list_exact,
11262 show_ip_bgp_ipv4_community_list_exact_cmd,
11263 "show ip bgp ipv4 <unicast|multicast> community-list <(1-500)|WORD> exact-match",
11264 SHOW_STR
11265 IP_STR
11266 BGP_STR
11267 "Address family\n"
11268 "Address Family modifier\n"
11269 "Address Family modifier\n"
11270 "Display routes matching the community-list\n"
11271 "community-list number\n"
11272 "community-list name\n"
11273 "Exact match of the communities\n")
11274 {
11275 int idx_safi = 4;
11276 int idx_comm_list = 6;
11277 if (strncmp (argv[idx_safi]->arg, "m", 1) == 0)
11278 return bgp_show_community_list (vty, NULL, argv[idx_comm_list]->arg, 1, AFI_IP, SAFI_MULTICAST);
11279
11280 return bgp_show_community_list (vty, NULL, argv[idx_comm_list]->arg, 1, AFI_IP, SAFI_UNICAST);
11281 }
11282
11283 #ifdef HAVE_IPV6
11284 /*
11285 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
11286 * "show bgp ipv6 community-list (<1-500>|WORD)",
11287 * SHOW_STR
11288 * BGP_STR
11289 * "Address family\n"
11290 * "Display routes matching the community-list\n"
11291 * "community-list number\n"
11292 * "community-list name\n"
11293 *
11294 */
11295 DEFUN (show_bgp_community_list,
11296 show_bgp_community_list_cmd,
11297 "show bgp community-list <(1-500)|WORD>",
11298 SHOW_STR
11299 BGP_STR
11300 "Display routes matching the community-list\n"
11301 "community-list number\n"
11302 "community-list name\n")
11303 {
11304 int idx_comm_list = 3;
11305 return bgp_show_community_list (vty, NULL, argv[idx_comm_list]->arg, 0, AFI_IP6, SAFI_UNICAST);
11306 }
11307
11308
11309 /* old command */
11310 DEFUN (show_ipv6_bgp_community_list,
11311 show_ipv6_bgp_community_list_cmd,
11312 "show ipv6 bgp community-list WORD",
11313 SHOW_STR
11314 IPV6_STR
11315 BGP_STR
11316 "Display routes matching the community-list\n"
11317 "community-list name\n")
11318 {
11319 int idx_word = 4;
11320 bgp_show_ipv6_bgp_deprecate_warning(vty);
11321 return bgp_show_community_list (vty, NULL, argv[idx_word]->arg, 0, AFI_IP6, SAFI_UNICAST);
11322 }
11323
11324 /* old command */
11325 DEFUN (show_ipv6_mbgp_community_list,
11326 show_ipv6_mbgp_community_list_cmd,
11327 "show ipv6 mbgp community-list WORD",
11328 SHOW_STR
11329 IPV6_STR
11330 MBGP_STR
11331 "Display routes matching the community-list\n"
11332 "community-list name\n")
11333 {
11334 int idx_word = 4;
11335 bgp_show_ipv6_bgp_deprecate_warning(vty);
11336 return bgp_show_community_list (vty, NULL, argv[idx_word]->arg, 0, AFI_IP6, SAFI_MULTICAST);
11337 }
11338
11339 /*
11340 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
11341 * "show bgp ipv6 community-list (<1-500>|WORD) exact-match",
11342 * SHOW_STR
11343 * BGP_STR
11344 * "Address family\n"
11345 * "Display routes matching the community-list\n"
11346 * "community-list number\n"
11347 * "community-list name\n"
11348 * "Exact match of the communities\n"
11349 *
11350 */
11351 DEFUN (show_bgp_community_list_exact,
11352 show_bgp_community_list_exact_cmd,
11353 "show bgp community-list <(1-500)|WORD> exact-match",
11354 SHOW_STR
11355 BGP_STR
11356 "Display routes matching the community-list\n"
11357 "community-list number\n"
11358 "community-list name\n"
11359 "Exact match of the communities\n")
11360 {
11361 int idx_comm_list = 3;
11362 return bgp_show_community_list (vty, NULL, argv[idx_comm_list]->arg, 1, AFI_IP6, SAFI_UNICAST);
11363 }
11364
11365
11366 /* old command */
11367 DEFUN (show_ipv6_bgp_community_list_exact,
11368 show_ipv6_bgp_community_list_exact_cmd,
11369 "show ipv6 bgp community-list WORD exact-match",
11370 SHOW_STR
11371 IPV6_STR
11372 BGP_STR
11373 "Display routes matching the community-list\n"
11374 "community-list name\n"
11375 "Exact match of the communities\n")
11376 {
11377 int idx_word = 4;
11378 bgp_show_ipv6_bgp_deprecate_warning(vty);
11379 return bgp_show_community_list (vty, NULL, argv[idx_word]->arg, 1, AFI_IP6, SAFI_UNICAST);
11380 }
11381
11382 /* old command */
11383 DEFUN (show_ipv6_mbgp_community_list_exact,
11384 show_ipv6_mbgp_community_list_exact_cmd,
11385 "show ipv6 mbgp community-list WORD exact-match",
11386 SHOW_STR
11387 IPV6_STR
11388 MBGP_STR
11389 "Display routes matching the community-list\n"
11390 "community-list name\n"
11391 "Exact match of the communities\n")
11392 {
11393 int idx_word = 4;
11394 bgp_show_ipv6_bgp_deprecate_warning(vty);
11395 return bgp_show_community_list (vty, NULL, argv[idx_word]->arg, 1, AFI_IP6, SAFI_MULTICAST);
11396 }
11397 #endif /* HAVE_IPV6 */
11398
11399 static int
11400 bgp_show_prefix_longer (struct vty *vty, const char *name,
11401 const char *prefix, afi_t afi,
11402 safi_t safi, enum bgp_show_type type)
11403 {
11404 int ret;
11405 struct prefix *p;
11406 struct bgp *bgp = NULL;
11407
11408 if (name && !(bgp = bgp_lookup_by_name(name)))
11409 {
11410 vty_out (vty, "%% No such BGP instance exists%s", VTY_NEWLINE);
11411 return CMD_WARNING;
11412 }
11413
11414 p = prefix_new();
11415
11416 ret = str2prefix (prefix, p);
11417 if (! ret)
11418 {
11419 vty_out (vty, "%% Malformed Prefix%s", VTY_NEWLINE);
11420 return CMD_WARNING;
11421 }
11422
11423 ret = bgp_show (vty, bgp, afi, safi, type, p, 0);
11424 prefix_free(p);
11425 return ret;
11426 }
11427
11428 DEFUN (show_ip_bgp_prefix_longer,
11429 show_ip_bgp_prefix_longer_cmd,
11430 "show ip bgp A.B.C.D/M longer-prefixes",
11431 SHOW_STR
11432 IP_STR
11433 BGP_STR
11434 "IP prefix <network>/<length>, e.g., 35.0.0.0/8\n"
11435 "Display route and more specific routes\n")
11436 {
11437 int idx_ipv4_prefixlen = 3;
11438 return bgp_show_prefix_longer (vty, NULL, argv[idx_ipv4_prefixlen]->arg, AFI_IP, SAFI_UNICAST,
11439 bgp_show_type_prefix_longer);
11440 }
11441
11442 DEFUN (show_ip_bgp_instance_prefix_longer,
11443 show_ip_bgp_instance_prefix_longer_cmd,
11444 "show ip bgp <view|vrf> WORD A.B.C.D/M longer-prefixes",
11445 SHOW_STR
11446 IP_STR
11447 BGP_STR
11448 BGP_INSTANCE_HELP_STR
11449 "IP prefix <network>/<length>, e.g., 35.0.0.0/8\n"
11450 "Display route and more specific routes\n")
11451 {
11452 int idx_word = 4;
11453 int idx_ipv4_prefixlen = 5;
11454 return bgp_show_prefix_longer (vty, argv[idx_word]->arg, argv[idx_ipv4_prefixlen]->arg, AFI_IP, SAFI_UNICAST,
11455 bgp_show_type_prefix_longer);
11456 }
11457
11458 /*
11459 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
11460 * "show ip bgp dampening flap-statistics A.B.C.D/M longer-prefixes",
11461 * SHOW_STR
11462 * IP_STR
11463 * BGP_STR
11464 * "Display detailed information about dampening\n"
11465 * "Display flap statistics of routes\n"
11466 * "IP prefix <network>/<length>, e.g., 35.0.0.0/8\n"
11467 * "Display route and more specific routes\n"
11468 *
11469 */
11470 DEFUN (show_ip_bgp_flap_prefix_longer,
11471 show_ip_bgp_flap_prefix_longer_cmd,
11472 "show ip bgp flap-statistics A.B.C.D/M longer-prefixes",
11473 SHOW_STR
11474 IP_STR
11475 BGP_STR
11476 "Display flap statistics of routes\n"
11477 "IP prefix <network>/<length>, e.g., 35.0.0.0/8\n"
11478 "Display route and more specific routes\n")
11479 {
11480 int idx_ipv4_prefixlen = 4;
11481 return bgp_show_prefix_longer (vty, NULL, argv[idx_ipv4_prefixlen]->arg, AFI_IP, SAFI_UNICAST,
11482 bgp_show_type_flap_prefix_longer);
11483 }
11484
11485
11486 DEFUN (show_ip_bgp_ipv4_prefix_longer,
11487 show_ip_bgp_ipv4_prefix_longer_cmd,
11488 "show ip bgp ipv4 <unicast|multicast> A.B.C.D/M longer-prefixes",
11489 SHOW_STR
11490 IP_STR
11491 BGP_STR
11492 "Address family\n"
11493 "Address Family modifier\n"
11494 "Address Family modifier\n"
11495 "IP prefix <network>/<length>, e.g., 35.0.0.0/8\n"
11496 "Display route and more specific routes\n")
11497 {
11498 int idx_safi = 4;
11499 int idx_ipv4_prefixlen = 5;
11500 if (strncmp (argv[idx_safi]->arg, "m", 1) == 0)
11501 return bgp_show_prefix_longer (vty, NULL, argv[idx_ipv4_prefixlen]->arg, AFI_IP, SAFI_MULTICAST,
11502 bgp_show_type_prefix_longer);
11503
11504 return bgp_show_prefix_longer (vty, NULL, argv[idx_ipv4_prefixlen]->arg, AFI_IP, SAFI_UNICAST,
11505 bgp_show_type_prefix_longer);
11506 }
11507
11508 /*
11509 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
11510 * "show ip bgp dampening flap-statistics A.B.C.D",
11511 * SHOW_STR
11512 * IP_STR
11513 * BGP_STR
11514 * "Display detailed information about dampening\n"
11515 * "Display flap statistics of routes\n"
11516 * "Network in the BGP routing table to display\n"
11517 *
11518 */
11519 DEFUN (show_ip_bgp_flap_address,
11520 show_ip_bgp_flap_address_cmd,
11521 "show ip bgp flap-statistics A.B.C.D",
11522 SHOW_STR
11523 IP_STR
11524 BGP_STR
11525 "Display flap statistics of routes\n"
11526 "Network in the BGP routing table to display\n")
11527 {
11528 int idx_ipv4 = 4;
11529 return bgp_show_prefix_longer (vty, NULL, argv[idx_ipv4]->arg, AFI_IP, SAFI_UNICAST,
11530 bgp_show_type_flap_address);
11531 }
11532
11533
11534 /*
11535 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
11536 * "show ip bgp dampening flap-statistics A.B.C.D/M",
11537 * SHOW_STR
11538 * IP_STR
11539 * BGP_STR
11540 * "Display detailed information about dampening\n"
11541 * "Display flap statistics of routes\n"
11542 * "IP prefix <network>/<length>, e.g., 35.0.0.0/8\n"
11543 *
11544 */
11545 DEFUN (show_ip_bgp_flap_prefix,
11546 show_ip_bgp_flap_prefix_cmd,
11547 "show ip bgp flap-statistics A.B.C.D/M",
11548 SHOW_STR
11549 IP_STR
11550 BGP_STR
11551 "Display flap statistics of routes\n"
11552 "IP prefix <network>/<length>, e.g., 35.0.0.0/8\n")
11553 {
11554 int idx_ipv4_prefixlen = 4;
11555 return bgp_show_prefix_longer (vty, NULL, argv[idx_ipv4_prefixlen]->arg, AFI_IP, SAFI_UNICAST,
11556 bgp_show_type_flap_prefix);
11557 }
11558
11559
11560 #ifdef HAVE_IPV6
11561 /*
11562 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
11563 * "show bgp ipv6 X:X::X:X/M longer-prefixes",
11564 * SHOW_STR
11565 * BGP_STR
11566 * "Address family\n"
11567 * "IPv6 prefix <network>/<length>\n"
11568 * "Display route and more specific routes\n"
11569 *
11570 */
11571 DEFUN (show_bgp_prefix_longer,
11572 show_bgp_prefix_longer_cmd,
11573 "show bgp X:X::X:X/M longer-prefixes",
11574 SHOW_STR
11575 BGP_STR
11576 "IPv6 prefix <network>/<length>\n"
11577 "Display route and more specific routes\n")
11578 {
11579 int idx_ipv6_prefixlen = 2;
11580 return bgp_show_prefix_longer (vty, NULL, argv[idx_ipv6_prefixlen]->arg, AFI_IP6, SAFI_UNICAST,
11581 bgp_show_type_prefix_longer);
11582 }
11583
11584
11585 /* old command */
11586 DEFUN (show_ipv6_bgp_prefix_longer,
11587 show_ipv6_bgp_prefix_longer_cmd,
11588 "show ipv6 bgp X:X::X:X/M longer-prefixes",
11589 SHOW_STR
11590 IPV6_STR
11591 BGP_STR
11592 "IPv6 prefix <network>/<length>, e.g., 3ffe::/16\n"
11593 "Display route and more specific routes\n")
11594 {
11595 int idx_ipv6_prefixlen = 3;
11596 bgp_show_ipv6_bgp_deprecate_warning(vty);
11597 return bgp_show_prefix_longer (vty, NULL, argv[idx_ipv6_prefixlen]->arg, AFI_IP6, SAFI_UNICAST,
11598 bgp_show_type_prefix_longer);
11599 }
11600
11601 /* old command */
11602 DEFUN (show_ipv6_mbgp_prefix_longer,
11603 show_ipv6_mbgp_prefix_longer_cmd,
11604 "show ipv6 mbgp X:X::X:X/M longer-prefixes",
11605 SHOW_STR
11606 IPV6_STR
11607 MBGP_STR
11608 "IPv6 prefix <network>/<length>, e.g., 3ffe::/16\n"
11609 "Display route and more specific routes\n")
11610 {
11611 int idx_ipv6_prefixlen = 3;
11612 bgp_show_ipv6_bgp_deprecate_warning(vty);
11613 return bgp_show_prefix_longer (vty, NULL, argv[idx_ipv6_prefixlen]->arg, AFI_IP6, SAFI_MULTICAST,
11614 bgp_show_type_prefix_longer);
11615 }
11616 #endif /* HAVE_IPV6 */
11617
11618 static struct peer *
11619 peer_lookup_in_view (struct vty *vty, const char *view_name,
11620 const char *ip_str, u_char use_json)
11621 {
11622 int ret;
11623 struct bgp *bgp;
11624 struct peer *peer;
11625 union sockunion su;
11626
11627 /* BGP structure lookup. */
11628 if (view_name)
11629 {
11630 bgp = bgp_lookup_by_name (view_name);
11631 if (! bgp)
11632 {
11633 if (use_json)
11634 {
11635 json_object *json_no = NULL;
11636 json_no = json_object_new_object();
11637 json_object_string_add(json_no, "warning", "Can't find BGP view");
11638 vty_out (vty, "%s%s", json_object_to_json_string(json_no), VTY_NEWLINE);
11639 json_object_free(json_no);
11640 }
11641 else
11642 vty_out (vty, "Can't find BGP instance %s%s", view_name, VTY_NEWLINE);
11643 return NULL;
11644 }
11645 }
11646 else
11647 {
11648 bgp = bgp_get_default ();
11649 if (! bgp)
11650 {
11651 if (use_json)
11652 {
11653 json_object *json_no = NULL;
11654 json_no = json_object_new_object();
11655 json_object_string_add(json_no, "warning", "No BGP process configured");
11656 vty_out (vty, "%s%s", json_object_to_json_string(json_no), VTY_NEWLINE);
11657 json_object_free(json_no);
11658 }
11659 else
11660 vty_out (vty, "No BGP process is configured%s", VTY_NEWLINE);
11661 return NULL;
11662 }
11663 }
11664
11665 /* Get peer sockunion. */
11666 ret = str2sockunion (ip_str, &su);
11667 if (ret < 0)
11668 {
11669 peer = peer_lookup_by_conf_if (bgp, ip_str);
11670 if (!peer)
11671 {
11672 peer = peer_lookup_by_hostname(bgp, ip_str);
11673
11674 if (!peer)
11675 {
11676 if (use_json)
11677 {
11678 json_object *json_no = NULL;
11679 json_no = json_object_new_object();
11680 json_object_string_add(json_no, "malformedAddressOrName", ip_str);
11681 vty_out (vty, "%s%s", json_object_to_json_string(json_no), VTY_NEWLINE);
11682 json_object_free(json_no);
11683 }
11684 else
11685 vty_out (vty, "%% Malformed address or name: %s%s", ip_str, VTY_NEWLINE);
11686 return NULL;
11687 }
11688 }
11689 return peer;
11690 }
11691
11692 /* Peer structure lookup. */
11693 peer = peer_lookup (bgp, &su);
11694 if (! peer)
11695 {
11696 if (use_json)
11697 {
11698 json_object *json_no = NULL;
11699 json_no = json_object_new_object();
11700 json_object_string_add(json_no, "warning","No such neighbor");
11701 vty_out (vty, "%s%s", json_object_to_json_string(json_no), VTY_NEWLINE);
11702 json_object_free(json_no);
11703 }
11704 else
11705 vty_out (vty, "No such neighbor%s", VTY_NEWLINE);
11706 return NULL;
11707 }
11708
11709 return peer;
11710 }
11711
11712 enum bgp_stats
11713 {
11714 BGP_STATS_MAXBITLEN = 0,
11715 BGP_STATS_RIB,
11716 BGP_STATS_PREFIXES,
11717 BGP_STATS_TOTPLEN,
11718 BGP_STATS_UNAGGREGATEABLE,
11719 BGP_STATS_MAX_AGGREGATEABLE,
11720 BGP_STATS_AGGREGATES,
11721 BGP_STATS_SPACE,
11722 BGP_STATS_ASPATH_COUNT,
11723 BGP_STATS_ASPATH_MAXHOPS,
11724 BGP_STATS_ASPATH_TOTHOPS,
11725 BGP_STATS_ASPATH_MAXSIZE,
11726 BGP_STATS_ASPATH_TOTSIZE,
11727 BGP_STATS_ASN_HIGHEST,
11728 BGP_STATS_MAX,
11729 };
11730
11731 static const char *table_stats_strs[] =
11732 {
11733 [BGP_STATS_PREFIXES] = "Total Prefixes",
11734 [BGP_STATS_TOTPLEN] = "Average prefix length",
11735 [BGP_STATS_RIB] = "Total Advertisements",
11736 [BGP_STATS_UNAGGREGATEABLE] = "Unaggregateable prefixes",
11737 [BGP_STATS_MAX_AGGREGATEABLE] = "Maximum aggregateable prefixes",
11738 [BGP_STATS_AGGREGATES] = "BGP Aggregate advertisements",
11739 [BGP_STATS_SPACE] = "Address space advertised",
11740 [BGP_STATS_ASPATH_COUNT] = "Advertisements with paths",
11741 [BGP_STATS_ASPATH_MAXHOPS] = "Longest AS-Path (hops)",
11742 [BGP_STATS_ASPATH_MAXSIZE] = "Largest AS-Path (bytes)",
11743 [BGP_STATS_ASPATH_TOTHOPS] = "Average AS-Path length (hops)",
11744 [BGP_STATS_ASPATH_TOTSIZE] = "Average AS-Path size (bytes)",
11745 [BGP_STATS_ASN_HIGHEST] = "Highest public ASN",
11746 [BGP_STATS_MAX] = NULL,
11747 };
11748
11749 struct bgp_table_stats
11750 {
11751 struct bgp_table *table;
11752 unsigned long long counts[BGP_STATS_MAX];
11753 };
11754
11755 #if 0
11756 #define TALLY_SIGFIG 100000
11757 static unsigned long
11758 ravg_tally (unsigned long count, unsigned long oldavg, unsigned long newval)
11759 {
11760 unsigned long newtot = (count-1) * oldavg + (newval * TALLY_SIGFIG);
11761 unsigned long res = (newtot * TALLY_SIGFIG) / count;
11762 unsigned long ret = newtot / count;
11763
11764 if ((res % TALLY_SIGFIG) > (TALLY_SIGFIG/2))
11765 return ret + 1;
11766 else
11767 return ret;
11768 }
11769 #endif
11770
11771 static int
11772 bgp_table_stats_walker (struct thread *t)
11773 {
11774 struct bgp_node *rn;
11775 struct bgp_node *top;
11776 struct bgp_table_stats *ts = THREAD_ARG (t);
11777 unsigned int space = 0;
11778
11779 if (!(top = bgp_table_top (ts->table)))
11780 return 0;
11781
11782 switch (top->p.family)
11783 {
11784 case AF_INET:
11785 space = IPV4_MAX_BITLEN;
11786 break;
11787 case AF_INET6:
11788 space = IPV6_MAX_BITLEN;
11789 break;
11790 }
11791
11792 ts->counts[BGP_STATS_MAXBITLEN] = space;
11793
11794 for (rn = top; rn; rn = bgp_route_next (rn))
11795 {
11796 struct bgp_info *ri;
11797 struct bgp_node *prn = bgp_node_parent_nolock (rn);
11798 unsigned int rinum = 0;
11799
11800 if (rn == top)
11801 continue;
11802
11803 if (!rn->info)
11804 continue;
11805
11806 ts->counts[BGP_STATS_PREFIXES]++;
11807 ts->counts[BGP_STATS_TOTPLEN] += rn->p.prefixlen;
11808
11809 #if 0
11810 ts->counts[BGP_STATS_AVGPLEN]
11811 = ravg_tally (ts->counts[BGP_STATS_PREFIXES],
11812 ts->counts[BGP_STATS_AVGPLEN],
11813 rn->p.prefixlen);
11814 #endif
11815
11816 /* check if the prefix is included by any other announcements */
11817 while (prn && !prn->info)
11818 prn = bgp_node_parent_nolock (prn);
11819
11820 if (prn == NULL || prn == top)
11821 {
11822 ts->counts[BGP_STATS_UNAGGREGATEABLE]++;
11823 /* announced address space */
11824 if (space)
11825 ts->counts[BGP_STATS_SPACE] += 1 << (space - rn->p.prefixlen);
11826 }
11827 else if (prn->info)
11828 ts->counts[BGP_STATS_MAX_AGGREGATEABLE]++;
11829
11830 for (ri = rn->info; ri; ri = ri->next)
11831 {
11832 rinum++;
11833 ts->counts[BGP_STATS_RIB]++;
11834
11835 if (ri->attr &&
11836 (CHECK_FLAG (ri->attr->flag,
11837 ATTR_FLAG_BIT (BGP_ATTR_ATOMIC_AGGREGATE))))
11838 ts->counts[BGP_STATS_AGGREGATES]++;
11839
11840 /* as-path stats */
11841 if (ri->attr && ri->attr->aspath)
11842 {
11843 unsigned int hops = aspath_count_hops (ri->attr->aspath);
11844 unsigned int size = aspath_size (ri->attr->aspath);
11845 as_t highest = aspath_highest (ri->attr->aspath);
11846
11847 ts->counts[BGP_STATS_ASPATH_COUNT]++;
11848
11849 if (hops > ts->counts[BGP_STATS_ASPATH_MAXHOPS])
11850 ts->counts[BGP_STATS_ASPATH_MAXHOPS] = hops;
11851
11852 if (size > ts->counts[BGP_STATS_ASPATH_MAXSIZE])
11853 ts->counts[BGP_STATS_ASPATH_MAXSIZE] = size;
11854
11855 ts->counts[BGP_STATS_ASPATH_TOTHOPS] += hops;
11856 ts->counts[BGP_STATS_ASPATH_TOTSIZE] += size;
11857 #if 0
11858 ts->counts[BGP_STATS_ASPATH_AVGHOPS]
11859 = ravg_tally (ts->counts[BGP_STATS_ASPATH_COUNT],
11860 ts->counts[BGP_STATS_ASPATH_AVGHOPS],
11861 hops);
11862 ts->counts[BGP_STATS_ASPATH_AVGSIZE]
11863 = ravg_tally (ts->counts[BGP_STATS_ASPATH_COUNT],
11864 ts->counts[BGP_STATS_ASPATH_AVGSIZE],
11865 size);
11866 #endif
11867 if (highest > ts->counts[BGP_STATS_ASN_HIGHEST])
11868 ts->counts[BGP_STATS_ASN_HIGHEST] = highest;
11869 }
11870 }
11871 }
11872 return 0;
11873 }
11874
11875 static int
11876 bgp_table_stats (struct vty *vty, struct bgp *bgp, afi_t afi, safi_t safi)
11877 {
11878 struct bgp_table_stats ts;
11879 unsigned int i;
11880
11881 if (!bgp->rib[afi][safi])
11882 {
11883 vty_out (vty, "%% No RIB exist's for the AFI(%d)/SAFI(%d)%s",
11884 afi, safi, VTY_NEWLINE);
11885 return CMD_WARNING;
11886 }
11887
11888 memset (&ts, 0, sizeof (ts));
11889 ts.table = bgp->rib[afi][safi];
11890 thread_execute (bm->master, bgp_table_stats_walker, &ts, 0);
11891
11892 vty_out (vty, "BGP %s RIB statistics%s%s",
11893 afi_safi_print (afi, safi), VTY_NEWLINE, VTY_NEWLINE);
11894
11895 for (i = 0; i < BGP_STATS_MAX; i++)
11896 {
11897 if (!table_stats_strs[i])
11898 continue;
11899
11900 switch (i)
11901 {
11902 #if 0
11903 case BGP_STATS_ASPATH_AVGHOPS:
11904 case BGP_STATS_ASPATH_AVGSIZE:
11905 case BGP_STATS_AVGPLEN:
11906 vty_out (vty, "%-30s: ", table_stats_strs[i]);
11907 vty_out (vty, "%12.2f",
11908 (float)ts.counts[i] / (float)TALLY_SIGFIG);
11909 break;
11910 #endif
11911 case BGP_STATS_ASPATH_TOTHOPS:
11912 case BGP_STATS_ASPATH_TOTSIZE:
11913 vty_out (vty, "%-30s: ", table_stats_strs[i]);
11914 vty_out (vty, "%12.2f",
11915 ts.counts[i] ?
11916 (float)ts.counts[i] /
11917 (float)ts.counts[BGP_STATS_ASPATH_COUNT]
11918 : 0);
11919 break;
11920 case BGP_STATS_TOTPLEN:
11921 vty_out (vty, "%-30s: ", table_stats_strs[i]);
11922 vty_out (vty, "%12.2f",
11923 ts.counts[i] ?
11924 (float)ts.counts[i] /
11925 (float)ts.counts[BGP_STATS_PREFIXES]
11926 : 0);
11927 break;
11928 case BGP_STATS_SPACE:
11929 vty_out (vty, "%-30s: ", table_stats_strs[i]);
11930 vty_out (vty, "%12llu%s", ts.counts[i], VTY_NEWLINE);
11931 if (ts.counts[BGP_STATS_MAXBITLEN] < 9)
11932 break;
11933 vty_out (vty, "%30s: ", "%% announced ");
11934 vty_out (vty, "%12.2f%s",
11935 100 * (float)ts.counts[BGP_STATS_SPACE] /
11936 (float)((uint64_t)1UL << ts.counts[BGP_STATS_MAXBITLEN]),
11937 VTY_NEWLINE);
11938 vty_out (vty, "%30s: ", "/8 equivalent ");
11939 vty_out (vty, "%12.2f%s",
11940 (float)ts.counts[BGP_STATS_SPACE] /
11941 (float)(1UL << (ts.counts[BGP_STATS_MAXBITLEN] - 8)),
11942 VTY_NEWLINE);
11943 if (ts.counts[BGP_STATS_MAXBITLEN] < 25)
11944 break;
11945 vty_out (vty, "%30s: ", "/24 equivalent ");
11946 vty_out (vty, "%12.2f",
11947 (float)ts.counts[BGP_STATS_SPACE] /
11948 (float)(1UL << (ts.counts[BGP_STATS_MAXBITLEN] - 24)));
11949 break;
11950 default:
11951 vty_out (vty, "%-30s: ", table_stats_strs[i]);
11952 vty_out (vty, "%12llu", ts.counts[i]);
11953 }
11954
11955 vty_out (vty, "%s", VTY_NEWLINE);
11956 }
11957 return CMD_SUCCESS;
11958 }
11959
11960 static int
11961 bgp_table_stats_vty (struct vty *vty, const char *name,
11962 const char *afi_str, const char *safi_str)
11963 {
11964 struct bgp *bgp;
11965 afi_t afi;
11966 safi_t safi;
11967
11968 if (name)
11969 bgp = bgp_lookup_by_name (name);
11970 else
11971 bgp = bgp_get_default ();
11972
11973 if (!bgp)
11974 {
11975 vty_out (vty, "%% No such BGP instance exist%s", VTY_NEWLINE);
11976 return CMD_WARNING;
11977 }
11978 if (strncmp (afi_str, "ipv", 3) == 0)
11979 {
11980 if (strncmp (afi_str, "ipv4", 4) == 0)
11981 afi = AFI_IP;
11982 else if (strncmp (afi_str, "ipv6", 4) == 0)
11983 afi = AFI_IP6;
11984 else
11985 {
11986 vty_out (vty, "%% Invalid address family %s%s",
11987 afi_str, VTY_NEWLINE);
11988 return CMD_WARNING;
11989 }
11990 if (strncmp (safi_str, "m", 1) == 0)
11991 safi = SAFI_MULTICAST;
11992 else if (strncmp (safi_str, "u", 1) == 0)
11993 safi = SAFI_UNICAST;
11994 else if (strncmp (safi_str, "e", 1) == 0)
11995 safi = SAFI_ENCAP;
11996 else if (strncmp (safi_str, "vpnv4", 5) == 0 || strncmp (safi_str, "vpnv6", 5) == 0)
11997 safi = SAFI_MPLS_VPN;
11998 else
11999 {
12000 vty_out (vty, "%% Invalid subsequent address family %s%s",
12001 safi_str, VTY_NEWLINE);
12002 return CMD_WARNING;
12003 }
12004 }
12005 else
12006 {
12007 vty_out (vty, "%% Invalid address family \"%s\"%s",
12008 afi_str, VTY_NEWLINE);
12009 return CMD_WARNING;
12010 }
12011
12012 return bgp_table_stats (vty, bgp, afi, safi);
12013 }
12014
12015 DEFUN (show_bgp_statistics,
12016 show_bgp_statistics_cmd,
12017 "show bgp <ipv4|ipv6> <encap|multicast|unicast|vpn> statistics",
12018 SHOW_STR
12019 BGP_STR
12020 "Address family\n"
12021 "Address family\n"
12022 "Address Family modifier\n"
12023 "Address Family modifier\n"
12024 "Address Family modifier\n"
12025 "Address Family modifier\n"
12026 "BGP RIB advertisement statistics\n")
12027 {
12028 int idx_afi = 2;
12029 int idx_safi = 3;
12030 return bgp_table_stats_vty (vty, NULL, argv[idx_afi]->arg, argv[idx_safi]->arg);
12031 }
12032
12033 DEFUN (show_bgp_statistics_view,
12034 show_bgp_statistics_view_cmd,
12035 "show bgp <view|vrf> WORD <ipv4|ipv6> <unicast|multicast|vpn|encap> statistics",
12036 SHOW_STR
12037 BGP_STR
12038 BGP_INSTANCE_HELP_STR
12039 "Address family\n"
12040 "Address family\n"
12041 "Address Family modifier\n"
12042 "Address Family modifier\n"
12043 "Address Family modifier\n"
12044 "Address Family modifier\n"
12045 "BGP RIB advertisement statistics\n")
12046 {
12047 int idx_word = 3;
12048 int idx_afi = 4;
12049 return bgp_table_stats_vty (vty, NULL, argv[idx_word]->arg, argv[idx_afi]->arg);
12050 }
12051
12052 enum bgp_pcounts
12053 {
12054 PCOUNT_ADJ_IN = 0,
12055 PCOUNT_DAMPED,
12056 PCOUNT_REMOVED,
12057 PCOUNT_HISTORY,
12058 PCOUNT_STALE,
12059 PCOUNT_VALID,
12060 PCOUNT_ALL,
12061 PCOUNT_COUNTED,
12062 PCOUNT_PFCNT, /* the figure we display to users */
12063 PCOUNT_MAX,
12064 };
12065
12066 static const char *pcount_strs[] =
12067 {
12068 [PCOUNT_ADJ_IN] = "Adj-in",
12069 [PCOUNT_DAMPED] = "Damped",
12070 [PCOUNT_REMOVED] = "Removed",
12071 [PCOUNT_HISTORY] = "History",
12072 [PCOUNT_STALE] = "Stale",
12073 [PCOUNT_VALID] = "Valid",
12074 [PCOUNT_ALL] = "All RIB",
12075 [PCOUNT_COUNTED] = "PfxCt counted",
12076 [PCOUNT_PFCNT] = "Useable",
12077 [PCOUNT_MAX] = NULL,
12078 };
12079
12080 struct peer_pcounts
12081 {
12082 unsigned int count[PCOUNT_MAX];
12083 const struct peer *peer;
12084 const struct bgp_table *table;
12085 };
12086
12087 static int
12088 bgp_peer_count_walker (struct thread *t)
12089 {
12090 struct bgp_node *rn;
12091 struct peer_pcounts *pc = THREAD_ARG (t);
12092 const struct peer *peer = pc->peer;
12093
12094 for (rn = bgp_table_top (pc->table); rn; rn = bgp_route_next (rn))
12095 {
12096 struct bgp_adj_in *ain;
12097 struct bgp_info *ri;
12098
12099 for (ain = rn->adj_in; ain; ain = ain->next)
12100 if (ain->peer == peer)
12101 pc->count[PCOUNT_ADJ_IN]++;
12102
12103 for (ri = rn->info; ri; ri = ri->next)
12104 {
12105 char buf[SU_ADDRSTRLEN];
12106
12107 if (ri->peer != peer)
12108 continue;
12109
12110 pc->count[PCOUNT_ALL]++;
12111
12112 if (CHECK_FLAG (ri->flags, BGP_INFO_DAMPED))
12113 pc->count[PCOUNT_DAMPED]++;
12114 if (CHECK_FLAG (ri->flags, BGP_INFO_HISTORY))
12115 pc->count[PCOUNT_HISTORY]++;
12116 if (CHECK_FLAG (ri->flags, BGP_INFO_REMOVED))
12117 pc->count[PCOUNT_REMOVED]++;
12118 if (CHECK_FLAG (ri->flags, BGP_INFO_STALE))
12119 pc->count[PCOUNT_STALE]++;
12120 if (CHECK_FLAG (ri->flags, BGP_INFO_VALID))
12121 pc->count[PCOUNT_VALID]++;
12122 if (!CHECK_FLAG (ri->flags, BGP_INFO_UNUSEABLE))
12123 pc->count[PCOUNT_PFCNT]++;
12124
12125 if (CHECK_FLAG (ri->flags, BGP_INFO_COUNTED))
12126 {
12127 pc->count[PCOUNT_COUNTED]++;
12128 if (CHECK_FLAG (ri->flags, BGP_INFO_UNUSEABLE))
12129 zlog_warn ("%s [pcount] %s/%d is counted but flags 0x%x",
12130 peer->host,
12131 inet_ntop(rn->p.family, &rn->p.u.prefix,
12132 buf, SU_ADDRSTRLEN),
12133 rn->p.prefixlen,
12134 ri->flags);
12135 }
12136 else
12137 {
12138 if (!CHECK_FLAG (ri->flags, BGP_INFO_UNUSEABLE))
12139 zlog_warn ("%s [pcount] %s/%d not counted but flags 0x%x",
12140 peer->host,
12141 inet_ntop(rn->p.family, &rn->p.u.prefix,
12142 buf, SU_ADDRSTRLEN),
12143 rn->p.prefixlen,
12144 ri->flags);
12145 }
12146 }
12147 }
12148 return 0;
12149 }
12150
12151 static int
12152 bgp_peer_counts (struct vty *vty, struct peer *peer, afi_t afi, safi_t safi, u_char use_json)
12153 {
12154 struct peer_pcounts pcounts = { .peer = peer };
12155 unsigned int i;
12156 json_object *json = NULL;
12157 json_object *json_loop = NULL;
12158
12159 if (use_json)
12160 {
12161 json = json_object_new_object();
12162 json_loop = json_object_new_object();
12163 }
12164
12165 if (!peer || !peer->bgp || !peer->afc[afi][safi]
12166 || !peer->bgp->rib[afi][safi])
12167 {
12168 if (use_json)
12169 {
12170 json_object_string_add(json, "warning", "No such neighbor or address family");
12171 vty_out (vty, "%s%s", json_object_to_json_string(json), VTY_NEWLINE);
12172 json_object_free(json);
12173 }
12174 else
12175 vty_out (vty, "%% No such neighbor or address family%s", VTY_NEWLINE);
12176
12177 return CMD_WARNING;
12178 }
12179
12180 memset (&pcounts, 0, sizeof(pcounts));
12181 pcounts.peer = peer;
12182 pcounts.table = peer->bgp->rib[afi][safi];
12183
12184 /* in-place call via thread subsystem so as to record execution time
12185 * * stats for the thread-walk (i.e. ensure this can't be blamed on
12186 * * on just vty_read()).
12187 * */
12188 thread_execute (bm->master, bgp_peer_count_walker, &pcounts, 0);
12189
12190 if (use_json)
12191 {
12192 json_object_string_add(json, "prefixCountsFor", peer->host);
12193 json_object_string_add(json, "multiProtocol", afi_safi_print (afi, safi));
12194 json_object_int_add(json, "pfxCounter", peer->pcount[afi][safi]);
12195
12196 for (i = 0; i < PCOUNT_MAX; i++)
12197 json_object_int_add(json_loop, pcount_strs[i], pcounts.count[i]);
12198
12199 json_object_object_add(json, "ribTableWalkCounters", json_loop);
12200
12201 if (pcounts.count[PCOUNT_PFCNT] != peer->pcount[afi][safi])
12202 {
12203 json_object_string_add(json, "pfxctDriftFor", peer->host);
12204 json_object_string_add(json, "recommended", "Please report this bug, with the above command output");
12205 }
12206 vty_out (vty, "%s%s", json_object_to_json_string(json), VTY_NEWLINE);
12207 json_object_free(json);
12208 }
12209 else
12210 {
12211
12212 if (peer->hostname && bgp_flag_check(peer->bgp, BGP_FLAG_SHOW_HOSTNAME))
12213 {
12214 vty_out (vty, "Prefix counts for %s/%s, %s%s",
12215 peer->hostname, peer->host, afi_safi_print (afi, safi),
12216 VTY_NEWLINE);
12217 }
12218 else
12219 {
12220 vty_out (vty, "Prefix counts for %s, %s%s",
12221 peer->host, afi_safi_print (afi, safi), VTY_NEWLINE);
12222 }
12223
12224 vty_out (vty, "PfxCt: %ld%s", peer->pcount[afi][safi], VTY_NEWLINE);
12225 vty_out (vty, "%sCounts from RIB table walk:%s%s",
12226 VTY_NEWLINE, VTY_NEWLINE, VTY_NEWLINE);
12227
12228 for (i = 0; i < PCOUNT_MAX; i++)
12229 vty_out (vty, "%20s: %-10d%s", pcount_strs[i], pcounts.count[i], VTY_NEWLINE);
12230
12231 if (pcounts.count[PCOUNT_PFCNT] != peer->pcount[afi][safi])
12232 {
12233 vty_out (vty, "%s [pcount] PfxCt drift!%s",
12234 peer->host, VTY_NEWLINE);
12235 vty_out (vty, "Please report this bug, with the above command output%s",
12236 VTY_NEWLINE);
12237 }
12238 }
12239
12240 return CMD_SUCCESS;
12241 }
12242
12243 DEFUN (show_ip_bgp_neighbor_prefix_counts,
12244 show_ip_bgp_neighbor_prefix_counts_cmd,
12245 "show ip bgp neighbors <A.B.C.D|X:X::X:X|WORD> prefix-counts [json]",
12246 SHOW_STR
12247 IP_STR
12248 BGP_STR
12249 "Detailed information on TCP and BGP neighbor connections\n"
12250 "Neighbor to display information about\n"
12251 "Neighbor to display information about\n"
12252 "Neighbor on bgp configured interface\n"
12253 "Display detailed prefix count information\n"
12254 "JavaScript Object Notation\n")
12255 {
12256 int idx_peer = 4;
12257 struct peer *peer;
12258 u_char uj = use_json(argc, argv);
12259
12260 peer = peer_lookup_in_view (vty, NULL, argv[idx_peer]->arg, uj);
12261 if (! peer)
12262 return CMD_WARNING;
12263
12264 return bgp_peer_counts (vty, peer, AFI_IP, SAFI_UNICAST, uj);
12265 }
12266
12267 DEFUN (show_ip_bgp_instance_neighbor_prefix_counts,
12268 show_ip_bgp_instance_neighbor_prefix_counts_cmd,
12269 "show ip bgp <view|vrf> WORD neighbors <A.B.C.D|X:X::X:X|WORD> prefix-counts [json]",
12270 SHOW_STR
12271 IP_STR
12272 BGP_STR
12273 BGP_INSTANCE_HELP_STR
12274 "Detailed information on TCP and BGP neighbor connections\n"
12275 "Neighbor to display information about\n"
12276 "Neighbor to display information about\n"
12277 "Neighbor on bgp configured interface\n"
12278 "Display detailed prefix count information\n"
12279 "JavaScript Object Notation\n")
12280 {
12281 int idx_word = 4;
12282 int idx_peer = 6;
12283 struct peer *peer;
12284 u_char uj = use_json(argc, argv);
12285
12286 peer = peer_lookup_in_view (vty, argv[idx_word]->arg, argv[idx_peer]->arg, uj);
12287 if (! peer)
12288 return CMD_WARNING;
12289
12290 return bgp_peer_counts (vty, peer, AFI_IP, SAFI_UNICAST, uj);
12291 }
12292
12293 DEFUN (show_bgp_ipv6_neighbor_prefix_counts,
12294 show_bgp_ipv6_neighbor_prefix_counts_cmd,
12295 "show bgp ipv6 neighbors <A.B.C.D|X:X::X:X|WORD> prefix-counts [json]",
12296 SHOW_STR
12297 BGP_STR
12298 "Address family\n"
12299 "Detailed information on TCP and BGP neighbor connections\n"
12300 "Neighbor to display information about\n"
12301 "Neighbor to display information about\n"
12302 "Neighbor on bgp configured interface\n"
12303 "Display detailed prefix count information\n"
12304 "JavaScript Object Notation\n")
12305 {
12306 int idx_peer = 4;
12307 struct peer *peer;
12308 u_char uj = use_json(argc, argv);
12309
12310 peer = peer_lookup_in_view (vty, NULL, argv[idx_peer]->arg, uj);
12311 if (! peer)
12312 return CMD_WARNING;
12313
12314 return bgp_peer_counts (vty, peer, AFI_IP6, SAFI_UNICAST, uj);
12315 }
12316
12317 DEFUN (show_bgp_instance_ipv6_neighbor_prefix_counts,
12318 show_bgp_instance_ipv6_neighbor_prefix_counts_cmd,
12319 "show bgp <view|vrf> WORD ipv6 neighbors <A.B.C.D|X:X::X:X|WORD> prefix-counts [json]",
12320 SHOW_STR
12321 BGP_STR
12322 BGP_INSTANCE_HELP_STR
12323 "Address family\n"
12324 "Detailed information on TCP and BGP neighbor connections\n"
12325 "Neighbor to display information about\n"
12326 "Neighbor to display information about\n"
12327 "Neighbor on bgp configured interface\n"
12328 "Display detailed prefix count information\n"
12329 "JavaScript Object Notation\n")
12330 {
12331 int idx_word = 3;
12332 int idx_peer = 6;
12333 struct peer *peer;
12334 u_char uj = use_json(argc, argv);
12335
12336 peer = peer_lookup_in_view (vty, argv[idx_word]->arg, argv[idx_peer]->arg, uj);
12337 if (! peer)
12338 return CMD_WARNING;
12339
12340 return bgp_peer_counts (vty, peer, AFI_IP6, SAFI_UNICAST, uj);
12341 }
12342
12343 DEFUN (show_ip_bgp_ipv4_neighbor_prefix_counts,
12344 show_ip_bgp_ipv4_neighbor_prefix_counts_cmd,
12345 "show ip bgp ipv4 <unicast|multicast> neighbors <A.B.C.D|X:X::X:X|WORD> prefix-counts [json]",
12346 SHOW_STR
12347 IP_STR
12348 BGP_STR
12349 "Address family\n"
12350 "Address Family modifier\n"
12351 "Address Family modifier\n"
12352 "Detailed information on TCP and BGP neighbor connections\n"
12353 "Neighbor to display information about\n"
12354 "Neighbor to display information about\n"
12355 "Neighbor on bgp configured interface\n"
12356 "Display detailed prefix count information\n"
12357 "JavaScript Object Notation\n")
12358 {
12359 int idx_safi = 4;
12360 int idx_peer = 6;
12361 struct peer *peer;
12362 u_char uj = use_json(argc, argv);
12363
12364 peer = peer_lookup_in_view (vty, NULL, argv[idx_peer]->arg, uj);
12365 if (! peer)
12366 return CMD_WARNING;
12367
12368 if (strncmp (argv[idx_safi]->arg, "m", 1) == 0)
12369 return bgp_peer_counts (vty, peer, AFI_IP, SAFI_MULTICAST, uj);
12370
12371 return bgp_peer_counts (vty, peer, AFI_IP, SAFI_UNICAST, uj);
12372 }
12373
12374 DEFUN (show_ip_bgp_vpnv4_neighbor_prefix_counts,
12375 show_ip_bgp_vpnv4_neighbor_prefix_counts_cmd,
12376 "show ip bgp vpnv4 all neighbors <A.B.C.D|X:X::X:X|WORD> prefix-counts [json]",
12377 SHOW_STR
12378 IP_STR
12379 BGP_STR
12380 "Address family\n"
12381 "Address Family modifier\n"
12382 "Address Family modifier\n"
12383 "Detailed information on TCP and BGP neighbor connections\n"
12384 "Neighbor to display information about\n"
12385 "Neighbor to display information about\n"
12386 "Neighbor on bgp configured interface\n"
12387 "Display detailed prefix count information\n"
12388 "JavaScript Object Notation\n")
12389 {
12390 int idx_peer = 6;
12391 struct peer *peer;
12392 u_char uj = use_json(argc, argv);
12393
12394 peer = peer_lookup_in_view (vty, NULL, argv[idx_peer]->arg, uj);
12395 if (! peer)
12396 return CMD_WARNING;
12397
12398 return bgp_peer_counts (vty, peer, AFI_IP, SAFI_MPLS_VPN, uj);
12399 }
12400
12401 static void
12402 show_adj_route (struct vty *vty, struct peer *peer, afi_t afi, safi_t safi,
12403 int in, const char *rmap_name, u_char use_json, json_object *json)
12404 {
12405 struct bgp_table *table;
12406 struct bgp_adj_in *ain;
12407 struct bgp_adj_out *adj;
12408 unsigned long output_count;
12409 unsigned long filtered_count;
12410 struct bgp_node *rn;
12411 int header1 = 1;
12412 struct bgp *bgp;
12413 int header2 = 1;
12414 struct attr attr;
12415 struct attr_extra extra;
12416 int ret;
12417 struct update_subgroup *subgrp;
12418 json_object *json_scode = NULL;
12419 json_object *json_ocode = NULL;
12420 json_object *json_ar = NULL;
12421 struct peer_af *paf;
12422
12423 if (use_json)
12424 {
12425 json_scode = json_object_new_object();
12426 json_ocode = json_object_new_object();
12427 json_ar = json_object_new_object();
12428
12429 json_object_string_add(json_scode, "suppressed", "s");
12430 json_object_string_add(json_scode, "damped", "d");
12431 json_object_string_add(json_scode, "history", "h");
12432 json_object_string_add(json_scode, "valid", "*");
12433 json_object_string_add(json_scode, "best", ">");
12434 json_object_string_add(json_scode, "multipath", "=");
12435 json_object_string_add(json_scode, "internal", "i");
12436 json_object_string_add(json_scode, "ribFailure", "r");
12437 json_object_string_add(json_scode, "stale", "S");
12438 json_object_string_add(json_scode, "removed", "R");
12439
12440 json_object_string_add(json_ocode, "igp", "i");
12441 json_object_string_add(json_ocode, "egp", "e");
12442 json_object_string_add(json_ocode, "incomplete", "?");
12443 }
12444
12445 bgp = peer->bgp;
12446
12447 if (! bgp)
12448 {
12449 if (use_json)
12450 {
12451 json_object_string_add(json, "alert", "no BGP");
12452 vty_out (vty, "%s%s", json_object_to_json_string(json), VTY_NEWLINE);
12453 json_object_free(json);
12454 }
12455 else
12456 vty_out (vty, "%% No bgp%s", VTY_NEWLINE);
12457 return;
12458 }
12459
12460 table = bgp->rib[afi][safi];
12461
12462 output_count = filtered_count = 0;
12463 subgrp = peer_subgroup(peer, afi, safi);
12464
12465 if (!in && subgrp && CHECK_FLAG (subgrp->sflags, SUBGRP_STATUS_DEFAULT_ORIGINATE))
12466 {
12467 if (use_json)
12468 {
12469 json_object_int_add(json, "bgpTableVersion", table->version);
12470 json_object_string_add(json, "bgpLocalRouterId", inet_ntoa (bgp->router_id));
12471 json_object_object_add(json, "bgpStatusCodes", json_scode);
12472 json_object_object_add(json, "bgpOriginCodes", json_ocode);
12473 json_object_string_add(json, "bgpOriginatingDefaultNetwork", "0.0.0.0");
12474 }
12475 else
12476 {
12477 vty_out (vty, "BGP table version is %" PRIu64 ", local router ID is %s%s", table->version, inet_ntoa (bgp->router_id), VTY_NEWLINE);
12478 vty_out (vty, BGP_SHOW_SCODE_HEADER, VTY_NEWLINE, VTY_NEWLINE);
12479 vty_out (vty, BGP_SHOW_OCODE_HEADER, VTY_NEWLINE, VTY_NEWLINE);
12480
12481 vty_out (vty, "Originating default network 0.0.0.0%s%s",
12482 VTY_NEWLINE, VTY_NEWLINE);
12483 }
12484 header1 = 0;
12485 }
12486
12487 attr.extra = &extra;
12488 for (rn = bgp_table_top (table); rn; rn = bgp_route_next (rn))
12489 {
12490 if (in)
12491 {
12492 for (ain = rn->adj_in; ain; ain = ain->next)
12493 {
12494 if (ain->peer == peer)
12495 {
12496 if (header1)
12497 {
12498 if (use_json)
12499 {
12500 json_object_int_add(json, "bgpTableVersion", 0);
12501 json_object_string_add(json, "bgpLocalRouterId", inet_ntoa (bgp->router_id));
12502 json_object_object_add(json, "bgpStatusCodes", json_scode);
12503 json_object_object_add(json, "bgpOriginCodes", json_ocode);
12504 }
12505 else
12506 {
12507 vty_out (vty, "BGP table version is 0, local router ID is %s%s", inet_ntoa (bgp->router_id), VTY_NEWLINE);
12508 vty_out (vty, BGP_SHOW_SCODE_HEADER, VTY_NEWLINE, VTY_NEWLINE);
12509 vty_out (vty, BGP_SHOW_OCODE_HEADER, VTY_NEWLINE, VTY_NEWLINE);
12510 }
12511 header1 = 0;
12512 }
12513 if (header2)
12514 {
12515 if (!use_json)
12516 vty_out (vty, BGP_SHOW_HEADER, VTY_NEWLINE);
12517 header2 = 0;
12518 }
12519 if (ain->attr)
12520 {
12521 bgp_attr_dup(&attr, ain->attr);
12522 if (bgp_input_modifier(peer, &rn->p, &attr, afi, safi, rmap_name) != RMAP_DENY)
12523 {
12524 route_vty_out_tmp (vty, &rn->p, &attr, safi, use_json, json_ar);
12525 output_count++;
12526 }
12527 else
12528 filtered_count++;
12529 }
12530 }
12531 }
12532 }
12533 else
12534 {
12535 for (adj = rn->adj_out; adj; adj = adj->next)
12536 SUBGRP_FOREACH_PEER(adj->subgroup, paf)
12537 if (paf->peer == peer)
12538 {
12539 if (header1)
12540 {
12541 if (use_json)
12542 {
12543 json_object_int_add(json, "bgpTableVersion", table->version);
12544 json_object_string_add(json, "bgpLocalRouterId", inet_ntoa (bgp->router_id));
12545 json_object_object_add(json, "bgpStatusCodes", json_scode);
12546 json_object_object_add(json, "bgpOriginCodes", json_ocode);
12547 }
12548 else
12549 {
12550 vty_out (vty, "BGP table version is %" PRIu64 ", local router ID is %s%s", table->version,
12551 inet_ntoa (bgp->router_id), VTY_NEWLINE);
12552 vty_out (vty, BGP_SHOW_SCODE_HEADER, VTY_NEWLINE, VTY_NEWLINE);
12553 vty_out (vty, BGP_SHOW_OCODE_HEADER, VTY_NEWLINE, VTY_NEWLINE);
12554 }
12555 header1 = 0;
12556 }
12557
12558 if (header2)
12559 {
12560 if (!use_json)
12561 vty_out (vty, BGP_SHOW_HEADER, VTY_NEWLINE);
12562 header2 = 0;
12563 }
12564
12565 if (adj->attr)
12566 {
12567 bgp_attr_dup(&attr, adj->attr);
12568 ret = bgp_output_modifier(peer, &rn->p, &attr, afi, safi, rmap_name);
12569 if (ret != RMAP_DENY)
12570 {
12571 route_vty_out_tmp (vty, &rn->p, &attr, safi, use_json, json_ar);
12572 output_count++;
12573 }
12574 else
12575 filtered_count++;
12576 }
12577 }
12578 }
12579 }
12580 if (use_json)
12581 json_object_object_add(json, "advertisedRoutes", json_ar);
12582
12583 if (output_count != 0)
12584 {
12585 if (use_json)
12586 json_object_int_add(json, "totalPrefixCounter", output_count);
12587 else
12588 vty_out (vty, "%sTotal number of prefixes %ld%s",
12589 VTY_NEWLINE, output_count, VTY_NEWLINE);
12590 }
12591 if (use_json)
12592 {
12593 vty_out (vty, "%s%s", json_object_to_json_string(json), VTY_NEWLINE);
12594 json_object_free(json);
12595 }
12596
12597 }
12598
12599 static int
12600 peer_adj_routes (struct vty *vty, struct peer *peer, afi_t afi, safi_t safi,
12601 int in, const char *rmap_name, u_char use_json)
12602 {
12603 json_object *json = NULL;
12604
12605 if (use_json)
12606 json = json_object_new_object();
12607
12608 if (!peer || !peer->afc[afi][safi])
12609 {
12610 if (use_json)
12611 {
12612 json_object_string_add(json, "warning", "No such neighbor or address family");
12613 vty_out (vty, "%s%s", json_object_to_json_string(json), VTY_NEWLINE);
12614 json_object_free(json);
12615 }
12616 else
12617 vty_out (vty, "%% No such neighbor or address family%s", VTY_NEWLINE);
12618
12619 return CMD_WARNING;
12620 }
12621
12622 if (in && !CHECK_FLAG(peer->af_flags[afi][safi], PEER_FLAG_SOFT_RECONFIG))
12623 {
12624 if (use_json)
12625 {
12626 json_object_string_add(json, "warning", "Inbound soft reconfiguration not enabled");
12627 vty_out (vty, "%s%s", json_object_to_json_string(json), VTY_NEWLINE);
12628 json_object_free(json);
12629 }
12630 else
12631 vty_out (vty, "%% Inbound soft reconfiguration not enabled%s", VTY_NEWLINE);
12632
12633 return CMD_WARNING;
12634 }
12635
12636 show_adj_route (vty, peer, afi, safi, in, rmap_name, use_json, json);
12637
12638 return CMD_SUCCESS;
12639 }
12640
12641 /*
12642 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
12643 * "show ip bgp <view|vrf> WORD neighbors (A.B.C.D|X:X::X:X|WORD) advertised-routes route-map WORD [json]",
12644 * SHOW_STR
12645 * IP_STR
12646 * BGP_STR
12647 * BGP_INSTANCE_HELP_STR
12648 * "Detailed information on TCP and BGP neighbor connections\n"
12649 * "Neighbor to display information about\n"
12650 * "Neighbor to display information about\n"
12651 * "Neighbor on bgp configured interface\n"
12652 * "Display the routes advertised to a BGP neighbor\n"
12653 * "JavaScript Object Notation\n"
12654 *
12655 */
12656 DEFUN (show_ip_bgp_instance_neighbor_advertised_route,
12657 show_ip_bgp_instance_neighbor_advertised_route_cmd,
12658 "show ip bgp <view|vrf> WORD neighbors <A.B.C.D|X:X::X:X|WORD> advertised-routes [json]",
12659 SHOW_STR
12660 IP_STR
12661 BGP_STR
12662 BGP_INSTANCE_HELP_STR
12663 "Detailed information on TCP and BGP neighbor connections\n"
12664 "Neighbor to display information about\n"
12665 "Neighbor to display information about\n"
12666 "Display the routes advertised to a BGP neighbor\n"
12667 "JavaScript Object Notation\n")
12668 {
12669 int idx_word = 4;
12670 int idx_peer = 6;
12671 struct peer *peer;
12672 u_char uj = use_json(argc, argv);
12673
12674 if (argc == 4 || (argc == 3 && argv[idx_peer]->arg && strcmp(argv[idx_peer]->arg, "json") != 0))
12675 peer = peer_lookup_in_view (vty, argv[idx_word]->arg, argv[idx_peer]->arg, uj);
12676 else
12677 peer = peer_lookup_in_view (vty, NULL, argv[idx_word]->arg, uj);
12678
12679 if (! peer)
12680 return CMD_WARNING;
12681
12682 return peer_adj_routes (vty, peer, AFI_IP, SAFI_UNICAST, 0, NULL, uj);
12683 }
12684
12685 /*
12686 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
12687 * "show ip bgp neighbors (A.B.C.D|X:X::X:X|WORD) advertised-routes route-map WORD [json]",
12688 * SHOW_STR
12689 * IP_STR
12690 * BGP_STR
12691 * "Detailed information on TCP and BGP neighbor connections\n"
12692 * "Neighbor to display information about\n"
12693 * "Neighbor to display information about\n"
12694 * "Neighbor on bgp configured interface\n"
12695 * "Display the routes advertised to a BGP neighbor\n"
12696 * "JavaScript Object Notation\n"
12697 *
12698 */
12699 DEFUN (show_ip_bgp_neighbor_advertised_route,
12700 show_ip_bgp_neighbor_advertised_route_cmd,
12701 "show ip bgp neighbors <A.B.C.D|X:X::X:X|WORD> advertised-routes [json]",
12702 SHOW_STR
12703 IP_STR
12704 BGP_STR
12705 "Detailed information on TCP and BGP neighbor connections\n"
12706 "Neighbor to display information about\n"
12707 "Neighbor to display information about\n"
12708 "Neighbor on bgp configured interface\n"
12709 "Display the routes advertised to a BGP neighbor\n"
12710 "JavaScript Object Notation\n")
12711
12712 {
12713 int idx_peer = 4;
12714 int idx_json = 6;
12715 struct peer *peer;
12716 const char *rmap_name = NULL;
12717 u_char uj = use_json(argc, argv);
12718
12719 peer = peer_lookup_in_view (vty, NULL, argv[idx_peer]->arg, uj);
12720
12721 if (! peer)
12722 return CMD_WARNING;
12723
12724 if ((argc == 2 && argv[idx_json]->arg && strcmp(argv[idx_json]->arg, "json") != 0)
12725 || (argc == 3))
12726 rmap_name = argv[idx_json]->arg;
12727
12728 return peer_adj_routes (vty, peer, AFI_IP, SAFI_UNICAST, 0, rmap_name, uj);
12729 }
12730
12731
12732 /*
12733 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
12734 * "show ip bgp ipv4 (unicast|multicast) neighbors (A.B.C.D|X:X::X:X|WORD) advertised-routes route-map WORD [json]",
12735 * SHOW_STR
12736 * IP_STR
12737 * BGP_STR
12738 * "Address family\n"
12739 * "Address Family modifier\n"
12740 * "Address Family modifier\n"
12741 * "Detailed information on TCP and BGP neighbor connections\n"
12742 * "Neighbor to display information about\n"
12743 * "Neighbor to display information about\n"
12744 * "Neighbor on bgp configured interface\n"
12745 * "Display the routes advertised to a BGP neighbor\n"
12746 * "Route-map to control what is displayed\n"
12747 * "JavaScript Object Notation\n"
12748 *
12749 */
12750 DEFUN (show_ip_bgp_ipv4_neighbor_advertised_route,
12751 show_ip_bgp_ipv4_neighbor_advertised_route_cmd,
12752 "show ip bgp ipv4 <unicast|multicast> neighbors <A.B.C.D|X:X::X:X|WORD> advertised-routes [json]",
12753 SHOW_STR
12754 IP_STR
12755 BGP_STR
12756 "Address family\n"
12757 "Address Family modifier\n"
12758 "Address Family modifier\n"
12759 "Detailed information on TCP and BGP neighbor connections\n"
12760 "Neighbor to display information about\n"
12761 "Neighbor to display information about\n"
12762 "Neighbor on bgp configured interface\n"
12763 "Display the routes advertised to a BGP neighbor\n"
12764 "JavaScript Object Notation\n")
12765 {
12766 int idx_safi = 4;
12767 int idx_peer = 6;
12768 int idx_json = 8;
12769 struct peer *peer;
12770 const char *rmap_name = NULL;
12771 u_char uj = use_json(argc, argv);
12772
12773 peer = peer_lookup_in_view (vty, NULL, argv[idx_peer]->arg, uj);
12774 if (! peer)
12775 return CMD_WARNING;
12776
12777 if ((argc == 4) || (argc == 3 && argv[idx_json]->arg && strcmp(argv[idx_json]->arg, "json") != 0))
12778 rmap_name = argv[idx_json]->arg;
12779
12780 if (strncmp (argv[idx_safi]->arg, "m", 1) == 0)
12781 return peer_adj_routes (vty, peer, AFI_IP, SAFI_MULTICAST, 0, rmap_name, uj);
12782 else
12783 return peer_adj_routes (vty, peer, AFI_IP, SAFI_UNICAST, 0, rmap_name, uj);
12784 }
12785
12786
12787 #ifdef HAVE_IPV6
12788 /*
12789 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
12790 * "show bgp <view|vrf> WORD ipv6 neighbors (A.B.C.D|X:X::X:X|WORD) advertised-routes [json]",
12791 * SHOW_STR
12792 * BGP_STR
12793 * BGP_INSTANCE_HELP_STR
12794 * "Address family\n"
12795 * "Detailed information on TCP and BGP neighbor connections\n"
12796 * "Neighbor to display information about\n"
12797 * "Neighbor to display information about\n"
12798 * "Neighbor on bgp configured interface\n"
12799 * "Display the routes advertised to a BGP neighbor\n"
12800 * "JavaScript Object Notation\n"
12801 *
12802 */
12803 DEFUN (show_bgp_instance_neighbor_advertised_route,
12804 show_bgp_instance_neighbor_advertised_route_cmd,
12805 "show bgp <view|vrf> WORD neighbors <A.B.C.D|X:X::X:X|WORD> advertised-routes [json]",
12806 SHOW_STR
12807 BGP_STR
12808 BGP_INSTANCE_HELP_STR
12809 "Detailed information on TCP and BGP neighbor connections\n"
12810 "Neighbor to display information about\n"
12811 "Neighbor to display information about\n"
12812 "Neighbor on bgp configured interface\n"
12813 "Display the routes advertised to a BGP neighbor\n"
12814 "JavaScript Object Notation\n")
12815 {
12816 int idx_word = 3;
12817 int idx_peer = 5;
12818 struct peer *peer;
12819 u_char uj = use_json(argc, argv);
12820
12821 if (argc == 4 || (argc == 3 && argv[idx_peer]->arg && strcmp(argv[idx_peer]->arg, "json") != 0))
12822 peer = peer_lookup_in_view (vty, argv[idx_word]->arg, argv[idx_peer]->arg, uj);
12823 else
12824 peer = peer_lookup_in_view (vty, NULL, argv[idx_word]->arg, uj);
12825
12826 if (! peer)
12827 return CMD_WARNING;
12828
12829 return peer_adj_routes (vty, peer, AFI_IP6, SAFI_UNICAST, 0, NULL, uj);
12830 }
12831
12832
12833 /*
12834 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
12835 * "show bgp ipv6 neighbors (A.B.C.D|X:X::X:X|WORD) advertised-routes [json]",
12836 * SHOW_STR
12837 * BGP_STR
12838 * "Address family\n"
12839 * "Detailed information on TCP and BGP neighbor connections\n"
12840 * "Neighbor to display information about\n"
12841 * "Neighbor to display information about\n"
12842 * "Neighbor on bgp configured interface\n"
12843 * "Display the routes advertised to a BGP neighbor\n"
12844 * "JavaScript Object Notation\n"
12845 *
12846 * "show ipv6 bgp neighbors (A.B.C.D|X:X::X:X|WORD) advertised-routes [json]",
12847 * SHOW_STR
12848 * IPV6_STR
12849 * BGP_STR
12850 * "Detailed information on TCP and BGP neighbor connections\n"
12851 * "Neighbor to display information about\n"
12852 * "Neighbor to display information about\n"
12853 * "Neighbor on bgp configured interface\n"
12854 * "Display the routes advertised to a BGP neighbor\n"
12855 * "JavaScript Object Notation\n"
12856 *
12857 */
12858 DEFUN (show_bgp_neighbor_advertised_route,
12859 show_bgp_neighbor_advertised_route_cmd,
12860 "show bgp neighbors <A.B.C.D|X:X::X:X|WORD> advertised-routes [json]",
12861 SHOW_STR
12862 BGP_STR
12863 "Detailed information on TCP and BGP neighbor connections\n"
12864 "Neighbor to display information about\n"
12865 "Neighbor to display information about\n"
12866 "Neighbor on bgp configured interface\n"
12867 "Display the routes advertised to a BGP neighbor\n"
12868 "JavaScript Object Notation\n")
12869
12870 {
12871 int idx_peer = 3;
12872 int idx_json = 5;
12873 struct peer *peer;
12874 const char *rmap_name = NULL;
12875 u_char uj = use_json(argc, argv);
12876
12877 peer = peer_lookup_in_view (vty, NULL, argv[idx_peer]->arg, uj);
12878
12879 if (!peer)
12880 return CMD_WARNING;
12881
12882 if (argc == 3 || (argc == 2 && argv[idx_json]->arg && strcmp(argv[idx_json]->arg, "json") != 0))
12883 rmap_name = argv[idx_json]->arg;
12884
12885 return peer_adj_routes (vty, peer, AFI_IP6, SAFI_UNICAST, 0, rmap_name, uj);
12886 }
12887
12888
12889 /* old command */
12890
12891 /* old command */
12892 DEFUN (ipv6_mbgp_neighbor_advertised_route,
12893 ipv6_mbgp_neighbor_advertised_route_cmd,
12894 "show ipv6 mbgp neighbors <A.B.C.D|X:X::X:X|WORD> advertised-routes [json]",
12895 SHOW_STR
12896 IPV6_STR
12897 MBGP_STR
12898 "Detailed information on TCP and BGP neighbor connections\n"
12899 "Neighbor to display information about\n"
12900 "Neighbor to display information about\n"
12901 "Neighbor on bgp configured interface\n"
12902 "Neighbor on bgp configured interface\n"
12903 "Display the routes advertised to a BGP neighbor\n"
12904 "JavaScript Object Notation\n")
12905 {
12906 int idx_peer = 4;
12907 struct peer *peer;
12908 u_char uj = use_json(argc, argv);
12909
12910 peer = peer_lookup_in_view (vty, NULL, argv[idx_peer]->arg, uj);
12911 if (! peer)
12912 return CMD_WARNING;
12913
12914 bgp_show_ipv6_bgp_deprecate_warning(vty);
12915 return peer_adj_routes (vty, peer, AFI_IP6, SAFI_MULTICAST, 0, NULL, uj);
12916 }
12917 #endif /* HAVE_IPV6 */
12918
12919 /*
12920 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
12921 * "show bgp <view|vrf> WORD ipv6 neighbors (A.B.C.D|X:X::X:X|WORD) received-routes [json]",
12922 * SHOW_STR
12923 * BGP_STR
12924 * BGP_INSTANCE_HELP_STR
12925 * "Address family\n"
12926 * "Detailed information on TCP and BGP neighbor connections\n"
12927 * "Neighbor to display information about\n"
12928 * "Neighbor to display information about\n"
12929 * "Neighbor on bgp configured interface\n"
12930 * "Display the received routes from neighbor\n"
12931 * "JavaScript Object Notation\n"
12932 *
12933 */
12934 DEFUN (show_bgp_instance_neighbor_received_routes,
12935 show_bgp_instance_neighbor_received_routes_cmd,
12936 "show bgp <view|vrf> WORD neighbors <A.B.C.D|X:X::X:X|WORD> received-routes [json]",
12937 SHOW_STR
12938 BGP_STR
12939 BGP_INSTANCE_HELP_STR
12940 "Detailed information on TCP and BGP neighbor connections\n"
12941 "Neighbor to display information about\n"
12942 "Neighbor to display information about\n"
12943 "Neighbor on bgp configured interface\n"
12944 "Display the received routes from neighbor\n"
12945 "JavaScript Object Notation\n")
12946 {
12947 int idx_word = 3;
12948 int idx_peer = 5;
12949 struct peer *peer;
12950 u_char uj = use_json(argc, argv);
12951
12952 peer = peer_lookup_in_view (vty, argv[idx_word]->arg, argv[idx_peer]->arg, uj);
12953 if (! peer)
12954 return CMD_WARNING;
12955
12956 return peer_adj_routes (vty, peer, AFI_IP6, SAFI_UNICAST, 1, NULL, uj);
12957 }
12958
12959 /*
12960 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
12961 * "show ip bgp <view|vrf> WORD neighbors (A.B.C.D|X:X::X:X|WORD) received-routes route-map WORD [json]",
12962 * SHOW_STR
12963 * IP_STR
12964 * BGP_STR
12965 * BGP_INSTANCE_HELP_STR
12966 * "Detailed information on TCP and BGP neighbor connections\n"
12967 * "Neighbor to display information about\n"
12968 * "Neighbor to display information about\n"
12969 * "Neighbor on bgp configured interface\n"
12970 * "Display the received routes from neighbor\n"
12971 * "JavaScript Object Notation\n"
12972 *
12973 */
12974 DEFUN (show_ip_bgp_instance_neighbor_received_routes,
12975 show_ip_bgp_instance_neighbor_received_routes_cmd,
12976 "show ip bgp <view|vrf> WORD neighbors <A.B.C.D|X:X::X:X|WORD> received-routes [json]",
12977 SHOW_STR
12978 IP_STR
12979 BGP_STR
12980 BGP_INSTANCE_HELP_STR
12981 "Detailed information on TCP and BGP neighbor connections\n"
12982 "Neighbor to display information about\n"
12983 "Neighbor to display information about\n"
12984 "Neighbor on bgp configured interface\n"
12985 "Display the received routes from neighbor\n"
12986 "JavaScript Object Notation\n")
12987 {
12988 int idx_word = 4;
12989 int idx_peer = 6;
12990 struct peer *peer;
12991 u_char uj = use_json(argc, argv);
12992
12993 peer = peer_lookup_in_view (vty, argv[idx_word]->arg, argv[idx_peer]->arg, uj);
12994 if (! peer)
12995 return CMD_WARNING;
12996
12997 return peer_adj_routes (vty, peer, AFI_IP, SAFI_UNICAST, 1, NULL, uj);
12998 }
12999
13000
13001 /*
13002 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
13003 * "show ip bgp neighbors (A.B.C.D|X:X::X:X|WORD) received-routes route-map WORD [json]",
13004 * SHOW_STR
13005 * IP_STR
13006 * BGP_STR
13007 * "Detailed information on TCP and BGP neighbor connections\n"
13008 * "Neighbor to display information about\n"
13009 * "Neighbor to display information about\n"
13010 * "Neighbor on bgp configured interface\n"
13011 * "Display the received routes from neighbor\n"
13012 * "JavaScript Object Notation\n"
13013 *
13014 */
13015 DEFUN (show_ip_bgp_neighbor_received_routes,
13016 show_ip_bgp_neighbor_received_routes_cmd,
13017 "show ip bgp neighbors <A.B.C.D|X:X::X:X|WORD> received-routes [json]",
13018 SHOW_STR
13019 IP_STR
13020 BGP_STR
13021 "Detailed information on TCP and BGP neighbor connections\n"
13022 "Neighbor to display information about\n"
13023 "Neighbor to display information about\n"
13024 "Neighbor on bgp configured interface\n"
13025 "Display the received routes from neighbor\n"
13026 "JavaScript Object Notation\n")
13027
13028 {
13029 int idx_peer = 4;
13030 int idx_json = 6;
13031 struct peer *peer;
13032 const char *rmap_name = NULL;
13033 u_char uj = use_json(argc, argv);
13034
13035 peer = peer_lookup_in_view (vty, NULL, argv[idx_peer]->arg, uj);
13036
13037 if (! peer)
13038 return CMD_WARNING;
13039
13040 if (argc == 3 || (argc == 2 && argv[idx_json]->arg && strcmp(argv[idx_json]->arg, "json") != 0))
13041 rmap_name = argv[idx_json]->arg;
13042
13043 return peer_adj_routes (vty, peer, AFI_IP, SAFI_UNICAST, 1, rmap_name, uj);
13044 }
13045
13046
13047
13048 /*
13049 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
13050 * "show ip bgp ipv4 (unicast|multicast) neighbors (A.B.C.D|X:X::X:X|WORD) received-routes route-map WORD [json]",
13051 * SHOW_STR
13052 * IP_STR
13053 * BGP_STR
13054 * "Address family\n"
13055 * "Address Family modifier\n"
13056 * "Address Family modifier\n"
13057 * "Detailed information on TCP and BGP neighbor connections\n"
13058 * "Neighbor to display information about\n"
13059 * "Neighbor to display information about\n"
13060 * "Neighbor on bgp configured interface\n"
13061 * "Display the received routes from neighbor\n"
13062 * "JavaScript Object Notation\n"
13063 *
13064 */
13065 DEFUN (show_ip_bgp_ipv4_neighbor_received_routes,
13066 show_ip_bgp_ipv4_neighbor_received_routes_cmd,
13067 "show ip bgp ipv4 <unicast|multicast> neighbors <A.B.C.D|X:X::X:X|WORD> received-routes [json]",
13068 SHOW_STR
13069 IP_STR
13070 BGP_STR
13071 "Address family\n"
13072 "Address Family modifier\n"
13073 "Address Family modifier\n"
13074 "Detailed information on TCP and BGP neighbor connections\n"
13075 "Neighbor to display information about\n"
13076 "Neighbor to display information about\n"
13077 "Neighbor on bgp configured interface\n"
13078 "Display the received routes from neighbor\n"
13079 "JavaScript Object Notation\n")
13080 {
13081 int idx_safi = 4;
13082 int idx_peer = 6;
13083 int idx_json = 8;
13084 struct peer *peer;
13085 const char *rmap_name = NULL;
13086 u_char uj = use_json(argc, argv);
13087
13088 peer = peer_lookup_in_view (vty, NULL, argv[idx_peer]->arg, uj);
13089 if (! peer)
13090 return CMD_WARNING;
13091
13092 if (argc == 4 || (argc == 3 && argv[idx_json]->arg && strcmp(argv[idx_json]->arg, "json") != 0))
13093 rmap_name = argv[idx_json]->arg;
13094
13095 if (strncmp (argv[idx_safi]->arg, "m", 1) == 0)
13096 return peer_adj_routes (vty, peer, AFI_IP, SAFI_MULTICAST, 1, rmap_name, uj);
13097 else
13098 return peer_adj_routes (vty, peer, AFI_IP, SAFI_UNICAST, 1, rmap_name, uj);
13099 }
13100
13101
13102 DEFUN (show_bgp_instance_afi_safi_neighbor_adv_recd_routes,
13103 show_bgp_instance_afi_safi_neighbor_adv_recd_routes_cmd,
13104 "show bgp <view|vrf> WORD <ipv4|ipv6> <unicast|multicast> neighbors <A.B.C.D|X:X::X:X|WORD> <advertised-routes|received-routes> [json]",
13105 SHOW_STR
13106 BGP_STR
13107 BGP_INSTANCE_HELP_STR
13108 "Address family\n"
13109 "Address family\n"
13110 "Address family modifier\n"
13111 "Address family modifier\n"
13112 "Detailed information on TCP and BGP neighbor connections\n"
13113 "Neighbor to display information about\n"
13114 "Neighbor to display information about\n"
13115 "Neighbor on bgp configured interface\n"
13116 "Display the advertised routes to neighbor\n"
13117 "Display the received routes from neighbor\n"
13118 "JavaScript Object Notation\n")
13119 {
13120 int idx_word = 3;
13121 int idx_afi = 4;
13122 int idx_safi = 5;
13123 int idx_peer = 7;
13124 int idx_adv_rcvd_routes = 8;
13125 int afi;
13126 int safi;
13127 int in;
13128 struct peer *peer;
13129 u_char uj = use_json(argc, argv);
13130
13131 peer = peer_lookup_in_view (vty, argv[idx_word]->arg, argv[idx_peer]->arg, uj);
13132
13133 if (! peer)
13134 return CMD_WARNING;
13135
13136 afi = (strncmp (argv[idx_afi]->arg, "ipv6", 4) == 0) ? AFI_IP6 : AFI_IP;
13137 safi = (strncmp (argv[idx_safi]->arg, "m", 1) == 0) ? SAFI_MULTICAST : SAFI_UNICAST;
13138 in = (strncmp (argv[idx_adv_rcvd_routes]->arg, "r", 1) == 0) ? 1 : 0;
13139
13140 return peer_adj_routes (vty, peer, afi, safi, in, NULL, uj);
13141 }
13142
13143 DEFUN (show_ip_bgp_neighbor_received_prefix_filter,
13144 show_ip_bgp_neighbor_received_prefix_filter_cmd,
13145 "show ip bgp neighbors <A.B.C.D|X:X::X:X|WORD> received prefix-filter [json]",
13146 SHOW_STR
13147 IP_STR
13148 BGP_STR
13149 "Detailed information on TCP and BGP neighbor connections\n"
13150 "Neighbor to display information about\n"
13151 "Neighbor to display information about\n"
13152 "Neighbor on bgp configured interface\n"
13153 "Display information received from a BGP neighbor\n"
13154 "Display the prefixlist filter\n"
13155 "JavaScript Object Notation\n")
13156 {
13157 int idx_peer = 4;
13158 char name[BUFSIZ];
13159 union sockunion su;
13160 struct peer *peer;
13161 int count, ret;
13162 u_char uj = use_json(argc, argv);
13163
13164 ret = str2sockunion (argv[idx_peer]->arg, &su);
13165 if (ret < 0)
13166 {
13167 peer = peer_lookup_by_conf_if (NULL, argv[idx_peer]->arg);
13168 if (! peer)
13169 {
13170 if (uj)
13171 {
13172 json_object *json_no = NULL;
13173 json_object *json_sub = NULL;
13174 json_no = json_object_new_object();
13175 json_sub = json_object_new_object();
13176 json_object_string_add(json_no, "warning", "Malformed address or name");
13177 json_object_string_add(json_sub, "warningCause", argv[idx_peer]->arg);
13178 json_object_object_add(json_no, "detail", json_sub);
13179 vty_out (vty, "%s%s", json_object_to_json_string(json_no), VTY_NEWLINE);
13180 json_object_free(json_no);
13181 }
13182 else
13183 vty_out (vty, "%% Malformed address or name: %s%s", argv[idx_peer]->arg, VTY_NEWLINE);
13184 return CMD_WARNING;
13185 }
13186 }
13187 else
13188 {
13189 peer = peer_lookup (NULL, &su);
13190 if (! peer)
13191 {
13192 if (uj)
13193 {
13194 json_object *json_no = NULL;
13195 json_no = json_object_new_object();
13196 json_object_string_add(json_no, "warning", "Peer not found");
13197 vty_out (vty, "%s%s", json_object_to_json_string(json_no), VTY_NEWLINE);
13198 json_object_free(json_no);
13199 }
13200 else
13201 vty_out (vty, "No peer%s", VTY_NEWLINE);
13202 return CMD_WARNING;
13203 }
13204 }
13205
13206 sprintf (name, "%s.%d.%d", peer->host, AFI_IP, SAFI_UNICAST);
13207 count = prefix_bgp_show_prefix_list (NULL, AFI_IP, name, uj);
13208 if (count)
13209 {
13210 if (!uj)
13211 vty_out (vty, "Address family: IPv4 Unicast%s", VTY_NEWLINE);
13212 prefix_bgp_show_prefix_list (vty, AFI_IP, name, uj);
13213 }
13214 else
13215 {
13216 if (uj)
13217 {
13218 json_object *json_no = NULL;
13219 json_no = json_object_new_object();
13220 json_object_boolean_true_add(json_no, "noFuntionalOutput");
13221 vty_out (vty, "%s%s", json_object_to_json_string(json_no), VTY_NEWLINE);
13222 json_object_free(json_no);
13223 }
13224 else
13225 vty_out (vty, "No functional output%s", VTY_NEWLINE);
13226 }
13227
13228 return CMD_SUCCESS;
13229 }
13230
13231 DEFUN (show_ip_bgp_ipv4_neighbor_received_prefix_filter,
13232 show_ip_bgp_ipv4_neighbor_received_prefix_filter_cmd,
13233 "show ip bgp ipv4 <unicast|multicast> neighbors <A.B.C.D|X:X::X:X|WORD> received prefix-filter [json]",
13234 SHOW_STR
13235 IP_STR
13236 BGP_STR
13237 "Address family\n"
13238 "Address Family modifier\n"
13239 "Address Family modifier\n"
13240 "Detailed information on TCP and BGP neighbor connections\n"
13241 "Neighbor to display information about\n"
13242 "Neighbor to display information about\n"
13243 "Neighbor on bgp configured interface\n"
13244 "Display information received from a BGP neighbor\n"
13245 "Display the prefixlist filter\n"
13246 "JavaScript Object Notation\n")
13247 {
13248 int idx_safi = 4;
13249 int idx_peer = 6;
13250 char name[BUFSIZ];
13251 union sockunion su;
13252 struct peer *peer;
13253 int count, ret;
13254 u_char uj = use_json(argc, argv);
13255
13256 ret = str2sockunion (argv[idx_peer]->arg, &su);
13257 if (ret < 0)
13258 {
13259 peer = peer_lookup_by_conf_if (NULL, argv[idx_peer]->arg);
13260 if (! peer)
13261 {
13262 if (uj)
13263 {
13264 json_object *json_no = NULL;
13265 json_object *json_sub = NULL;
13266 json_no = json_object_new_object();
13267 json_sub = json_object_new_object();
13268 json_object_string_add(json_no, "warning", "Malformed address or name");
13269 json_object_string_add(json_sub, "warningCause", argv[idx_peer]->arg);
13270 json_object_object_add(json_no, "detail", json_sub);
13271 vty_out (vty, "%s%s", json_object_to_json_string(json_no), VTY_NEWLINE);
13272 json_object_free(json_no);
13273 }
13274 else
13275 vty_out (vty, "%% Malformed address or name: %s%s", argv[idx_peer]->arg, VTY_NEWLINE);
13276 return CMD_WARNING;
13277 }
13278 }
13279 else
13280 {
13281 peer = peer_lookup (NULL, &su);
13282 if (! peer)
13283 {
13284 if (uj)
13285 {
13286 json_object *json_no = NULL;
13287 json_no = json_object_new_object();
13288 json_object_string_add(json_no, "warning", "Peer not found");
13289 vty_out (vty, "%s%s", json_object_to_json_string(json_no), VTY_NEWLINE);
13290 json_object_free(json_no);
13291 }
13292 else
13293 vty_out (vty, "No peer%s", VTY_NEWLINE);
13294 return CMD_WARNING;
13295 }
13296 }
13297
13298 if (strncmp (argv[idx_safi]->arg, "m", 1) == 0)
13299 {
13300 sprintf (name, "%s.%d.%d", peer->host, AFI_IP, SAFI_MULTICAST);
13301 count = prefix_bgp_show_prefix_list (NULL, AFI_IP, name, uj);
13302 if (count)
13303 {
13304 if (!uj)
13305 vty_out (vty, "Address family: IPv4 Multicast%s", VTY_NEWLINE);
13306 prefix_bgp_show_prefix_list (vty, AFI_IP, name, uj);
13307 }
13308 else
13309 {
13310 if (uj)
13311 {
13312 json_object *json_no = NULL;
13313 json_no = json_object_new_object();
13314 json_object_boolean_true_add(json_no, "noFuntionalOutput");
13315 vty_out (vty, "%s%s", json_object_to_json_string(json_no), VTY_NEWLINE);
13316 json_object_free(json_no);
13317 }
13318 else
13319 vty_out (vty, "No functional output%s", VTY_NEWLINE);
13320 }
13321 }
13322 else
13323 {
13324 sprintf (name, "%s.%d.%d", peer->host, AFI_IP, SAFI_UNICAST);
13325 count = prefix_bgp_show_prefix_list (NULL, AFI_IP, name, uj);
13326 if (count)
13327 {
13328 if (!uj)
13329 vty_out (vty, "Address family: IPv4 Unicast%s", VTY_NEWLINE);
13330 prefix_bgp_show_prefix_list (vty, AFI_IP, name, uj);
13331 }
13332 else
13333 {
13334 if (uj)
13335 {
13336 json_object *json_no = NULL;
13337 json_no = json_object_new_object();
13338 json_object_boolean_true_add(json_no, "noFuntionalOutput");
13339 vty_out (vty, "%s%s", json_object_to_json_string(json_no), VTY_NEWLINE);
13340 json_object_free(json_no);
13341 }
13342 else
13343 vty_out (vty, "No functional output%s", VTY_NEWLINE);
13344 }
13345 }
13346
13347 return CMD_SUCCESS;
13348 }
13349 #ifdef HAVE_IPV6
13350 /*
13351 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
13352 * "show bgp ipv6 neighbors (A.B.C.D|X:X::X:X|WORD) received-routes [json]",
13353 * SHOW_STR
13354 * BGP_STR
13355 * "Address family\n"
13356 * "Detailed information on TCP and BGP neighbor connections\n"
13357 * "Neighbor to display information about\n"
13358 * "Neighbor to display information about\n"
13359 * "Neighbor on bgp configured interface\n"
13360 * "Display the received routes from neighbor\n"
13361 * "JavaScript Object Notation\n"
13362 *
13363 * "show ipv6 bgp neighbors (A.B.C.D|X:X::X:X|WORD) received-routes [json]",
13364 * SHOW_STR
13365 * IPV6_STR
13366 * BGP_STR
13367 * "Detailed information on TCP and BGP neighbor connections\n"
13368 * "Neighbor to display information about\n"
13369 * "Neighbor to display information about\n"
13370 * "Neighbor on bgp configured interface\n"
13371 * "Display the received routes from neighbor\n"
13372 * "JavaScript Object Notation\n"
13373 *
13374 */
13375 DEFUN (show_bgp_neighbor_received_routes,
13376 show_bgp_neighbor_received_routes_cmd,
13377 "show bgp neighbors <A.B.C.D|X:X::X:X|WORD> received-routes [json]",
13378 SHOW_STR
13379 BGP_STR
13380 "Detailed information on TCP and BGP neighbor connections\n"
13381 "Neighbor to display information about\n"
13382 "Neighbor to display information about\n"
13383 "Neighbor on bgp configured interface\n"
13384 "Display the received routes from neighbor\n"
13385 "JavaScript Object Notation\n")
13386 {
13387 int idx_peer = 3;
13388 int idx_json = 5;
13389 struct peer *peer;
13390 const char *rmap_name = NULL;
13391 u_char uj = use_json(argc, argv);
13392
13393 peer = peer_lookup_in_view (vty, NULL, argv[idx_peer]->arg, uj);
13394
13395 if (! peer)
13396 return CMD_WARNING;
13397
13398 if (argc == 3 || (argc == 2 && argv[idx_json]->arg && strcmp(argv[idx_json]->arg, "json") != 0))
13399 rmap_name = argv[idx_json]->arg;
13400
13401 return peer_adj_routes (vty, peer, AFI_IP6, SAFI_UNICAST, 1, rmap_name, uj);
13402 }
13403
13404
13405 /*
13406 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
13407 * "show bgp ipv6 neighbors (A.B.C.D|X:X::X:X|WORD) received prefix-filter [json]",
13408 * SHOW_STR
13409 * BGP_STR
13410 * "Address family\n"
13411 * "Detailed information on TCP and BGP neighbor connections\n"
13412 * "Neighbor to display information about\n"
13413 * "Neighbor to display information about\n"
13414 * "Neighbor on bgp configured interface\n"
13415 * "Display information received from a BGP neighbor\n"
13416 * "Display the prefixlist filter\n"
13417 * "JavaScript Object Notation\n"
13418 *
13419 */
13420 DEFUN (show_bgp_neighbor_received_prefix_filter,
13421 show_bgp_neighbor_received_prefix_filter_cmd,
13422 "show bgp neighbors <A.B.C.D|X:X::X:X|WORD> received prefix-filter [json]",
13423 SHOW_STR
13424 BGP_STR
13425 "Detailed information on TCP and BGP neighbor connections\n"
13426 "Neighbor to display information about\n"
13427 "Neighbor to display information about\n"
13428 "Neighbor on bgp configured interface\n"
13429 "Display information received from a BGP neighbor\n"
13430 "Display the prefixlist filter\n"
13431 "JavaScript Object Notation\n")
13432 {
13433 int idx_peer = 3;
13434 char name[BUFSIZ];
13435 union sockunion su;
13436 struct peer *peer;
13437 int count, ret;
13438 u_char uj = use_json(argc, argv);
13439
13440 ret = str2sockunion (argv[idx_peer]->arg, &su);
13441 if (ret < 0)
13442 {
13443 peer = peer_lookup_by_conf_if (NULL, argv[idx_peer]->arg);
13444 if (! peer)
13445 {
13446 if (uj)
13447 {
13448 json_object *json_no = NULL;
13449 json_object *json_sub = NULL;
13450 json_no = json_object_new_object();
13451 json_sub = json_object_new_object();
13452 json_object_string_add(json_no, "warning", "Malformed address or name");
13453 json_object_string_add(json_sub, "warningCause", argv[idx_peer]->arg);
13454 json_object_object_add(json_no, "detail", json_sub);
13455 vty_out (vty, "%s%s", json_object_to_json_string(json_no), VTY_NEWLINE);
13456 json_object_free(json_no);
13457 }
13458 else
13459 vty_out (vty, "%% Malformed address or name: %s%s", argv[idx_peer]->arg, VTY_NEWLINE);
13460 return CMD_WARNING;
13461 }
13462 }
13463 else
13464 {
13465 peer = peer_lookup (NULL, &su);
13466 if (! peer)
13467 {
13468 if (uj)
13469 {
13470 json_object *json_no = NULL;
13471 json_no = json_object_new_object();
13472 json_object_string_add(json_no, "warning", "No Peer");
13473 vty_out (vty, "%s%s", json_object_to_json_string(json_no), VTY_NEWLINE);
13474 json_object_free(json_no);
13475 }
13476 else
13477 vty_out (vty, "No peer%s", VTY_NEWLINE);
13478 return CMD_WARNING;
13479 }
13480 }
13481
13482 sprintf (name, "%s.%d.%d", peer->host, AFI_IP6, SAFI_UNICAST);
13483 count = prefix_bgp_show_prefix_list (NULL, AFI_IP6, name, uj);
13484 if (count)
13485 {
13486 if (!uj)
13487 vty_out (vty, "Address family: IPv6 Unicast%s", VTY_NEWLINE);
13488 prefix_bgp_show_prefix_list (vty, AFI_IP6, name, uj);
13489 }
13490 else
13491 {
13492 if (uj)
13493 {
13494 json_object *json_no = NULL;
13495 json_no = json_object_new_object();
13496 json_object_boolean_true_add(json_no, "noFuntionalOutput");
13497 vty_out (vty, "%s%s", json_object_to_json_string(json_no), VTY_NEWLINE);
13498 json_object_free(json_no);
13499 }
13500 else
13501 vty_out (vty, "No functional output%s", VTY_NEWLINE);
13502 }
13503
13504 return CMD_SUCCESS;
13505 }
13506
13507
13508 /* old command */
13509
13510 /* old command */
13511 DEFUN (ipv6_mbgp_neighbor_received_routes,
13512 ipv6_mbgp_neighbor_received_routes_cmd,
13513 "show ipv6 mbgp neighbors <A.B.C.D|X:X::X:X|WORD> received-routes [json]",
13514 SHOW_STR
13515 IPV6_STR
13516 MBGP_STR
13517 "Detailed information on TCP and BGP neighbor connections\n"
13518 "Neighbor to display information about\n"
13519 "Neighbor to display information about\n"
13520 "Neighbor on bgp configured interface\n"
13521 "Display the received routes from neighbor\n"
13522 "JavaScript Object Notation\n")
13523 {
13524 int idx_peer = 4;
13525 struct peer *peer;
13526 u_char uj = use_json(argc, argv);
13527
13528 peer = peer_lookup_in_view (vty, NULL, argv[idx_peer]->arg, uj);
13529 if (! peer)
13530 return CMD_WARNING;
13531
13532 bgp_show_ipv6_bgp_deprecate_warning(vty);
13533 return peer_adj_routes (vty, peer, AFI_IP6, SAFI_MULTICAST, 1, NULL, uj);
13534 }
13535
13536 /*
13537 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
13538 * "show bgp <view|vrf> WORD ipv6 neighbors (A.B.C.D|X:X::X:X|WORD) received prefix-filter [json]",
13539 * SHOW_STR
13540 * BGP_STR
13541 * BGP_INSTANCE_HELP_STR
13542 * "Address family\n"
13543 * "Detailed information on TCP and BGP neighbor connections\n"
13544 * "Neighbor to display information about\n"
13545 * "Neighbor to display information about\n"
13546 * "Neighbor on bgp configured interface\n"
13547 * "Display information received from a BGP neighbor\n"
13548 * "Display the prefixlist filter\n"
13549 * "JavaScript Object NOtation\n"
13550 *
13551 */
13552 DEFUN (show_bgp_instance_neighbor_received_prefix_filter,
13553 show_bgp_instance_neighbor_received_prefix_filter_cmd,
13554 "show bgp <view|vrf> WORD neighbors <A.B.C.D|X:X::X:X|WORD> received prefix-filter [json]",
13555 SHOW_STR
13556 BGP_STR
13557 BGP_INSTANCE_HELP_STR
13558 "Detailed information on TCP and BGP neighbor connections\n"
13559 "Neighbor to display information about\n"
13560 "Neighbor to display information about\n"
13561 "Neighbor on bgp configured interface\n"
13562 "Display information received from a BGP neighbor\n"
13563 "Display the prefixlist filter\n"
13564 "JavaScript Object Notation\n")
13565 {
13566 int idx_word = 3;
13567 int idx_peer = 5;
13568 char name[BUFSIZ];
13569 union sockunion su;
13570 struct peer *peer;
13571 struct bgp *bgp;
13572 int count, ret;
13573 u_char uj = use_json(argc, argv);
13574
13575 /* BGP structure lookup. */
13576 bgp = bgp_lookup_by_name (argv[idx_word]->arg);
13577 if (bgp == NULL)
13578 {
13579 if (uj)
13580 {
13581 json_object *json_no = NULL;
13582 json_no = json_object_new_object();
13583 json_object_string_add(json_no, "warning", "Can't find BGP view");
13584 vty_out (vty, "%s%s", json_object_to_json_string(json_no), VTY_NEWLINE);
13585 json_object_free(json_no);
13586 }
13587 else
13588 vty_out (vty, "Can't find BGP instance %s%s", argv[idx_word]->arg, VTY_NEWLINE);
13589 return CMD_WARNING;
13590 }
13591
13592 ret = str2sockunion (argv[idx_peer]->arg, &su);
13593 if (ret < 0)
13594 {
13595 peer = peer_lookup_by_conf_if (bgp, argv[idx_peer]->arg);
13596 if (! peer)
13597 {
13598 if (uj)
13599 {
13600 json_object *json_no = NULL;
13601 json_object *json_sub = NULL;
13602 json_no = json_object_new_object();
13603 json_sub = json_object_new_object();
13604 json_object_string_add(json_no, "warning", "Malformed address or name");
13605 json_object_string_add(json_sub, "warningCause", argv[idx_peer]->arg);
13606 json_object_object_add(json_no, "detail", json_sub);
13607 vty_out (vty, "%s%s", json_object_to_json_string(json_no), VTY_NEWLINE);
13608 json_object_free(json_no);
13609 }
13610 else
13611 vty_out (vty, "%% Malformed address or name: %s%s", argv[idx_peer]->arg, VTY_NEWLINE);
13612 return CMD_WARNING;
13613 }
13614 }
13615 else
13616 {
13617 peer = peer_lookup (bgp, &su);
13618 if (! peer)
13619 {
13620 if (uj)
13621 {
13622 json_object *json_no = NULL;
13623 json_no = json_object_new_object();
13624 json_object_boolean_true_add(json_no, "noPeer");
13625 vty_out (vty, "%s%s", json_object_to_json_string(json_no), VTY_NEWLINE);
13626 json_object_free(json_no);
13627 }
13628 else
13629 vty_out (vty, "No peer%s", VTY_NEWLINE);
13630 return CMD_WARNING;
13631 }
13632
13633 }
13634
13635 sprintf (name, "%s.%d.%d", peer->host, AFI_IP6, SAFI_UNICAST);
13636 count = prefix_bgp_show_prefix_list (NULL, AFI_IP6, name, uj);
13637 if (count)
13638 {
13639 if (!uj)
13640 vty_out (vty, "Address family: IPv6 Unicast%s", VTY_NEWLINE);
13641 prefix_bgp_show_prefix_list (vty, AFI_IP6, name, uj);
13642 }
13643
13644 return CMD_SUCCESS;
13645 }
13646 #endif /* HAVE_IPV6 */
13647
13648 static int
13649 bgp_show_neighbor_route (struct vty *vty, struct peer *peer, afi_t afi,
13650 safi_t safi, enum bgp_show_type type, u_char use_json)
13651 {
13652 if (! peer || ! peer->afc[afi][safi])
13653 {
13654 if (use_json)
13655 {
13656 json_object *json_no = NULL;
13657 json_no = json_object_new_object();
13658 json_object_string_add(json_no, "warning", "No such neighbor or address family");
13659 vty_out (vty, "%s%s", json_object_to_json_string(json_no), VTY_NEWLINE);
13660 json_object_free(json_no);
13661 }
13662 else
13663 vty_out (vty, "%% No such neighbor or address family%s", VTY_NEWLINE);
13664 return CMD_WARNING;
13665 }
13666
13667 return bgp_show (vty, peer->bgp, afi, safi, type, &peer->su, use_json);
13668 }
13669
13670 DEFUN (show_ip_bgp_neighbor_routes,
13671 show_ip_bgp_neighbor_routes_cmd,
13672 "show ip bgp neighbors <A.B.C.D|X:X::X:X|WORD> routes [json]",
13673 SHOW_STR
13674 IP_STR
13675 BGP_STR
13676 "Detailed information on TCP and BGP neighbor connections\n"
13677 "Neighbor to display information about\n"
13678 "Neighbor to display information about\n"
13679 "Neighbor on bgp configured interface\n"
13680 "Display routes learned from neighbor\n"
13681 "JavaScript Object Notation\n")
13682 {
13683 int idx_peer = 4;
13684 struct peer *peer;
13685 u_char uj = use_json(argc, argv);
13686
13687 peer = peer_lookup_in_view (vty, NULL, argv[idx_peer]->arg, uj);
13688 if (! peer)
13689 return CMD_WARNING;
13690
13691 return bgp_show_neighbor_route (vty, peer, AFI_IP, SAFI_UNICAST,
13692 bgp_show_type_neighbor, uj);
13693 }
13694
13695 DEFUN (show_ip_bgp_instance_neighbor_routes,
13696 show_ip_bgp_instance_neighbor_routes_cmd,
13697 "show ip bgp <view|vrf> WORD neighbors <A.B.C.D|X:X::X:X|WORD> routes [json]",
13698 SHOW_STR
13699 IP_STR
13700 BGP_STR
13701 BGP_INSTANCE_HELP_STR
13702 "Detailed information on TCP and BGP neighbor connections\n"
13703 "Neighbor to display information about\n"
13704 "Neighbor to display information about\n"
13705 "Neighbor on bgp configured interface\n"
13706 "Display routes learned from neighbor\n"
13707 "JavaScript Object Notation\n")
13708 {
13709 int idx_word = 4;
13710 int idx_peer = 6;
13711 struct peer *peer;
13712 u_char uj = use_json(argc, argv);
13713
13714 peer = peer_lookup_in_view (vty, argv[idx_word]->arg, argv[idx_peer]->arg, uj);
13715 if (! peer)
13716 return CMD_WARNING;
13717
13718 return bgp_show_neighbor_route (vty, peer, AFI_IP, SAFI_UNICAST,
13719 bgp_show_type_neighbor, uj);
13720 }
13721
13722 DEFUN (show_ip_bgp_neighbor_flap,
13723 show_ip_bgp_neighbor_flap_cmd,
13724 "show ip bgp neighbors <A.B.C.D|X:X::X:X|WORD> flap-statistics [json]",
13725 SHOW_STR
13726 IP_STR
13727 BGP_STR
13728 "Detailed information on TCP and BGP neighbor connections\n"
13729 "Neighbor to display information about\n"
13730 "Neighbor to display information about\n"
13731 "Neighbor on bgp configured interface\n"
13732 "Display flap statistics of the routes learned from neighbor\n"
13733 "JavaScript Object Notation\n")
13734 {
13735 int idx_peer = 4;
13736 struct peer *peer;
13737 u_char uj = use_json(argc, argv);
13738
13739 peer = peer_lookup_in_view (vty, NULL, argv[idx_peer]->arg, uj);
13740 if (! peer)
13741 return CMD_WARNING;
13742
13743 return bgp_show_neighbor_route (vty, peer, AFI_IP, SAFI_UNICAST,
13744 bgp_show_type_flap_neighbor, uj);
13745 }
13746
13747 DEFUN (show_ip_bgp_neighbor_damp,
13748 show_ip_bgp_neighbor_damp_cmd,
13749 "show ip bgp neighbors <A.B.C.D|X:X::X:X|WORD> dampened-routes [json]",
13750 SHOW_STR
13751 IP_STR
13752 BGP_STR
13753 "Detailed information on TCP and BGP neighbor connections\n"
13754 "Neighbor to display information about\n"
13755 "Neighbor to display information about\n"
13756 "Neighbor on bgp configured interface\n"
13757 "Display the dampened routes received from neighbor\n"
13758 "JavaScript Object Notation\n")
13759 {
13760 int idx_peer = 4;
13761 struct peer *peer;
13762 u_char uj = use_json(argc, argv);
13763
13764 peer = peer_lookup_in_view (vty, NULL, argv[idx_peer]->arg, uj);
13765 if (! peer)
13766 return CMD_WARNING;
13767
13768 return bgp_show_neighbor_route (vty, peer, AFI_IP, SAFI_UNICAST,
13769 bgp_show_type_damp_neighbor, uj);
13770 }
13771
13772 DEFUN (show_ip_bgp_ipv4_neighbor_routes,
13773 show_ip_bgp_ipv4_neighbor_routes_cmd,
13774 "show ip bgp ipv4 <unicast|multicast> neighbors <A.B.C.D|X:X::X:X|WORD> routes [json]",
13775 SHOW_STR
13776 IP_STR
13777 BGP_STR
13778 "Address family\n"
13779 "Address Family modifier\n"
13780 "Address Family modifier\n"
13781 "Detailed information on TCP and BGP neighbor connections\n"
13782 "Neighbor to display information about\n"
13783 "Neighbor to display information about\n"
13784 "Neighbor on bgp configured interface\n"
13785 "Display routes learned from neighbor\n"
13786 "JavaScript Object Notation\n")
13787 {
13788 int idx_safi = 4;
13789 int idx_peer = 6;
13790 struct peer *peer;
13791 u_char uj = use_json(argc, argv);
13792
13793 peer = peer_lookup_in_view (vty, NULL, argv[idx_peer]->arg, uj);
13794 if (! peer)
13795 return CMD_WARNING;
13796
13797 if (strncmp (argv[idx_safi]->arg, "m", 1) == 0)
13798 return bgp_show_neighbor_route (vty, peer, AFI_IP, SAFI_MULTICAST,
13799 bgp_show_type_neighbor, uj);
13800
13801 return bgp_show_neighbor_route (vty, peer, AFI_IP, SAFI_UNICAST,
13802 bgp_show_type_neighbor, uj);
13803 }
13804
13805 #ifdef HAVE_IPV6
13806 /*
13807 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
13808 * "show bgp <view|vrf> WORD ipv6 neighbors (A.B.C.D|X:X::X:X|WORD) routes [json]",
13809 * SHOW_STR
13810 * BGP_STR
13811 * BGP_INSTANCE_HELP_STR
13812 * "Address family\n"
13813 * "Detailed information on TCP and BGP neighbor connections\n"
13814 * "Neighbor to display information about\n"
13815 * "Neighbor to display information about\n"
13816 * "Neighbor on bgp configured interface\n"
13817 * "Display routes learned from neighbor\n"
13818 * "JavaScript Object Notation\n"
13819 *
13820 */
13821 DEFUN (show_bgp_instance_neighbor_routes,
13822 show_bgp_instance_neighbor_routes_cmd,
13823 "show bgp <view|vrf> WORD neighbors <A.B.C.D|X:X::X:X|WORD> routes [json]",
13824 SHOW_STR
13825 BGP_STR
13826 BGP_INSTANCE_HELP_STR
13827 "Detailed information on TCP and BGP neighbor connections\n"
13828 "Neighbor to display information about\n"
13829 "Neighbor to display information about\n"
13830 "Neighbor on bgp configured interface\n"
13831 "Display routes learned from neighbor\n"
13832 "JavaScript Object Notation\n")
13833 {
13834 int idx_word = 3;
13835 int idx_peer = 5;
13836 struct peer *peer;
13837 u_char uj = use_json(argc, argv);
13838
13839 peer = peer_lookup_in_view (vty, argv[idx_word]->arg, argv[idx_peer]->arg, uj);
13840 if (! peer)
13841 return CMD_WARNING;
13842
13843 return bgp_show_neighbor_route (vty, peer, AFI_IP6, SAFI_UNICAST,
13844 bgp_show_type_neighbor, uj);
13845 }
13846
13847
13848 /*
13849 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
13850 * "show bgp neighbors (A.B.C.D|X:X::X:X|WORD) dampened-routes [json]",
13851 * SHOW_STR
13852 * BGP_STR
13853 * "Detailed information on TCP and BGP neighbor connections\n"
13854 * "Neighbor to display information about\n"
13855 * "Neighbor to display information about\n"
13856 * "Neighbor on bgp configured interface\n"
13857 * "Display the dampened routes received from neighbor\n"
13858 * "JavaScript Object Notation\n"
13859 *
13860 * "show bgp <view|vrf> WORD ipv6 neighbors (A.B.C.D|X:X::X:X|WORD) dampened-routes [json]",
13861 * SHOW_STR
13862 * BGP_STR
13863 * BGP_INSTANCE_HELP_STR
13864 * "Address family\n"
13865 * "Detailed information on TCP and BGP neighbor connections\n"
13866 * "Neighbor to display information about\n"
13867 * "Neighbor to display information about\n"
13868 * "Neighbor on bgp configured interface\n"
13869 * "Display the dampened routes received from neighbor\n"
13870 * "JavaScript Object Notation\n"
13871 *
13872 * "show bgp ipv6 neighbors (A.B.C.D|X:X::X:X|WORD) dampened-routes [json]",
13873 * SHOW_STR
13874 * BGP_STR
13875 * "Address family\n"
13876 * "Detailed information on TCP and BGP neighbor connections\n"
13877 * "Neighbor to display information about\n"
13878 * "Neighbor to display information about\n"
13879 * "Neighbor on bgp configured interface\n"
13880 * "Display the dampened routes received from neighbor\n"
13881 * "JavaScript Object Notation\n"
13882 *
13883 */
13884 DEFUN (show_bgp_instance_neighbor_damp,
13885 show_bgp_instance_neighbor_damp_cmd,
13886 "show bgp <view|vrf> WORD neighbors <A.B.C.D|X:X::X:X|WORD> dampened-routes [json]",
13887 SHOW_STR
13888 BGP_STR
13889 BGP_INSTANCE_HELP_STR
13890 "Detailed information on TCP and BGP neighbor connections\n"
13891 "Neighbor to display information about\n"
13892 "Neighbor to display information about\n"
13893 "Neighbor on bgp configured interface\n"
13894 "Display the dampened routes received from neighbor\n"
13895 "JavaScript Object Notation\n")
13896 {
13897 int idx_word = 3;
13898 int idx_peer = 5;
13899 int idx_json = 7;
13900 struct peer *peer;
13901 u_char uj = use_json(argc, argv);
13902
13903 if ((argc == 4 && argv[idx_json]->arg && strcmp(argv[idx_json]->arg, "json") == 0)
13904 || (argc == 3 && argv[idx_peer]->arg && strcmp(argv[idx_peer]->arg, "json") != 0))
13905 peer = peer_lookup_in_view (vty, argv[idx_word]->arg, argv[idx_peer]->arg, uj);
13906 else
13907 peer = peer_lookup_in_view (vty, NULL, argv[idx_word]->arg, uj);
13908
13909 if (! peer)
13910 return CMD_WARNING;
13911
13912 return bgp_show_neighbor_route (vty, peer, AFI_IP6, SAFI_UNICAST,
13913 bgp_show_type_damp_neighbor, uj);
13914 }
13915
13916
13917 /*
13918 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
13919 * "show bgp neighbors (A.B.C.D|X:X::X:X|WORD) flap-statistics [json]",
13920 * SHOW_STR
13921 * BGP_STR
13922 * "Detailed information on TCP and BGP neighbor connections\n"
13923 * "Neighbor to display information about\n"
13924 * "Neighbor to display information about\n"
13925 * "Neighbor on bgp configured interface\n"
13926 * "Display flap statistics of the routes learned from neighbor\n"
13927 * "JavaScript Object Notation\n"
13928 *
13929 * "show bgp <view|vrf> WORD ipv6 neighbors (A.B.C.D|X:X::X:X|WORD) flap-statistics [json]",
13930 * SHOW_STR
13931 * BGP_STR
13932 * BGP_INSTANCE_HELP_STR
13933 * "Address family\n"
13934 * "Detailed information on TCP and BGP neighbor connections\n"
13935 * "Neighbor to display information about\n"
13936 * "Neighbor to display information about\n"
13937 * "Neighbor on bgp configured interface\n"
13938 * "Display flap statistics of the routes learned from neighbor\n"
13939 * "JavaScript Object Notation\n"
13940 *
13941 * "show bgp ipv6 neighbors (A.B.C.D|X:X::X:X|WORD) flap-statistics [json]",
13942 * SHOW_STR
13943 * BGP_STR
13944 * "Address family\n"
13945 * "Detailed information on TCP and BGP neighbor connections\n"
13946 * "Neighbor to display information about\n"
13947 * "Neighbor to display information about\n"
13948 * "Neighbor on bgp configured interface\n"
13949 * "Display flap statistics of the routes learned from neighbor\n"
13950 * "JavaScript Object Notation\n"
13951 *
13952 */
13953 DEFUN (show_bgp_instance_neighbor_flap,
13954 show_bgp_instance_neighbor_flap_cmd,
13955 "show bgp <view|vrf> WORD neighbors <A.B.C.D|X:X::X:X|WORD> flap-statistics [json]",
13956 SHOW_STR
13957 BGP_STR
13958 BGP_INSTANCE_HELP_STR
13959 "Detailed information on TCP and BGP neighbor connections\n"
13960 "Neighbor to display information about\n"
13961 "Neighbor to display information about\n"
13962 "Neighbor on bgp configured interface\n"
13963 "Display flap statistics of the routes learned from neighbor\n"
13964 "JavaScript Object Notation\n")
13965 {
13966 int idx_word = 3;
13967 int idx_peer = 5;
13968 int idx_json = 7;
13969 struct peer *peer;
13970 u_char uj = use_json(argc, argv);
13971
13972 if ((argc == 4 && argv[idx_json]->arg && strcmp(argv[idx_json]->arg, "json") == 0)
13973 || (argc == 3 && argv[idx_peer]->arg && strcmp(argv[idx_peer]->arg, "json") != 0))
13974 peer = peer_lookup_in_view (vty, argv[idx_word]->arg, argv[idx_peer]->arg, uj);
13975 else
13976 peer = peer_lookup_in_view (vty, NULL, argv[idx_word]->arg, uj);
13977
13978 if (! peer)
13979 return CMD_WARNING;
13980
13981 return bgp_show_neighbor_route (vty, peer, AFI_IP6, SAFI_UNICAST,
13982 bgp_show_type_flap_neighbor, uj);
13983 }
13984
13985
13986 /*
13987 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
13988 * "show ipv6 bgp neighbors (A.B.C.D|X:X::X:X|WORD) routes [json]",
13989 * SHOW_STR
13990 * IPV6_STR
13991 * BGP_STR
13992 * "Detailed information on TCP and BGP neighbor connections\n"
13993 * "Neighbor to display information about\n"
13994 * "Neighbor to display information about\n"
13995 * "Neighbor on bgp configured interface\n"
13996 * "Display routes learned from neighbor\n"
13997 * "JavaScript Object Notation\n"
13998 *
13999 * "show bgp ipv6 neighbors (A.B.C.D|X:X::X:X|WORD) routes [json]",
14000 * SHOW_STR
14001 * BGP_STR
14002 * "Address family\n"
14003 * "Detailed information on TCP and BGP neighbor connections\n"
14004 * "Neighbor to display information about\n"
14005 * "Neighbor to display information about\n"
14006 * "Neighbor on bgp configured interface\n"
14007 * "Display routes learned from neighbor\n"
14008 * "JavaScript Object Notation\n"
14009 *
14010 */
14011 DEFUN (show_bgp_neighbor_routes,
14012 show_bgp_neighbor_routes_cmd,
14013 "show bgp neighbors <A.B.C.D|X:X::X:X|WORD> routes [json]",
14014 SHOW_STR
14015 BGP_STR
14016 "Detailed information on TCP and BGP neighbor connections\n"
14017 "Neighbor to display information about\n"
14018 "Neighbor to display information about\n"
14019 "Neighbor on bgp configured interface\n"
14020 "Display routes learned from neighbor\n"
14021 "JavaScript Object Notation\n")
14022 {
14023 int idx_peer = 3;
14024 struct peer *peer;
14025 u_char uj = use_json(argc, argv);
14026
14027 peer = peer_lookup_in_view (vty, NULL, argv[idx_peer]->arg, uj);
14028 if (! peer)
14029 return CMD_WARNING;
14030
14031 return bgp_show_neighbor_route (vty, peer, AFI_IP6, SAFI_UNICAST,
14032 bgp_show_type_neighbor, uj);
14033 }
14034
14035
14036
14037 /* old command */
14038
14039 /* old command */
14040 DEFUN (ipv6_mbgp_neighbor_routes,
14041 ipv6_mbgp_neighbor_routes_cmd,
14042 "show ipv6 mbgp neighbors <A.B.C.D|X:X::X:X|WORD> routes [json]",
14043 SHOW_STR
14044 IPV6_STR
14045 MBGP_STR
14046 "Detailed information on TCP and BGP neighbor connections\n"
14047 "Neighbor to display information about\n"
14048 "Neighbor to display information about\n"
14049 "Neighbor on bgp configured interface\n"
14050 "Display routes learned from neighbor\n"
14051 "JavaScript Object Notation\n")
14052 {
14053 int idx_peer = 4;
14054 struct peer *peer;
14055 u_char uj = use_json(argc, argv);
14056
14057 peer = peer_lookup_in_view (vty, NULL, argv[idx_peer]->arg, uj);
14058 if (! peer)
14059 return CMD_WARNING;
14060
14061 bgp_show_ipv6_bgp_deprecate_warning(vty);
14062 return bgp_show_neighbor_route (vty, peer, AFI_IP6, SAFI_MULTICAST,
14063 bgp_show_type_neighbor, uj);
14064 }
14065
14066
14067
14068
14069
14070 #endif /* HAVE_IPV6 */
14071
14072 struct bgp_table *bgp_distance_table;
14073
14074 struct bgp_distance
14075 {
14076 /* Distance value for the IP source prefix. */
14077 u_char distance;
14078
14079 /* Name of the access-list to be matched. */
14080 char *access_list;
14081 };
14082
14083 static struct bgp_distance *
14084 bgp_distance_new (void)
14085 {
14086 return XCALLOC (MTYPE_BGP_DISTANCE, sizeof (struct bgp_distance));
14087 }
14088
14089 static void
14090 bgp_distance_free (struct bgp_distance *bdistance)
14091 {
14092 XFREE (MTYPE_BGP_DISTANCE, bdistance);
14093 }
14094
14095 static int
14096 bgp_distance_set (struct vty *vty, const char *distance_str,
14097 const char *ip_str, const char *access_list_str)
14098 {
14099 int ret;
14100 struct prefix_ipv4 p;
14101 u_char distance;
14102 struct bgp_node *rn;
14103 struct bgp_distance *bdistance;
14104
14105 ret = str2prefix_ipv4 (ip_str, &p);
14106 if (ret == 0)
14107 {
14108 vty_out (vty, "Malformed prefix%s", VTY_NEWLINE);
14109 return CMD_WARNING;
14110 }
14111
14112 distance = atoi (distance_str);
14113
14114 /* Get BGP distance node. */
14115 rn = bgp_node_get (bgp_distance_table, (struct prefix *) &p);
14116 if (rn->info)
14117 {
14118 bdistance = rn->info;
14119 bgp_unlock_node (rn);
14120 }
14121 else
14122 {
14123 bdistance = bgp_distance_new ();
14124 rn->info = bdistance;
14125 }
14126
14127 /* Set distance value. */
14128 bdistance->distance = distance;
14129
14130 /* Reset access-list configuration. */
14131 if (bdistance->access_list)
14132 {
14133 XFREE(MTYPE_AS_LIST, bdistance->access_list);
14134 bdistance->access_list = NULL;
14135 }
14136 if (access_list_str)
14137 bdistance->access_list = XSTRDUP(MTYPE_AS_LIST, access_list_str);
14138
14139 return CMD_SUCCESS;
14140 }
14141
14142 static int
14143 bgp_distance_unset (struct vty *vty, const char *distance_str,
14144 const char *ip_str, const char *access_list_str)
14145 {
14146 int ret;
14147 int distance;
14148 struct prefix_ipv4 p;
14149 struct bgp_node *rn;
14150 struct bgp_distance *bdistance;
14151
14152 ret = str2prefix_ipv4 (ip_str, &p);
14153 if (ret == 0)
14154 {
14155 vty_out (vty, "Malformed prefix%s", VTY_NEWLINE);
14156 return CMD_WARNING;
14157 }
14158
14159 rn = bgp_node_lookup (bgp_distance_table, (struct prefix *)&p);
14160 if (! rn)
14161 {
14162 vty_out (vty, "Can't find specified prefix%s", VTY_NEWLINE);
14163 return CMD_WARNING;
14164 }
14165
14166 bdistance = rn->info;
14167 distance = atoi(distance_str);
14168
14169 if (bdistance->distance != distance)
14170 {
14171 vty_out (vty, "Distance does not match configured%s", VTY_NEWLINE);
14172 return CMD_WARNING;
14173 }
14174
14175 if (bdistance->access_list)
14176 XFREE(MTYPE_AS_LIST, bdistance->access_list);
14177 bgp_distance_free (bdistance);
14178
14179 rn->info = NULL;
14180 bgp_unlock_node (rn);
14181 bgp_unlock_node (rn);
14182
14183 return CMD_SUCCESS;
14184 }
14185
14186 /* Apply BGP information to distance method. */
14187 u_char
14188 bgp_distance_apply (struct prefix *p, struct bgp_info *rinfo, struct bgp *bgp)
14189 {
14190 struct bgp_node *rn;
14191 struct prefix_ipv4 q;
14192 struct peer *peer;
14193 struct bgp_distance *bdistance;
14194 struct access_list *alist;
14195 struct bgp_static *bgp_static;
14196
14197 if (! bgp)
14198 return 0;
14199
14200 if (p->family != AF_INET)
14201 return 0;
14202
14203 peer = rinfo->peer;
14204
14205 if (peer->su.sa.sa_family != AF_INET)
14206 return 0;
14207
14208 memset (&q, 0, sizeof (struct prefix_ipv4));
14209 q.family = AF_INET;
14210 q.prefix = peer->su.sin.sin_addr;
14211 q.prefixlen = IPV4_MAX_BITLEN;
14212
14213 /* Check source address. */
14214 rn = bgp_node_match (bgp_distance_table, (struct prefix *) &q);
14215 if (rn)
14216 {
14217 bdistance = rn->info;
14218 bgp_unlock_node (rn);
14219
14220 if (bdistance->access_list)
14221 {
14222 alist = access_list_lookup (AFI_IP, bdistance->access_list);
14223 if (alist && access_list_apply (alist, p) == FILTER_PERMIT)
14224 return bdistance->distance;
14225 }
14226 else
14227 return bdistance->distance;
14228 }
14229
14230 /* Backdoor check. */
14231 rn = bgp_node_lookup (bgp->route[AFI_IP][SAFI_UNICAST], p);
14232 if (rn)
14233 {
14234 bgp_static = rn->info;
14235 bgp_unlock_node (rn);
14236
14237 if (bgp_static->backdoor)
14238 {
14239 if (bgp->distance_local)
14240 return bgp->distance_local;
14241 else
14242 return ZEBRA_IBGP_DISTANCE_DEFAULT;
14243 }
14244 }
14245
14246 if (peer->sort == BGP_PEER_EBGP)
14247 {
14248 if (bgp->distance_ebgp)
14249 return bgp->distance_ebgp;
14250 return ZEBRA_EBGP_DISTANCE_DEFAULT;
14251 }
14252 else
14253 {
14254 if (bgp->distance_ibgp)
14255 return bgp->distance_ibgp;
14256 return ZEBRA_IBGP_DISTANCE_DEFAULT;
14257 }
14258 }
14259
14260 DEFUN (bgp_distance,
14261 bgp_distance_cmd,
14262 "distance bgp (1-255) (1-255) (1-255)",
14263 "Define an administrative distance\n"
14264 "BGP distance\n"
14265 "Distance for routes external to the AS\n"
14266 "Distance for routes internal to the AS\n"
14267 "Distance for local routes\n")
14268 {
14269 int idx_number = 2;
14270 int idx_number_2 = 3;
14271 int idx_number_3 = 4;
14272 struct bgp *bgp;
14273
14274 bgp = vty->index;
14275
14276 bgp->distance_ebgp = atoi (argv[idx_number]->arg);
14277 bgp->distance_ibgp = atoi (argv[idx_number_2]->arg);
14278 bgp->distance_local = atoi (argv[idx_number_3]->arg);
14279 return CMD_SUCCESS;
14280 }
14281
14282 /*
14283 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
14284 * "no distance bgp",
14285 * NO_STR
14286 * "Define an administrative distance\n"
14287 * "BGP distance\n"
14288 *
14289 */
14290 DEFUN (no_bgp_distance,
14291 no_bgp_distance_cmd,
14292 "no distance bgp (1-255) (1-255) (1-255)",
14293 NO_STR
14294 "Define an administrative distance\n"
14295 "BGP distance\n"
14296 "Distance for routes external to the AS\n"
14297 "Distance for routes internal to the AS\n"
14298 "Distance for local routes\n")
14299 {
14300 struct bgp *bgp;
14301
14302 bgp = vty->index;
14303
14304 bgp->distance_ebgp= 0;
14305 bgp->distance_ibgp = 0;
14306 bgp->distance_local = 0;
14307 return CMD_SUCCESS;
14308 }
14309
14310
14311 DEFUN (bgp_distance_source,
14312 bgp_distance_source_cmd,
14313 "distance (1-255) A.B.C.D/M",
14314 "Define an administrative distance\n"
14315 "Administrative distance\n"
14316 "IP source prefix\n")
14317 {
14318 int idx_number = 1;
14319 int idx_ipv4_prefixlen = 2;
14320 bgp_distance_set (vty, argv[idx_number]->arg, argv[idx_ipv4_prefixlen]->arg, NULL);
14321 return CMD_SUCCESS;
14322 }
14323
14324 DEFUN (no_bgp_distance_source,
14325 no_bgp_distance_source_cmd,
14326 "no distance (1-255) A.B.C.D/M",
14327 NO_STR
14328 "Define an administrative distance\n"
14329 "Administrative distance\n"
14330 "IP source prefix\n")
14331 {
14332 int idx_number = 2;
14333 int idx_ipv4_prefixlen = 3;
14334 bgp_distance_unset (vty, argv[idx_number]->arg, argv[idx_ipv4_prefixlen]->arg, NULL);
14335 return CMD_SUCCESS;
14336 }
14337
14338 DEFUN (bgp_distance_source_access_list,
14339 bgp_distance_source_access_list_cmd,
14340 "distance (1-255) A.B.C.D/M WORD",
14341 "Define an administrative distance\n"
14342 "Administrative distance\n"
14343 "IP source prefix\n"
14344 "Access list name\n")
14345 {
14346 int idx_number = 1;
14347 int idx_ipv4_prefixlen = 2;
14348 int idx_word = 3;
14349 bgp_distance_set (vty, argv[idx_number]->arg, argv[idx_ipv4_prefixlen]->arg, argv[idx_word]->arg);
14350 return CMD_SUCCESS;
14351 }
14352
14353 DEFUN (no_bgp_distance_source_access_list,
14354 no_bgp_distance_source_access_list_cmd,
14355 "no distance (1-255) A.B.C.D/M WORD",
14356 NO_STR
14357 "Define an administrative distance\n"
14358 "Administrative distance\n"
14359 "IP source prefix\n"
14360 "Access list name\n")
14361 {
14362 int idx_number = 2;
14363 int idx_ipv4_prefixlen = 3;
14364 int idx_word = 4;
14365 bgp_distance_unset (vty, argv[idx_number]->arg, argv[idx_ipv4_prefixlen]->arg, argv[idx_word]->arg);
14366 return CMD_SUCCESS;
14367 }
14368
14369 /*
14370 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
14371 * "bgp dampening",
14372 * "BGP Specific commands\n"
14373 * "Enable route-flap dampening\n"
14374 *
14375 * "bgp dampening <1-45>",
14376 * "BGP Specific commands\n"
14377 * "Enable route-flap dampening\n"
14378 * "Half-life time for the penalty\n"
14379 *
14380 */
14381 DEFUN (bgp_damp_set,
14382 bgp_damp_set_cmd,
14383 "bgp dampening (1-45) (1-20000) (1-20000) (1-255)",
14384 "BGP Specific commands\n"
14385 "Enable route-flap dampening\n"
14386 "Half-life time for the penalty\n"
14387 "Value to start reusing a route\n"
14388 "Value to start suppressing a route\n"
14389 "Maximum duration to suppress a stable route\n")
14390 {
14391 int idx_number = 2;
14392 int idx_number_2 = 3;
14393 int idx_number_3 = 4;
14394 int idx_number_4 = 5;
14395 struct bgp *bgp;
14396 int half = DEFAULT_HALF_LIFE * 60;
14397 int reuse = DEFAULT_REUSE;
14398 int suppress = DEFAULT_SUPPRESS;
14399 int max = 4 * half;
14400
14401 if (argc == 4)
14402 {
14403 half = atoi (argv[idx_number]->arg) * 60;
14404 reuse = atoi (argv[idx_number_2]->arg);
14405 suppress = atoi (argv[idx_number_3]->arg);
14406 max = atoi (argv[idx_number_4]->arg) * 60;
14407 }
14408 else if (argc == 1)
14409 {
14410 half = atoi (argv[idx_number]->arg) * 60;
14411 max = 4 * half;
14412 }
14413
14414 bgp = vty->index;
14415
14416 if (suppress < reuse)
14417 {
14418 vty_out (vty, "Suppress value cannot be less than reuse value %s",
14419 VTY_NEWLINE);
14420 return 0;
14421 }
14422
14423 return bgp_damp_enable (bgp, bgp_node_afi (vty), bgp_node_safi (vty),
14424 half, reuse, suppress, max);
14425 }
14426
14427
14428
14429 /*
14430 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
14431 * "no bgp dampening <1-45>",
14432 * NO_STR
14433 * "BGP Specific commands\n"
14434 * "Enable route-flap dampening\n"
14435 * "Half-life time for the penalty\n"
14436 *
14437 * "no bgp dampening <1-45> <1-20000> <1-20000> <1-255>",
14438 * NO_STR
14439 * "BGP Specific commands\n"
14440 * "Enable route-flap dampening\n"
14441 * "Half-life time for the penalty\n"
14442 * "Value to start reusing a route\n"
14443 * "Value to start suppressing a route\n"
14444 * "Maximum duration to suppress a stable route\n"
14445 *
14446 */
14447 DEFUN (bgp_damp_unset,
14448 bgp_damp_unset_cmd,
14449 "no bgp dampening",
14450 NO_STR
14451 "BGP Specific commands\n"
14452 "Enable route-flap dampening\n")
14453 {
14454 struct bgp *bgp;
14455
14456 bgp = vty->index;
14457 return bgp_damp_disable (bgp, bgp_node_afi (vty), bgp_node_safi (vty));
14458 }
14459
14460
14461
14462 /*
14463 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
14464 * "show ip bgp dampening dampened-paths",
14465 * SHOW_STR
14466 * IP_STR
14467 * BGP_STR
14468 * "Display detailed information about dampening\n"
14469 * "Display paths suppressed due to dampening\n"
14470 *
14471 */
14472 DEFUN (show_ip_bgp_dampened_paths,
14473 show_ip_bgp_dampened_paths_cmd,
14474 "show ip bgp dampened-paths",
14475 SHOW_STR
14476 IP_STR
14477 BGP_STR
14478 "Display paths suppressed due to dampening\n")
14479 {
14480 return bgp_show (vty, NULL, AFI_IP, SAFI_UNICAST, bgp_show_type_dampend_paths,
14481 NULL, 0);
14482 }
14483
14484
14485 /*
14486 * CHECK ME - The following ALIASes need to be implemented in this DEFUN
14487 * "show ip bgp dampening flap-statistics",
14488 * SHOW_STR
14489 * IP_STR
14490 * BGP_STR
14491 * "Display detailed information about dampening\n"
14492 * "Display flap statistics of routes\n"
14493 *
14494 */
14495 DEFUN (show_ip_bgp_flap_statistics,
14496 show_ip_bgp_flap_statistics_cmd,
14497 "show ip bgp flap-statistics",
14498 SHOW_STR
14499 IP_STR
14500 BGP_STR
14501 "Display flap statistics of routes\n")
14502 {
14503 return bgp_show (vty, NULL, AFI_IP, SAFI_UNICAST,
14504 bgp_show_type_flap_statistics, NULL, 0);
14505 }
14506
14507
14508 /* Display specified route of BGP table. */
14509 static int
14510 bgp_clear_damp_route (struct vty *vty, const char *view_name,
14511 const char *ip_str, afi_t afi, safi_t safi,
14512 struct prefix_rd *prd, int prefix_check)
14513 {
14514 int ret;
14515 struct prefix match;
14516 struct bgp_node *rn;
14517 struct bgp_node *rm;
14518 struct bgp_info *ri;
14519 struct bgp_info *ri_temp;
14520 struct bgp *bgp;
14521 struct bgp_table *table;
14522
14523 /* BGP structure lookup. */
14524 if (view_name)
14525 {
14526 bgp = bgp_lookup_by_name (view_name);
14527 if (bgp == NULL)
14528 {
14529 vty_out (vty, "%% Can't find BGP instance %s%s", view_name, VTY_NEWLINE);
14530 return CMD_WARNING;
14531 }
14532 }
14533 else
14534 {
14535 bgp = bgp_get_default ();
14536 if (bgp == NULL)
14537 {
14538 vty_out (vty, "%% No BGP process is configured%s", VTY_NEWLINE);
14539 return CMD_WARNING;
14540 }
14541 }
14542
14543 /* Check IP address argument. */
14544 ret = str2prefix (ip_str, &match);
14545 if (! ret)
14546 {
14547 vty_out (vty, "%% address is malformed%s", VTY_NEWLINE);
14548 return CMD_WARNING;
14549 }
14550
14551 match.family = afi2family (afi);
14552
14553 if ((safi == SAFI_MPLS_VPN) || (safi == SAFI_ENCAP))
14554 {
14555 for (rn = bgp_table_top (bgp->rib[AFI_IP][safi]); rn; rn = bgp_route_next (rn))
14556 {
14557 if (prd && memcmp (rn->p.u.val, prd->val, 8) != 0)
14558 continue;
14559
14560 if ((table = rn->info) != NULL)
14561 if ((rm = bgp_node_match (table, &match)) != NULL)
14562 {
14563 if (! prefix_check || rm->p.prefixlen == match.prefixlen)
14564 {
14565 ri = rm->info;
14566 while (ri)
14567 {
14568 if (ri->extra && ri->extra->damp_info)
14569 {
14570 ri_temp = ri->next;
14571 bgp_damp_info_free (ri->extra->damp_info, 1);
14572 ri = ri_temp;
14573 }
14574 else
14575 ri = ri->next;
14576 }
14577 }
14578
14579 bgp_unlock_node (rm);
14580 }
14581 }
14582 }
14583 else
14584 {
14585 if ((rn = bgp_node_match (bgp->rib[afi][safi], &match)) != NULL)
14586 {
14587 if (! prefix_check || rn->p.prefixlen == match.prefixlen)
14588 {
14589 ri = rn->info;
14590 while (ri)
14591 {
14592 if (ri->extra && ri->extra->damp_info)
14593 {
14594 ri_temp = ri->next;
14595 bgp_damp_info_free (ri->extra->damp_info, 1);
14596 ri = ri_temp;
14597 }
14598 else
14599 ri = ri->next;
14600 }
14601 }
14602
14603 bgp_unlock_node (rn);
14604 }
14605 }
14606
14607 return CMD_SUCCESS;
14608 }
14609
14610 DEFUN (clear_ip_bgp_dampening,
14611 clear_ip_bgp_dampening_cmd,
14612 "clear ip bgp dampening",
14613 CLEAR_STR
14614 IP_STR
14615 BGP_STR
14616 "Clear route flap dampening information\n")
14617 {
14618 bgp_damp_info_clean ();
14619 return CMD_SUCCESS;
14620 }
14621
14622 DEFUN (clear_ip_bgp_dampening_prefix,
14623 clear_ip_bgp_dampening_prefix_cmd,
14624 "clear ip bgp dampening A.B.C.D/M",
14625 CLEAR_STR
14626 IP_STR
14627 BGP_STR
14628 "Clear route flap dampening information\n"
14629 "IP prefix <network>/<length>, e.g., 35.0.0.0/8\n")
14630 {
14631 int idx_ipv4_prefixlen = 4;
14632 return bgp_clear_damp_route (vty, NULL, argv[idx_ipv4_prefixlen]->arg, AFI_IP,
14633 SAFI_UNICAST, NULL, 1);
14634 }
14635
14636 DEFUN (clear_ip_bgp_dampening_address,
14637 clear_ip_bgp_dampening_address_cmd,
14638 "clear ip bgp dampening A.B.C.D",
14639 CLEAR_STR
14640 IP_STR
14641 BGP_STR
14642 "Clear route flap dampening information\n"
14643 "Network to clear damping information\n")
14644 {
14645 int idx_ipv4 = 4;
14646 return bgp_clear_damp_route (vty, NULL, argv[idx_ipv4]->arg, AFI_IP,
14647 SAFI_UNICAST, NULL, 0);
14648 }
14649
14650 DEFUN (clear_ip_bgp_dampening_address_mask,
14651 clear_ip_bgp_dampening_address_mask_cmd,
14652 "clear ip bgp dampening A.B.C.D A.B.C.D",
14653 CLEAR_STR
14654 IP_STR
14655 BGP_STR
14656 "Clear route flap dampening information\n"
14657 "Network to clear damping information\n"
14658 "Network mask\n")
14659 {
14660 int idx_ipv4 = 4;
14661 int idx_ipv4_2 = 5;
14662 int ret;
14663 char prefix_str[BUFSIZ];
14664
14665 ret = netmask_str2prefix_str (argv[idx_ipv4]->arg, argv[idx_ipv4_2]->arg, prefix_str);
14666 if (! ret)
14667 {
14668 vty_out (vty, "%% Inconsistent address and mask%s", VTY_NEWLINE);
14669 return CMD_WARNING;
14670 }
14671
14672 return bgp_clear_damp_route (vty, NULL, prefix_str, AFI_IP,
14673 SAFI_UNICAST, NULL, 0);
14674 }
14675
14676 /* also used for encap safi */
14677 static int
14678 bgp_config_write_network_vpnv4 (struct vty *vty, struct bgp *bgp,
14679 afi_t afi, safi_t safi, int *write)
14680 {
14681 struct bgp_node *prn;
14682 struct bgp_node *rn;
14683 struct bgp_table *table;
14684 struct prefix *p;
14685 struct prefix_rd *prd;
14686 struct bgp_static *bgp_static;
14687 u_int32_t label;
14688 char buf[SU_ADDRSTRLEN];
14689 char rdbuf[RD_ADDRSTRLEN];
14690
14691 /* Network configuration. */
14692 for (prn = bgp_table_top (bgp->route[afi][safi]); prn; prn = bgp_route_next (prn))
14693 if ((table = prn->info) != NULL)
14694 for (rn = bgp_table_top (table); rn; rn = bgp_route_next (rn))
14695 if ((bgp_static = rn->info) != NULL)
14696 {
14697 p = &rn->p;
14698 prd = (struct prefix_rd *) &prn->p;
14699
14700 /* "address-family" display. */
14701 bgp_config_write_family_header (vty, afi, safi, write);
14702
14703 /* "network" configuration display. */
14704 prefix_rd2str (prd, rdbuf, RD_ADDRSTRLEN);
14705 label = decode_label (bgp_static->tag);
14706
14707 vty_out (vty, " network %s/%d rd %s tag %d",
14708 inet_ntop (p->family, &p->u.prefix, buf, SU_ADDRSTRLEN),
14709 p->prefixlen,
14710 rdbuf, label);
14711 vty_out (vty, "%s", VTY_NEWLINE);
14712 }
14713 return 0;
14714 }
14715
14716 /* Configuration of static route announcement and aggregate
14717 information. */
14718 int
14719 bgp_config_write_network (struct vty *vty, struct bgp *bgp,
14720 afi_t afi, safi_t safi, int *write)
14721 {
14722 struct bgp_node *rn;
14723 struct prefix *p;
14724 struct bgp_static *bgp_static;
14725 struct bgp_aggregate *bgp_aggregate;
14726 char buf[SU_ADDRSTRLEN];
14727
14728 if (afi == AFI_IP && ((safi == SAFI_MPLS_VPN) || (safi == SAFI_ENCAP)))
14729 return bgp_config_write_network_vpnv4 (vty, bgp, afi, safi, write);
14730
14731 /* Network configuration. */
14732 for (rn = bgp_table_top (bgp->route[afi][safi]); rn; rn = bgp_route_next (rn))
14733 if ((bgp_static = rn->info) != NULL)
14734 {
14735 p = &rn->p;
14736
14737 /* "address-family" display. */
14738 bgp_config_write_family_header (vty, afi, safi, write);
14739
14740 /* "network" configuration display. */
14741 if (bgp_option_check (BGP_OPT_CONFIG_CISCO) && afi == AFI_IP)
14742 {
14743 u_int32_t destination;
14744 struct in_addr netmask;
14745
14746 destination = ntohl (p->u.prefix4.s_addr);
14747 masklen2ip (p->prefixlen, &netmask);
14748 vty_out (vty, " network %s",
14749 inet_ntop (p->family, &p->u.prefix, buf, SU_ADDRSTRLEN));
14750
14751 if ((IN_CLASSC (destination) && p->prefixlen == 24)
14752 || (IN_CLASSB (destination) && p->prefixlen == 16)
14753 || (IN_CLASSA (destination) && p->prefixlen == 8)
14754 || p->u.prefix4.s_addr == 0)
14755 {
14756 /* Natural mask is not display. */
14757 }
14758 else
14759 vty_out (vty, " mask %s", inet_ntoa (netmask));
14760 }
14761 else
14762 {
14763 vty_out (vty, " network %s/%d",
14764 inet_ntop (p->family, &p->u.prefix, buf, SU_ADDRSTRLEN),
14765 p->prefixlen);
14766 }
14767
14768 if (bgp_static->rmap.name)
14769 vty_out (vty, " route-map %s", bgp_static->rmap.name);
14770 else
14771 {
14772 if (bgp_static->backdoor)
14773 vty_out (vty, " backdoor");
14774 }
14775
14776 vty_out (vty, "%s", VTY_NEWLINE);
14777 }
14778
14779 /* Aggregate-address configuration. */
14780 for (rn = bgp_table_top (bgp->aggregate[afi][safi]); rn; rn = bgp_route_next (rn))
14781 if ((bgp_aggregate = rn->info) != NULL)
14782 {
14783 p = &rn->p;
14784
14785 /* "address-family" display. */
14786 bgp_config_write_family_header (vty, afi, safi, write);
14787
14788 if (bgp_option_check (BGP_OPT_CONFIG_CISCO) && afi == AFI_IP)
14789 {
14790 struct in_addr netmask;
14791
14792 masklen2ip (p->prefixlen, &netmask);
14793 vty_out (vty, " aggregate-address %s %s",
14794 inet_ntop (p->family, &p->u.prefix, buf, SU_ADDRSTRLEN),
14795 inet_ntoa (netmask));
14796 }
14797 else
14798 {
14799 vty_out (vty, " aggregate-address %s/%d",
14800 inet_ntop (p->family, &p->u.prefix, buf, SU_ADDRSTRLEN),
14801 p->prefixlen);
14802 }
14803
14804 if (bgp_aggregate->as_set)
14805 vty_out (vty, " as-set");
14806
14807 if (bgp_aggregate->summary_only)
14808 vty_out (vty, " summary-only");
14809
14810 vty_out (vty, "%s", VTY_NEWLINE);
14811 }
14812
14813 return 0;
14814 }
14815
14816 int
14817 bgp_config_write_distance (struct vty *vty, struct bgp *bgp)
14818 {
14819 struct bgp_node *rn;
14820 struct bgp_distance *bdistance;
14821
14822 /* Distance configuration. */
14823 if (bgp->distance_ebgp
14824 && bgp->distance_ibgp
14825 && bgp->distance_local
14826 && (bgp->distance_ebgp != ZEBRA_EBGP_DISTANCE_DEFAULT
14827 || bgp->distance_ibgp != ZEBRA_IBGP_DISTANCE_DEFAULT
14828 || bgp->distance_local != ZEBRA_IBGP_DISTANCE_DEFAULT))
14829 vty_out (vty, " distance bgp %d %d %d%s",
14830 bgp->distance_ebgp, bgp->distance_ibgp, bgp->distance_local,
14831 VTY_NEWLINE);
14832
14833 for (rn = bgp_table_top (bgp_distance_table); rn; rn = bgp_route_next (rn))
14834 if ((bdistance = rn->info) != NULL)
14835 {
14836 vty_out (vty, " distance %d %s/%d %s%s", bdistance->distance,
14837 inet_ntoa (rn->p.u.prefix4), rn->p.prefixlen,
14838 bdistance->access_list ? bdistance->access_list : "",
14839 VTY_NEWLINE);
14840 }
14841
14842 return 0;
14843 }
14844
14845 /* Allocate routing table structure and install commands. */
14846 void
14847 bgp_route_init (void)
14848 {
14849 /* Init BGP distance table. */
14850 bgp_distance_table = bgp_table_init (AFI_IP, SAFI_UNICAST);
14851
14852 /* IPv4 BGP commands. */
14853 install_element (BGP_NODE, &bgp_table_map_cmd);
14854 install_element (BGP_NODE, &bgp_network_cmd);
14855 install_element (BGP_NODE, &bgp_network_mask_cmd);
14856 install_element (BGP_NODE, &bgp_network_mask_natural_cmd);
14857 install_element (BGP_NODE, &bgp_network_route_map_cmd);
14858 install_element (BGP_NODE, &bgp_network_mask_route_map_cmd);
14859 install_element (BGP_NODE, &bgp_network_mask_natural_route_map_cmd);
14860 install_element (BGP_NODE, &bgp_network_backdoor_cmd);
14861 install_element (BGP_NODE, &bgp_network_mask_backdoor_cmd);
14862 install_element (BGP_NODE, &bgp_network_mask_natural_backdoor_cmd);
14863 install_element (BGP_NODE, &no_bgp_table_map_cmd);
14864 install_element (BGP_NODE, &no_bgp_network_cmd);
14865 install_element (BGP_NODE, &no_bgp_network_mask_cmd);
14866 install_element (BGP_NODE, &no_bgp_network_mask_natural_cmd);
14867
14868 install_element (BGP_NODE, &aggregate_address_cmd);
14869 install_element (BGP_NODE, &aggregate_address_mask_cmd);
14870 install_element (BGP_NODE, &aggregate_address_summary_only_cmd);
14871 install_element (BGP_NODE, &aggregate_address_mask_summary_only_cmd);
14872 install_element (BGP_NODE, &aggregate_address_as_set_cmd);
14873 install_element (BGP_NODE, &aggregate_address_mask_as_set_cmd);
14874 install_element (BGP_NODE, &aggregate_address_as_set_summary_cmd);
14875 install_element (BGP_NODE, &aggregate_address_mask_as_set_summary_cmd);
14876 install_element (BGP_NODE, &no_aggregate_address_cmd);
14877 install_element (BGP_NODE, &no_aggregate_address_mask_cmd);
14878
14879 /* IPv4 unicast configuration. */
14880 install_element (BGP_IPV4_NODE, &bgp_table_map_cmd);
14881 install_element (BGP_IPV4_NODE, &bgp_network_cmd);
14882 install_element (BGP_IPV4_NODE, &bgp_network_mask_cmd);
14883 install_element (BGP_IPV4_NODE, &bgp_network_mask_natural_cmd);
14884 install_element (BGP_IPV4_NODE, &bgp_network_route_map_cmd);
14885 install_element (BGP_IPV4_NODE, &bgp_network_mask_route_map_cmd);
14886 install_element (BGP_IPV4_NODE, &bgp_network_mask_natural_route_map_cmd);
14887 install_element (BGP_IPV4_NODE, &no_bgp_table_map_cmd);
14888 install_element (BGP_IPV4_NODE, &no_bgp_network_cmd);
14889 install_element (BGP_IPV4_NODE, &no_bgp_network_mask_cmd);
14890 install_element (BGP_IPV4_NODE, &no_bgp_network_mask_natural_cmd);
14891
14892 install_element (BGP_IPV4_NODE, &aggregate_address_cmd);
14893 install_element (BGP_IPV4_NODE, &aggregate_address_mask_cmd);
14894 install_element (BGP_IPV4_NODE, &aggregate_address_summary_only_cmd);
14895 install_element (BGP_IPV4_NODE, &aggregate_address_mask_summary_only_cmd);
14896 install_element (BGP_IPV4_NODE, &aggregate_address_as_set_cmd);
14897 install_element (BGP_IPV4_NODE, &aggregate_address_mask_as_set_cmd);
14898 install_element (BGP_IPV4_NODE, &aggregate_address_as_set_summary_cmd);
14899 install_element (BGP_IPV4_NODE, &aggregate_address_mask_as_set_summary_cmd);
14900 install_element (BGP_IPV4_NODE, &no_aggregate_address_cmd);
14901 install_element (BGP_IPV4_NODE, &no_aggregate_address_mask_cmd);
14902
14903 /* IPv4 multicast configuration. */
14904 install_element (BGP_IPV4M_NODE, &bgp_table_map_cmd);
14905 install_element (BGP_IPV4M_NODE, &bgp_network_cmd);
14906 install_element (BGP_IPV4M_NODE, &bgp_network_mask_cmd);
14907 install_element (BGP_IPV4M_NODE, &bgp_network_mask_natural_cmd);
14908 install_element (BGP_IPV4M_NODE, &bgp_network_route_map_cmd);
14909 install_element (BGP_IPV4M_NODE, &bgp_network_mask_route_map_cmd);
14910 install_element (BGP_IPV4M_NODE, &bgp_network_mask_natural_route_map_cmd);
14911 install_element (BGP_IPV4M_NODE, &no_bgp_table_map_cmd);
14912 install_element (BGP_IPV4M_NODE, &no_bgp_network_cmd);
14913 install_element (BGP_IPV4M_NODE, &no_bgp_network_mask_cmd);
14914 install_element (BGP_IPV4M_NODE, &no_bgp_network_mask_natural_cmd);
14915 install_element (BGP_IPV4M_NODE, &aggregate_address_cmd);
14916 install_element (BGP_IPV4M_NODE, &aggregate_address_mask_cmd);
14917 install_element (BGP_IPV4M_NODE, &aggregate_address_summary_only_cmd);
14918 install_element (BGP_IPV4M_NODE, &aggregate_address_mask_summary_only_cmd);
14919 install_element (BGP_IPV4M_NODE, &aggregate_address_as_set_cmd);
14920 install_element (BGP_IPV4M_NODE, &aggregate_address_mask_as_set_cmd);
14921 install_element (BGP_IPV4M_NODE, &aggregate_address_as_set_summary_cmd);
14922 install_element (BGP_IPV4M_NODE, &aggregate_address_mask_as_set_summary_cmd);
14923 install_element (BGP_IPV4M_NODE, &no_aggregate_address_cmd);
14924 install_element (BGP_IPV4M_NODE, &no_aggregate_address_mask_cmd);
14925
14926 install_element (VIEW_NODE, &show_ip_bgp_cmd);
14927 install_element (VIEW_NODE, &show_ip_bgp_instance_cmd);
14928 install_element (VIEW_NODE, &show_ip_bgp_instance_all_cmd);
14929 install_element (VIEW_NODE, &show_ip_bgp_ipv4_cmd);
14930 install_element (VIEW_NODE, &show_ip_bgp_route_cmd);
14931 install_element (VIEW_NODE, &show_ip_bgp_instance_route_cmd);
14932 install_element (VIEW_NODE, &show_ip_bgp_route_pathtype_cmd);
14933 install_element (VIEW_NODE, &show_ip_bgp_instance_route_pathtype_cmd);
14934 install_element (VIEW_NODE, &show_bgp_ipv4_safi_route_pathtype_cmd);
14935 install_element (VIEW_NODE, &show_ip_bgp_ipv4_route_cmd);
14936 install_element (VIEW_NODE, &show_ip_bgp_vpnv4_all_route_cmd);
14937 install_element (VIEW_NODE, &show_ip_bgp_vpnv4_rd_route_cmd);
14938 install_element (VIEW_NODE, &show_ip_bgp_prefix_cmd);
14939 install_element (VIEW_NODE, &show_ip_bgp_instance_prefix_cmd);
14940 install_element (VIEW_NODE, &show_ip_bgp_ipv4_prefix_cmd);
14941 install_element (VIEW_NODE, &show_ip_bgp_ipv4_prefix_pathtype_cmd);
14942 install_element (VIEW_NODE, &show_ip_bgp_prefix_pathtype_cmd);
14943 install_element (VIEW_NODE, &show_ip_bgp_instance_prefix_pathtype_cmd);
14944 install_element (VIEW_NODE, &show_ip_bgp_vpnv4_all_prefix_cmd);
14945 install_element (VIEW_NODE, &show_ip_bgp_vpnv4_rd_prefix_cmd);
14946
14947 install_element (VIEW_NODE, &show_ip_bgp_regexp_cmd);
14948 install_element (VIEW_NODE, &show_ip_bgp_ipv4_regexp_cmd);
14949 install_element (VIEW_NODE, &show_ip_bgp_prefix_list_cmd);
14950 install_element (VIEW_NODE, &show_ip_bgp_instance_prefix_list_cmd);
14951 install_element (VIEW_NODE, &show_ip_bgp_ipv4_prefix_list_cmd);
14952 install_element (VIEW_NODE, &show_ip_bgp_filter_list_cmd);
14953 install_element (VIEW_NODE, &show_ip_bgp_instance_filter_list_cmd);
14954 install_element (VIEW_NODE, &show_ip_bgp_ipv4_filter_list_cmd);
14955 install_element (VIEW_NODE, &show_ip_bgp_route_map_cmd);
14956 install_element (VIEW_NODE, &show_ip_bgp_instance_route_map_cmd);
14957 install_element (VIEW_NODE, &show_ip_bgp_ipv4_route_map_cmd);
14958 install_element (VIEW_NODE, &show_ip_bgp_cidr_only_cmd);
14959 install_element (VIEW_NODE, &show_ip_bgp_ipv4_cidr_only_cmd);
14960 install_element (VIEW_NODE, &show_ip_bgp_community_all_cmd);
14961 install_element (VIEW_NODE, &show_ip_bgp_ipv4_community_all_cmd);
14962 install_element (VIEW_NODE, &show_ip_bgp_community_cmd);
14963 install_element (VIEW_NODE, &show_ip_bgp_ipv4_community_cmd);
14964 install_element (VIEW_NODE, &show_bgp_instance_afi_safi_community_all_cmd);
14965 install_element (VIEW_NODE, &show_bgp_instance_afi_safi_community_cmd);
14966 install_element (VIEW_NODE, &show_ip_bgp_community_exact_cmd);
14967 install_element (VIEW_NODE, &show_ip_bgp_ipv4_community_exact_cmd);
14968 install_element (VIEW_NODE, &show_ip_bgp_community_list_cmd);
14969 install_element (VIEW_NODE, &show_ip_bgp_instance_community_list_cmd);
14970 install_element (VIEW_NODE, &show_ip_bgp_ipv4_community_list_cmd);
14971 install_element (VIEW_NODE, &show_ip_bgp_community_list_exact_cmd);
14972 install_element (VIEW_NODE, &show_ip_bgp_ipv4_community_list_exact_cmd);
14973 install_element (VIEW_NODE, &show_ip_bgp_prefix_longer_cmd);
14974 install_element (VIEW_NODE, &show_ip_bgp_instance_prefix_longer_cmd);
14975 install_element (VIEW_NODE, &show_ip_bgp_ipv4_prefix_longer_cmd);
14976 install_element (VIEW_NODE, &show_ip_bgp_neighbor_advertised_route_cmd);
14977 install_element (VIEW_NODE, &show_ip_bgp_instance_neighbor_advertised_route_cmd);
14978 install_element (VIEW_NODE, &show_ip_bgp_ipv4_neighbor_advertised_route_cmd);
14979 install_element (VIEW_NODE, &show_ip_bgp_neighbor_received_routes_cmd);
14980 install_element (VIEW_NODE, &show_ip_bgp_instance_neighbor_received_routes_cmd);
14981 install_element (VIEW_NODE, &show_ip_bgp_ipv4_neighbor_received_routes_cmd);
14982 install_element (VIEW_NODE, &show_bgp_instance_afi_safi_neighbor_adv_recd_routes_cmd);
14983 install_element (VIEW_NODE, &show_ip_bgp_neighbor_routes_cmd);
14984 install_element (VIEW_NODE, &show_ip_bgp_instance_neighbor_routes_cmd);
14985 install_element (VIEW_NODE, &show_ip_bgp_ipv4_neighbor_routes_cmd);
14986 install_element (VIEW_NODE, &show_ip_bgp_neighbor_received_prefix_filter_cmd);
14987 install_element (VIEW_NODE, &show_ip_bgp_ipv4_neighbor_received_prefix_filter_cmd);
14988 install_element (VIEW_NODE, &show_ip_bgp_dampening_params_cmd);
14989 install_element (VIEW_NODE, &show_ip_bgp_ipv4_dampening_parameters_cmd);
14990 install_element (VIEW_NODE, &show_ip_bgp_dampened_paths_cmd);
14991 install_element (VIEW_NODE, &show_ip_bgp_ipv4_dampening_dampd_paths_cmd);
14992 install_element (VIEW_NODE, &show_ip_bgp_ipv4_dampening_flap_stats_cmd);
14993 install_element (VIEW_NODE, &show_ip_bgp_flap_statistics_cmd);
14994 install_element (VIEW_NODE, &show_ip_bgp_flap_address_cmd);
14995 install_element (VIEW_NODE, &show_ip_bgp_flap_prefix_cmd);
14996 install_element (VIEW_NODE, &show_ip_bgp_flap_cidr_only_cmd);
14997 install_element (VIEW_NODE, &show_ip_bgp_flap_regexp_cmd);
14998 install_element (VIEW_NODE, &show_ip_bgp_flap_filter_list_cmd);
14999 install_element (VIEW_NODE, &show_ip_bgp_flap_prefix_list_cmd);
15000 install_element (VIEW_NODE, &show_ip_bgp_flap_prefix_longer_cmd);
15001 install_element (VIEW_NODE, &show_ip_bgp_flap_route_map_cmd);
15002 install_element (VIEW_NODE, &show_ip_bgp_neighbor_flap_cmd);
15003 install_element (VIEW_NODE, &show_ip_bgp_neighbor_damp_cmd);
15004
15005 /* Restricted node: VIEW_NODE - (set of dangerous commands) */
15006 install_element (RESTRICTED_NODE, &show_ip_bgp_route_cmd);
15007 install_element (RESTRICTED_NODE, &show_ip_bgp_instance_route_cmd);
15008 install_element (RESTRICTED_NODE, &show_ip_bgp_route_pathtype_cmd);
15009 install_element (RESTRICTED_NODE, &show_ip_bgp_instance_route_pathtype_cmd);
15010 install_element (RESTRICTED_NODE, &show_bgp_ipv4_safi_route_pathtype_cmd);
15011 install_element (RESTRICTED_NODE, &show_ip_bgp_ipv4_route_cmd);
15012 install_element (RESTRICTED_NODE, &show_ip_bgp_vpnv4_rd_route_cmd);
15013 install_element (RESTRICTED_NODE, &show_ip_bgp_prefix_cmd);
15014 install_element (RESTRICTED_NODE, &show_ip_bgp_instance_prefix_cmd);
15015 install_element (RESTRICTED_NODE, &show_ip_bgp_ipv4_prefix_cmd);
15016 install_element (RESTRICTED_NODE, &show_ip_bgp_ipv4_prefix_pathtype_cmd);
15017 install_element (RESTRICTED_NODE, &show_ip_bgp_prefix_pathtype_cmd);
15018 install_element (RESTRICTED_NODE, &show_ip_bgp_instance_prefix_pathtype_cmd);
15019 install_element (RESTRICTED_NODE, &show_ip_bgp_vpnv4_all_prefix_cmd);
15020 install_element (RESTRICTED_NODE, &show_ip_bgp_vpnv4_rd_prefix_cmd);
15021 install_element (RESTRICTED_NODE, &show_ip_bgp_instance_route_cmd);
15022 install_element (RESTRICTED_NODE, &show_ip_bgp_instance_prefix_cmd);
15023 install_element (RESTRICTED_NODE, &show_ip_bgp_community_cmd);
15024 install_element (RESTRICTED_NODE, &show_ip_bgp_ipv4_community_cmd);
15025 install_element (RESTRICTED_NODE, &show_bgp_instance_afi_safi_community_all_cmd);
15026 install_element (RESTRICTED_NODE, &show_bgp_instance_afi_safi_community_cmd);
15027 install_element (RESTRICTED_NODE, &show_ip_bgp_community_exact_cmd);
15028 install_element (RESTRICTED_NODE, &show_ip_bgp_ipv4_community_exact_cmd);
15029
15030 install_element (ENABLE_NODE, &show_ip_bgp_cmd);
15031 install_element (ENABLE_NODE, &show_ip_bgp_instance_cmd);
15032 install_element (ENABLE_NODE, &show_ip_bgp_instance_all_cmd);
15033 install_element (ENABLE_NODE, &show_ip_bgp_ipv4_cmd);
15034 install_element (ENABLE_NODE, &show_ip_bgp_route_cmd);
15035 install_element (ENABLE_NODE, &show_ip_bgp_instance_route_cmd);
15036 install_element (ENABLE_NODE, &show_ip_bgp_route_pathtype_cmd);
15037 install_element (ENABLE_NODE, &show_ip_bgp_instance_route_pathtype_cmd);
15038 install_element (ENABLE_NODE, &show_bgp_ipv4_safi_route_pathtype_cmd);
15039 install_element (ENABLE_NODE, &show_ip_bgp_ipv4_route_cmd);
15040 install_element (ENABLE_NODE, &show_ip_bgp_vpnv4_all_route_cmd);
15041 install_element (ENABLE_NODE, &show_ip_bgp_vpnv4_rd_route_cmd);
15042 install_element (ENABLE_NODE, &show_ip_bgp_prefix_cmd);
15043 install_element (ENABLE_NODE, &show_ip_bgp_instance_prefix_cmd);
15044 install_element (ENABLE_NODE, &show_ip_bgp_ipv4_prefix_cmd);
15045 install_element (ENABLE_NODE, &show_ip_bgp_ipv4_prefix_pathtype_cmd);
15046 install_element (ENABLE_NODE, &show_ip_bgp_prefix_pathtype_cmd);
15047 install_element (ENABLE_NODE, &show_ip_bgp_instance_prefix_pathtype_cmd);
15048 install_element (ENABLE_NODE, &show_ip_bgp_vpnv4_all_prefix_cmd);
15049 install_element (ENABLE_NODE, &show_ip_bgp_vpnv4_rd_prefix_cmd);
15050
15051 install_element (ENABLE_NODE, &show_ip_bgp_regexp_cmd);
15052 install_element (ENABLE_NODE, &show_ip_bgp_ipv4_regexp_cmd);
15053 install_element (ENABLE_NODE, &show_ip_bgp_prefix_list_cmd);
15054 install_element (ENABLE_NODE, &show_ip_bgp_instance_prefix_list_cmd);
15055 install_element (ENABLE_NODE, &show_ip_bgp_ipv4_prefix_list_cmd);
15056 install_element (ENABLE_NODE, &show_ip_bgp_filter_list_cmd);
15057 install_element (ENABLE_NODE, &show_ip_bgp_instance_filter_list_cmd);
15058 install_element (ENABLE_NODE, &show_ip_bgp_ipv4_filter_list_cmd);
15059 install_element (ENABLE_NODE, &show_ip_bgp_route_map_cmd);
15060 install_element (ENABLE_NODE, &show_ip_bgp_instance_route_map_cmd);
15061 install_element (ENABLE_NODE, &show_ip_bgp_ipv4_route_map_cmd);
15062 install_element (ENABLE_NODE, &show_ip_bgp_cidr_only_cmd);
15063 install_element (ENABLE_NODE, &show_ip_bgp_ipv4_cidr_only_cmd);
15064 install_element (ENABLE_NODE, &show_ip_bgp_community_all_cmd);
15065 install_element (ENABLE_NODE, &show_ip_bgp_ipv4_community_all_cmd);
15066 install_element (ENABLE_NODE, &show_ip_bgp_community_cmd);
15067 install_element (ENABLE_NODE, &show_ip_bgp_ipv4_community_cmd);
15068 install_element (ENABLE_NODE, &show_bgp_instance_afi_safi_community_all_cmd);
15069 install_element (ENABLE_NODE, &show_bgp_instance_afi_safi_community_cmd);
15070 install_element (ENABLE_NODE, &show_ip_bgp_community_exact_cmd);
15071 install_element (ENABLE_NODE, &show_ip_bgp_ipv4_community_exact_cmd);
15072 install_element (ENABLE_NODE, &show_ip_bgp_community_list_cmd);
15073 install_element (ENABLE_NODE, &show_ip_bgp_instance_community_list_cmd);
15074 install_element (ENABLE_NODE, &show_ip_bgp_ipv4_community_list_cmd);
15075 install_element (ENABLE_NODE, &show_ip_bgp_community_list_exact_cmd);
15076 install_element (ENABLE_NODE, &show_ip_bgp_ipv4_community_list_exact_cmd);
15077 install_element (ENABLE_NODE, &show_ip_bgp_prefix_longer_cmd);
15078 install_element (ENABLE_NODE, &show_ip_bgp_instance_prefix_longer_cmd);
15079 install_element (ENABLE_NODE, &show_ip_bgp_ipv4_prefix_longer_cmd);
15080 install_element (ENABLE_NODE, &show_ip_bgp_neighbor_advertised_route_cmd);
15081 install_element (ENABLE_NODE, &show_ip_bgp_instance_neighbor_advertised_route_cmd);
15082 install_element (ENABLE_NODE, &show_ip_bgp_ipv4_neighbor_advertised_route_cmd);
15083 install_element (ENABLE_NODE, &show_ip_bgp_neighbor_received_routes_cmd);
15084 install_element (ENABLE_NODE, &show_ip_bgp_instance_neighbor_received_routes_cmd);
15085 install_element (ENABLE_NODE, &show_ip_bgp_ipv4_neighbor_received_routes_cmd);
15086 install_element (ENABLE_NODE, &show_bgp_instance_afi_safi_neighbor_adv_recd_routes_cmd);
15087 install_element (ENABLE_NODE, &show_ip_bgp_neighbor_routes_cmd);
15088 install_element (ENABLE_NODE, &show_ip_bgp_instance_neighbor_routes_cmd);
15089 install_element (ENABLE_NODE, &show_ip_bgp_ipv4_neighbor_routes_cmd);
15090 install_element (ENABLE_NODE, &show_ip_bgp_neighbor_received_prefix_filter_cmd);
15091 install_element (ENABLE_NODE, &show_ip_bgp_ipv4_neighbor_received_prefix_filter_cmd);
15092 install_element (ENABLE_NODE, &show_ip_bgp_dampening_params_cmd);
15093 install_element (ENABLE_NODE, &show_ip_bgp_dampened_paths_cmd);
15094 install_element (ENABLE_NODE, &show_ip_bgp_ipv4_dampening_parameters_cmd);
15095 install_element (ENABLE_NODE, &show_ip_bgp_ipv4_dampening_dampd_paths_cmd);
15096 install_element (ENABLE_NODE, &show_ip_bgp_ipv4_dampening_flap_stats_cmd);
15097 install_element (ENABLE_NODE, &show_ip_bgp_flap_statistics_cmd);
15098 install_element (ENABLE_NODE, &show_ip_bgp_flap_address_cmd);
15099 install_element (ENABLE_NODE, &show_ip_bgp_flap_prefix_cmd);
15100 install_element (ENABLE_NODE, &show_ip_bgp_flap_cidr_only_cmd);
15101 install_element (ENABLE_NODE, &show_ip_bgp_flap_regexp_cmd);
15102 install_element (ENABLE_NODE, &show_ip_bgp_flap_filter_list_cmd);
15103 install_element (ENABLE_NODE, &show_ip_bgp_flap_prefix_list_cmd);
15104 install_element (ENABLE_NODE, &show_ip_bgp_flap_prefix_longer_cmd);
15105 install_element (ENABLE_NODE, &show_ip_bgp_flap_route_map_cmd);
15106 install_element (ENABLE_NODE, &show_ip_bgp_neighbor_flap_cmd);
15107 install_element (ENABLE_NODE, &show_ip_bgp_neighbor_damp_cmd);
15108
15109 install_element (VIEW_NODE, &show_bgp_ipv4_prefix_cmd);
15110 install_element (ENABLE_NODE, &show_bgp_ipv4_prefix_cmd);
15111 install_element (VIEW_NODE, &show_bgp_ipv4_vpn_rd_route_cmd);
15112 install_element (ENABLE_NODE, &show_bgp_ipv4_vpn_rd_route_cmd);
15113 install_element (VIEW_NODE, &show_bgp_ipv4_vpn_route_cmd);
15114 install_element (ENABLE_NODE, &show_bgp_ipv4_vpn_route_cmd);
15115
15116 install_element (VIEW_NODE, &show_bgp_ipv6_vpn_rd_route_cmd);
15117 install_element (ENABLE_NODE, &show_bgp_ipv6_vpn_rd_route_cmd);
15118 install_element (VIEW_NODE, &show_bgp_ipv6_vpn_route_cmd);
15119 install_element (ENABLE_NODE, &show_bgp_ipv6_vpn_route_cmd);
15120
15121 /* BGP dampening clear commands */
15122 install_element (ENABLE_NODE, &clear_ip_bgp_dampening_cmd);
15123 install_element (ENABLE_NODE, &clear_ip_bgp_dampening_prefix_cmd);
15124 install_element (ENABLE_NODE, &clear_ip_bgp_dampening_address_cmd);
15125 install_element (ENABLE_NODE, &clear_ip_bgp_dampening_address_mask_cmd);
15126
15127 /* prefix count */
15128 install_element (ENABLE_NODE, &show_ip_bgp_neighbor_prefix_counts_cmd);
15129 install_element (ENABLE_NODE, &show_ip_bgp_instance_neighbor_prefix_counts_cmd);
15130 install_element (ENABLE_NODE, &show_ip_bgp_ipv4_neighbor_prefix_counts_cmd);
15131 install_element (ENABLE_NODE, &show_ip_bgp_vpnv4_neighbor_prefix_counts_cmd);
15132 #ifdef HAVE_IPV6
15133 install_element (ENABLE_NODE, &show_bgp_ipv6_neighbor_prefix_counts_cmd);
15134 install_element (ENABLE_NODE, &show_bgp_instance_ipv6_neighbor_prefix_counts_cmd);
15135
15136 /* New config IPv6 BGP commands. */
15137 install_element (BGP_IPV6_NODE, &bgp_table_map_cmd);
15138 install_element (BGP_IPV6_NODE, &ipv6_bgp_network_cmd);
15139 install_element (BGP_IPV6_NODE, &ipv6_bgp_network_route_map_cmd);
15140 install_element (BGP_IPV6_NODE, &no_bgp_table_map_cmd);
15141 install_element (BGP_IPV6_NODE, &no_ipv6_bgp_network_cmd);
15142
15143 install_element (BGP_IPV6_NODE, &ipv6_aggregate_address_cmd);
15144 install_element (BGP_IPV6_NODE, &ipv6_aggregate_address_summary_only_cmd);
15145 install_element (BGP_IPV6_NODE, &no_ipv6_aggregate_address_cmd);
15146 install_element (BGP_IPV6_NODE, &no_ipv6_aggregate_address_summary_only_cmd);
15147
15148 install_element (BGP_IPV6M_NODE, &ipv6_bgp_network_cmd);
15149 install_element (BGP_IPV6M_NODE, &no_ipv6_bgp_network_cmd);
15150
15151 /* Old config IPv6 BGP commands. */
15152
15153
15154 install_element (VIEW_NODE, &show_bgp_cmd);
15155 install_element (VIEW_NODE, &show_bgp_ipv6_safi_cmd);
15156 install_element (VIEW_NODE, &show_bgp_route_cmd);
15157 install_element (VIEW_NODE, &show_bgp_ipv6_route_cmd);
15158 install_element (VIEW_NODE, &show_bgp_ipv6_safi_route_cmd);
15159 install_element (VIEW_NODE, &show_bgp_route_pathtype_cmd);
15160 install_element (VIEW_NODE, &show_bgp_ipv6_safi_route_pathtype_cmd);
15161 install_element (VIEW_NODE, &show_bgp_prefix_cmd);
15162 install_element (VIEW_NODE, &show_bgp_ipv6_prefix_cmd);
15163 install_element (VIEW_NODE, &show_bgp_ipv6_safi_prefix_cmd);
15164 install_element (VIEW_NODE, &show_bgp_prefix_pathtype_cmd);
15165 install_element (VIEW_NODE, &show_bgp_ipv6_safi_prefix_pathtype_cmd);
15166 install_element (VIEW_NODE, &show_bgp_regexp_cmd);
15167 install_element (VIEW_NODE, &show_bgp_prefix_list_cmd);
15168 install_element (VIEW_NODE, &show_bgp_filter_list_cmd);
15169 install_element (VIEW_NODE, &show_bgp_route_map_cmd);
15170 install_element (VIEW_NODE, &show_bgp_community_all_cmd);
15171 install_element (VIEW_NODE, &show_bgp_community_cmd);
15172 install_element (VIEW_NODE, &show_bgp_community_exact_cmd);
15173 install_element (VIEW_NODE, &show_bgp_community_list_cmd);
15174 install_element (VIEW_NODE, &show_bgp_community_list_exact_cmd);
15175 install_element (VIEW_NODE, &show_bgp_prefix_longer_cmd);
15176 install_element (VIEW_NODE, &show_bgp_neighbor_advertised_route_cmd);
15177 install_element (VIEW_NODE, &show_bgp_neighbor_received_routes_cmd);
15178 install_element (VIEW_NODE, &show_bgp_neighbor_routes_cmd);
15179 install_element (VIEW_NODE, &show_bgp_neighbor_received_prefix_filter_cmd);
15180 install_element (VIEW_NODE, &show_bgp_instance_cmd);
15181 install_element (VIEW_NODE, &show_bgp_instance_all_cmd);
15182 install_element (VIEW_NODE, &show_bgp_instance_route_cmd);
15183 install_element (VIEW_NODE, &show_bgp_instance_route_pathtype_cmd);
15184 install_element (VIEW_NODE, &show_bgp_instance_prefix_cmd);
15185 install_element (VIEW_NODE, &show_bgp_instance_prefix_pathtype_cmd);
15186 install_element (VIEW_NODE, &show_bgp_instance_prefix_list_cmd);
15187 install_element (VIEW_NODE, &show_bgp_instance_filter_list_cmd);
15188 install_element (VIEW_NODE, &show_bgp_instance_route_map_cmd);
15189 install_element (VIEW_NODE, &show_bgp_instance_community_list_cmd);
15190 install_element (VIEW_NODE, &show_bgp_instance_prefix_longer_cmd);
15191 install_element (VIEW_NODE, &show_bgp_instance_neighbor_advertised_route_cmd);
15192 install_element (VIEW_NODE, &show_bgp_instance_neighbor_received_routes_cmd);
15193 install_element (VIEW_NODE, &show_bgp_instance_neighbor_routes_cmd);
15194 install_element (VIEW_NODE, &show_bgp_instance_neighbor_received_prefix_filter_cmd);
15195 install_element (VIEW_NODE, &show_bgp_instance_neighbor_flap_cmd);
15196 install_element (VIEW_NODE, &show_bgp_instance_neighbor_damp_cmd);
15197
15198 /* Restricted:
15199 * VIEW_NODE - (set of dangerous commands) - (commands dependent on prev)
15200 */
15201 install_element (RESTRICTED_NODE, &show_bgp_route_cmd);
15202 install_element (RESTRICTED_NODE, &show_bgp_ipv6_route_cmd);
15203 install_element (RESTRICTED_NODE, &show_bgp_ipv6_safi_route_cmd);
15204 install_element (RESTRICTED_NODE, &show_bgp_route_pathtype_cmd);
15205 install_element (RESTRICTED_NODE, &show_bgp_ipv6_safi_route_pathtype_cmd);
15206 install_element (RESTRICTED_NODE, &show_bgp_prefix_cmd);
15207 install_element (RESTRICTED_NODE, &show_bgp_ipv6_prefix_cmd);
15208 install_element (RESTRICTED_NODE, &show_bgp_ipv6_safi_prefix_cmd);
15209 install_element (RESTRICTED_NODE, &show_bgp_prefix_pathtype_cmd);
15210 install_element (RESTRICTED_NODE, &show_bgp_ipv6_safi_prefix_pathtype_cmd);
15211 install_element (RESTRICTED_NODE, &show_bgp_community_cmd);
15212 install_element (RESTRICTED_NODE, &show_bgp_community_exact_cmd);
15213 install_element (RESTRICTED_NODE, &show_bgp_instance_route_cmd);
15214 install_element (RESTRICTED_NODE, &show_bgp_instance_route_pathtype_cmd);
15215 install_element (RESTRICTED_NODE, &show_bgp_instance_prefix_cmd);
15216 install_element (RESTRICTED_NODE, &show_bgp_instance_neighbor_received_prefix_filter_cmd);
15217
15218 install_element (ENABLE_NODE, &show_bgp_cmd);
15219 install_element (ENABLE_NODE, &show_bgp_ipv6_safi_cmd);
15220 install_element (ENABLE_NODE, &show_bgp_route_cmd);
15221 install_element (ENABLE_NODE, &show_bgp_ipv6_route_cmd);
15222 install_element (ENABLE_NODE, &show_bgp_ipv6_safi_route_cmd);
15223 install_element (ENABLE_NODE, &show_bgp_route_pathtype_cmd);
15224 install_element (ENABLE_NODE, &show_bgp_ipv6_safi_route_pathtype_cmd);
15225 install_element (ENABLE_NODE, &show_bgp_prefix_cmd);
15226 install_element (ENABLE_NODE, &show_bgp_prefix_pathtype_cmd);
15227 install_element (ENABLE_NODE, &show_bgp_ipv6_safi_prefix_pathtype_cmd);
15228 install_element (ENABLE_NODE, &show_bgp_ipv6_prefix_cmd);
15229 install_element (ENABLE_NODE, &show_bgp_ipv6_safi_prefix_cmd);
15230 install_element (ENABLE_NODE, &show_bgp_regexp_cmd);
15231 install_element (ENABLE_NODE, &show_bgp_prefix_list_cmd);
15232 install_element (ENABLE_NODE, &show_bgp_filter_list_cmd);
15233 install_element (ENABLE_NODE, &show_bgp_route_map_cmd);
15234 install_element (ENABLE_NODE, &show_bgp_community_all_cmd);
15235 install_element (ENABLE_NODE, &show_bgp_community_cmd);
15236 install_element (ENABLE_NODE, &show_bgp_community_exact_cmd);
15237 install_element (ENABLE_NODE, &show_bgp_community_list_cmd);
15238 install_element (ENABLE_NODE, &show_bgp_community_list_exact_cmd);
15239 install_element (ENABLE_NODE, &show_bgp_prefix_longer_cmd);
15240 install_element (ENABLE_NODE, &show_bgp_neighbor_advertised_route_cmd);
15241 install_element (ENABLE_NODE, &show_bgp_neighbor_received_routes_cmd);
15242 install_element (ENABLE_NODE, &show_bgp_neighbor_routes_cmd);
15243 install_element (ENABLE_NODE, &show_bgp_neighbor_received_prefix_filter_cmd);
15244 install_element (ENABLE_NODE, &show_bgp_instance_cmd);
15245 install_element (ENABLE_NODE, &show_bgp_instance_all_cmd);
15246 install_element (ENABLE_NODE, &show_bgp_instance_route_cmd);
15247 install_element (ENABLE_NODE, &show_bgp_instance_route_pathtype_cmd);
15248 install_element (ENABLE_NODE, &show_bgp_instance_prefix_cmd);
15249 install_element (ENABLE_NODE, &show_bgp_instance_prefix_pathtype_cmd);
15250 install_element (ENABLE_NODE, &show_bgp_instance_prefix_list_cmd);
15251 install_element (ENABLE_NODE, &show_bgp_instance_filter_list_cmd);
15252 install_element (ENABLE_NODE, &show_bgp_instance_route_map_cmd);
15253 install_element (ENABLE_NODE, &show_bgp_instance_community_list_cmd);
15254 install_element (ENABLE_NODE, &show_bgp_instance_prefix_longer_cmd);
15255 install_element (ENABLE_NODE, &show_bgp_instance_neighbor_advertised_route_cmd);
15256 install_element (ENABLE_NODE, &show_bgp_instance_neighbor_received_routes_cmd);
15257 install_element (ENABLE_NODE, &show_bgp_instance_neighbor_routes_cmd);
15258 install_element (ENABLE_NODE, &show_bgp_instance_neighbor_received_prefix_filter_cmd);
15259 install_element (ENABLE_NODE, &show_bgp_instance_neighbor_flap_cmd);
15260 install_element (ENABLE_NODE, &show_bgp_instance_neighbor_damp_cmd);
15261
15262 /* Statistics */
15263 install_element (ENABLE_NODE, &show_bgp_statistics_cmd);
15264 //install_element (ENABLE_NODE, &show_bgp_statistics_vpnv4_cmd);
15265 install_element (ENABLE_NODE, &show_bgp_statistics_view_cmd);
15266 //install_element (ENABLE_NODE, &show_bgp_statistics_view_vpnv4_cmd);
15267
15268 /* old command */
15269 install_element (VIEW_NODE, &show_ipv6_bgp_cmd);
15270 install_element (VIEW_NODE, &show_ipv6_bgp_route_cmd);
15271 install_element (VIEW_NODE, &show_ipv6_bgp_prefix_cmd);
15272 install_element (VIEW_NODE, &show_ipv6_bgp_regexp_cmd);
15273 install_element (VIEW_NODE, &show_ipv6_bgp_prefix_list_cmd);
15274 install_element (VIEW_NODE, &show_ipv6_bgp_filter_list_cmd);
15275 install_element (VIEW_NODE, &show_ipv6_bgp_community_all_cmd);
15276 install_element (VIEW_NODE, &show_ipv6_bgp_community_cmd);
15277 install_element (VIEW_NODE, &show_ipv6_bgp_community_exact_cmd);
15278 install_element (VIEW_NODE, &show_ipv6_bgp_community_list_cmd);
15279 install_element (VIEW_NODE, &show_ipv6_bgp_community_list_exact_cmd);
15280 install_element (VIEW_NODE, &show_ipv6_bgp_prefix_longer_cmd);
15281 install_element (VIEW_NODE, &show_ipv6_mbgp_cmd);
15282 install_element (VIEW_NODE, &show_ipv6_mbgp_route_cmd);
15283 install_element (VIEW_NODE, &show_ipv6_mbgp_prefix_cmd);
15284 install_element (VIEW_NODE, &show_ipv6_mbgp_regexp_cmd);
15285 install_element (VIEW_NODE, &show_ipv6_mbgp_prefix_list_cmd);
15286 install_element (VIEW_NODE, &show_ipv6_mbgp_filter_list_cmd);
15287 install_element (VIEW_NODE, &show_ipv6_mbgp_community_all_cmd);
15288 install_element (VIEW_NODE, &show_ipv6_mbgp_community_cmd);
15289 install_element (VIEW_NODE, &show_ipv6_mbgp_community_exact_cmd);
15290 install_element (VIEW_NODE, &show_ipv6_mbgp_community_list_cmd);
15291 install_element (VIEW_NODE, &show_ipv6_mbgp_community_list_exact_cmd);
15292 install_element (VIEW_NODE, &show_ipv6_mbgp_prefix_longer_cmd);
15293
15294 /* old command */
15295 install_element (ENABLE_NODE, &show_ipv6_bgp_cmd);
15296 install_element (ENABLE_NODE, &show_ipv6_bgp_route_cmd);
15297 install_element (ENABLE_NODE, &show_ipv6_bgp_prefix_cmd);
15298 install_element (ENABLE_NODE, &show_ipv6_bgp_regexp_cmd);
15299 install_element (ENABLE_NODE, &show_ipv6_bgp_prefix_list_cmd);
15300 install_element (ENABLE_NODE, &show_ipv6_bgp_filter_list_cmd);
15301 install_element (ENABLE_NODE, &show_ipv6_bgp_community_all_cmd);
15302 install_element (ENABLE_NODE, &show_ipv6_bgp_community_cmd);
15303 install_element (ENABLE_NODE, &show_ipv6_bgp_community_exact_cmd);
15304 install_element (ENABLE_NODE, &show_ipv6_bgp_community_list_cmd);
15305 install_element (ENABLE_NODE, &show_ipv6_bgp_community_list_exact_cmd);
15306 install_element (ENABLE_NODE, &show_ipv6_bgp_prefix_longer_cmd);
15307 install_element (ENABLE_NODE, &show_ipv6_mbgp_cmd);
15308 install_element (ENABLE_NODE, &show_ipv6_mbgp_route_cmd);
15309 install_element (ENABLE_NODE, &show_ipv6_mbgp_prefix_cmd);
15310 install_element (ENABLE_NODE, &show_ipv6_mbgp_regexp_cmd);
15311 install_element (ENABLE_NODE, &show_ipv6_mbgp_prefix_list_cmd);
15312 install_element (ENABLE_NODE, &show_ipv6_mbgp_filter_list_cmd);
15313 install_element (ENABLE_NODE, &show_ipv6_mbgp_community_all_cmd);
15314 install_element (ENABLE_NODE, &show_ipv6_mbgp_community_cmd);
15315 install_element (ENABLE_NODE, &show_ipv6_mbgp_community_exact_cmd);
15316 install_element (ENABLE_NODE, &show_ipv6_mbgp_community_list_cmd);
15317 install_element (ENABLE_NODE, &show_ipv6_mbgp_community_list_exact_cmd);
15318 install_element (ENABLE_NODE, &show_ipv6_mbgp_prefix_longer_cmd);
15319
15320 /* old command */
15321 install_element (VIEW_NODE, &ipv6_mbgp_neighbor_advertised_route_cmd);
15322 install_element (ENABLE_NODE, &ipv6_mbgp_neighbor_advertised_route_cmd);
15323
15324 /* old command */
15325 install_element (VIEW_NODE, &ipv6_mbgp_neighbor_received_routes_cmd);
15326 install_element (ENABLE_NODE, &ipv6_mbgp_neighbor_received_routes_cmd);
15327
15328 /* old command */
15329 install_element (VIEW_NODE, &ipv6_mbgp_neighbor_routes_cmd);
15330 install_element (ENABLE_NODE, &ipv6_mbgp_neighbor_routes_cmd);
15331 #endif /* HAVE_IPV6 */
15332
15333 install_element (BGP_NODE, &bgp_distance_cmd);
15334 install_element (BGP_NODE, &no_bgp_distance_cmd);
15335 install_element (BGP_NODE, &bgp_distance_source_cmd);
15336 install_element (BGP_NODE, &no_bgp_distance_source_cmd);
15337 install_element (BGP_NODE, &bgp_distance_source_access_list_cmd);
15338 install_element (BGP_NODE, &no_bgp_distance_source_access_list_cmd);
15339
15340 install_element (BGP_NODE, &bgp_damp_set_cmd);
15341 install_element (BGP_NODE, &bgp_damp_unset_cmd);
15342 install_element (BGP_IPV4_NODE, &bgp_damp_set_cmd);
15343 install_element (BGP_IPV4_NODE, &bgp_damp_unset_cmd);
15344
15345 /* IPv4 Multicast Mode */
15346 install_element (BGP_IPV4M_NODE, &bgp_damp_set_cmd);
15347 install_element (BGP_IPV4M_NODE, &bgp_damp_unset_cmd);
15348 }
15349
15350 void
15351 bgp_route_finish (void)
15352 {
15353 bgp_table_unlock (bgp_distance_table);
15354 bgp_distance_table = NULL;
15355 }