]> git.proxmox.com Git - mirror_frr.git/blob - zebra/zserv.c
Merge branch 'stable/2.0-for-merge'
[mirror_frr.git] / zebra / zserv.c
1 /* Zebra daemon server routine.
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
22 #include <zebra.h>
23
24 #include "prefix.h"
25 #include "command.h"
26 #include "if.h"
27 #include "thread.h"
28 #include "stream.h"
29 #include "memory.h"
30 #include "zebra_memory.h"
31 #include "table.h"
32 #include "rib.h"
33 #include "network.h"
34 #include "sockunion.h"
35 #include "log.h"
36 #include "zclient.h"
37 #include "privs.h"
38 #include "network.h"
39 #include "buffer.h"
40 #include "nexthop.h"
41 #include "vrf.h"
42
43 #include "zebra/zserv.h"
44 #include "zebra/zebra_ns.h"
45 #include "zebra/zebra_vrf.h"
46 #include "zebra/router-id.h"
47 #include "zebra/redistribute.h"
48 #include "zebra/debug.h"
49 #include "zebra/ipforward.h"
50 #include "zebra/zebra_rnh.h"
51 #include "zebra/rt_netlink.h"
52 #include "zebra/interface.h"
53 #include "zebra/zebra_ptm.h"
54 #include "zebra/rtadv.h"
55 #include "zebra/zebra_mpls.h"
56 #include "zebra/zebra_fpm.h"
57
58 /* Event list of zebra. */
59 enum event { ZEBRA_SERV, ZEBRA_READ, ZEBRA_WRITE };
60
61 static void zebra_event (enum event event, int sock, struct zserv *client);
62
63 extern struct zebra_privs_t zserv_privs;
64
65 static void zebra_client_close (struct zserv *client);
66
67 static int
68 zserv_delayed_close(struct thread *thread)
69 {
70 struct zserv *client = THREAD_ARG(thread);
71
72 client->t_suicide = NULL;
73 zebra_client_close(client);
74 return 0;
75 }
76
77 static int
78 zserv_flush_data(struct thread *thread)
79 {
80 struct zserv *client = THREAD_ARG(thread);
81
82 client->t_write = NULL;
83 if (client->t_suicide)
84 {
85 zebra_client_close(client);
86 return -1;
87 }
88 switch (buffer_flush_available(client->wb, client->sock))
89 {
90 case BUFFER_ERROR:
91 zlog_warn("%s: buffer_flush_available failed on zserv client fd %d, "
92 "closing", __func__, client->sock);
93 zebra_client_close(client);
94 break;
95 case BUFFER_PENDING:
96 client->t_write = thread_add_write(zebrad.master, zserv_flush_data,
97 client, client->sock);
98 break;
99 case BUFFER_EMPTY:
100 break;
101 }
102
103 client->last_write_time = quagga_monotime();
104 return 0;
105 }
106
107 int
108 zebra_server_send_message(struct zserv *client)
109 {
110 if (client->t_suicide)
111 return -1;
112
113 stream_set_getp(client->obuf, 0);
114 client->last_write_cmd = stream_getw_from(client->obuf, 6);
115 switch (buffer_write(client->wb, client->sock, STREAM_DATA(client->obuf),
116 stream_get_endp(client->obuf)))
117 {
118 case BUFFER_ERROR:
119 zlog_warn("%s: buffer_write failed to zserv client fd %d, closing",
120 __func__, client->sock);
121 /* Schedule a delayed close since many of the functions that call this
122 one do not check the return code. They do not allow for the
123 possibility that an I/O error may have caused the client to be
124 deleted. */
125 client->t_suicide = thread_add_event(zebrad.master, zserv_delayed_close,
126 client, 0);
127 return -1;
128 case BUFFER_EMPTY:
129 THREAD_OFF(client->t_write);
130 break;
131 case BUFFER_PENDING:
132 THREAD_WRITE_ON(zebrad.master, client->t_write,
133 zserv_flush_data, client, client->sock);
134 break;
135 }
136
137 client->last_write_time = quagga_monotime();
138 return 0;
139 }
140
141 void
142 zserv_create_header (struct stream *s, uint16_t cmd, vrf_id_t vrf_id)
143 {
144 /* length placeholder, caller can update */
145 stream_putw (s, ZEBRA_HEADER_SIZE);
146 stream_putc (s, ZEBRA_HEADER_MARKER);
147 stream_putc (s, ZSERV_VERSION);
148 stream_putw (s, vrf_id);
149 stream_putw (s, cmd);
150 }
151
152 static void
153 zserv_encode_interface (struct stream *s, struct interface *ifp)
154 {
155 /* Interface information. */
156 stream_put (s, ifp->name, INTERFACE_NAMSIZ);
157 stream_putl (s, ifp->ifindex);
158 stream_putc (s, ifp->status);
159 stream_putq (s, ifp->flags);
160 stream_putc (s, ifp->ptm_enable);
161 stream_putc (s, ifp->ptm_status);
162 stream_putl (s, ifp->metric);
163 stream_putl (s, ifp->mtu);
164 stream_putl (s, ifp->mtu6);
165 stream_putl (s, ifp->bandwidth);
166 stream_putl (s, ifp->ll_type);
167 stream_putl (s, ifp->hw_addr_len);
168 if (ifp->hw_addr_len)
169 stream_put (s, ifp->hw_addr, ifp->hw_addr_len);
170
171 /* Then, Traffic Engineering parameters if any */
172 if (HAS_LINK_PARAMS(ifp) && IS_LINK_PARAMS_SET(ifp->link_params))
173 {
174 stream_putc (s, 1);
175 zebra_interface_link_params_write (s, ifp);
176 }
177 else
178 stream_putc (s, 0);
179
180 /* Write packet size. */
181 stream_putw_at (s, 0, stream_get_endp (s));
182 }
183
184 static void
185 zserv_encode_vrf (struct stream *s, struct zebra_vrf *zvrf)
186 {
187 /* Interface information. */
188 stream_put (s, zvrf_name (zvrf), VRF_NAMSIZ);
189
190 /* Write packet size. */
191 stream_putw_at (s, 0, stream_get_endp (s));
192 }
193
194 /* Interface is added. Send ZEBRA_INTERFACE_ADD to client. */
195 /*
196 * This function is called in the following situations:
197 * - in response to a 3-byte ZEBRA_INTERFACE_ADD request
198 * from the client.
199 * - at startup, when zebra figures out the available interfaces
200 * - when an interface is added (where support for
201 * RTM_IFANNOUNCE or AF_NETLINK sockets is available), or when
202 * an interface is marked IFF_UP (i.e., an RTM_IFINFO message is
203 * received)
204 */
205 int
206 zsend_interface_add (struct zserv *client, struct interface *ifp)
207 {
208 struct stream *s;
209
210 s = client->obuf;
211 stream_reset (s);
212
213 zserv_create_header (s, ZEBRA_INTERFACE_ADD, ifp->vrf_id);
214 zserv_encode_interface (s, ifp);
215
216 client->ifadd_cnt++;
217 return zebra_server_send_message(client);
218 }
219
220 /* Interface deletion from zebra daemon. */
221 int
222 zsend_interface_delete (struct zserv *client, struct interface *ifp)
223 {
224 struct stream *s;
225
226 s = client->obuf;
227 stream_reset (s);
228
229 zserv_create_header (s, ZEBRA_INTERFACE_DELETE, ifp->vrf_id);
230 zserv_encode_interface (s, ifp);
231
232 client->ifdel_cnt++;
233 return zebra_server_send_message (client);
234 }
235
236 int
237 zsend_vrf_add (struct zserv *client, struct zebra_vrf *zvrf)
238 {
239 struct stream *s;
240
241 s = client->obuf;
242 stream_reset (s);
243
244 zserv_create_header (s, ZEBRA_VRF_ADD, zvrf_id (zvrf));
245 zserv_encode_vrf (s, zvrf);
246
247 client->vrfadd_cnt++;
248 return zebra_server_send_message(client);
249 }
250
251 /* VRF deletion from zebra daemon. */
252 int
253 zsend_vrf_delete (struct zserv *client, struct zebra_vrf *zvrf)
254 {
255 struct stream *s;
256
257 s = client->obuf;
258 stream_reset (s);
259
260 zserv_create_header (s, ZEBRA_VRF_DELETE, zvrf_id (zvrf));
261 zserv_encode_vrf (s, zvrf);
262
263 client->vrfdel_cnt++;
264 return zebra_server_send_message (client);
265 }
266
267 int
268 zsend_interface_link_params (struct zserv *client, struct interface *ifp)
269 {
270 struct stream *s;
271
272 /* Check this client need interface information. */
273 if (! client->ifinfo)
274 return 0;
275
276 if (!ifp->link_params)
277 return 0;
278 s = client->obuf;
279 stream_reset (s);
280
281 zserv_create_header (s, ZEBRA_INTERFACE_LINK_PARAMS, ifp->vrf_id);
282
283 /* Add Interface Index */
284 stream_putl (s, ifp->ifindex);
285
286 /* Then TE Link Parameters */
287 if (zebra_interface_link_params_write (s, ifp) == 0)
288 return 0;
289
290 /* Write packet size. */
291 stream_putw_at (s, 0, stream_get_endp (s));
292
293 return zebra_server_send_message (client);
294 }
295
296 /* Interface address is added/deleted. Send ZEBRA_INTERFACE_ADDRESS_ADD or
297 * ZEBRA_INTERFACE_ADDRESS_DELETE to the client.
298 *
299 * A ZEBRA_INTERFACE_ADDRESS_ADD is sent in the following situations:
300 * - in response to a 3-byte ZEBRA_INTERFACE_ADD request
301 * from the client, after the ZEBRA_INTERFACE_ADD has been
302 * sent from zebra to the client
303 * - redistribute new address info to all clients in the following situations
304 * - at startup, when zebra figures out the available interfaces
305 * - when an interface is added (where support for
306 * RTM_IFANNOUNCE or AF_NETLINK sockets is available), or when
307 * an interface is marked IFF_UP (i.e., an RTM_IFINFO message is
308 * received)
309 * - for the vty commands "ip address A.B.C.D/M [<secondary>|<label LINE>]"
310 * and "no bandwidth <1-10000000>", "ipv6 address X:X::X:X/M"
311 * - when an RTM_NEWADDR message is received from the kernel,
312 *
313 * The call tree that triggers ZEBRA_INTERFACE_ADDRESS_DELETE:
314 *
315 * zsend_interface_address(DELETE)
316 * ^
317 * |
318 * zebra_interface_address_delete_update
319 * ^ ^ ^
320 * | | if_delete_update
321 * | |
322 * ip_address_uninstall connected_delete_ipv4
323 * [ipv6_addresss_uninstall] [connected_delete_ipv6]
324 * ^ ^
325 * | |
326 * | RTM_NEWADDR on routing/netlink socket
327 * |
328 * vty commands:
329 * "no ip address A.B.C.D/M [label LINE]"
330 * "no ip address A.B.C.D/M secondary"
331 * ["no ipv6 address X:X::X:X/M"]
332 *
333 */
334 int
335 zsend_interface_address (int cmd, struct zserv *client,
336 struct interface *ifp, struct connected *ifc)
337 {
338 int blen;
339 struct stream *s;
340 struct prefix *p;
341
342 s = client->obuf;
343 stream_reset (s);
344
345 zserv_create_header (s, cmd, ifp->vrf_id);
346 stream_putl (s, ifp->ifindex);
347
348 /* Interface address flag. */
349 stream_putc (s, ifc->flags);
350
351 /* Prefix information. */
352 p = ifc->address;
353 stream_putc (s, p->family);
354 blen = prefix_blen (p);
355 stream_put (s, &p->u.prefix, blen);
356
357 /*
358 * XXX gnu version does not send prefixlen for ZEBRA_INTERFACE_ADDRESS_DELETE
359 * but zebra_interface_address_delete_read() in the gnu version
360 * expects to find it
361 */
362 stream_putc (s, p->prefixlen);
363
364 /* Destination. */
365 p = ifc->destination;
366 if (p)
367 stream_put (s, &p->u.prefix, blen);
368 else
369 stream_put (s, NULL, blen);
370
371 /* Write packet size. */
372 stream_putw_at (s, 0, stream_get_endp (s));
373
374 client->connected_rt_add_cnt++;
375 return zebra_server_send_message(client);
376 }
377
378 static int
379 zsend_interface_nbr_address (int cmd, struct zserv *client,
380 struct interface *ifp, struct nbr_connected *ifc)
381 {
382 int blen;
383 struct stream *s;
384 struct prefix *p;
385
386 s = client->obuf;
387 stream_reset (s);
388
389 zserv_create_header (s, cmd, ifp->vrf_id);
390 stream_putl (s, ifp->ifindex);
391
392 /* Prefix information. */
393 p = ifc->address;
394 stream_putc (s, p->family);
395 blen = prefix_blen (p);
396 stream_put (s, &p->u.prefix, blen);
397
398 /*
399 * XXX gnu version does not send prefixlen for ZEBRA_INTERFACE_ADDRESS_DELETE
400 * but zebra_interface_address_delete_read() in the gnu version
401 * expects to find it
402 */
403 stream_putc (s, p->prefixlen);
404
405 /* Write packet size. */
406 stream_putw_at (s, 0, stream_get_endp (s));
407
408 return zebra_server_send_message(client);
409 }
410
411 /* Interface address addition. */
412 static void
413 zebra_interface_nbr_address_add_update (struct interface *ifp,
414 struct nbr_connected *ifc)
415 {
416 struct listnode *node, *nnode;
417 struct zserv *client;
418 struct prefix *p;
419
420 if (IS_ZEBRA_DEBUG_EVENT)
421 {
422 char buf[INET6_ADDRSTRLEN];
423
424 p = ifc->address;
425 zlog_debug ("MESSAGE: ZEBRA_INTERFACE_NBR_ADDRESS_ADD %s/%d on %s",
426 inet_ntop (p->family, &p->u.prefix, buf, INET6_ADDRSTRLEN),
427 p->prefixlen, ifc->ifp->name);
428 }
429
430 for (ALL_LIST_ELEMENTS (zebrad.client_list, node, nnode, client))
431 zsend_interface_nbr_address (ZEBRA_INTERFACE_NBR_ADDRESS_ADD, client, ifp, ifc);
432 }
433
434 /* Interface address deletion. */
435 static void
436 zebra_interface_nbr_address_delete_update (struct interface *ifp,
437 struct nbr_connected *ifc)
438 {
439 struct listnode *node, *nnode;
440 struct zserv *client;
441 struct prefix *p;
442
443 if (IS_ZEBRA_DEBUG_EVENT)
444 {
445 char buf[INET6_ADDRSTRLEN];
446
447 p = ifc->address;
448 zlog_debug ("MESSAGE: ZEBRA_INTERFACE_NBR_ADDRESS_DELETE %s/%d on %s",
449 inet_ntop (p->family, &p->u.prefix, buf, INET6_ADDRSTRLEN),
450 p->prefixlen, ifc->ifp->name);
451 }
452
453 for (ALL_LIST_ELEMENTS (zebrad.client_list, node, nnode, client))
454 zsend_interface_nbr_address (ZEBRA_INTERFACE_NBR_ADDRESS_DELETE, client, ifp, ifc);
455 }
456
457 /* Send addresses on interface to client */
458 int
459 zsend_interface_addresses (struct zserv *client, struct interface *ifp)
460 {
461 struct listnode *cnode, *cnnode;
462 struct connected *c;
463 struct nbr_connected *nc;
464
465 /* Send interface addresses. */
466 for (ALL_LIST_ELEMENTS (ifp->connected, cnode, cnnode, c))
467 {
468 if (!CHECK_FLAG (c->conf, ZEBRA_IFC_REAL))
469 continue;
470
471 if (zsend_interface_address (ZEBRA_INTERFACE_ADDRESS_ADD, client,
472 ifp, c) < 0)
473 return -1;
474 }
475
476 /* Send interface neighbors. */
477 for (ALL_LIST_ELEMENTS (ifp->nbr_connected, cnode, cnnode, nc))
478 {
479 if (zsend_interface_nbr_address (ZEBRA_INTERFACE_NBR_ADDRESS_ADD,
480 client, ifp, nc) < 0)
481 return -1;
482 }
483
484 return 0;
485 }
486
487 /* Notify client about interface moving from one VRF to another.
488 * Whether client is interested in old and new VRF is checked by caller.
489 */
490 int
491 zsend_interface_vrf_update (struct zserv *client, struct interface *ifp,
492 vrf_id_t vrf_id)
493 {
494 struct stream *s;
495
496 s = client->obuf;
497 stream_reset (s);
498
499 zserv_create_header (s, ZEBRA_INTERFACE_VRF_UPDATE, ifp->vrf_id);
500
501 /* Fill in the ifIndex of the interface and its new VRF (id) */
502 stream_putl (s, ifp->ifindex);
503 stream_putw (s, vrf_id);
504
505 /* Write packet size. */
506 stream_putw_at (s, 0, stream_get_endp (s));
507
508 client->if_vrfchg_cnt++;
509 return zebra_server_send_message(client);
510 }
511
512 /* Add new nbr connected IPv6 address */
513 void
514 nbr_connected_add_ipv6 (struct interface *ifp, struct in6_addr *address)
515 {
516 struct nbr_connected *ifc;
517 struct prefix p;
518
519 p.family = AF_INET6;
520 IPV6_ADDR_COPY (&p.u.prefix, address);
521 p.prefixlen = IPV6_MAX_PREFIXLEN;
522
523 if (!(ifc = listnode_head(ifp->nbr_connected)))
524 {
525 /* new addition */
526 ifc = nbr_connected_new ();
527 ifc->address = prefix_new();
528 ifc->ifp = ifp;
529 listnode_add (ifp->nbr_connected, ifc);
530 }
531
532 prefix_copy(ifc->address, &p);
533
534 zebra_interface_nbr_address_add_update (ifp, ifc);
535
536 if_nbr_ipv6ll_to_ipv4ll_neigh_update (ifp, address, 1);
537 }
538
539 void
540 nbr_connected_delete_ipv6 (struct interface *ifp, struct in6_addr *address)
541 {
542 struct nbr_connected *ifc;
543 struct prefix p;
544
545 p.family = AF_INET6;
546 IPV6_ADDR_COPY (&p.u.prefix, address);
547 p.prefixlen = IPV6_MAX_PREFIXLEN;
548
549 ifc = nbr_connected_check(ifp, &p);
550 if (!ifc)
551 return;
552
553 listnode_delete (ifp->nbr_connected, ifc);
554
555 zebra_interface_nbr_address_delete_update (ifp, ifc);
556
557 if_nbr_ipv6ll_to_ipv4ll_neigh_update (ifp, address, 0);
558
559 nbr_connected_free (ifc);
560 }
561
562 /*
563 * The cmd passed to zsend_interface_update may be ZEBRA_INTERFACE_UP or
564 * ZEBRA_INTERFACE_DOWN.
565 *
566 * The ZEBRA_INTERFACE_UP message is sent from the zebra server to
567 * the clients in one of 2 situations:
568 * - an if_up is detected e.g., as a result of an RTM_IFINFO message
569 * - a vty command modifying the bandwidth of an interface is received.
570 * The ZEBRA_INTERFACE_DOWN message is sent when an if_down is detected.
571 */
572 int
573 zsend_interface_update (int cmd, struct zserv *client, struct interface *ifp)
574 {
575 struct stream *s;
576
577 s = client->obuf;
578 stream_reset (s);
579
580 zserv_create_header (s, cmd, ifp->vrf_id);
581 zserv_encode_interface (s, ifp);
582
583 if (cmd == ZEBRA_INTERFACE_UP)
584 client->ifup_cnt++;
585 else
586 client->ifdown_cnt++;
587
588 return zebra_server_send_message(client);
589 }
590
591 /*
592 * This is the new function to announce and withdraw redistributed routes, used
593 * by Zebra. This is the old zsend_route_multipath() function. That function
594 * was duplicating code to send a lot of information that was essentially thrown
595 * away or ignored by the receiver. This is the leaner function that is not a
596 * duplicate of the zapi_ipv4_route_add/del.
597 *
598 * The primary difference is that this function merely sends a single NH instead of
599 * all the nexthops.
600 */
601 int
602 zsend_redistribute_route (int add, struct zserv *client, struct prefix *p,
603 struct rib *rib)
604 {
605 afi_t afi;
606 int cmd;
607 int psize;
608 struct stream *s;
609 struct nexthop *nexthop;
610 unsigned long nhnummark = 0, messmark = 0;
611 int nhnum = 0;
612 u_char zapi_flags = 0;
613 struct nexthop dummy_nh;
614
615 afi = family2afi (p->family);
616 if (add)
617 {
618 switch (afi)
619 {
620 case AFI_IP:
621 cmd = ZEBRA_REDISTRIBUTE_IPV4_ADD;
622 client->redist_v4_add_cnt++;
623 break;
624 case AFI_IP6:
625 cmd = ZEBRA_REDISTRIBUTE_IPV6_ADD;
626 client->redist_v6_add_cnt++;
627 break;
628 default:
629 return -1;
630 }
631 }
632 else
633 {
634 switch (afi)
635 {
636 case AFI_IP:
637 cmd = ZEBRA_REDISTRIBUTE_IPV4_DEL;
638 client->redist_v4_del_cnt++;
639 break;
640 case AFI_IP6:
641 cmd = ZEBRA_REDISTRIBUTE_IPV6_DEL;
642 client->redist_v6_del_cnt++;
643 break;
644 default:
645 return -1;
646 }
647 }
648
649 s = client->obuf;
650 stream_reset (s);
651 memset(&dummy_nh, 0, sizeof(struct nexthop));
652
653 zserv_create_header (s, cmd, rib->vrf_id);
654
655 /* Put type and nexthop. */
656 stream_putc (s, rib->type);
657 stream_putw (s, rib->instance);
658 stream_putl (s, rib->flags);
659
660 /* marker for message flags field */
661 messmark = stream_get_endp (s);
662 stream_putc (s, 0);
663
664 /* Prefix. */
665 psize = PSIZE (p->prefixlen);
666 stream_putc (s, p->prefixlen);
667 stream_write (s, (u_char *) & p->u.prefix, psize);
668
669 for (nexthop = rib->nexthop; nexthop; nexthop = nexthop->next)
670 {
671 /* We don't send any nexthops when there's a multipath */
672 if (rib->nexthop_active_num > 1 && client->proto != ZEBRA_ROUTE_LDP)
673 {
674 SET_FLAG (zapi_flags, ZAPI_MESSAGE_NEXTHOP);
675 SET_FLAG (zapi_flags, ZAPI_MESSAGE_IFINDEX);
676
677 stream_putc(s, 1);
678 if (p->family == AF_INET)
679 {
680 stream_put_in_addr (s, &dummy_nh.gate.ipv4);
681 }
682 else if (p->family == AF_INET6)
683 {
684 stream_write (s, (u_char *) &dummy_nh.gate.ipv6, 16);
685 }
686 else
687 {
688 /* We don't handle anything else now, abort */
689 zlog_err("%s: Unable to redistribute route of unknown family, %d\n",
690 __func__, p->family);
691 return -1;
692 }
693 stream_putc (s, 1);
694 stream_putl (s, 0); /* dummy ifindex */
695 break;
696 }
697
698 if (CHECK_FLAG(nexthop->flags, NEXTHOP_FLAG_ACTIVE))
699 {
700 SET_FLAG (zapi_flags, ZAPI_MESSAGE_NEXTHOP);
701 SET_FLAG (zapi_flags, ZAPI_MESSAGE_IFINDEX);
702 if (nhnummark == 0)
703 {
704 nhnummark = stream_get_endp (s);
705 stream_putc (s, 1); /* placeholder */
706 }
707 nhnum++;
708
709 switch(nexthop->type)
710 {
711 case NEXTHOP_TYPE_IPV4:
712 case NEXTHOP_TYPE_IPV4_IFINDEX:
713 stream_put_in_addr (s, &nexthop->gate.ipv4);
714 break;
715 case NEXTHOP_TYPE_IPV6:
716 case NEXTHOP_TYPE_IPV6_IFINDEX:
717 /* Only BGP supports IPv4 prefix with IPv6 NH, so kill this */
718 if (p->family == AF_INET)
719 stream_put_in_addr(s, &dummy_nh.gate.ipv4);
720 else
721 stream_write (s, (u_char *) &nexthop->gate.ipv6, 16);
722 break;
723 default:
724 if (cmd == ZEBRA_REDISTRIBUTE_IPV4_ADD
725 || cmd == ZEBRA_REDISTRIBUTE_IPV4_DEL)
726 {
727 struct in_addr empty;
728 memset (&empty, 0, sizeof (struct in_addr));
729 stream_write (s, (u_char *) &empty, IPV4_MAX_BYTELEN);
730 }
731 else
732 {
733 struct in6_addr empty;
734 memset (&empty, 0, sizeof (struct in6_addr));
735 stream_write (s, (u_char *) &empty, IPV6_MAX_BYTELEN);
736 }
737 }
738
739 /* Interface index. */
740 stream_putc (s, 1);
741 stream_putl (s, nexthop->ifindex);
742
743 /* ldpd needs all nexthops */
744 if (client->proto != ZEBRA_ROUTE_LDP)
745 break;
746 }
747 }
748
749 /* Distance */
750 SET_FLAG (zapi_flags, ZAPI_MESSAGE_DISTANCE);
751 stream_putc (s, rib->distance);
752
753 /* Metric */
754 SET_FLAG (zapi_flags, ZAPI_MESSAGE_METRIC);
755 stream_putl (s, rib->metric);
756
757 /* Tag */
758 if (rib->tag)
759 {
760 SET_FLAG(zapi_flags, ZAPI_MESSAGE_TAG);
761 stream_putl(s, rib->tag);
762 }
763
764 /* MTU */
765 SET_FLAG (zapi_flags, ZAPI_MESSAGE_MTU);
766 stream_putl (s, rib->mtu);
767
768 /* write real message flags value */
769 stream_putc_at (s, messmark, zapi_flags);
770
771 /* Write next-hop number */
772 if (nhnummark)
773 stream_putc_at (s, nhnummark, nhnum);
774
775 /* Write packet size. */
776 stream_putw_at (s, 0, stream_get_endp (s));
777
778 return zebra_server_send_message(client);
779 }
780
781 static int
782 zsend_write_nexthop (struct stream *s, struct nexthop *nexthop)
783 {
784 stream_putc (s, nexthop->type);
785 switch (nexthop->type)
786 {
787 case NEXTHOP_TYPE_IPV4:
788 stream_put_in_addr (s, &nexthop->gate.ipv4);
789 break;
790 case NEXTHOP_TYPE_IPV4_IFINDEX:
791 stream_put_in_addr (s, &nexthop->gate.ipv4);
792 stream_putl (s, nexthop->ifindex);
793 break;
794 case NEXTHOP_TYPE_IPV6:
795 stream_put (s, &nexthop->gate.ipv6, 16);
796 break;
797 case NEXTHOP_TYPE_IPV6_IFINDEX:
798 stream_put (s, &nexthop->gate.ipv6, 16);
799 stream_putl (s, nexthop->ifindex);
800 break;
801 case NEXTHOP_TYPE_IFINDEX:
802 stream_putl (s, nexthop->ifindex);
803 break;
804 default:
805 /* do nothing */
806 break;
807 }
808 return 1;
809 }
810
811 /* Nexthop register */
812 static int
813 zserv_rnh_register (struct zserv *client, int sock, u_short length,
814 rnh_type_t type, struct zebra_vrf *zvrf)
815 {
816 struct rnh *rnh;
817 struct stream *s;
818 struct prefix p;
819 u_short l = 0;
820 u_char flags = 0;
821
822 if (IS_ZEBRA_DEBUG_NHT)
823 zlog_debug("rnh_register msg from client %s: length=%d, type=%s\n",
824 zebra_route_string(client->proto), length,
825 (type == RNH_NEXTHOP_TYPE) ? "nexthop" : "route");
826
827 s = client->ibuf;
828
829 client->nh_reg_time = quagga_monotime();
830
831 while (l < length)
832 {
833 flags = stream_getc(s);
834 p.family = stream_getw(s);
835 p.prefixlen = stream_getc(s);
836 l += 4;
837 if (p.family == AF_INET)
838 {
839 p.u.prefix4.s_addr = stream_get_ipv4(s);
840 l += IPV4_MAX_BYTELEN;
841 }
842 else if (p.family == AF_INET6)
843 {
844 stream_get(&p.u.prefix6, s, IPV6_MAX_BYTELEN);
845 l += IPV6_MAX_BYTELEN;
846 }
847 else
848 {
849 zlog_err("rnh_register: Received unknown family type %d\n",
850 p.family);
851 return -1;
852 }
853 rnh = zebra_add_rnh(&p, zvrf_id (zvrf), type);
854 if (type == RNH_NEXTHOP_TYPE)
855 {
856 if (flags && !CHECK_FLAG(rnh->flags, ZEBRA_NHT_CONNECTED))
857 SET_FLAG(rnh->flags, ZEBRA_NHT_CONNECTED);
858 else if (!flags && CHECK_FLAG(rnh->flags, ZEBRA_NHT_CONNECTED))
859 UNSET_FLAG(rnh->flags, ZEBRA_NHT_CONNECTED);
860 }
861 else if (type == RNH_IMPORT_CHECK_TYPE)
862 {
863 if (flags && !CHECK_FLAG(rnh->flags, ZEBRA_NHT_EXACT_MATCH))
864 SET_FLAG(rnh->flags, ZEBRA_NHT_EXACT_MATCH);
865 else if (!flags && CHECK_FLAG(rnh->flags, ZEBRA_NHT_EXACT_MATCH))
866 UNSET_FLAG(rnh->flags, ZEBRA_NHT_EXACT_MATCH);
867 }
868
869 zebra_add_rnh_client(rnh, client, type, zvrf_id (zvrf));
870 /* Anything not AF_INET/INET6 has been filtered out above */
871 zebra_evaluate_rnh(zvrf_id (zvrf), p.family, 1, type, &p);
872 }
873 return 0;
874 }
875
876 /* Nexthop register */
877 static int
878 zserv_rnh_unregister (struct zserv *client, int sock, u_short length,
879 rnh_type_t type, struct zebra_vrf *zvrf)
880 {
881 struct rnh *rnh;
882 struct stream *s;
883 struct prefix p;
884 u_short l = 0;
885
886 if (IS_ZEBRA_DEBUG_NHT)
887 zlog_debug("rnh_unregister msg from client %s: length=%d\n",
888 zebra_route_string(client->proto), length);
889
890 s = client->ibuf;
891
892 while (l < length)
893 {
894 (void)stream_getc(s); //Connected or not. Not used in this function
895 p.family = stream_getw(s);
896 p.prefixlen = stream_getc(s);
897 l += 4;
898 if (p.family == AF_INET)
899 {
900 p.u.prefix4.s_addr = stream_get_ipv4(s);
901 l += IPV4_MAX_BYTELEN;
902 }
903 else if (p.family == AF_INET6)
904 {
905 stream_get(&p.u.prefix6, s, IPV6_MAX_BYTELEN);
906 l += IPV6_MAX_BYTELEN;
907 }
908 else
909 {
910 zlog_err("rnh_register: Received unknown family type %d\n",
911 p.family);
912 return -1;
913 }
914 rnh = zebra_lookup_rnh(&p, zvrf_id (zvrf), type);
915 if (rnh)
916 {
917 client->nh_dereg_time = quagga_monotime();
918 zebra_remove_rnh_client(rnh, client, type);
919 }
920 }
921 return 0;
922 }
923
924 /*
925 Modified version of zsend_ipv4_nexthop_lookup():
926 Query unicast rib if nexthop is not found on mrib.
927 Returns both route metric and protocol distance.
928 */
929 static int
930 zsend_ipv4_nexthop_lookup_mrib (struct zserv *client, struct in_addr addr, struct rib *rib, struct zebra_vrf *zvrf)
931 {
932 struct stream *s;
933 unsigned long nump;
934 u_char num;
935 struct nexthop *nexthop;
936
937 /* Get output stream. */
938 s = client->obuf;
939 stream_reset (s);
940
941 /* Fill in result. */
942 zserv_create_header (s, ZEBRA_IPV4_NEXTHOP_LOOKUP_MRIB, zvrf_id (zvrf));
943 stream_put_in_addr (s, &addr);
944
945 if (rib)
946 {
947 stream_putc (s, rib->distance);
948 stream_putl (s, rib->metric);
949 num = 0;
950 nump = stream_get_endp(s); /* remember position for nexthop_num */
951 stream_putc (s, 0); /* reserve room for nexthop_num */
952 /* Only non-recursive routes are elegible to resolve the nexthop we
953 * are looking up. Therefore, we will just iterate over the top
954 * chain of nexthops. */
955 for (nexthop = rib->nexthop; nexthop; nexthop = nexthop->next)
956 if (CHECK_FLAG (nexthop->flags, NEXTHOP_FLAG_ACTIVE))
957 num += zsend_write_nexthop (s, nexthop);
958
959 stream_putc_at (s, nump, num); /* store nexthop_num */
960 }
961 else
962 {
963 stream_putc (s, 0); /* distance */
964 stream_putl (s, 0); /* metric */
965 stream_putc (s, 0); /* nexthop_num */
966 }
967
968 stream_putw_at (s, 0, stream_get_endp (s));
969
970 return zebra_server_send_message(client);
971 }
972
973 /* Router-id is updated. Send ZEBRA_ROUTER_ID_ADD to client. */
974 int
975 zsend_router_id_update (struct zserv *client, struct prefix *p,
976 vrf_id_t vrf_id)
977 {
978 struct stream *s;
979 int blen;
980
981 /* Check this client need interface information. */
982 if (! vrf_bitmap_check (client->ridinfo, vrf_id))
983 return 0;
984
985 s = client->obuf;
986 stream_reset (s);
987
988 /* Message type. */
989 zserv_create_header (s, ZEBRA_ROUTER_ID_UPDATE, vrf_id);
990
991 /* Prefix information. */
992 stream_putc (s, p->family);
993 blen = prefix_blen (p);
994 stream_put (s, &p->u.prefix, blen);
995 stream_putc (s, p->prefixlen);
996
997 /* Write packet size. */
998 stream_putw_at (s, 0, stream_get_endp (s));
999
1000 return zebra_server_send_message(client);
1001 }
1002
1003 /* Register zebra server interface information. Send current all
1004 interface and address information. */
1005 static int
1006 zread_interface_add (struct zserv *client, u_short length, struct zebra_vrf *zvrf)
1007 {
1008 struct vrf *vrf;
1009 struct listnode *ifnode, *ifnnode;
1010 struct interface *ifp;
1011
1012 /* Interface information is needed. */
1013 vrf_bitmap_set (client->ifinfo, zvrf_id (zvrf));
1014
1015 RB_FOREACH (vrf, vrf_id_head, &vrfs_by_id)
1016 {
1017 for (ALL_LIST_ELEMENTS (vrf->iflist, ifnode, ifnnode, ifp))
1018 {
1019 /* Skip pseudo interface. */
1020 if (! CHECK_FLAG (ifp->status, ZEBRA_INTERFACE_ACTIVE))
1021 continue;
1022
1023 if (zsend_interface_add (client, ifp) < 0)
1024 return -1;
1025
1026 if (zsend_interface_addresses (client, ifp) < 0)
1027 return -1;
1028 }
1029 }
1030 return 0;
1031 }
1032
1033 /* Unregister zebra server interface information. */
1034 static int
1035 zread_interface_delete (struct zserv *client, u_short length, struct zebra_vrf *zvrf)
1036 {
1037 vrf_bitmap_unset (client->ifinfo, zvrf_id (zvrf));
1038 return 0;
1039 }
1040
1041 void
1042 zserv_nexthop_num_warn (const char *caller, const struct prefix *p, const unsigned int nexthop_num)
1043 {
1044 if (nexthop_num > MULTIPATH_NUM)
1045 {
1046 char buff[PREFIX2STR_BUFFER];
1047 prefix2str(p, buff, sizeof (buff));
1048 zlog_warn("%s: Prefix %s has %d nexthops, but we can only use the first %d",
1049 caller, buff, nexthop_num, MULTIPATH_NUM);
1050 }
1051 }
1052
1053 /* This function support multiple nexthop. */
1054 /*
1055 * Parse the ZEBRA_IPV4_ROUTE_ADD sent from client. Update rib and
1056 * add kernel route.
1057 */
1058 static int
1059 zread_ipv4_add (struct zserv *client, u_short length, struct zebra_vrf *zvrf)
1060 {
1061 int i;
1062 struct rib *rib;
1063 struct prefix p;
1064 u_char message;
1065 struct in_addr nexthop;
1066 u_char nexthop_num;
1067 u_char nexthop_type;
1068 struct stream *s;
1069 ifindex_t ifindex;
1070 safi_t safi;
1071 int ret;
1072
1073 /* Get input stream. */
1074 s = client->ibuf;
1075
1076 /* Allocate new rib. */
1077 rib = XCALLOC (MTYPE_RIB, sizeof (struct rib));
1078
1079 /* Type, flags, message. */
1080 rib->type = stream_getc (s);
1081 rib->instance = stream_getw (s);
1082 rib->flags = stream_getl (s);
1083 message = stream_getc (s);
1084 safi = stream_getw (s);
1085 rib->uptime = time (NULL);
1086
1087 /* IPv4 prefix. */
1088 memset (&p, 0, sizeof (struct prefix_ipv4));
1089 p.family = AF_INET;
1090 p.prefixlen = stream_getc (s);
1091 stream_get (&p.u.prefix4, s, PSIZE (p.prefixlen));
1092
1093 /* VRF ID */
1094 rib->vrf_id = zvrf_id (zvrf);
1095
1096 /* Nexthop parse. */
1097 if (CHECK_FLAG (message, ZAPI_MESSAGE_NEXTHOP))
1098 {
1099 nexthop_num = stream_getc (s);
1100 zserv_nexthop_num_warn(__func__, (const struct prefix *)&p, nexthop_num);
1101
1102 for (i = 0; i < nexthop_num; i++)
1103 {
1104 nexthop_type = stream_getc (s);
1105
1106 switch (nexthop_type)
1107 {
1108 case NEXTHOP_TYPE_IFINDEX:
1109 ifindex = stream_getl (s);
1110 rib_nexthop_ifindex_add (rib, ifindex);
1111 break;
1112 case NEXTHOP_TYPE_IPV4:
1113 nexthop.s_addr = stream_get_ipv4 (s);
1114 rib_nexthop_ipv4_add (rib, &nexthop, NULL);
1115 break;
1116 case NEXTHOP_TYPE_IPV4_IFINDEX:
1117 nexthop.s_addr = stream_get_ipv4 (s);
1118 ifindex = stream_getl (s);
1119 rib_nexthop_ipv4_ifindex_add (rib, &nexthop, NULL, ifindex);
1120 break;
1121 case NEXTHOP_TYPE_IPV6:
1122 stream_forward_getp (s, IPV6_MAX_BYTELEN);
1123 break;
1124 case NEXTHOP_TYPE_BLACKHOLE:
1125 rib_nexthop_blackhole_add (rib);
1126 break;
1127 }
1128 }
1129 }
1130
1131 /* Distance. */
1132 if (CHECK_FLAG (message, ZAPI_MESSAGE_DISTANCE))
1133 rib->distance = stream_getc (s);
1134
1135 /* Metric. */
1136 if (CHECK_FLAG (message, ZAPI_MESSAGE_METRIC))
1137 rib->metric = stream_getl (s);
1138
1139 /* Tag */
1140 if (CHECK_FLAG (message, ZAPI_MESSAGE_TAG))
1141 rib->tag = stream_getl (s);
1142 else
1143 rib->tag = 0;
1144
1145 if (CHECK_FLAG (message, ZAPI_MESSAGE_MTU))
1146 rib->mtu = stream_getl (s);
1147 else
1148 rib->mtu = 0;
1149
1150 /* Table */
1151 rib->table = zvrf->table_id;
1152
1153 ret = rib_add_multipath (AFI_IP, safi, &p, rib);
1154
1155 /* Stats */
1156 if (ret > 0)
1157 client->v4_route_add_cnt++;
1158 else if (ret < 0)
1159 client->v4_route_upd8_cnt++;
1160 return 0;
1161 }
1162
1163 /* Zebra server IPv4 prefix delete function. */
1164 static int
1165 zread_ipv4_delete (struct zserv *client, u_short length, struct zebra_vrf *zvrf)
1166 {
1167 int i;
1168 struct stream *s;
1169 struct zapi_ipv4 api;
1170 struct in_addr nexthop;
1171 union g_addr *nexthop_p;
1172 unsigned long ifindex;
1173 struct prefix p;
1174 u_char nexthop_num;
1175 u_char nexthop_type;
1176 u_int32_t table_id;
1177
1178 s = client->ibuf;
1179 ifindex = 0;
1180 nexthop.s_addr = 0;
1181 nexthop_p = NULL;
1182
1183 /* Type, flags, message. */
1184 api.type = stream_getc (s);
1185 api.instance = stream_getw (s);
1186 api.flags = stream_getl (s);
1187 api.message = stream_getc (s);
1188 api.safi = stream_getw (s);
1189
1190 /* IPv4 prefix. */
1191 memset (&p, 0, sizeof (struct prefix_ipv4));
1192 p.family = AF_INET;
1193 p.prefixlen = stream_getc (s);
1194 stream_get (&p.u.prefix4, s, PSIZE (p.prefixlen));
1195
1196 /* Nexthop, ifindex, distance, metric. */
1197 if (CHECK_FLAG (api.message, ZAPI_MESSAGE_NEXTHOP))
1198 {
1199 nexthop_num = stream_getc (s);
1200
1201 for (i = 0; i < nexthop_num; i++)
1202 {
1203 nexthop_type = stream_getc (s);
1204
1205 switch (nexthop_type)
1206 {
1207 case NEXTHOP_TYPE_IFINDEX:
1208 ifindex = stream_getl (s);
1209 break;
1210 case NEXTHOP_TYPE_IPV4:
1211 nexthop.s_addr = stream_get_ipv4 (s);
1212 nexthop_p = (union g_addr *)&nexthop;
1213 break;
1214 case NEXTHOP_TYPE_IPV4_IFINDEX:
1215 nexthop.s_addr = stream_get_ipv4 (s);
1216 nexthop_p = (union g_addr *)&nexthop;
1217 ifindex = stream_getl (s);
1218 break;
1219 case NEXTHOP_TYPE_IPV6:
1220 stream_forward_getp (s, IPV6_MAX_BYTELEN);
1221 break;
1222 }
1223 }
1224 }
1225
1226 /* Distance. */
1227 if (CHECK_FLAG (api.message, ZAPI_MESSAGE_DISTANCE))
1228 api.distance = stream_getc (s);
1229 else
1230 api.distance = 0;
1231
1232 /* Metric. */
1233 if (CHECK_FLAG (api.message, ZAPI_MESSAGE_METRIC))
1234 api.metric = stream_getl (s);
1235 else
1236 api.metric = 0;
1237
1238 /* tag */
1239 if (CHECK_FLAG (api.message, ZAPI_MESSAGE_TAG))
1240 api.tag = stream_getl (s);
1241 else
1242 api.tag = 0;
1243
1244 table_id = zvrf->table_id;
1245
1246 rib_delete (AFI_IP, api.safi, zvrf_id (zvrf), api.type, api.instance,
1247 api.flags, &p, nexthop_p, ifindex, table_id);
1248 client->v4_route_del_cnt++;
1249 return 0;
1250 }
1251
1252 /* MRIB Nexthop lookup for IPv4. */
1253 static int
1254 zread_ipv4_nexthop_lookup_mrib (struct zserv *client, u_short length, struct zebra_vrf *zvrf)
1255 {
1256 struct in_addr addr;
1257 struct rib *rib;
1258
1259 addr.s_addr = stream_get_ipv4 (client->ibuf);
1260 rib = rib_match_ipv4_multicast (zvrf_id (zvrf), addr, NULL);
1261 return zsend_ipv4_nexthop_lookup_mrib (client, addr, rib, zvrf);
1262 }
1263
1264 /* Zebra server IPv6 prefix add function. */
1265 static int
1266 zread_ipv4_route_ipv6_nexthop_add (struct zserv *client, u_short length, struct zebra_vrf *zvrf)
1267 {
1268 int i;
1269 struct stream *s;
1270 struct in6_addr nexthop;
1271 struct rib *rib;
1272 u_char message;
1273 u_char nexthop_num;
1274 u_char nexthop_type;
1275 struct prefix p;
1276 safi_t safi;
1277 static struct in6_addr nexthops[MULTIPATH_NUM];
1278 static unsigned int ifindices[MULTIPATH_NUM];
1279 int ret;
1280
1281 /* Get input stream. */
1282 s = client->ibuf;
1283
1284 memset (&nexthop, 0, sizeof (struct in6_addr));
1285
1286 /* Allocate new rib. */
1287 rib = XCALLOC (MTYPE_RIB, sizeof (struct rib));
1288
1289 /* Type, flags, message. */
1290 rib->type = stream_getc (s);
1291 rib->instance = stream_getw (s);
1292 rib->flags = stream_getl (s);
1293 message = stream_getc (s);
1294 safi = stream_getw (s);
1295 rib->uptime = time (NULL);
1296
1297 /* IPv4 prefix. */
1298 memset (&p, 0, sizeof (struct prefix_ipv4));
1299 p.family = AF_INET;
1300 p.prefixlen = stream_getc (s);
1301 stream_get (&p.u.prefix4, s, PSIZE (p.prefixlen));
1302
1303 /* VRF ID */
1304 rib->vrf_id = zvrf_id (zvrf);
1305
1306 /* We need to give nh-addr, nh-ifindex with the same next-hop object
1307 * to the rib to ensure that IPv6 multipathing works; need to coalesce
1308 * these. Clients should send the same number of paired set of
1309 * next-hop-addr/next-hop-ifindices. */
1310 if (CHECK_FLAG (message, ZAPI_MESSAGE_NEXTHOP))
1311 {
1312 int nh_count = 0;
1313 int if_count = 0;
1314 int max_nh_if = 0;
1315
1316 nexthop_num = stream_getc (s);
1317 zserv_nexthop_num_warn(__func__, (const struct prefix *)&p, nexthop_num);
1318 for (i = 0; i < nexthop_num; i++)
1319 {
1320 nexthop_type = stream_getc (s);
1321
1322 switch (nexthop_type)
1323 {
1324 case NEXTHOP_TYPE_IPV6:
1325 stream_get (&nexthop, s, 16);
1326 if (nh_count < MULTIPATH_NUM) {
1327 nexthops[nh_count++] = nexthop;
1328 }
1329 break;
1330 case NEXTHOP_TYPE_IFINDEX:
1331 if (if_count < MULTIPATH_NUM) {
1332 ifindices[if_count++] = stream_getl (s);
1333 }
1334 break;
1335 case NEXTHOP_TYPE_BLACKHOLE:
1336 rib_nexthop_blackhole_add (rib);
1337 break;
1338 }
1339 }
1340
1341 max_nh_if = (nh_count > if_count) ? nh_count : if_count;
1342 for (i = 0; i < max_nh_if; i++)
1343 {
1344 if ((i < nh_count) && !IN6_IS_ADDR_UNSPECIFIED (&nexthops[i])) {
1345 if ((i < if_count) && ifindices[i]) {
1346 rib_nexthop_ipv6_ifindex_add (rib, &nexthops[i], ifindices[i]);
1347 }
1348 else {
1349 rib_nexthop_ipv6_add (rib, &nexthops[i]);
1350 }
1351 }
1352 else {
1353 if ((i < if_count) && ifindices[i]) {
1354 rib_nexthop_ifindex_add (rib, ifindices[i]);
1355 }
1356 }
1357 }
1358 }
1359
1360 /* Distance. */
1361 if (CHECK_FLAG (message, ZAPI_MESSAGE_DISTANCE))
1362 rib->distance = stream_getc (s);
1363
1364 /* Metric. */
1365 if (CHECK_FLAG (message, ZAPI_MESSAGE_METRIC))
1366 rib->metric = stream_getl (s);
1367
1368 /* Tag */
1369 if (CHECK_FLAG (message, ZAPI_MESSAGE_TAG))
1370 rib->tag = stream_getl (s);
1371 else
1372 rib->tag = 0;
1373
1374 if (CHECK_FLAG (message, ZAPI_MESSAGE_MTU))
1375 rib->mtu = stream_getl (s);
1376 else
1377 rib->mtu = 0;
1378
1379 /* Table */
1380 rib->table = zvrf->table_id;
1381
1382 ret = rib_add_multipath (AFI_IP6, safi, &p, rib);
1383 /* Stats */
1384 if (ret > 0)
1385 client->v4_route_add_cnt++;
1386 else if (ret < 0)
1387 client->v4_route_upd8_cnt++;
1388
1389 return 0;
1390 }
1391
1392 static int
1393 zread_ipv6_add (struct zserv *client, u_short length, struct zebra_vrf *zvrf)
1394 {
1395 int i;
1396 struct stream *s;
1397 struct in6_addr nexthop;
1398 struct rib *rib;
1399 u_char message;
1400 u_char nexthop_num;
1401 u_char nexthop_type;
1402 struct prefix p;
1403 safi_t safi;
1404 static struct in6_addr nexthops[MULTIPATH_NUM];
1405 static unsigned int ifindices[MULTIPATH_NUM];
1406 int ret;
1407
1408 /* Get input stream. */
1409 s = client->ibuf;
1410
1411 memset (&nexthop, 0, sizeof (struct in6_addr));
1412
1413 /* Allocate new rib. */
1414 rib = XCALLOC (MTYPE_RIB, sizeof (struct rib));
1415
1416 /* Type, flags, message. */
1417 rib->type = stream_getc (s);
1418 rib->instance = stream_getw (s);
1419 rib->flags = stream_getl (s);
1420 message = stream_getc (s);
1421 safi = stream_getw (s);
1422 rib->uptime = time (NULL);
1423
1424 /* IPv6 prefix. */
1425 memset (&p, 0, sizeof (struct prefix_ipv6));
1426 p.family = AF_INET6;
1427 p.prefixlen = stream_getc (s);
1428 stream_get (&p.u.prefix6, s, PSIZE (p.prefixlen));
1429
1430 /* We need to give nh-addr, nh-ifindex with the same next-hop object
1431 * to the rib to ensure that IPv6 multipathing works; need to coalesce
1432 * these. Clients should send the same number of paired set of
1433 * next-hop-addr/next-hop-ifindices. */
1434 if (CHECK_FLAG (message, ZAPI_MESSAGE_NEXTHOP))
1435 {
1436 int nh_count = 0;
1437 int if_count = 0;
1438 int max_nh_if = 0;
1439
1440 nexthop_num = stream_getc (s);
1441 zserv_nexthop_num_warn(__func__, (const struct prefix *)&p, nexthop_num);
1442 for (i = 0; i < nexthop_num; i++)
1443 {
1444 nexthop_type = stream_getc (s);
1445
1446 switch (nexthop_type)
1447 {
1448 case NEXTHOP_TYPE_IPV6:
1449 stream_get (&nexthop, s, 16);
1450 if (nh_count < MULTIPATH_NUM) {
1451 nexthops[nh_count++] = nexthop;
1452 }
1453 break;
1454 case NEXTHOP_TYPE_IFINDEX:
1455 if (if_count < MULTIPATH_NUM) {
1456 ifindices[if_count++] = stream_getl (s);
1457 }
1458 break;
1459 case NEXTHOP_TYPE_BLACKHOLE:
1460 rib_nexthop_blackhole_add (rib);
1461 break;
1462 }
1463 }
1464
1465 max_nh_if = (nh_count > if_count) ? nh_count : if_count;
1466 for (i = 0; i < max_nh_if; i++)
1467 {
1468 if ((i < nh_count) && !IN6_IS_ADDR_UNSPECIFIED (&nexthops[i])) {
1469 if ((i < if_count) && ifindices[i])
1470 rib_nexthop_ipv6_ifindex_add (rib, &nexthops[i], ifindices[i]);
1471 else
1472 rib_nexthop_ipv6_add (rib, &nexthops[i]);
1473 }
1474 else {
1475 if ((i < if_count) && ifindices[i])
1476 rib_nexthop_ifindex_add (rib, ifindices[i]);
1477 }
1478 }
1479 }
1480
1481 /* Distance. */
1482 if (CHECK_FLAG (message, ZAPI_MESSAGE_DISTANCE))
1483 rib->distance = stream_getc (s);
1484
1485 /* Metric. */
1486 if (CHECK_FLAG (message, ZAPI_MESSAGE_METRIC))
1487 rib->metric = stream_getl (s);
1488
1489 /* Tag */
1490 if (CHECK_FLAG (message, ZAPI_MESSAGE_TAG))
1491 rib->tag = stream_getl (s);
1492 else
1493 rib->tag = 0;
1494
1495 if (CHECK_FLAG (message, ZAPI_MESSAGE_MTU))
1496 rib->mtu = stream_getl (s);
1497 else
1498 rib->mtu = 0;
1499
1500 /* VRF ID */
1501 rib->vrf_id = zvrf_id (zvrf);
1502 rib->table = zvrf->table_id;
1503
1504 ret = rib_add_multipath (AFI_IP6, safi, &p, rib);
1505 /* Stats */
1506 if (ret > 0)
1507 client->v6_route_add_cnt++;
1508 else if (ret < 0)
1509 client->v6_route_upd8_cnt++;
1510
1511 return 0;
1512 }
1513
1514 /* Zebra server IPv6 prefix delete function. */
1515 static int
1516 zread_ipv6_delete (struct zserv *client, u_short length, struct zebra_vrf *zvrf)
1517 {
1518 int i;
1519 struct stream *s;
1520 struct zapi_ipv6 api;
1521 struct in6_addr nexthop;
1522 union g_addr *pnexthop;
1523 unsigned long ifindex;
1524 struct prefix p;
1525
1526 s = client->ibuf;
1527 ifindex = 0;
1528 memset (&nexthop, 0, sizeof (struct in6_addr));
1529
1530 /* Type, flags, message. */
1531 api.type = stream_getc (s);
1532 api.instance = stream_getw (s);
1533 api.flags = stream_getl (s);
1534 api.message = stream_getc (s);
1535 api.safi = stream_getw (s);
1536
1537 /* IPv4 prefix. */
1538 memset (&p, 0, sizeof (struct prefix_ipv6));
1539 p.family = AF_INET6;
1540 p.prefixlen = stream_getc (s);
1541 stream_get (&p.u.prefix6, s, PSIZE (p.prefixlen));
1542
1543 /* Nexthop, ifindex, distance, metric. */
1544 if (CHECK_FLAG (api.message, ZAPI_MESSAGE_NEXTHOP))
1545 {
1546 u_char nexthop_type;
1547
1548 api.nexthop_num = stream_getc (s);
1549 for (i = 0; i < api.nexthop_num; i++)
1550 {
1551 nexthop_type = stream_getc (s);
1552
1553 switch (nexthop_type)
1554 {
1555 case NEXTHOP_TYPE_IPV6:
1556 stream_get (&nexthop, s, 16);
1557 pnexthop = (union g_addr *)&nexthop;
1558 break;
1559 case NEXTHOP_TYPE_IFINDEX:
1560 ifindex = stream_getl (s);
1561 break;
1562 }
1563 }
1564 }
1565
1566 /* Distance. */
1567 if (CHECK_FLAG (api.message, ZAPI_MESSAGE_DISTANCE))
1568 api.distance = stream_getc (s);
1569 else
1570 api.distance = 0;
1571
1572 /* Metric. */
1573 if (CHECK_FLAG (api.message, ZAPI_MESSAGE_METRIC))
1574 api.metric = stream_getl (s);
1575 else
1576 api.metric = 0;
1577
1578 /* tag */
1579 if (CHECK_FLAG (api.message, ZAPI_MESSAGE_TAG))
1580 api.tag = stream_getl (s);
1581 else
1582 api.tag = 0;
1583
1584 if (IN6_IS_ADDR_UNSPECIFIED (&nexthop))
1585 rib_delete (AFI_IP6, api.safi, zvrf_id (zvrf), api.type, api.instance,
1586 api.flags, &p, NULL, ifindex, client->rtm_table);
1587 else
1588 rib_delete (AFI_IP6, api.safi, zvrf_id (zvrf), api.type, api.instance,
1589 api.flags, &p, pnexthop, ifindex, client->rtm_table);
1590
1591 client->v6_route_del_cnt++;
1592 return 0;
1593 }
1594
1595 /* Register zebra server router-id information. Send current router-id */
1596 static int
1597 zread_router_id_add (struct zserv *client, u_short length, struct zebra_vrf *zvrf)
1598 {
1599 struct prefix p;
1600
1601 /* Router-id information is needed. */
1602 vrf_bitmap_set (client->ridinfo, zvrf_id (zvrf));
1603
1604 router_id_get (&p, zvrf_id (zvrf));
1605
1606 return zsend_router_id_update (client, &p, zvrf_id (zvrf));
1607 }
1608
1609 /* Unregister zebra server router-id information. */
1610 static int
1611 zread_router_id_delete (struct zserv *client, u_short length, struct zebra_vrf *zvrf)
1612 {
1613 vrf_bitmap_unset (client->ridinfo, zvrf_id (zvrf));
1614 return 0;
1615 }
1616
1617 /* Tie up route-type and client->sock */
1618 static void
1619 zread_hello (struct zserv *client)
1620 {
1621 /* type of protocol (lib/zebra.h) */
1622 u_char proto;
1623 u_short instance;
1624
1625 proto = stream_getc (client->ibuf);
1626 instance = stream_getw (client->ibuf);
1627
1628 /* accept only dynamic routing protocols */
1629 if ((proto < ZEBRA_ROUTE_MAX)
1630 && (proto > ZEBRA_ROUTE_STATIC))
1631 {
1632 zlog_notice ("client %d says hello and bids fair to announce only %s routes",
1633 client->sock, zebra_route_string(proto));
1634 if (instance)
1635 zlog_notice ("client protocol instance %d", instance);
1636
1637 client->proto = proto;
1638 client->instance = instance;
1639 }
1640 }
1641
1642 /* Unregister all information in a VRF. */
1643 static int
1644 zread_vrf_unregister (struct zserv *client, u_short length, struct zebra_vrf *zvrf)
1645 {
1646 int i;
1647 afi_t afi;
1648
1649 for (afi = AFI_IP; afi < AFI_MAX; afi++)
1650 for (i = 0; i < ZEBRA_ROUTE_MAX; i++)
1651 vrf_bitmap_unset (client->redist[afi][i], zvrf_id (zvrf));
1652 vrf_bitmap_unset (client->redist_default, zvrf_id (zvrf));
1653 vrf_bitmap_unset (client->ifinfo, zvrf_id (zvrf));
1654 vrf_bitmap_unset (client->ridinfo, zvrf_id (zvrf));
1655
1656 return 0;
1657 }
1658
1659 static void
1660 zread_mpls_labels (int command, struct zserv *client, u_short length,
1661 vrf_id_t vrf_id)
1662 {
1663 struct stream *s;
1664 enum lsp_types_t type;
1665 struct prefix prefix;
1666 enum nexthop_types_t gtype;
1667 union g_addr gate;
1668 ifindex_t ifindex;
1669 mpls_label_t in_label, out_label;
1670 u_int8_t distance;
1671 struct zebra_vrf *zvrf;
1672
1673 zvrf = vrf_info_lookup (vrf_id);
1674 if (!zvrf)
1675 return;
1676
1677 /* Get input stream. */
1678 s = client->ibuf;
1679
1680 /* Get data. */
1681 type = stream_getc (s);
1682 prefix.family = stream_getl (s);
1683 switch (prefix.family)
1684 {
1685 case AF_INET:
1686 prefix.u.prefix4.s_addr = stream_get_ipv4 (s);
1687 prefix.prefixlen = stream_getc (s);
1688 gate.ipv4.s_addr = stream_get_ipv4 (s);
1689 break;
1690 case AF_INET6:
1691 stream_get (&prefix.u.prefix6, s, 16);
1692 prefix.prefixlen = stream_getc (s);
1693 stream_get (&gate.ipv6, s, 16);
1694 break;
1695 default:
1696 return;
1697 }
1698 ifindex = stream_getl (s);
1699 distance = stream_getc (s);
1700 in_label = stream_getl (s);
1701 out_label = stream_getl (s);
1702
1703 switch (prefix.family)
1704 {
1705 case AF_INET:
1706 if (ifindex)
1707 gtype = NEXTHOP_TYPE_IPV4_IFINDEX;
1708 else
1709 gtype = NEXTHOP_TYPE_IPV4;
1710 break;
1711 case AF_INET6:
1712 if (ifindex)
1713 gtype = NEXTHOP_TYPE_IPV6_IFINDEX;
1714 else
1715 gtype = NEXTHOP_TYPE_IPV6;
1716 break;
1717 default:
1718 return;
1719 }
1720
1721 if (! mpls_enabled)
1722 return;
1723
1724 if (command == ZEBRA_MPLS_LABELS_ADD)
1725 {
1726 mpls_lsp_install (zvrf, type, in_label, out_label, gtype, &gate,
1727 NULL, ifindex);
1728 if (out_label != MPLS_IMP_NULL_LABEL)
1729 mpls_ftn_update (1, zvrf, type, &prefix, gtype, &gate, ifindex,
1730 distance, out_label);
1731 }
1732 else if (command == ZEBRA_MPLS_LABELS_DELETE)
1733 {
1734 mpls_lsp_uninstall (zvrf, type, in_label, gtype, &gate, NULL, ifindex);
1735 if (out_label != MPLS_IMP_NULL_LABEL)
1736 mpls_ftn_update (0, zvrf, type, &prefix, gtype, &gate, ifindex,
1737 distance, out_label);
1738 }
1739 }
1740
1741 /* Cleanup registered nexthops (across VRFs) upon client disconnect. */
1742 static void
1743 zebra_client_close_cleanup_rnh (struct zserv *client)
1744 {
1745 struct vrf *vrf;
1746 struct zebra_vrf *zvrf;
1747
1748 RB_FOREACH (vrf, vrf_id_head, &vrfs_by_id)
1749 {
1750 if ((zvrf = vrf->info) != NULL)
1751 {
1752 zebra_cleanup_rnh_client(zvrf_id (zvrf), AF_INET, client, RNH_NEXTHOP_TYPE);
1753 zebra_cleanup_rnh_client(zvrf_id (zvrf), AF_INET6, client, RNH_NEXTHOP_TYPE);
1754 zebra_cleanup_rnh_client(zvrf_id (zvrf), AF_INET, client, RNH_IMPORT_CHECK_TYPE);
1755 zebra_cleanup_rnh_client(zvrf_id (zvrf), AF_INET6, client, RNH_IMPORT_CHECK_TYPE);
1756 if (client->proto == ZEBRA_ROUTE_LDP)
1757 {
1758 hash_iterate(zvrf->lsp_table, mpls_ldp_lsp_uninstall_all,
1759 zvrf->lsp_table);
1760 mpls_ldp_ftn_uninstall_all (zvrf, AFI_IP);
1761 mpls_ldp_ftn_uninstall_all (zvrf, AFI_IP6);
1762 }
1763 }
1764 }
1765 }
1766
1767 /* Close zebra client. */
1768 static void
1769 zebra_client_close (struct zserv *client)
1770 {
1771 /* Send client de-registration to BFD */
1772 zebra_ptm_bfd_client_deregister(client->proto);
1773
1774 /* Cleanup any registered nexthops - across all VRFs. */
1775 zebra_client_close_cleanup_rnh (client);
1776
1777 /* Close file descriptor. */
1778 if (client->sock)
1779 {
1780 unsigned long nroutes;
1781
1782 close (client->sock);
1783 nroutes = rib_score_proto (client->proto, client->instance);
1784 zlog_notice ("client %d disconnected. %lu %s routes removed from the rib",
1785 client->sock, nroutes, zebra_route_string (client->proto));
1786 client->sock = -1;
1787 }
1788
1789 /* Free stream buffers. */
1790 if (client->ibuf)
1791 stream_free (client->ibuf);
1792 if (client->obuf)
1793 stream_free (client->obuf);
1794 if (client->wb)
1795 buffer_free(client->wb);
1796
1797 /* Release threads. */
1798 if (client->t_read)
1799 thread_cancel (client->t_read);
1800 if (client->t_write)
1801 thread_cancel (client->t_write);
1802 if (client->t_suicide)
1803 thread_cancel (client->t_suicide);
1804
1805 /* Free client structure. */
1806 listnode_delete (zebrad.client_list, client);
1807 XFREE (MTYPE_TMP, client);
1808 }
1809
1810 /* Make new client. */
1811 static void
1812 zebra_client_create (int sock)
1813 {
1814 struct zserv *client;
1815 int i;
1816 afi_t afi;
1817
1818 client = XCALLOC (MTYPE_TMP, sizeof (struct zserv));
1819
1820 /* Make client input/output buffer. */
1821 client->sock = sock;
1822 client->ibuf = stream_new (ZEBRA_MAX_PACKET_SIZ);
1823 client->obuf = stream_new (ZEBRA_MAX_PACKET_SIZ);
1824 client->wb = buffer_new(0);
1825
1826 /* Set table number. */
1827 client->rtm_table = zebrad.rtm_table_default;
1828
1829 client->connect_time = quagga_monotime();
1830 /* Initialize flags */
1831 for (afi = AFI_IP; afi < AFI_MAX; afi++)
1832 for (i = 0; i < ZEBRA_ROUTE_MAX; i++)
1833 client->redist[afi][i] = vrf_bitmap_init ();
1834 client->redist_default = vrf_bitmap_init ();
1835 client->ifinfo = vrf_bitmap_init ();
1836 client->ridinfo = vrf_bitmap_init ();
1837
1838 /* Add this client to linked list. */
1839 listnode_add (zebrad.client_list, client);
1840
1841 /* Make new read thread. */
1842 zebra_event (ZEBRA_READ, sock, client);
1843
1844 zebra_vrf_update_all (client);
1845 }
1846
1847 /* Handler of zebra service request. */
1848 static int
1849 zebra_client_read (struct thread *thread)
1850 {
1851 int sock;
1852 struct zserv *client;
1853 size_t already;
1854 uint16_t length, command;
1855 uint8_t marker, version;
1856 vrf_id_t vrf_id;
1857 struct zebra_vrf *zvrf;
1858
1859 /* Get thread data. Reset reading thread because I'm running. */
1860 sock = THREAD_FD (thread);
1861 client = THREAD_ARG (thread);
1862 client->t_read = NULL;
1863
1864 if (client->t_suicide)
1865 {
1866 zebra_client_close(client);
1867 return -1;
1868 }
1869
1870 /* Read length and command (if we don't have it already). */
1871 if ((already = stream_get_endp(client->ibuf)) < ZEBRA_HEADER_SIZE)
1872 {
1873 ssize_t nbyte;
1874 if (((nbyte = stream_read_try (client->ibuf, sock,
1875 ZEBRA_HEADER_SIZE-already)) == 0) ||
1876 (nbyte == -1))
1877 {
1878 if (IS_ZEBRA_DEBUG_EVENT)
1879 zlog_debug ("connection closed socket [%d]", sock);
1880 zebra_client_close (client);
1881 return -1;
1882 }
1883 if (nbyte != (ssize_t)(ZEBRA_HEADER_SIZE-already))
1884 {
1885 /* Try again later. */
1886 zebra_event (ZEBRA_READ, sock, client);
1887 return 0;
1888 }
1889 already = ZEBRA_HEADER_SIZE;
1890 }
1891
1892 /* Reset to read from the beginning of the incoming packet. */
1893 stream_set_getp(client->ibuf, 0);
1894
1895 /* Fetch header values */
1896 length = stream_getw (client->ibuf);
1897 marker = stream_getc (client->ibuf);
1898 version = stream_getc (client->ibuf);
1899 vrf_id = stream_getw (client->ibuf);
1900 command = stream_getw (client->ibuf);
1901
1902 if (marker != ZEBRA_HEADER_MARKER || version != ZSERV_VERSION)
1903 {
1904 zlog_err("%s: socket %d version mismatch, marker %d, version %d",
1905 __func__, sock, marker, version);
1906 zebra_client_close (client);
1907 return -1;
1908 }
1909 if (length < ZEBRA_HEADER_SIZE)
1910 {
1911 zlog_warn("%s: socket %d message length %u is less than header size %d",
1912 __func__, sock, length, ZEBRA_HEADER_SIZE);
1913 zebra_client_close (client);
1914 return -1;
1915 }
1916 if (length > STREAM_SIZE(client->ibuf))
1917 {
1918 zlog_warn("%s: socket %d message length %u exceeds buffer size %lu",
1919 __func__, sock, length, (u_long)STREAM_SIZE(client->ibuf));
1920 zebra_client_close (client);
1921 return -1;
1922 }
1923
1924 /* Read rest of data. */
1925 if (already < length)
1926 {
1927 ssize_t nbyte;
1928 if (((nbyte = stream_read_try (client->ibuf, sock,
1929 length-already)) == 0) ||
1930 (nbyte == -1))
1931 {
1932 if (IS_ZEBRA_DEBUG_EVENT)
1933 zlog_debug ("connection closed [%d] when reading zebra data", sock);
1934 zebra_client_close (client);
1935 return -1;
1936 }
1937 if (nbyte != (ssize_t)(length-already))
1938 {
1939 /* Try again later. */
1940 zebra_event (ZEBRA_READ, sock, client);
1941 return 0;
1942 }
1943 }
1944
1945 length -= ZEBRA_HEADER_SIZE;
1946
1947 /* Debug packet information. */
1948 if (IS_ZEBRA_DEBUG_EVENT)
1949 zlog_debug ("zebra message comes from socket [%d]", sock);
1950
1951 if (IS_ZEBRA_DEBUG_PACKET && IS_ZEBRA_DEBUG_RECV)
1952 zlog_debug ("zebra message received [%s] %d in VRF %u",
1953 zserv_command_string (command), length, vrf_id);
1954
1955 client->last_read_time = quagga_monotime();
1956 client->last_read_cmd = command;
1957
1958 zvrf = zebra_vrf_lookup_by_id (vrf_id);
1959 if (!zvrf)
1960 {
1961 if (IS_ZEBRA_DEBUG_PACKET && IS_ZEBRA_DEBUG_RECV)
1962 zlog_debug ("zebra received unknown VRF[%u]", vrf_id);
1963 goto zclient_read_out;
1964 }
1965
1966 switch (command)
1967 {
1968 case ZEBRA_ROUTER_ID_ADD:
1969 zread_router_id_add (client, length, zvrf);
1970 break;
1971 case ZEBRA_ROUTER_ID_DELETE:
1972 zread_router_id_delete (client, length, zvrf);
1973 break;
1974 case ZEBRA_INTERFACE_ADD:
1975 zread_interface_add (client, length, zvrf);
1976 break;
1977 case ZEBRA_INTERFACE_DELETE:
1978 zread_interface_delete (client, length, zvrf);
1979 break;
1980 case ZEBRA_IPV4_ROUTE_ADD:
1981 zread_ipv4_add (client, length, zvrf);
1982 break;
1983 case ZEBRA_IPV4_ROUTE_DELETE:
1984 zread_ipv4_delete (client, length, zvrf);
1985 break;
1986 case ZEBRA_IPV4_ROUTE_IPV6_NEXTHOP_ADD:
1987 zread_ipv4_route_ipv6_nexthop_add (client, length, zvrf);
1988 break;
1989 case ZEBRA_IPV4_NEXTHOP_ADD:
1990 zread_ipv4_add(client, length, zvrf); /* LB: r1.0 merge - id was 1 */
1991 break;
1992 case ZEBRA_IPV4_NEXTHOP_DELETE:
1993 zread_ipv4_delete(client, length, zvrf); /* LB: r1.0 merge - id was 1 */
1994 break;
1995 case ZEBRA_IPV6_ROUTE_ADD:
1996 zread_ipv6_add (client, length, zvrf);
1997 break;
1998 case ZEBRA_IPV6_ROUTE_DELETE:
1999 zread_ipv6_delete (client, length, zvrf);
2000 break;
2001 case ZEBRA_REDISTRIBUTE_ADD:
2002 zebra_redistribute_add (command, client, length, zvrf);
2003 break;
2004 case ZEBRA_REDISTRIBUTE_DELETE:
2005 zebra_redistribute_delete (command, client, length, zvrf);
2006 break;
2007 case ZEBRA_REDISTRIBUTE_DEFAULT_ADD:
2008 zebra_redistribute_default_add (command, client, length, zvrf);
2009 break;
2010 case ZEBRA_REDISTRIBUTE_DEFAULT_DELETE:
2011 zebra_redistribute_default_delete (command, client, length, zvrf);
2012 break;
2013 case ZEBRA_IPV4_NEXTHOP_LOOKUP_MRIB:
2014 zread_ipv4_nexthop_lookup_mrib (client, length, zvrf);
2015 break;
2016 case ZEBRA_HELLO:
2017 zread_hello (client);
2018 break;
2019 case ZEBRA_NEXTHOP_REGISTER:
2020 zserv_rnh_register(client, sock, length, RNH_NEXTHOP_TYPE, zvrf);
2021 break;
2022 case ZEBRA_NEXTHOP_UNREGISTER:
2023 zserv_rnh_unregister(client, sock, length, RNH_NEXTHOP_TYPE, zvrf);
2024 break;
2025 case ZEBRA_IMPORT_ROUTE_REGISTER:
2026 zserv_rnh_register(client, sock, length, RNH_IMPORT_CHECK_TYPE, zvrf);
2027 break;
2028 case ZEBRA_IMPORT_ROUTE_UNREGISTER:
2029 zserv_rnh_unregister(client, sock, length, RNH_IMPORT_CHECK_TYPE, zvrf);
2030 break;
2031 case ZEBRA_BFD_DEST_UPDATE:
2032 case ZEBRA_BFD_DEST_REGISTER:
2033 zebra_ptm_bfd_dst_register(client, sock, length, command, zvrf);
2034 break;
2035 case ZEBRA_BFD_DEST_DEREGISTER:
2036 zebra_ptm_bfd_dst_deregister(client, sock, length, zvrf);
2037 break;
2038 case ZEBRA_VRF_UNREGISTER:
2039 zread_vrf_unregister (client, length, zvrf);
2040 break;
2041 case ZEBRA_BFD_CLIENT_REGISTER:
2042 zebra_ptm_bfd_client_register(client, sock, length);
2043 break;
2044 case ZEBRA_INTERFACE_ENABLE_RADV:
2045 zebra_interface_radv_set (client, sock, length, zvrf, 1);
2046 break;
2047 case ZEBRA_INTERFACE_DISABLE_RADV:
2048 zebra_interface_radv_set (client, sock, length, zvrf, 0);
2049 break;
2050 case ZEBRA_MPLS_LABELS_ADD:
2051 case ZEBRA_MPLS_LABELS_DELETE:
2052 zread_mpls_labels (command, client, length, vrf_id);
2053 break;
2054 default:
2055 zlog_info ("Zebra received unknown command %d", command);
2056 break;
2057 }
2058
2059 if (client->t_suicide)
2060 {
2061 /* No need to wait for thread callback, just kill immediately. */
2062 zebra_client_close(client);
2063 return -1;
2064 }
2065
2066 zclient_read_out:
2067 stream_reset (client->ibuf);
2068 zebra_event (ZEBRA_READ, sock, client);
2069 return 0;
2070 }
2071
2072
2073 /* Accept code of zebra server socket. */
2074 static int
2075 zebra_accept (struct thread *thread)
2076 {
2077 int accept_sock;
2078 int client_sock;
2079 struct sockaddr_in client;
2080 socklen_t len;
2081
2082 accept_sock = THREAD_FD (thread);
2083
2084 /* Reregister myself. */
2085 zebra_event (ZEBRA_SERV, accept_sock, NULL);
2086
2087 len = sizeof (struct sockaddr_in);
2088 client_sock = accept (accept_sock, (struct sockaddr *) &client, &len);
2089
2090 if (client_sock < 0)
2091 {
2092 zlog_warn ("Can't accept zebra socket: %s", safe_strerror (errno));
2093 return -1;
2094 }
2095
2096 /* Make client socket non-blocking. */
2097 set_nonblocking(client_sock);
2098
2099 /* Create new zebra client. */
2100 zebra_client_create (client_sock);
2101
2102 return 0;
2103 }
2104
2105 #ifdef HAVE_TCP_ZEBRA
2106 /* Make zebra's server socket. */
2107 static void
2108 zebra_serv ()
2109 {
2110 int ret;
2111 int accept_sock;
2112 struct sockaddr_in addr;
2113
2114 accept_sock = socket (AF_INET, SOCK_STREAM, 0);
2115
2116 if (accept_sock < 0)
2117 {
2118 zlog_warn ("Can't create zserv stream socket: %s",
2119 safe_strerror (errno));
2120 zlog_warn ("zebra can't provice full functionality due to above error");
2121 return;
2122 }
2123
2124 memset (&addr, 0, sizeof (struct sockaddr_in));
2125 addr.sin_family = AF_INET;
2126 addr.sin_port = htons (ZEBRA_PORT);
2127 #ifdef HAVE_STRUCT_SOCKADDR_IN_SIN_LEN
2128 addr.sin_len = sizeof (struct sockaddr_in);
2129 #endif /* HAVE_STRUCT_SOCKADDR_IN_SIN_LEN */
2130 addr.sin_addr.s_addr = htonl (INADDR_LOOPBACK);
2131
2132 sockopt_reuseaddr (accept_sock);
2133 sockopt_reuseport (accept_sock);
2134
2135 if ( zserv_privs.change(ZPRIVS_RAISE) )
2136 zlog (NULL, LOG_ERR, "Can't raise privileges");
2137
2138 ret = bind (accept_sock, (struct sockaddr *)&addr,
2139 sizeof (struct sockaddr_in));
2140 if (ret < 0)
2141 {
2142 zlog_warn ("Can't bind to stream socket: %s",
2143 safe_strerror (errno));
2144 zlog_warn ("zebra can't provice full functionality due to above error");
2145 close (accept_sock); /* Avoid sd leak. */
2146 return;
2147 }
2148
2149 if ( zserv_privs.change(ZPRIVS_LOWER) )
2150 zlog (NULL, LOG_ERR, "Can't lower privileges");
2151
2152 ret = listen (accept_sock, 1);
2153 if (ret < 0)
2154 {
2155 zlog_warn ("Can't listen to stream socket: %s",
2156 safe_strerror (errno));
2157 zlog_warn ("zebra can't provice full functionality due to above error");
2158 close (accept_sock); /* Avoid sd leak. */
2159 return;
2160 }
2161
2162 zebra_event (ZEBRA_SERV, accept_sock, NULL);
2163 }
2164 #else /* HAVE_TCP_ZEBRA */
2165
2166 /* For sockaddr_un. */
2167 #include <sys/un.h>
2168
2169 /* zebra server UNIX domain socket. */
2170 static void
2171 zebra_serv_un (const char *path)
2172 {
2173 int ret;
2174 int sock, len;
2175 struct sockaddr_un serv;
2176 mode_t old_mask;
2177
2178 /* First of all, unlink existing socket */
2179 unlink (path);
2180
2181 /* Set umask */
2182 old_mask = umask (0077);
2183
2184 /* Make UNIX domain socket. */
2185 sock = socket (AF_UNIX, SOCK_STREAM, 0);
2186 if (sock < 0)
2187 {
2188 zlog_warn ("Can't create zserv unix socket: %s",
2189 safe_strerror (errno));
2190 zlog_warn ("zebra can't provide full functionality due to above error");
2191 return;
2192 }
2193
2194 /* Make server socket. */
2195 memset (&serv, 0, sizeof (struct sockaddr_un));
2196 serv.sun_family = AF_UNIX;
2197 strncpy (serv.sun_path, path, strlen (path));
2198 #ifdef HAVE_STRUCT_SOCKADDR_UN_SUN_LEN
2199 len = serv.sun_len = SUN_LEN(&serv);
2200 #else
2201 len = sizeof (serv.sun_family) + strlen (serv.sun_path);
2202 #endif /* HAVE_STRUCT_SOCKADDR_UN_SUN_LEN */
2203
2204 ret = bind (sock, (struct sockaddr *) &serv, len);
2205 if (ret < 0)
2206 {
2207 zlog_warn ("Can't bind to unix socket %s: %s",
2208 path, safe_strerror (errno));
2209 zlog_warn ("zebra can't provide full functionality due to above error");
2210 close (sock);
2211 return;
2212 }
2213
2214 ret = listen (sock, 5);
2215 if (ret < 0)
2216 {
2217 zlog_warn ("Can't listen to unix socket %s: %s",
2218 path, safe_strerror (errno));
2219 zlog_warn ("zebra can't provide full functionality due to above error");
2220 close (sock);
2221 return;
2222 }
2223
2224 umask (old_mask);
2225
2226 zebra_event (ZEBRA_SERV, sock, NULL);
2227 }
2228 #endif /* HAVE_TCP_ZEBRA */
2229
2230
2231 static void
2232 zebra_event (enum event event, int sock, struct zserv *client)
2233 {
2234 switch (event)
2235 {
2236 case ZEBRA_SERV:
2237 thread_add_read (zebrad.master, zebra_accept, client, sock);
2238 break;
2239 case ZEBRA_READ:
2240 client->t_read =
2241 thread_add_read (zebrad.master, zebra_client_read, client, sock);
2242 break;
2243 case ZEBRA_WRITE:
2244 /**/
2245 break;
2246 }
2247 }
2248
2249 #define ZEBRA_TIME_BUF 32
2250 static char *
2251 zserv_time_buf(time_t *time1, char *buf, int buflen)
2252 {
2253 struct tm *tm;
2254 time_t now;
2255
2256 assert (buf != NULL);
2257 assert (buflen >= ZEBRA_TIME_BUF);
2258 assert (time1 != NULL);
2259
2260 if (!*time1)
2261 {
2262 snprintf(buf, buflen, "never ");
2263 return (buf);
2264 }
2265
2266 now = quagga_monotime();
2267 now -= *time1;
2268 tm = gmtime(&now);
2269
2270 /* Making formatted timer strings. */
2271 #define ONE_DAY_SECOND 60*60*24
2272 #define ONE_WEEK_SECOND 60*60*24*7
2273
2274 if (now < ONE_DAY_SECOND)
2275 snprintf (buf, buflen, "%02d:%02d:%02d",
2276 tm->tm_hour, tm->tm_min, tm->tm_sec);
2277 else if (now < ONE_WEEK_SECOND)
2278 snprintf (buf, buflen, "%dd%02dh%02dm",
2279 tm->tm_yday, tm->tm_hour, tm->tm_min);
2280 else
2281 snprintf (buf, buflen, "%02dw%dd%02dh",
2282 tm->tm_yday/7, tm->tm_yday - ((tm->tm_yday/7) * 7), tm->tm_hour);
2283 return buf;
2284 }
2285
2286 static void
2287 zebra_show_client_detail (struct vty *vty, struct zserv *client)
2288 {
2289 char cbuf[ZEBRA_TIME_BUF], rbuf[ZEBRA_TIME_BUF];
2290 char wbuf[ZEBRA_TIME_BUF], nhbuf[ZEBRA_TIME_BUF], mbuf[ZEBRA_TIME_BUF];
2291
2292 vty_out (vty, "Client: %s", zebra_route_string(client->proto));
2293 if (client->instance)
2294 vty_out (vty, " Instance: %d", client->instance);
2295 vty_out (vty, "%s", VTY_NEWLINE);
2296
2297 vty_out (vty, "------------------------ %s", VTY_NEWLINE);
2298 vty_out (vty, "FD: %d %s", client->sock, VTY_NEWLINE);
2299 vty_out (vty, "Route Table ID: %d %s", client->rtm_table, VTY_NEWLINE);
2300
2301 vty_out (vty, "Connect Time: %s %s",
2302 zserv_time_buf(&client->connect_time, cbuf, ZEBRA_TIME_BUF),
2303 VTY_NEWLINE);
2304 if (client->nh_reg_time)
2305 {
2306 vty_out (vty, "Nexthop Registry Time: %s %s",
2307 zserv_time_buf(&client->nh_reg_time, nhbuf, ZEBRA_TIME_BUF),
2308 VTY_NEWLINE);
2309 if (client->nh_last_upd_time)
2310 vty_out (vty, "Nexthop Last Update Time: %s %s",
2311 zserv_time_buf(&client->nh_last_upd_time, mbuf, ZEBRA_TIME_BUF),
2312 VTY_NEWLINE);
2313 else
2314 vty_out (vty, "No Nexthop Update sent%s", VTY_NEWLINE);
2315 }
2316 else
2317 vty_out (vty, "Not registered for Nexthop Updates%s", VTY_NEWLINE);
2318
2319 vty_out (vty, "Last Msg Rx Time: %s %s",
2320 zserv_time_buf(&client->last_read_time, rbuf, ZEBRA_TIME_BUF),
2321 VTY_NEWLINE);
2322 vty_out (vty, "Last Msg Tx Time: %s %s",
2323 zserv_time_buf(&client->last_write_time, wbuf, ZEBRA_TIME_BUF),
2324 VTY_NEWLINE);
2325 if (client->last_read_time)
2326 vty_out (vty, "Last Rcvd Cmd: %s %s",
2327 zserv_command_string(client->last_read_cmd), VTY_NEWLINE);
2328 if (client->last_write_time)
2329 vty_out (vty, "Last Sent Cmd: %s %s",
2330 zserv_command_string(client->last_write_cmd), VTY_NEWLINE);
2331 vty_out (vty, "%s", VTY_NEWLINE);
2332
2333 vty_out (vty, "Type Add Update Del %s", VTY_NEWLINE);
2334 vty_out (vty, "================================================== %s", VTY_NEWLINE);
2335 vty_out (vty, "IPv4 %-12d%-12d%-12d%s", client->v4_route_add_cnt,
2336 client->v4_route_upd8_cnt, client->v4_route_del_cnt, VTY_NEWLINE);
2337 vty_out (vty, "IPv6 %-12d%-12d%-12d%s", client->v6_route_add_cnt,
2338 client->v6_route_upd8_cnt, client->v6_route_del_cnt, VTY_NEWLINE);
2339 vty_out (vty, "Redist:v4 %-12d%-12d%-12d%s", client->redist_v4_add_cnt, 0,
2340 client->redist_v4_del_cnt, VTY_NEWLINE);
2341 vty_out (vty, "Redist:v6 %-12d%-12d%-12d%s", client->redist_v6_add_cnt, 0,
2342 client->redist_v6_del_cnt, VTY_NEWLINE);
2343 vty_out (vty, "Connected %-12d%-12d%-12d%s", client->ifadd_cnt, 0,
2344 client->ifdel_cnt, VTY_NEWLINE);
2345 vty_out (vty, "BFD peer %-12d%-12d%-12d%s", client->bfd_peer_add_cnt,
2346 client->bfd_peer_upd8_cnt, client->bfd_peer_del_cnt, VTY_NEWLINE);
2347 vty_out (vty, "Interface Up Notifications: %d%s", client->ifup_cnt,
2348 VTY_NEWLINE);
2349 vty_out (vty, "Interface Down Notifications: %d%s", client->ifdown_cnt,
2350 VTY_NEWLINE);
2351
2352 vty_out (vty, "%s", VTY_NEWLINE);
2353 return;
2354 }
2355
2356 static void
2357 zebra_show_client_brief (struct vty *vty, struct zserv *client)
2358 {
2359 char cbuf[ZEBRA_TIME_BUF], rbuf[ZEBRA_TIME_BUF];
2360 char wbuf[ZEBRA_TIME_BUF];
2361
2362 vty_out (vty, "%-8s%12s %12s%12s%8d/%-8d%8d/%-8d%s",
2363 zebra_route_string(client->proto),
2364 zserv_time_buf(&client->connect_time, cbuf, ZEBRA_TIME_BUF),
2365 zserv_time_buf(&client->last_read_time, rbuf, ZEBRA_TIME_BUF),
2366 zserv_time_buf(&client->last_write_time, wbuf, ZEBRA_TIME_BUF),
2367 client->v4_route_add_cnt+client->v4_route_upd8_cnt,
2368 client->v4_route_del_cnt,
2369 client->v6_route_add_cnt+client->v6_route_upd8_cnt,
2370 client->v6_route_del_cnt, VTY_NEWLINE);
2371
2372 }
2373
2374
2375 /* Display default rtm_table for all clients. */
2376 DEFUN (show_table,
2377 show_table_cmd,
2378 "show table",
2379 SHOW_STR
2380 "default routing table to use for all clients\n")
2381 {
2382 vty_out (vty, "table %d%s", zebrad.rtm_table_default,
2383 VTY_NEWLINE);
2384 return CMD_SUCCESS;
2385 }
2386
2387 DEFUN (config_table,
2388 config_table_cmd,
2389 "table TABLENO",
2390 "Configure target kernel routing table\n"
2391 "TABLE integer\n")
2392 {
2393 zebrad.rtm_table_default = strtol (argv[1]->arg, (char**)0, 10);
2394 return CMD_SUCCESS;
2395 }
2396
2397 DEFUN (no_config_table,
2398 no_config_table_cmd,
2399 "no table [TABLENO]",
2400 NO_STR
2401 "Configure target kernel routing table\n"
2402 "TABLE integer\n")
2403 {
2404 zebrad.rtm_table_default = 0;
2405 return CMD_SUCCESS;
2406 }
2407
2408 DEFUN (ip_forwarding,
2409 ip_forwarding_cmd,
2410 "ip forwarding",
2411 IP_STR
2412 "Turn on IP forwarding")
2413 {
2414 int ret;
2415
2416 ret = ipforward ();
2417 if (ret == 0)
2418 ret = ipforward_on ();
2419
2420 if (ret == 0)
2421 {
2422 vty_out (vty, "Can't turn on IP forwarding%s", VTY_NEWLINE);
2423 return CMD_WARNING;
2424 }
2425
2426 return CMD_SUCCESS;
2427 }
2428
2429 DEFUN (no_ip_forwarding,
2430 no_ip_forwarding_cmd,
2431 "no ip forwarding",
2432 NO_STR
2433 IP_STR
2434 "Turn off IP forwarding")
2435 {
2436 int ret;
2437
2438 ret = ipforward ();
2439 if (ret != 0)
2440 ret = ipforward_off ();
2441
2442 if (ret != 0)
2443 {
2444 vty_out (vty, "Can't turn off IP forwarding%s", VTY_NEWLINE);
2445 return CMD_WARNING;
2446 }
2447
2448 return CMD_SUCCESS;
2449 }
2450
2451 /* This command is for debugging purpose. */
2452 DEFUN (show_zebra_client,
2453 show_zebra_client_cmd,
2454 "show zebra client",
2455 SHOW_STR
2456 "Zebra information\n"
2457 "Client information")
2458 {
2459 struct listnode *node;
2460 struct zserv *client;
2461
2462 for (ALL_LIST_ELEMENTS_RO (zebrad.client_list, node, client))
2463 zebra_show_client_detail(vty, client);
2464
2465 return CMD_SUCCESS;
2466 }
2467
2468 /* This command is for debugging purpose. */
2469 DEFUN (show_zebra_client_summary,
2470 show_zebra_client_summary_cmd,
2471 "show zebra client summary",
2472 SHOW_STR
2473 "Zebra information brief"
2474 "Client information brief")
2475 {
2476 struct listnode *node;
2477 struct zserv *client;
2478
2479 vty_out (vty, "Name Connect Time Last Read Last Write IPv4 Routes IPv6 Routes %s",
2480 VTY_NEWLINE);
2481 vty_out (vty,"--------------------------------------------------------------------------------%s",
2482 VTY_NEWLINE);
2483
2484 for (ALL_LIST_ELEMENTS_RO (zebrad.client_list, node, client))
2485 zebra_show_client_brief(vty, client);
2486
2487 vty_out (vty, "Routes column shows (added+updated)/deleted%s", VTY_NEWLINE);
2488 return CMD_SUCCESS;
2489 }
2490
2491 /* Table configuration write function. */
2492 static int
2493 config_write_table (struct vty *vty)
2494 {
2495 if (zebrad.rtm_table_default)
2496 vty_out (vty, "table %d%s", zebrad.rtm_table_default,
2497 VTY_NEWLINE);
2498 return 0;
2499 }
2500
2501 /* table node for routing tables. */
2502 static struct cmd_node table_node =
2503 {
2504 TABLE_NODE,
2505 "", /* This node has no interface. */
2506 1
2507 };
2508
2509 /* Only display ip forwarding is enabled or not. */
2510 DEFUN (show_ip_forwarding,
2511 show_ip_forwarding_cmd,
2512 "show ip forwarding",
2513 SHOW_STR
2514 IP_STR
2515 "IP forwarding status\n")
2516 {
2517 int ret;
2518
2519 ret = ipforward ();
2520
2521 if (ret == 0)
2522 vty_out (vty, "IP forwarding is off%s", VTY_NEWLINE);
2523 else
2524 vty_out (vty, "IP forwarding is on%s", VTY_NEWLINE);
2525 return CMD_SUCCESS;
2526 }
2527
2528 #ifdef HAVE_IPV6
2529 /* Only display ipv6 forwarding is enabled or not. */
2530 DEFUN (show_ipv6_forwarding,
2531 show_ipv6_forwarding_cmd,
2532 "show ipv6 forwarding",
2533 SHOW_STR
2534 "IPv6 information\n"
2535 "Forwarding status\n")
2536 {
2537 int ret;
2538
2539 ret = ipforward_ipv6 ();
2540
2541 switch (ret)
2542 {
2543 case -1:
2544 vty_out (vty, "ipv6 forwarding is unknown%s", VTY_NEWLINE);
2545 break;
2546 case 0:
2547 vty_out (vty, "ipv6 forwarding is %s%s", "off", VTY_NEWLINE);
2548 break;
2549 case 1:
2550 vty_out (vty, "ipv6 forwarding is %s%s", "on", VTY_NEWLINE);
2551 break;
2552 default:
2553 vty_out (vty, "ipv6 forwarding is %s%s", "off", VTY_NEWLINE);
2554 break;
2555 }
2556 return CMD_SUCCESS;
2557 }
2558
2559 DEFUN (ipv6_forwarding,
2560 ipv6_forwarding_cmd,
2561 "ipv6 forwarding",
2562 IPV6_STR
2563 "Turn on IPv6 forwarding")
2564 {
2565 int ret;
2566
2567 ret = ipforward_ipv6 ();
2568 if (ret == 0)
2569 ret = ipforward_ipv6_on ();
2570
2571 if (ret == 0)
2572 {
2573 vty_out (vty, "Can't turn on IPv6 forwarding%s", VTY_NEWLINE);
2574 return CMD_WARNING;
2575 }
2576
2577 return CMD_SUCCESS;
2578 }
2579
2580 DEFUN (no_ipv6_forwarding,
2581 no_ipv6_forwarding_cmd,
2582 "no ipv6 forwarding",
2583 NO_STR
2584 IPV6_STR
2585 "Turn off IPv6 forwarding")
2586 {
2587 int ret;
2588
2589 ret = ipforward_ipv6 ();
2590 if (ret != 0)
2591 ret = ipforward_ipv6_off ();
2592
2593 if (ret != 0)
2594 {
2595 vty_out (vty, "Can't turn off IPv6 forwarding%s", VTY_NEWLINE);
2596 return CMD_WARNING;
2597 }
2598
2599 return CMD_SUCCESS;
2600 }
2601
2602 #endif /* HAVE_IPV6 */
2603
2604 /* IPForwarding configuration write function. */
2605 static int
2606 config_write_forwarding (struct vty *vty)
2607 {
2608 /* FIXME: Find better place for that. */
2609 router_id_write (vty);
2610
2611 if (!ipforward ())
2612 vty_out (vty, "no ip forwarding%s", VTY_NEWLINE);
2613 #ifdef HAVE_IPV6
2614 if (!ipforward_ipv6 ())
2615 vty_out (vty, "no ipv6 forwarding%s", VTY_NEWLINE);
2616 #endif /* HAVE_IPV6 */
2617 vty_out (vty, "!%s", VTY_NEWLINE);
2618 return 0;
2619 }
2620
2621 /* table node for routing tables. */
2622 static struct cmd_node forwarding_node =
2623 {
2624 FORWARDING_NODE,
2625 "", /* This node has no interface. */
2626 1
2627 };
2628
2629 #ifdef HAVE_FPM
2630 /* function to write the fpm config info */
2631 static int
2632 config_write_fpm (struct vty *vty)
2633 {
2634 return
2635 fpm_remote_srv_write (vty);
2636 }
2637
2638 /* Zebra node */
2639 static struct cmd_node zebra_node =
2640 {
2641 ZEBRA_NODE,
2642 "",
2643 1
2644 };
2645 #endif
2646
2647
2648 /* Initialisation of zebra and installation of commands. */
2649 void
2650 zebra_init (void)
2651 {
2652 /* Client list init. */
2653 zebrad.client_list = list_new ();
2654
2655 /* Install configuration write function. */
2656 install_node (&table_node, config_write_table);
2657 install_node (&forwarding_node, config_write_forwarding);
2658 #ifdef HAVE_FPM
2659 install_node (&zebra_node, config_write_fpm);
2660 #endif
2661
2662 install_element (VIEW_NODE, &show_ip_forwarding_cmd);
2663 install_element (CONFIG_NODE, &ip_forwarding_cmd);
2664 install_element (CONFIG_NODE, &no_ip_forwarding_cmd);
2665 install_element (ENABLE_NODE, &show_zebra_client_cmd);
2666 install_element (ENABLE_NODE, &show_zebra_client_summary_cmd);
2667
2668 #ifdef HAVE_NETLINK
2669 install_element (VIEW_NODE, &show_table_cmd);
2670 install_element (CONFIG_NODE, &config_table_cmd);
2671 install_element (CONFIG_NODE, &no_config_table_cmd);
2672 #endif /* HAVE_NETLINK */
2673
2674 #ifdef HAVE_IPV6
2675 install_element (VIEW_NODE, &show_ipv6_forwarding_cmd);
2676 install_element (CONFIG_NODE, &ipv6_forwarding_cmd);
2677 install_element (CONFIG_NODE, &no_ipv6_forwarding_cmd);
2678 #endif /* HAVE_IPV6 */
2679
2680 /* Route-map */
2681 zebra_route_map_init ();
2682 }
2683
2684 /* Make zebra server socket, wiping any existing one (see bug #403). */
2685 void
2686 zebra_zserv_socket_init (char *path)
2687 {
2688 #ifdef HAVE_TCP_ZEBRA
2689 zebra_serv ();
2690 #else
2691 zebra_serv_un (path ? path : ZEBRA_SERV_PATH);
2692 #endif /* HAVE_TCP_ZEBRA */
2693 }