]> git.proxmox.com Git - mirror_frr.git/blob - bgpd/bgp_zebra.c
bgpd, zebra: rfc-5549-generic.patch
[mirror_frr.git] / bgpd / bgp_zebra.c
1 /* zebra client
2 Copyright (C) 1997, 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
18 Free Software Foundation, Inc., 59 Temple Place - Suite 330,
19 Boston, MA 02111-1307, USA. */
20
21 #include <zebra.h>
22
23 #include "command.h"
24 #include "stream.h"
25 #include "network.h"
26 #include "prefix.h"
27 #include "log.h"
28 #include "sockunion.h"
29 #include "zclient.h"
30 #include "routemap.h"
31 #include "thread.h"
32 #include "queue.h"
33
34 #include "bgpd/bgpd.h"
35 #include "bgpd/bgp_route.h"
36 #include "bgpd/bgp_attr.h"
37 #include "bgpd/bgp_nexthop.h"
38 #include "bgpd/bgp_zebra.h"
39 #include "bgpd/bgp_fsm.h"
40 #include "bgpd/bgp_debug.h"
41 #include "bgpd/bgp_mpath.h"
42 #include "bgpd/bgp_nexthop.h"
43 #include "bgpd/bgp_nht.h"
44
45 /* All information about zebra. */
46 struct zclient *zclient = NULL;
47 struct in_addr router_id_zebra;
48
49 /* Growable buffer for nexthops sent to zebra */
50 struct stream *bgp_nexthop_buf = NULL;
51 struct stream *bgp_ifindices_buf = NULL;
52
53 /* These array buffers are used in making a copy of the attributes for
54 route-map apply. Arrays are being used here to minimize mallocs and
55 frees for the temporary copy of the attributes.
56 Given the zapi api expects the nexthop buffer to contain pointer to
57 pointers for nexthops, we couldnt have used a single nexthop variable
58 on the stack, hence we had two options:
59 1. maintain a linked-list and free it after zapi_*_route call
60 2. use an array to avoid number of mallocs.
61 Number of supported next-hops are finite, use of arrays should be ok. */
62 struct attr attr_cp[BGP_MAXIMUM_MAXPATHS];
63 struct attr_extra attr_extra_cp[BGP_MAXIMUM_MAXPATHS];
64 int attr_index = 0;
65
66 /* Once per address-family initialization of the attribute array */
67 #define BGP_INFO_ATTR_BUF_INIT()\
68 do {\
69 memset(attr_cp, 0, BGP_MAXIMUM_MAXPATHS * sizeof(struct attr));\
70 memset(attr_extra_cp, 0, BGP_MAXIMUM_MAXPATHS * sizeof(struct attr_extra));\
71 attr_index = 0;\
72 } while (0)
73
74 #define BGP_INFO_ATTR_BUF_COPY(info_src, info_dst)\
75 do { \
76 *info_dst = *info_src; \
77 assert(attr_index != BGP_MAXIMUM_MAXPATHS);\
78 attr_cp[attr_index].extra = &attr_extra_cp[attr_index]; \
79 bgp_attr_dup (&attr_cp[attr_index], info_src->attr); \
80 bgp_attr_deep_dup (&attr_cp[attr_index], info_src->attr); \
81 info_dst->attr = &attr_cp[attr_index]; \
82 attr_index++;\
83 } while (0)
84
85 #define BGP_INFO_ATTR_BUF_FREE(info) \
86 do { \
87 bgp_attr_deep_free(info->attr); \
88 } while (0)
89
90 /* Router-id update message from zebra. */
91 static int
92 bgp_router_id_update (int command, struct zclient *zclient, zebra_size_t length)
93 {
94 struct prefix router_id;
95 struct listnode *node, *nnode;
96 struct bgp *bgp;
97
98 zebra_router_id_update_read(zclient->ibuf,&router_id);
99
100 if (BGP_DEBUG (zebra, ZEBRA))
101 {
102 char buf[128];
103 prefix2str(&router_id, buf, sizeof(buf));
104 zlog_debug("Zebra rcvd: router id update %s", buf);
105 }
106
107 router_id_zebra = router_id.u.prefix4;
108
109 for (ALL_LIST_ELEMENTS (bm->bgp, node, nnode, bgp))
110 {
111 if (!bgp->router_id_static.s_addr)
112 bgp_router_id_set (bgp, &router_id.u.prefix4);
113 }
114
115 return 0;
116 }
117
118 /* Nexthop update message from zebra. */
119 static int
120 bgp_read_nexthop_update (int command, struct zclient *zclient,
121 zebra_size_t length)
122 {
123 bgp_parse_nexthop_update(command);
124 return 0;
125 }
126
127 static int
128 bgp_read_import_check_update(int command, struct zclient *zclient,
129 zebra_size_t length)
130 {
131 bgp_parse_nexthop_update(command);
132 return 0;
133 }
134
135 static void
136 bgp_nbr_connected_add (struct nbr_connected *ifc)
137 {
138 struct listnode *node, *nnode, *mnode;
139 struct bgp *bgp;
140 struct peer *peer;
141
142 for (ALL_LIST_ELEMENTS_RO (bm->bgp, mnode, bgp))
143 {
144 for (ALL_LIST_ELEMENTS (bgp->peer, node, nnode, peer))
145 {
146 if (peer->conf_if && (strcmp (peer->conf_if, ifc->ifp->name) == 0))
147 {
148 if (peer_active(peer))
149 BGP_EVENT_ADD (peer, BGP_Stop);
150 BGP_EVENT_ADD (peer, BGP_Start);
151 }
152 }
153 }
154 }
155
156 static void
157 bgp_nbr_connected_delete (struct nbr_connected *ifc)
158 {
159 struct listnode *node, *nnode, *mnode;
160 struct bgp *bgp;
161 struct peer *peer;
162
163 for (ALL_LIST_ELEMENTS_RO (bm->bgp, mnode, bgp))
164 {
165 for (ALL_LIST_ELEMENTS (bgp->peer, node, nnode, peer))
166 {
167 if (peer->conf_if && (strcmp (peer->conf_if, ifc->ifp->name) == 0))
168 {
169 BGP_EVENT_ADD (peer, BGP_Stop);
170 }
171 }
172 }
173 }
174
175 /* Inteface addition message from zebra. */
176 static int
177 bgp_interface_add (int command, struct zclient *zclient, zebra_size_t length)
178 {
179 struct interface *ifp;
180
181 ifp = zebra_interface_add_read (zclient->ibuf);
182
183 if (BGP_DEBUG (zebra, ZEBRA) && ifp)
184 zlog_debug("Zebra rcvd: interface add %s", ifp->name);
185
186 return 0;
187 }
188
189 static int
190 bgp_interface_delete (int command, struct zclient *zclient,
191 zebra_size_t length)
192 {
193 struct stream *s;
194 struct interface *ifp;
195
196 s = zclient->ibuf;
197 ifp = zebra_interface_state_read (s);
198 ifp->ifindex = IFINDEX_INTERNAL;
199
200 if (BGP_DEBUG (zebra, ZEBRA))
201 zlog_debug("Zebra rcvd: interface delete %s", ifp->name);
202
203 return 0;
204 }
205
206 static int
207 bgp_interface_up (int command, struct zclient *zclient, zebra_size_t length)
208 {
209 struct stream *s;
210 struct interface *ifp;
211 struct connected *c;
212 struct nbr_connected *nc;
213 struct listnode *node, *nnode;
214
215 s = zclient->ibuf;
216 ifp = zebra_interface_state_read (s);
217
218 if (! ifp)
219 return 0;
220
221 if (BGP_DEBUG (zebra, ZEBRA))
222 zlog_debug("Zebra rcvd: interface %s up", ifp->name);
223
224 for (ALL_LIST_ELEMENTS (ifp->connected, node, nnode, c))
225 bgp_connected_add (c);
226
227 for (ALL_LIST_ELEMENTS (ifp->nbr_connected, node, nnode, nc))
228 bgp_nbr_connected_add (nc);
229
230 return 0;
231 }
232
233 static int
234 bgp_interface_down (int command, struct zclient *zclient, zebra_size_t length)
235 {
236 struct stream *s;
237 struct interface *ifp;
238 struct connected *c;
239 struct nbr_connected *nc;
240 struct listnode *node, *nnode;
241
242 s = zclient->ibuf;
243 ifp = zebra_interface_state_read (s);
244 if (! ifp)
245 return 0;
246
247 if (BGP_DEBUG (zebra, ZEBRA))
248 zlog_debug("Zebra rcvd: interface %s down", ifp->name);
249
250 for (ALL_LIST_ELEMENTS (ifp->connected, node, nnode, c))
251 bgp_connected_delete (c);
252
253 for (ALL_LIST_ELEMENTS (ifp->nbr_connected, node, nnode, nc))
254 bgp_nbr_connected_delete (nc);
255
256 /* Fast external-failover */
257 {
258 struct listnode *mnode;
259 struct bgp *bgp;
260 struct peer *peer;
261
262 for (ALL_LIST_ELEMENTS_RO (bm->bgp, mnode, bgp))
263 {
264 if (CHECK_FLAG (bgp->flags, BGP_FLAG_NO_FAST_EXT_FAILOVER))
265 continue;
266
267 for (ALL_LIST_ELEMENTS (bgp->peer, node, nnode, peer))
268 {
269 if ((peer->ttl != 1) && (peer->gtsm_hops != 1))
270 continue;
271
272 if (ifp == peer->nexthop.ifp)
273 BGP_EVENT_ADD (peer, BGP_Stop);
274 }
275 }
276 }
277
278 return 0;
279 }
280
281 static int
282 bgp_interface_bfd_dest_down (int command, struct zclient *zclient,
283 zebra_size_t length)
284 {
285 struct interface *ifp;
286 struct prefix p;
287
288 ifp = zebra_interface_bfd_read (zclient->ibuf, &p);
289
290 if (ifp == NULL)
291 return 0;
292
293 if (BGP_DEBUG (zebra, ZEBRA))
294 {
295 char buf[128];
296 prefix2str(&p, buf, sizeof(buf));
297 zlog_debug("Zebra: interface %s bfd destination %s down", ifp->name, buf);
298 }
299
300 /* Bring the peer down if BFD is enabled in BGP */
301 {
302 struct listnode *mnode, *node, *nnode;
303 struct bgp *bgp;
304 struct peer *peer;
305
306 for (ALL_LIST_ELEMENTS_RO (bm->bgp, mnode, bgp))
307 {
308 for (ALL_LIST_ELEMENTS (bgp->peer, node, nnode, peer))
309 {
310 if (!CHECK_FLAG (peer->flags, PEER_FLAG_BFD))
311 continue;
312
313 if (ifp == peer->nexthop.ifp)
314 BGP_EVENT_ADD (peer, BGP_Stop);
315 }
316 }
317 }
318
319 return 0;
320 }
321
322 static int
323 bgp_interface_address_add (int command, struct zclient *zclient,
324 zebra_size_t length)
325 {
326 struct connected *ifc;
327
328 ifc = zebra_interface_address_read (command, zclient->ibuf);
329
330 if (ifc == NULL)
331 return 0;
332
333 if (bgp_debug_zebra(ifc->address))
334 {
335 char buf[128];
336 prefix2str(ifc->address, buf, sizeof(buf));
337 zlog_debug("Zebra rcvd: interface %s address add %s",
338 ifc->ifp->name, buf);
339 }
340
341 if (if_is_operative (ifc->ifp))
342 bgp_connected_add (ifc);
343
344 return 0;
345 }
346
347 static int
348 bgp_interface_address_delete (int command, struct zclient *zclient,
349 zebra_size_t length)
350 {
351 struct connected *ifc;
352
353 ifc = zebra_interface_address_read (command, zclient->ibuf);
354
355 if (ifc == NULL)
356 return 0;
357
358 if (bgp_debug_zebra(ifc->address))
359 {
360 char buf[128];
361 prefix2str(ifc->address, buf, sizeof(buf));
362 zlog_debug("Zebra rcvd: interface %s address delete %s",
363 ifc->ifp->name, buf);
364 }
365
366 if (if_is_operative (ifc->ifp))
367 bgp_connected_delete (ifc);
368
369 connected_free (ifc);
370
371 return 0;
372 }
373
374 static int
375 bgp_interface_nbr_address_add (int command, struct zclient *zclient,
376 zebra_size_t length)
377 {
378 struct nbr_connected *ifc = NULL;
379
380 ifc = zebra_interface_nbr_address_read (command, zclient->ibuf);
381
382 if (ifc == NULL)
383 return 0;
384
385 if (bgp_debug_zebra(ifc->address))
386 {
387 char buf[128];
388 prefix2str(ifc->address, buf, sizeof(buf));
389 zlog_debug("Zebra rcvd: interface %s nbr address add %s",
390 ifc->ifp->name, buf);
391 }
392
393 if (if_is_operative (ifc->ifp))
394 bgp_nbr_connected_add (ifc);
395
396 return 0;
397 }
398
399 static int
400 bgp_interface_nbr_address_delete (int command, struct zclient *zclient,
401 zebra_size_t length)
402 {
403 struct nbr_connected *ifc = NULL;
404
405 ifc = zebra_interface_nbr_address_read (command, zclient->ibuf);
406
407 if (ifc == NULL)
408 return 0;
409
410 if (bgp_debug_zebra(ifc->address))
411 {
412 char buf[128];
413 prefix2str(ifc->address, buf, sizeof(buf));
414 zlog_debug("Zebra rcvd: interface %s nbr address delete %s",
415 ifc->ifp->name, buf);
416 }
417
418 if (if_is_operative (ifc->ifp))
419 bgp_nbr_connected_delete (ifc);
420
421 nbr_connected_free (ifc);
422
423 return 0;
424 }
425
426 /* Zebra route add and delete treatment. */
427 static int
428 zebra_read_ipv4 (int command, struct zclient *zclient, zebra_size_t length)
429 {
430 struct stream *s;
431 struct zapi_ipv4 api;
432 struct in_addr nexthop;
433 struct prefix_ipv4 p;
434 unsigned int ifindex;
435
436 s = zclient->ibuf;
437 nexthop.s_addr = 0;
438
439 /* Type, flags, message. */
440 api.type = stream_getc (s);
441 api.instance = stream_getw (s);
442 api.flags = stream_getc (s);
443 api.message = stream_getc (s);
444
445 /* IPv4 prefix. */
446 memset (&p, 0, sizeof (struct prefix_ipv4));
447 p.family = AF_INET;
448 p.prefixlen = stream_getc (s);
449 stream_get (&p.prefix, s, PSIZE (p.prefixlen));
450
451 /* Nexthop, ifindex, distance, metric. */
452 if (CHECK_FLAG (api.message, ZAPI_MESSAGE_NEXTHOP))
453 {
454 api.nexthop_num = stream_getc (s);
455 nexthop.s_addr = stream_get_ipv4 (s);
456 }
457
458 if (CHECK_FLAG (api.message, ZAPI_MESSAGE_IFINDEX))
459 {
460 api.ifindex_num = stream_getc (s);
461 ifindex = stream_getl (s); /* ifindex, unused */
462 }
463 else
464 {
465 ifindex = 0;
466 }
467
468 if (CHECK_FLAG (api.message, ZAPI_MESSAGE_DISTANCE))
469 api.distance = stream_getc (s);
470
471 if (CHECK_FLAG (api.message, ZAPI_MESSAGE_METRIC))
472 api.metric = stream_getl (s);
473 else
474 api.metric = 0;
475
476 if (CHECK_FLAG (api.message, ZAPI_MESSAGE_TAG))
477 api.tag = stream_getw (s);
478 else
479 api.tag = 0;
480
481 if (command == ZEBRA_IPV4_ROUTE_ADD)
482 {
483 if (bgp_debug_zebra((struct prefix *)&p))
484 {
485 char buf[2][INET_ADDRSTRLEN];
486 zlog_debug("Zebra rcvd: IPv4 route add %s[%d] %s/%d nexthop %s metric %u tag %d",
487 zebra_route_string(api.type), api.instance,
488 inet_ntop(AF_INET, &p.prefix, buf[0], sizeof(buf[0])),
489 p.prefixlen,
490 inet_ntop(AF_INET, &nexthop, buf[1], sizeof(buf[1])),
491 api.metric,
492 api.tag);
493 }
494 bgp_redistribute_add((struct prefix *)&p, &nexthop, NULL, ifindex,
495 api.metric, api.type, api.instance, api.tag);
496 }
497 else
498 {
499 if (bgp_debug_zebra((struct prefix *)&p))
500 {
501 char buf[2][INET_ADDRSTRLEN];
502 zlog_debug("Zebra rcvd: IPv4 route delete %s[%d] %s/%d "
503 "nexthop %s metric %u tag %d",
504 zebra_route_string(api.type), api.instance,
505 inet_ntop(AF_INET, &p.prefix, buf[0], sizeof(buf[0])),
506 p.prefixlen,
507 inet_ntop(AF_INET, &nexthop, buf[1], sizeof(buf[1])),
508 api.metric,
509 api.tag);
510 }
511 bgp_redistribute_delete((struct prefix *)&p, api.type, api.instance);
512 }
513
514 return 0;
515 }
516
517 #ifdef HAVE_IPV6
518 /* Zebra route add and delete treatment. */
519 static int
520 zebra_read_ipv6 (int command, struct zclient *zclient, zebra_size_t length)
521 {
522 struct stream *s;
523 struct zapi_ipv6 api;
524 struct in6_addr nexthop;
525 struct prefix_ipv6 p;
526 unsigned int ifindex;
527
528 s = zclient->ibuf;
529 memset (&nexthop, 0, sizeof (struct in6_addr));
530
531 /* Type, flags, message. */
532 api.type = stream_getc (s);
533 api.instance = stream_getw (s);
534 api.flags = stream_getc (s);
535 api.message = stream_getc (s);
536
537 /* IPv6 prefix. */
538 memset (&p, 0, sizeof (struct prefix_ipv6));
539 p.family = AF_INET6;
540 p.prefixlen = stream_getc (s);
541 stream_get (&p.prefix, s, PSIZE (p.prefixlen));
542
543 /* Nexthop, ifindex, distance, metric. */
544 if (CHECK_FLAG (api.message, ZAPI_MESSAGE_NEXTHOP))
545 {
546 api.nexthop_num = stream_getc (s);
547 stream_get (&nexthop, s, 16);
548 }
549
550 if (CHECK_FLAG (api.message, ZAPI_MESSAGE_IFINDEX))
551 {
552 api.ifindex_num = stream_getc (s);
553 ifindex = stream_getl (s); /* ifindex, unused */
554 }
555 else
556 {
557 ifindex = 0;
558 }
559
560 if (CHECK_FLAG (api.message, ZAPI_MESSAGE_DISTANCE))
561 api.distance = stream_getc (s);
562 else
563 api.distance = 0;
564
565 if (CHECK_FLAG (api.message, ZAPI_MESSAGE_METRIC))
566 api.metric = stream_getl (s);
567 else
568 api.metric = 0;
569
570 if (CHECK_FLAG (api.message, ZAPI_MESSAGE_TAG))
571 api.tag = stream_getw (s);
572 else
573 api.tag = 0;
574
575 /* Simply ignore link-local address. */
576 if (IN6_IS_ADDR_LINKLOCAL (&p.prefix))
577 return 0;
578
579 if (command == ZEBRA_IPV6_ROUTE_ADD)
580 {
581 if (bgp_debug_zebra((struct prefix *)&p))
582 {
583 char buf[2][INET6_ADDRSTRLEN];
584 zlog_debug("Zebra rcvd: IPv6 route add %s[%d] %s/%d nexthop %s metric %u tag %d",
585 zebra_route_string(api.type), api.instance,
586 inet_ntop(AF_INET6, &p.prefix, buf[0], sizeof(buf[0])),
587 p.prefixlen,
588 inet_ntop(AF_INET, &nexthop, buf[1], sizeof(buf[1])),
589 api.metric,
590 api.tag);
591 }
592 bgp_redistribute_add ((struct prefix *)&p, NULL, &nexthop, ifindex,
593 api.metric, api.type, api.instance, api.tag);
594 }
595 else
596 {
597 if (bgp_debug_zebra((struct prefix *)&p))
598 {
599 char buf[2][INET6_ADDRSTRLEN];
600 zlog_debug("Zebra rcvd: IPv6 route delete %s[%d] %s/%d "
601 "nexthop %s metric %u tag %d",
602 zebra_route_string(api.type), api.instance,
603 inet_ntop(AF_INET6, &p.prefix, buf[0], sizeof(buf[0])),
604 p.prefixlen,
605 inet_ntop(AF_INET6, &nexthop, buf[1], sizeof(buf[1])),
606 api.metric,
607 api.tag);
608 }
609 bgp_redistribute_delete ((struct prefix *) &p, api.type, api.instance);
610 }
611
612 return 0;
613 }
614 #endif /* HAVE_IPV6 */
615
616 struct interface *
617 if_lookup_by_ipv4 (struct in_addr *addr)
618 {
619 struct listnode *ifnode;
620 struct listnode *cnode;
621 struct interface *ifp;
622 struct connected *connected;
623 struct prefix_ipv4 p;
624 struct prefix *cp;
625
626 p.family = AF_INET;
627 p.prefix = *addr;
628 p.prefixlen = IPV4_MAX_BITLEN;
629
630 for (ALL_LIST_ELEMENTS_RO (iflist, ifnode, ifp))
631 {
632 for (ALL_LIST_ELEMENTS_RO (ifp->connected, cnode, connected))
633 {
634 cp = connected->address;
635
636 if (cp->family == AF_INET)
637 if (prefix_match (cp, (struct prefix *)&p))
638 return ifp;
639 }
640 }
641 return NULL;
642 }
643
644 struct interface *
645 if_lookup_by_ipv4_exact (struct in_addr *addr)
646 {
647 struct listnode *ifnode;
648 struct listnode *cnode;
649 struct interface *ifp;
650 struct connected *connected;
651 struct prefix *cp;
652
653 for (ALL_LIST_ELEMENTS_RO (iflist, ifnode, ifp))
654 {
655 for (ALL_LIST_ELEMENTS_RO (ifp->connected, cnode, connected))
656 {
657 cp = connected->address;
658
659 if (cp->family == AF_INET)
660 if (IPV4_ADDR_SAME (&cp->u.prefix4, addr))
661 return ifp;
662 }
663 }
664 return NULL;
665 }
666
667 #ifdef HAVE_IPV6
668 struct interface *
669 if_lookup_by_ipv6 (struct in6_addr *addr, unsigned int ifindex)
670 {
671 struct listnode *ifnode;
672 struct listnode *cnode;
673 struct interface *ifp;
674 struct connected *connected;
675 struct prefix_ipv6 p;
676 struct prefix *cp;
677
678 p.family = AF_INET6;
679 p.prefix = *addr;
680 p.prefixlen = IPV6_MAX_BITLEN;
681
682 for (ALL_LIST_ELEMENTS_RO (iflist, ifnode, ifp))
683 {
684 for (ALL_LIST_ELEMENTS_RO (ifp->connected, cnode, connected))
685 {
686 cp = connected->address;
687
688 if (cp->family == AF_INET6)
689 if (prefix_match (cp, (struct prefix *)&p))
690 {
691 if (IN6_IS_ADDR_LINKLOCAL(&cp->u.prefix6.s6_addr32[0]))
692 {
693 if (ifindex == ifp->ifindex)
694 return ifp;
695 }
696 else
697 return ifp;
698 }
699 }
700 }
701 return NULL;
702 }
703
704 struct interface *
705 if_lookup_by_ipv6_exact (struct in6_addr *addr, unsigned int ifindex)
706 {
707 struct listnode *ifnode;
708 struct listnode *cnode;
709 struct interface *ifp;
710 struct connected *connected;
711 struct prefix *cp;
712
713 for (ALL_LIST_ELEMENTS_RO (iflist, ifnode, ifp))
714 {
715 for (ALL_LIST_ELEMENTS_RO (ifp->connected, cnode, connected))
716 {
717 cp = connected->address;
718
719 if (cp->family == AF_INET6)
720 if (IPV6_ADDR_SAME (&cp->u.prefix6, addr))
721 {
722 if (IN6_IS_ADDR_LINKLOCAL(&cp->u.prefix6))
723 {
724 if (ifindex == ifp->ifindex)
725 return ifp;
726 }
727 else
728 return ifp;
729 }
730 }
731 }
732 return NULL;
733 }
734
735 static int
736 if_get_ipv6_global (struct interface *ifp, struct in6_addr *addr)
737 {
738 struct listnode *cnode;
739 struct connected *connected;
740 struct prefix *cp;
741
742 for (ALL_LIST_ELEMENTS_RO (ifp->connected, cnode, connected))
743 {
744 cp = connected->address;
745
746 if (cp->family == AF_INET6)
747 if (! IN6_IS_ADDR_LINKLOCAL (&cp->u.prefix6))
748 {
749 memcpy (addr, &cp->u.prefix6, IPV6_MAX_BYTELEN);
750 return 1;
751 }
752 }
753 return 0;
754 }
755
756 static int
757 if_get_ipv6_local (struct interface *ifp, struct in6_addr *addr)
758 {
759 struct listnode *cnode;
760 struct connected *connected;
761 struct prefix *cp;
762
763 for (ALL_LIST_ELEMENTS_RO (ifp->connected, cnode, connected))
764 {
765 cp = connected->address;
766
767 if (cp->family == AF_INET6)
768 if (IN6_IS_ADDR_LINKLOCAL (&cp->u.prefix6))
769 {
770 memcpy (addr, &cp->u.prefix6, IPV6_MAX_BYTELEN);
771 return 1;
772 }
773 }
774 return 0;
775 }
776 #endif /* HAVE_IPV6 */
777
778 static int
779 if_get_ipv4_address (struct interface *ifp, struct in_addr *addr)
780 {
781 struct listnode *cnode;
782 struct connected *connected;
783 struct prefix *cp;
784
785 for (ALL_LIST_ELEMENTS_RO (ifp->connected, cnode, connected))
786 {
787 cp = connected->address;
788 if ((cp->family == AF_INET) && !ipv4_martian(&(cp->u.prefix4)))
789 {
790 *addr = cp->u.prefix4;
791 return 1;
792 }
793 }
794 return 0;
795 }
796
797 int
798 bgp_nexthop_set (union sockunion *local, union sockunion *remote,
799 struct bgp_nexthop *nexthop, struct peer *peer)
800 {
801 int ret = 0;
802 struct interface *ifp = NULL;
803
804 memset (nexthop, 0, sizeof (struct bgp_nexthop));
805
806 if (!local)
807 return -1;
808 if (!remote)
809 return -1;
810
811 if (local->sa.sa_family == AF_INET)
812 {
813 nexthop->v4 = local->sin.sin_addr;
814 if (peer->update_if)
815 ifp = if_lookup_by_name (peer->update_if);
816 else
817 ifp = if_lookup_by_ipv4_exact (&local->sin.sin_addr);
818 }
819 #ifdef HAVE_IPV6
820 if (local->sa.sa_family == AF_INET6)
821 {
822 if (IN6_IS_ADDR_LINKLOCAL (&local->sin6.sin6_addr))
823 {
824 if (peer->conf_if || peer->ifname)
825 ifp = if_lookup_by_index (if_nametoindex (peer->conf_if ? peer->conf_if : peer->ifname));
826 }
827 else if (peer->update_if)
828 ifp = if_lookup_by_name (peer->update_if);
829 else
830 ifp = if_lookup_by_ipv6_exact (&local->sin6.sin6_addr,
831 local->sin6.sin6_scope_id);
832 }
833 #endif /* HAVE_IPV6 */
834
835 if (!ifp)
836 return -1;
837
838 nexthop->ifp = ifp;
839
840 /* IPv4 connection. */
841 if (local->sa.sa_family == AF_INET)
842 {
843 #ifdef HAVE_IPV6
844 /* IPv6 nexthop*/
845 ret = if_get_ipv6_global (ifp, &nexthop->v6_global);
846
847 /* There is no global nexthop. */
848 if (!ret)
849 if_get_ipv6_local (ifp, &nexthop->v6_global);
850 else
851 if_get_ipv6_local (ifp, &nexthop->v6_local);
852 #endif /* HAVE_IPV6 */
853 }
854
855 #ifdef HAVE_IPV6
856 /* IPv6 connection. */
857 if (local->sa.sa_family == AF_INET6)
858 {
859 struct interface *direct = NULL;
860
861 /* IPv4 nexthop. */
862 ret = if_get_ipv4_address(ifp, &nexthop->v4);
863 if (!ret && peer->local_id.s_addr)
864 nexthop->v4 = peer->local_id;
865
866 /* Global address*/
867 if (! IN6_IS_ADDR_LINKLOCAL (&local->sin6.sin6_addr))
868 {
869 memcpy (&nexthop->v6_global, &local->sin6.sin6_addr,
870 IPV6_MAX_BYTELEN);
871
872 /* If directory connected set link-local address. */
873 direct = if_lookup_by_ipv6 (&remote->sin6.sin6_addr,
874 remote->sin6.sin6_scope_id);
875 if (direct)
876 if_get_ipv6_local (ifp, &nexthop->v6_local);
877 }
878 else
879 /* Link-local address. */
880 {
881 ret = if_get_ipv6_global (ifp, &nexthop->v6_global);
882
883 /* If there is no global address. Set link-local address as
884 global. I know this break RFC specification... */
885 if (!ret)
886 memcpy (&nexthop->v6_global, &local->sin6.sin6_addr,
887 IPV6_MAX_BYTELEN);
888 else
889 memcpy (&nexthop->v6_local, &local->sin6.sin6_addr,
890 IPV6_MAX_BYTELEN);
891 }
892 }
893
894 if (IN6_IS_ADDR_LINKLOCAL (&local->sin6.sin6_addr) ||
895 if_lookup_by_ipv6 (&remote->sin6.sin6_addr, remote->sin6.sin6_scope_id))
896 peer->shared_network = 1;
897 else
898 peer->shared_network = 0;
899
900 /* KAME stack specific treatment. */
901 #ifdef KAME
902 if (IN6_IS_ADDR_LINKLOCAL (&nexthop->v6_global)
903 && IN6_LINKLOCAL_IFINDEX (nexthop->v6_global))
904 {
905 SET_IN6_LINKLOCAL_IFINDEX (nexthop->v6_global, 0);
906 }
907 if (IN6_IS_ADDR_LINKLOCAL (&nexthop->v6_local)
908 && IN6_LINKLOCAL_IFINDEX (nexthop->v6_local))
909 {
910 SET_IN6_LINKLOCAL_IFINDEX (nexthop->v6_local, 0);
911 }
912 #endif /* KAME */
913 #endif /* HAVE_IPV6 */
914 return ret;
915 }
916
917 static struct in6_addr *
918 bgp_info_to_ipv6_nexthop (struct bgp_info *info)
919 {
920 struct in6_addr *nexthop = NULL;
921
922 /* Only global address nexthop exists. */
923 if (info->attr->extra->mp_nexthop_len == BGP_ATTR_NHLEN_IPV6_GLOBAL)
924 nexthop = &info->attr->extra->mp_nexthop_global;
925
926 /* If both global and link-local address present. */
927 if (info->attr->extra->mp_nexthop_len == BGP_ATTR_NHLEN_IPV6_GLOBAL_AND_LL)
928 {
929 /* Workaround for Cisco's nexthop bug. */
930 if (IN6_IS_ADDR_UNSPECIFIED (&info->attr->extra->mp_nexthop_global)
931 && info->peer->su_remote->sa.sa_family == AF_INET6)
932 nexthop = &info->peer->su_remote->sin6.sin6_addr;
933 else
934 nexthop = &info->attr->extra->mp_nexthop_local;
935 }
936
937 return nexthop;
938 }
939
940 static int
941 bgp_table_map_apply (struct route_map *map, struct prefix *p,
942 struct bgp_info *info)
943 {
944 if (route_map_apply(map, p, RMAP_BGP, info) != RMAP_DENYMATCH)
945 return 1;
946
947 if (bgp_debug_zebra(p))
948 {
949 if (p->family == AF_INET)
950 {
951 char buf[2][INET_ADDRSTRLEN];
952 zlog_debug("Zebra rmap deny: IPv4 route %s/%d nexthop %s",
953 inet_ntop(AF_INET, &p->u.prefix4, buf[0], sizeof(buf[0])),
954 p->prefixlen,
955 inet_ntop(AF_INET, &info->attr->nexthop, buf[1],
956 sizeof(buf[1])));
957 }
958 if (p->family == AF_INET6)
959 {
960 char buf[2][INET6_ADDRSTRLEN];
961 zlog_debug("Zebra rmap deny: IPv6 route %s/%d nexthop %s",
962 inet_ntop(AF_INET6, &p->u.prefix6, buf[0], sizeof(buf[0])),
963 p->prefixlen,
964 inet_ntop(AF_INET6, bgp_info_to_ipv6_nexthop(info), buf[1],
965 sizeof(buf[1])));
966 }
967 }
968 return 0;
969 }
970
971 void
972 bgp_zebra_announce (struct prefix *p, struct bgp_info *info, struct bgp *bgp,
973 afi_t afi, safi_t safi)
974 {
975 int flags;
976 u_char distance;
977 struct peer *peer;
978 struct bgp_info *mpinfo;
979 size_t oldsize, newsize;
980 u_int32_t nhcount, metric;
981 struct bgp_info local_info;
982 struct bgp_info *info_cp = &local_info;
983 u_short tag;
984
985 if (zclient->sock < 0)
986 return;
987
988 if ((p->family == AF_INET && !zclient->redist[AFI_IP][ZEBRA_ROUTE_BGP].enabled)
989 || (p->family == AF_INET6 && !zclient->redist[AFI_IP6][ZEBRA_ROUTE_BGP].enabled))
990 return;
991
992 if (bgp->main_zebra_update_hold)
993 return;
994
995 flags = 0;
996 peer = info->peer;
997
998 if ((info->attr->extra) && (info->attr->extra->tag != 0))
999 tag = info->attr->extra->tag;
1000 else
1001 tag = 0;
1002
1003 /* When we create an aggregate route we must also install a Null0 route in
1004 * the RIB */
1005 if (info->sub_type == BGP_ROUTE_AGGREGATE)
1006 SET_FLAG (flags, ZEBRA_FLAG_BLACKHOLE);
1007
1008 if (peer->sort == BGP_PEER_IBGP || peer->sort == BGP_PEER_CONFED ||
1009 info->sub_type == BGP_ROUTE_AGGREGATE)
1010 {
1011 SET_FLAG (flags, ZEBRA_FLAG_IBGP);
1012 SET_FLAG (flags, ZEBRA_FLAG_INTERNAL);
1013 }
1014
1015 if ((peer->sort == BGP_PEER_EBGP && peer->ttl != 1)
1016 || CHECK_FLAG (peer->flags, PEER_FLAG_DISABLE_CONNECTED_CHECK)
1017 || bgp_flag_check(bgp, BGP_FLAG_DISABLE_NH_CONNECTED_CHK))
1018
1019 SET_FLAG (flags, ZEBRA_FLAG_INTERNAL);
1020
1021 nhcount = 1 + bgp_info_mpath_count (info);
1022
1023 if (p->family == AF_INET && !BGP_ATTR_NEXTHOP_AFI_IP6(info->attr))
1024 {
1025 struct zapi_ipv4 api;
1026 struct in_addr *nexthop;
1027 char buf[2][INET_ADDRSTRLEN];
1028 int valid_nh_count = 0;
1029
1030 /* resize nexthop buffer size if necessary */
1031 if ((oldsize = stream_get_size (bgp_nexthop_buf)) <
1032 (sizeof (struct in_addr *) * nhcount))
1033 {
1034 newsize = (sizeof (struct in_addr *) * nhcount);
1035 newsize = stream_resize (bgp_nexthop_buf, newsize);
1036 if (newsize == oldsize)
1037 {
1038 zlog_err ("can't resize nexthop buffer");
1039 return;
1040 }
1041 }
1042 stream_reset (bgp_nexthop_buf);
1043 nexthop = NULL;
1044
1045 /* Metric is currently based on the best-path only. */
1046 metric = info->attr->med;
1047
1048 if (bgp->table_map[afi][safi].name)
1049 {
1050 BGP_INFO_ATTR_BUF_INIT();
1051
1052 /* Copy info and attributes, so the route-map apply doesn't modify the
1053 BGP route info. */
1054 BGP_INFO_ATTR_BUF_COPY(info, info_cp);
1055 if (bgp_table_map_apply(bgp->table_map[afi][safi].map, p, info_cp))
1056 {
1057 metric = info_cp->attr->med;
1058 nexthop = &info_cp->attr->nexthop;
1059
1060 if (info_cp->attr->extra)
1061 tag = info_cp->attr->extra->tag;
1062 }
1063 BGP_INFO_ATTR_BUF_FREE(info_cp);
1064 }
1065 else
1066 {
1067 nexthop = &info->attr->nexthop;
1068 }
1069
1070 if (nexthop)
1071 {
1072 stream_put (bgp_nexthop_buf, &nexthop, sizeof (struct in_addr *));
1073 valid_nh_count++;
1074 }
1075
1076 for (mpinfo = bgp_info_mpath_first (info); mpinfo;
1077 mpinfo = bgp_info_mpath_next (mpinfo))
1078 {
1079 nexthop = NULL;
1080
1081 if (bgp->table_map[afi][safi].name)
1082 {
1083 /* Copy info and attributes, so the route-map apply doesn't modify the
1084 BGP route info. */
1085 BGP_INFO_ATTR_BUF_COPY(mpinfo, info_cp);
1086 if (bgp_table_map_apply(bgp->table_map[afi][safi].map, p, info_cp))
1087 nexthop = &info_cp->attr->nexthop;
1088 BGP_INFO_ATTR_BUF_FREE(info_cp);
1089 }
1090 else
1091 {
1092 nexthop = &mpinfo->attr->nexthop;
1093 }
1094
1095 if (nexthop == NULL)
1096 continue;
1097
1098 stream_put (bgp_nexthop_buf, &nexthop, sizeof (struct in_addr *));
1099 valid_nh_count++;
1100 }
1101
1102 api.flags = flags;
1103 api.type = ZEBRA_ROUTE_BGP;
1104 api.instance = 0;
1105 api.message = 0;
1106 api.safi = safi;
1107 SET_FLAG (api.message, ZAPI_MESSAGE_NEXTHOP);
1108
1109 /* Note that this currently only applies to Null0 routes for aggregates.
1110 * ZEBRA_FLAG_BLACKHOLE signals zapi_ipv4_route to encode a special
1111 * BLACKHOLE nexthop. We want to set api.nexthop_num to zero since we
1112 * do not want to also encode the 0.0.0.0 nexthop for the aggregate route.
1113 */
1114 if (CHECK_FLAG(flags, ZEBRA_FLAG_BLACKHOLE))
1115 api.nexthop_num = 0;
1116 else
1117 api.nexthop_num = valid_nh_count;
1118
1119 api.nexthop = (struct in_addr **)STREAM_DATA (bgp_nexthop_buf);
1120 api.ifindex_num = 0;
1121 SET_FLAG (api.message, ZAPI_MESSAGE_METRIC);
1122 api.metric = metric;
1123
1124 if (tag)
1125 {
1126 SET_FLAG (api.message, ZAPI_MESSAGE_TAG);
1127 api.tag = tag;
1128 }
1129
1130 distance = bgp_distance_apply (p, info, bgp);
1131
1132 if (distance)
1133 {
1134 SET_FLAG (api.message, ZAPI_MESSAGE_DISTANCE);
1135 api.distance = distance;
1136 }
1137
1138 if (bgp_debug_zebra(p))
1139 {
1140 int i;
1141 zlog_debug("Zebra send: IPv4 route %s %s/%d metric %u tag %d"
1142 " count %d", (valid_nh_count ? "add":"delete"),
1143 inet_ntop(AF_INET, &p->u.prefix4, buf[0], sizeof(buf[0])),
1144 p->prefixlen, api.metric, api.tag, api.nexthop_num);
1145 for (i = 0; i < api.nexthop_num; i++)
1146 zlog_debug(" IPv4 [nexthop %d] %s", i+1,
1147 inet_ntop(AF_INET, api.nexthop[i], buf[1], sizeof(buf[1])));
1148 }
1149
1150 zapi_ipv4_route (valid_nh_count ? ZEBRA_IPV4_ROUTE_ADD: ZEBRA_IPV4_ROUTE_DELETE,
1151 zclient, (struct prefix_ipv4 *) p, &api);
1152 }
1153 #ifdef HAVE_IPV6
1154
1155 /* We have to think about a IPv6 link-local address curse. */
1156 if (p->family == AF_INET6 ||
1157 (p->family == AF_INET && BGP_ATTR_NEXTHOP_AFI_IP6(info->attr)))
1158 {
1159 unsigned int ifindex;
1160 struct in6_addr *nexthop;
1161 struct zapi_ipv6 api;
1162 int valid_nh_count = 0;
1163 char buf[2][INET6_ADDRSTRLEN];
1164
1165 /* resize nexthop buffer size if necessary */
1166 if ((oldsize = stream_get_size (bgp_nexthop_buf)) <
1167 (sizeof (struct in6_addr *) * nhcount))
1168 {
1169 newsize = (sizeof (struct in6_addr *) * nhcount);
1170 newsize = stream_resize (bgp_nexthop_buf, newsize);
1171 if (newsize == oldsize)
1172 {
1173 zlog_err ("can't resize nexthop buffer");
1174 return;
1175 }
1176 }
1177 stream_reset (bgp_nexthop_buf);
1178
1179 /* resize ifindices buffer size if necessary */
1180 if ((oldsize = stream_get_size (bgp_ifindices_buf)) <
1181 (sizeof (unsigned int) * nhcount))
1182 {
1183 newsize = (sizeof (unsigned int) * nhcount);
1184 newsize = stream_resize (bgp_ifindices_buf, newsize);
1185 if (newsize == oldsize)
1186 {
1187 zlog_err ("can't resize nexthop buffer");
1188 return;
1189 }
1190 }
1191 stream_reset (bgp_ifindices_buf);
1192
1193 ifindex = 0;
1194 nexthop = NULL;
1195
1196 assert (info->attr->extra);
1197
1198 /* Metric is currently based on the best-path only. */
1199 metric = info->attr->med;
1200
1201 if (bgp->table_map[afi][safi].name)
1202 {
1203 BGP_INFO_ATTR_BUF_INIT();
1204
1205 /* Copy info and attributes, so the route-map apply doesn't modify the
1206 BGP route info. */
1207 BGP_INFO_ATTR_BUF_COPY(info, info_cp);
1208 if (bgp_table_map_apply(bgp->table_map[afi][safi].map, p, info_cp))
1209 {
1210 metric = info_cp->attr->med;
1211 nexthop = bgp_info_to_ipv6_nexthop(info_cp);
1212
1213 if (info_cp->attr->extra)
1214 tag = info_cp->attr->extra->tag;
1215 }
1216 BGP_INFO_ATTR_BUF_FREE(info_cp);
1217 }
1218 else
1219 {
1220 nexthop = bgp_info_to_ipv6_nexthop(info);
1221 }
1222
1223 if (nexthop)
1224 {
1225 if (info->attr->extra->mp_nexthop_len == BGP_ATTR_NHLEN_IPV6_GLOBAL_AND_LL)
1226 if (info->peer->nexthop.ifp)
1227 ifindex = info->peer->nexthop.ifp->ifindex;
1228
1229 if (!ifindex)
1230 {
1231 if (info->peer->conf_if || info->peer->ifname)
1232 ifindex = if_nametoindex (info->peer->conf_if ? info->peer->conf_if : info->peer->ifname);
1233 else if (info->peer->nexthop.ifp)
1234 ifindex = info->peer->nexthop.ifp->ifindex;
1235 }
1236 stream_put (bgp_nexthop_buf, &nexthop, sizeof (struct in6_addr *));
1237 stream_put (bgp_ifindices_buf, &ifindex, sizeof (unsigned int));
1238 valid_nh_count++;
1239 }
1240
1241 for (mpinfo = bgp_info_mpath_first (info); mpinfo;
1242 mpinfo = bgp_info_mpath_next (mpinfo))
1243 {
1244 ifindex = 0;
1245 nexthop = NULL;
1246
1247 if (bgp->table_map[afi][safi].name)
1248 {
1249 /* Copy info and attributes, so the route-map apply doesn't modify the
1250 BGP route info. */
1251 BGP_INFO_ATTR_BUF_COPY(mpinfo, info_cp);
1252 if (bgp_table_map_apply(bgp->table_map[afi][safi].map, p, info_cp))
1253 nexthop = bgp_info_to_ipv6_nexthop(info_cp);
1254 BGP_INFO_ATTR_BUF_FREE(info_cp);
1255 }
1256 else
1257 {
1258 nexthop = bgp_info_to_ipv6_nexthop(mpinfo);
1259 }
1260
1261 if (nexthop == NULL)
1262 continue;
1263
1264 if (mpinfo->attr->extra->mp_nexthop_len == BGP_ATTR_NHLEN_IPV6_GLOBAL_AND_LL)
1265 if (mpinfo->peer->nexthop.ifp)
1266 ifindex = mpinfo->peer->nexthop.ifp->ifindex;
1267
1268 if (!ifindex)
1269 {
1270 if (mpinfo->peer->conf_if || mpinfo->peer->ifname)
1271 ifindex = if_nametoindex (mpinfo->peer->conf_if ? mpinfo->peer->conf_if : mpinfo->peer->ifname);
1272 else if (mpinfo->peer->nexthop.ifp)
1273 ifindex = mpinfo->peer->nexthop.ifp->ifindex;
1274 }
1275 if (ifindex == 0)
1276 continue;
1277
1278 stream_put (bgp_nexthop_buf, &nexthop, sizeof (struct in6_addr *));
1279 stream_put (bgp_ifindices_buf, &ifindex, sizeof (unsigned int));
1280 valid_nh_count++;
1281 }
1282
1283 /* Make Zebra API structure. */
1284 api.flags = flags;
1285 api.type = ZEBRA_ROUTE_BGP;
1286 api.instance = 0;
1287 api.message = 0;
1288 api.safi = safi;
1289 SET_FLAG (api.message, ZAPI_MESSAGE_NEXTHOP);
1290
1291 /* Note that this currently only applies to Null0 routes for aggregates.
1292 * ZEBRA_FLAG_BLACKHOLE signals zapi_ipv6_route to encode a special
1293 * BLACKHOLE nexthop. We want to set api.nexthop_num to zero since we
1294 * do not want to also encode the :: nexthop for the aggregate route.
1295 */
1296 if (CHECK_FLAG(flags, ZEBRA_FLAG_BLACKHOLE))
1297 api.nexthop_num = 0;
1298 else
1299 api.nexthop_num = valid_nh_count;
1300
1301 api.nexthop = (struct in6_addr **)STREAM_DATA (bgp_nexthop_buf);
1302 SET_FLAG (api.message, ZAPI_MESSAGE_IFINDEX);
1303 api.ifindex_num = valid_nh_count;
1304 api.ifindex = (unsigned int *)STREAM_DATA (bgp_ifindices_buf);
1305 SET_FLAG (api.message, ZAPI_MESSAGE_METRIC);
1306 api.metric = metric;
1307
1308 if (tag)
1309 {
1310 SET_FLAG (api.message, ZAPI_MESSAGE_TAG);
1311 api.tag = tag;
1312 }
1313
1314 if (p->family == AF_INET)
1315 {
1316 if (bgp_debug_zebra(p))
1317 {
1318 int i;
1319 zlog_debug("Zebra send: IPv4 route %s %s/%d metric %u tag %d",
1320 valid_nh_count ? "add" : "delete",
1321 inet_ntop(AF_INET, &p->u.prefix4, buf[0], sizeof(buf[0])),
1322 p->prefixlen, api.metric, api.tag);
1323 for (i = 0; i < api.nexthop_num; i++)
1324 zlog_debug(" IPv6 [nexthop %d] %s", i+1,
1325 inet_ntop(AF_INET6, api.nexthop[i], buf[1], sizeof(buf[1])));
1326 }
1327
1328 if (valid_nh_count)
1329 zapi_ipv4_route_ipv6_nexthop (ZEBRA_IPV4_ROUTE_IPV6_NEXTHOP_ADD,
1330 zclient, (struct prefix_ipv4 *) p, &api);
1331 else
1332 zapi_ipv4_route (ZEBRA_IPV4_ROUTE_DELETE,
1333 zclient, (struct prefix_ipv4 *) p, &api);
1334 }
1335 else
1336 {
1337 if (bgp_debug_zebra(p))
1338 {
1339 int i;
1340 zlog_debug("Zebra send: IPv6 route %s %s/%d metric %u tag %d",
1341 valid_nh_count ? "add" : "delete",
1342 inet_ntop(AF_INET6, &p->u.prefix6, buf[0], sizeof(buf[0])),
1343 p->prefixlen, api.metric, api.tag);
1344 for (i = 0; i < api.nexthop_num; i++)
1345 zlog_debug(" IPv6 [nexthop %d] %s", i+1,
1346 inet_ntop(AF_INET6, api.nexthop[i], buf[1], sizeof(buf[1])));
1347 }
1348
1349 zapi_ipv6_route (valid_nh_count ?
1350 ZEBRA_IPV6_ROUTE_ADD : ZEBRA_IPV6_ROUTE_DELETE,
1351 zclient, (struct prefix_ipv6 *) p, &api);
1352 }
1353 }
1354 #endif /* HAVE_IPV6 */
1355 }
1356
1357 /* Announce all routes of a table to zebra */
1358 void
1359 bgp_zebra_announce_table (struct bgp *bgp, afi_t afi, safi_t safi)
1360 {
1361 struct bgp_node *rn;
1362 struct bgp_table *table;
1363 struct bgp_info *ri;
1364
1365 table = bgp->rib[afi][safi];
1366 if (!table) return;
1367
1368 for (rn = bgp_table_top (table); rn; rn = bgp_route_next (rn))
1369 for (ri = rn->info; ri; ri = ri->next)
1370 if (CHECK_FLAG (ri->flags, BGP_INFO_SELECTED)
1371 && ri->type == ZEBRA_ROUTE_BGP
1372 && ri->sub_type == BGP_ROUTE_NORMAL)
1373 bgp_zebra_announce (&rn->p, ri, bgp, afi, safi);
1374 }
1375
1376 void
1377 bgp_zebra_withdraw (struct prefix *p, struct bgp_info *info, safi_t safi)
1378 {
1379 int flags;
1380 struct peer *peer;
1381
1382 if (zclient->sock < 0)
1383 return;
1384
1385 if ((p->family == AF_INET && !zclient->redist[AFI_IP][ZEBRA_ROUTE_BGP].enabled)
1386 || (p->family == AF_INET6 && !zclient->redist[AFI_IP6][ZEBRA_ROUTE_BGP].enabled))
1387 return;
1388
1389 peer = info->peer;
1390
1391 flags = 0;
1392
1393 if (peer->sort == BGP_PEER_IBGP)
1394 {
1395 SET_FLAG (flags, ZEBRA_FLAG_INTERNAL);
1396 SET_FLAG (flags, ZEBRA_FLAG_IBGP);
1397 }
1398
1399 if ((peer->sort == BGP_PEER_EBGP && peer->ttl != 1)
1400 || CHECK_FLAG (peer->flags, PEER_FLAG_DISABLE_CONNECTED_CHECK)
1401 || bgp_flag_check(peer->bgp, BGP_FLAG_DISABLE_NH_CONNECTED_CHK))
1402 SET_FLAG (flags, ZEBRA_FLAG_INTERNAL);
1403
1404 if (p->family == AF_INET)
1405 {
1406 struct zapi_ipv4 api;
1407 struct in_addr *nexthop;
1408
1409 api.flags = flags;
1410 nexthop = &info->attr->nexthop;
1411
1412 api.type = ZEBRA_ROUTE_BGP;
1413 api.instance = 0;
1414 api.message = 0;
1415 api.safi = safi;
1416 SET_FLAG (api.message, ZAPI_MESSAGE_NEXTHOP);
1417 api.nexthop_num = 0;
1418 api.nexthop = NULL;
1419 api.ifindex_num = 0;
1420 SET_FLAG (api.message, ZAPI_MESSAGE_METRIC);
1421 api.metric = info->attr->med;
1422
1423 if ((info->attr->extra) && (info->attr->extra->tag != 0))
1424 {
1425 SET_FLAG(api.message, ZAPI_MESSAGE_TAG);
1426 api.tag = info->attr->extra->tag;
1427 }
1428
1429 if (bgp_debug_zebra(p))
1430 {
1431 char buf[2][INET_ADDRSTRLEN];
1432 zlog_debug("Zebra send: IPv4 route delete %s/%d nexthop %s metric %u tag %d",
1433 inet_ntop(AF_INET, &p->u.prefix4, buf[0], sizeof(buf[0])),
1434 p->prefixlen,
1435 inet_ntop(AF_INET, nexthop, buf[1], sizeof(buf[1])),
1436 api.metric,
1437 api.tag);
1438 }
1439
1440 zapi_ipv4_route (ZEBRA_IPV4_ROUTE_DELETE, zclient,
1441 (struct prefix_ipv4 *) p, &api);
1442 }
1443 #ifdef HAVE_IPV6
1444 /* We have to think about a IPv6 link-local address curse. */
1445 if (p->family == AF_INET6)
1446 {
1447 struct zapi_ipv6 api;
1448 unsigned int ifindex;
1449 struct in6_addr *nexthop;
1450
1451 assert (info->attr->extra);
1452
1453 ifindex = 0;
1454 nexthop = NULL;
1455
1456 /* Only global address nexthop exists. */
1457 if (info->attr->extra->mp_nexthop_len == BGP_ATTR_NHLEN_IPV6_GLOBAL)
1458 nexthop = &info->attr->extra->mp_nexthop_global;
1459
1460 /* If both global and link-local address present. */
1461 if (info->attr->extra->mp_nexthop_len == BGP_ATTR_NHLEN_IPV6_GLOBAL_AND_LL)
1462 {
1463 nexthop = &info->attr->extra->mp_nexthop_local;
1464 if (info->peer->nexthop.ifp)
1465 ifindex = info->peer->nexthop.ifp->ifindex;
1466 }
1467
1468 if (nexthop == NULL)
1469 return;
1470
1471 if (IN6_IS_ADDR_LINKLOCAL (nexthop) && ! ifindex)
1472 if (info->peer->conf_if || info->peer->ifname)
1473 ifindex = if_nametoindex (info->peer->conf_if ? info->peer->conf_if : info->peer->ifname);
1474
1475 api.flags = flags;
1476 api.type = ZEBRA_ROUTE_BGP;
1477 api.instance = 0;
1478 api.message = 0;
1479 api.safi = safi;
1480 SET_FLAG (api.message, ZAPI_MESSAGE_NEXTHOP);
1481 api.nexthop_num = 1;
1482 api.nexthop = &nexthop;
1483 SET_FLAG (api.message, ZAPI_MESSAGE_IFINDEX);
1484 api.ifindex_num = 1;
1485 api.ifindex = &ifindex;
1486 SET_FLAG (api.message, ZAPI_MESSAGE_METRIC);
1487 api.metric = info->attr->med;
1488
1489 if ((info->attr->extra) && (info->attr->extra->tag != 0))
1490 {
1491 SET_FLAG(api.message, ZAPI_MESSAGE_TAG);
1492 api.tag = info->attr->extra->tag;
1493 }
1494
1495 if (bgp_debug_zebra(p))
1496 {
1497 char buf[2][INET6_ADDRSTRLEN];
1498 zlog_debug("Zebra send: IPv6 route delete %s/%d nexthop %s metric %u tag %d",
1499 inet_ntop(AF_INET6, &p->u.prefix6, buf[0], sizeof(buf[0])),
1500 p->prefixlen,
1501 inet_ntop(AF_INET6, nexthop, buf[1], sizeof(buf[1])),
1502 api.metric,
1503 api.tag);
1504 }
1505
1506 zapi_ipv6_route (ZEBRA_IPV6_ROUTE_DELETE, zclient,
1507 (struct prefix_ipv6 *) p, &api);
1508 }
1509 #endif /* HAVE_IPV6 */
1510 }
1511 struct bgp_redist *
1512 bgp_redist_lookup (struct bgp *bgp, afi_t afi, u_char type, u_short instance)
1513 {
1514 struct list *red_list;
1515 struct listnode *node;
1516 struct bgp_redist *red;
1517
1518 red_list = bgp->redist[afi][type];
1519 if (!red_list)
1520 return(NULL);
1521
1522 for (ALL_LIST_ELEMENTS_RO(red_list, node, red))
1523 if (red->instance == instance)
1524 return red;
1525
1526 return NULL;
1527 }
1528
1529 struct bgp_redist *
1530 bgp_redist_add (struct bgp *bgp, afi_t afi, u_char type, u_short instance)
1531 {
1532 struct list *red_list;
1533 struct bgp_redist *red;
1534
1535 red = bgp_redist_lookup(bgp, afi, type, instance);
1536 if (red)
1537 return red;
1538
1539 if (!bgp->redist[afi][type])
1540 bgp->redist[afi][type] = list_new();
1541
1542 red_list = bgp->redist[afi][type];
1543 red = (struct bgp_redist *)calloc (1, sizeof(struct bgp_redist));
1544 red->instance = instance;
1545
1546 listnode_add(red_list, red);
1547
1548 return red;
1549 }
1550
1551 static void
1552 bgp_redist_del (struct bgp *bgp, afi_t afi, u_char type, u_short instance)
1553 {
1554 struct bgp_redist *red;
1555
1556 red = bgp_redist_lookup(bgp, afi, type, instance);
1557
1558 if (red)
1559 {
1560 listnode_delete(bgp->redist[afi][type], red);
1561 if (!bgp->redist[afi][type]->count)
1562 {
1563 list_free(bgp->redist[afi][type]);
1564 bgp->redist[afi][type] = NULL;
1565 }
1566 }
1567 }
1568
1569 /* Other routes redistribution into BGP. */
1570 int
1571 bgp_redistribute_set (afi_t afi, int type, u_short instance)
1572 {
1573
1574 /* Return if already redistribute flag is set. */
1575 if (redist_check_instance(&zclient->redist[afi][type], instance))
1576 return CMD_WARNING;
1577
1578 redist_add_instance(&zclient->redist[afi][type], instance);
1579
1580 /* Return if zebra connection is not established. */
1581 if (zclient->sock < 0)
1582 return CMD_WARNING;
1583
1584 if (BGP_DEBUG (zebra, ZEBRA))
1585 zlog_debug("Zebra send: redistribute add afi %d %s %d", afi,
1586 zebra_route_string(type), instance);
1587
1588 /* Send distribute add message to zebra. */
1589 zebra_redistribute_send (ZEBRA_REDISTRIBUTE_ADD, zclient, afi, type, instance);
1590
1591 return CMD_SUCCESS;
1592 }
1593
1594 int
1595 bgp_redistribute_resend (struct bgp *bgp, afi_t afi, int type, u_short instance)
1596 {
1597 /* Return if zebra connection is not established. */
1598 if (zclient->sock < 0)
1599 return -1;
1600
1601 if (BGP_DEBUG (zebra, ZEBRA))
1602 zlog_debug("Zebra send: redistribute delete/add afi %d %s %d", afi,
1603 zebra_route_string(type), instance);
1604
1605 /* Send distribute add message to zebra. */
1606 zebra_redistribute_send (ZEBRA_REDISTRIBUTE_DELETE, zclient, afi, type, instance);
1607 zebra_redistribute_send (ZEBRA_REDISTRIBUTE_ADD, zclient, afi, type, instance);
1608
1609 return 0;
1610 }
1611
1612 /* Redistribute with route-map specification. */
1613 int
1614 bgp_redistribute_rmap_set (struct bgp_redist *red, const char *name)
1615 {
1616 if (red->rmap.name
1617 && (strcmp (red->rmap.name, name) == 0))
1618 return 0;
1619
1620 if (red->rmap.name)
1621 free (red->rmap.name);
1622 red->rmap.name = strdup (name);
1623 red->rmap.map = route_map_lookup_by_name (name);
1624
1625 return 1;
1626 }
1627
1628 /* Redistribute with metric specification. */
1629 int
1630 bgp_redistribute_metric_set (struct bgp_redist *red, u_int32_t metric)
1631 {
1632 if (red->redist_metric_flag
1633 && red->redist_metric == metric)
1634 return 0;
1635
1636 red->redist_metric_flag = 1;
1637 red->redist_metric = metric;
1638
1639 return 1;
1640 }
1641
1642 /* Unset redistribution. */
1643 int
1644 bgp_redistribute_unset (struct bgp *bgp, afi_t afi, int type, u_short instance)
1645 {
1646 struct bgp_redist *red;
1647
1648 red = bgp_redist_lookup(bgp, afi, type, instance);
1649 if (!red)
1650 return CMD_SUCCESS;
1651
1652 /* Unset route-map. */
1653 if (red->rmap.name)
1654 free (red->rmap.name);
1655 red->rmap.name = NULL;
1656 red->rmap.map = NULL;
1657
1658 /* Unset metric. */
1659 red->redist_metric_flag = 0;
1660 red->redist_metric = 0;
1661
1662 bgp_redist_del(bgp, afi, type, instance);
1663
1664 /* Return if zebra connection is disabled. */
1665 if (!redist_check_instance(&zclient->redist[afi][type], instance))
1666 return CMD_WARNING;
1667 redist_del_instance(&zclient->redist[afi][type], instance);
1668
1669 if (zclient->sock >= 0)
1670 {
1671 /* Send distribute delete message to zebra. */
1672 if (BGP_DEBUG (zebra, ZEBRA))
1673 zlog_debug("Zebra send: redistribute delete afi %d %s %d",
1674 afi, zebra_route_string(type), instance);
1675 zebra_redistribute_send (ZEBRA_REDISTRIBUTE_DELETE, zclient, afi, type, instance);
1676 }
1677
1678 /* Withdraw redistributed routes from current BGP's routing table. */
1679 bgp_redistribute_withdraw (bgp, afi, type, instance);
1680
1681 return CMD_SUCCESS;
1682 }
1683
1684 void
1685 bgp_zclient_reset (void)
1686 {
1687 zclient_reset (zclient);
1688 }
1689
1690 void
1691 bgp_zebra_init (void)
1692 {
1693 /* Set default values. */
1694 zclient = zclient_new ();
1695 zclient_init (zclient, ZEBRA_ROUTE_BGP, 0);
1696 zclient->router_id_update = bgp_router_id_update;
1697 zclient->interface_add = bgp_interface_add;
1698 zclient->interface_delete = bgp_interface_delete;
1699 zclient->interface_address_add = bgp_interface_address_add;
1700 zclient->interface_address_delete = bgp_interface_address_delete;
1701 zclient->interface_nbr_address_add = bgp_interface_nbr_address_add;
1702 zclient->interface_nbr_address_delete = bgp_interface_nbr_address_delete;
1703 zclient->ipv4_route_add = zebra_read_ipv4;
1704 zclient->ipv4_route_delete = zebra_read_ipv4;
1705 zclient->interface_up = bgp_interface_up;
1706 zclient->interface_down = bgp_interface_down;
1707 zclient->interface_bfd_dest_down = bgp_interface_bfd_dest_down;
1708 #ifdef HAVE_IPV6
1709 zclient->ipv6_route_add = zebra_read_ipv6;
1710 zclient->ipv6_route_delete = zebra_read_ipv6;
1711 #endif /* HAVE_IPV6 */
1712 zclient->nexthop_update = bgp_read_nexthop_update;
1713 zclient->import_check_update = bgp_read_import_check_update;
1714
1715 /* Interface related init. */
1716 if_init ();
1717
1718 bgp_nexthop_buf = stream_new(BGP_NEXTHOP_BUF_SIZE);
1719 bgp_ifindices_buf = stream_new(BGP_IFINDICES_BUF_SIZE);
1720 }