]> git.proxmox.com Git - mirror_frr.git/blame - ripngd/ripng_zebra.c
Merge pull request #3502 from donaldsharp/socket_to_me_baby
[mirror_frr.git] / ripngd / ripng_zebra.c
CommitLineData
718e3744 1/*
2 * RIPngd and zebra interface.
3 * Copyright (C) 1998, 1999 Kunihiro Ishiguro
4 *
5 * This file is part of GNU Zebra.
6 *
7 * GNU Zebra is free software; you can redistribute it and/or modify it
8 * under the terms of the GNU General Public License as published by the
9 * Free Software Foundation; either version 2, or (at your option) any
10 * later version.
11 *
12 * GNU Zebra is distributed in the hope that it will be useful, but
13 * WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15 * General Public License for more details.
16 *
896014f4
DL
17 * You should have received a copy of the GNU General Public License along
18 * with this program; see the file COPYING; if not, write to the Free Software
19 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
718e3744 20 */
21
22#include <zebra.h>
23
24#include "command.h"
25#include "prefix.h"
fe08ba7e 26#include "agg_table.h"
718e3744 27#include "stream.h"
c880b636 28#include "memory.h"
718e3744 29#include "routemap.h"
30#include "zclient.h"
31#include "log.h"
32
33#include "ripngd/ripngd.h"
c880b636 34#include "ripngd/ripng_debug.h"
718e3744 35
36/* All information about zebra. */
37struct zclient *zclient = NULL;
38
c880b636 39/* Send ECMP routes to zebra. */
fe08ba7e 40static void ripng_zebra_ipv6_send(struct agg_node *rp, uint8_t cmd)
718e3744 41{
d62a17ae 42 struct list *list = (struct list *)rp->info;
c9fb3e23
RW
43 struct zapi_route api;
44 struct zapi_nexthop *api_nh;
d62a17ae 45 struct listnode *listnode = NULL;
46 struct ripng_info *rinfo = NULL;
47 int count = 0;
48
c9fb3e23 49 memset(&api, 0, sizeof(api));
d00061ea
RW
50 api.vrf_id = VRF_DEFAULT;
51 api.type = ZEBRA_ROUTE_RIPNG;
d00061ea 52 api.safi = SAFI_UNICAST;
c9fb3e23 53 api.prefix = rp->p;
d62a17ae 54
d00061ea 55 SET_FLAG(api.message, ZAPI_MESSAGE_NEXTHOP);
d00061ea 56 for (ALL_LIST_ELEMENTS_RO(list, listnode, rinfo)) {
a74e593b
RW
57 if (count >= MULTIPATH_NUM)
58 break;
c9fb3e23 59 api_nh = &api.nexthops[count];
4a7371e9 60 api_nh->vrf_id = VRF_DEFAULT;
c9fb3e23
RW
61 api_nh->gate.ipv6 = rinfo->nexthop;
62 api_nh->ifindex = rinfo->ifindex;
63 api_nh->type = NEXTHOP_TYPE_IPV6_IFINDEX;
d00061ea 64 count++;
c9fb3e23 65 if (cmd == ZEBRA_ROUTE_ADD)
d00061ea
RW
66 SET_FLAG(rinfo->flags, RIPNG_RTF_FIB);
67 else
68 UNSET_FLAG(rinfo->flags, RIPNG_RTF_FIB);
69 }
d62a17ae 70
d00061ea 71 api.nexthop_num = count;
d62a17ae 72
d00061ea 73 rinfo = listgetdata(listhead(list));
d62a17ae 74
d00061ea
RW
75 SET_FLAG(api.message, ZAPI_MESSAGE_METRIC);
76 api.metric = rinfo->metric;
d62a17ae 77
d00061ea
RW
78 if (rinfo->tag) {
79 SET_FLAG(api.message, ZAPI_MESSAGE_TAG);
80 api.tag = rinfo->tag;
81 }
d62a17ae 82
c9fb3e23 83 zclient_route_send(cmd, zclient, &api);
d00061ea
RW
84
85 if (IS_RIPNG_DEBUG_ZEBRA) {
86 if (ripng->ecmp)
87 zlog_debug("%s: %s/%d nexthops %d",
c9fb3e23 88 (cmd == ZEBRA_ROUTE_ADD)
d00061ea
RW
89 ? "Install into zebra"
90 : "Delete from zebra",
91 inet6_ntoa(rp->p.u.prefix6), rp->p.prefixlen,
92 count);
93 else
c9fb3e23
RW
94 zlog_debug(
95 "%s: %s/%d",
96 (cmd == ZEBRA_ROUTE_ADD) ? "Install into zebra"
97 : "Delete from zebra",
98 inet6_ntoa(rp->p.u.prefix6), rp->p.prefixlen);
d62a17ae 99 }
718e3744 100}
101
c880b636 102/* Add/update ECMP routes to zebra. */
fe08ba7e 103void ripng_zebra_ipv6_add(struct agg_node *rp)
718e3744 104{
c9fb3e23 105 ripng_zebra_ipv6_send(rp, ZEBRA_ROUTE_ADD);
c880b636 106}
718e3744 107
c880b636 108/* Delete ECMP routes from zebra. */
fe08ba7e 109void ripng_zebra_ipv6_delete(struct agg_node *rp)
c880b636 110{
c9fb3e23 111 ripng_zebra_ipv6_send(rp, ZEBRA_ROUTE_DELETE);
718e3744 112}
113
114/* Zebra route add and delete treatment. */
74489921
RW
115static int ripng_zebra_read_route(int command, struct zclient *zclient,
116 zebra_size_t length, vrf_id_t vrf_id)
718e3744 117{
74489921 118 struct zapi_route api;
d62a17ae 119 struct in6_addr nexthop;
74489921 120 unsigned long ifindex;
d62a17ae 121
74489921
RW
122 if (zapi_route_decode(zclient->ibuf, &api) < 0)
123 return -1;
d62a17ae 124
74489921
RW
125 /* we completely ignore srcdest routes for now. */
126 if (CHECK_FLAG(api.message, ZAPI_MESSAGE_SRCPFX))
127 return 0;
d62a17ae 128
74489921
RW
129 nexthop = api.nexthops[0].gate.ipv6;
130 ifindex = api.nexthops[0].ifindex;
d62a17ae 131
74489921
RW
132 if (command == ZEBRA_REDISTRIBUTE_ROUTE_ADD)
133 ripng_redistribute_add(api.type, RIPNG_ROUTE_REDISTRIBUTE,
134 (struct prefix_ipv6 *)&api.prefix,
d62a17ae 135 ifindex, &nexthop, api.tag);
136 else
137 ripng_redistribute_delete(api.type, RIPNG_ROUTE_REDISTRIBUTE,
74489921
RW
138 (struct prefix_ipv6 *)&api.prefix,
139 ifindex);
d62a17ae 140
141 return 0;
718e3744 142}
143
db2038c7 144void ripng_redistribute_conf_update(int type)
718e3744 145{
db2038c7
RW
146 zclient_redistribute(ZEBRA_REDISTRIBUTE_ADD, zclient, AFI_IP6, type, 0,
147 VRF_DEFAULT);
148}
7076bb2f 149
db2038c7
RW
150void ripng_redistribute_conf_delete(int type)
151{
d62a17ae 152 if (zclient->sock > 0)
153 zebra_redistribute_send(ZEBRA_REDISTRIBUTE_DELETE, zclient,
154 AFI_IP6, type, 0, VRF_DEFAULT);
718e3744 155
d62a17ae 156 ripng_redistribute_withdraw(type);
718e3744 157}
158
d62a17ae 159int ripng_redistribute_check(int type)
a94434b6 160{
d62a17ae 161 return vrf_bitmap_check(zclient->redist[AFI_IP6][type], VRF_DEFAULT);
a94434b6 162}
163
d62a17ae 164void ripng_redistribute_clean()
a94434b6 165{
db2038c7
RW
166 for (int i = 0; i < ZEBRA_ROUTE_MAX; i++) {
167 if (!vrf_bitmap_check(zclient->redist[AFI_IP6][i], VRF_DEFAULT))
168 continue;
d62a17ae 169
db2038c7
RW
170 if (zclient->sock > 0)
171 zebra_redistribute_send(ZEBRA_REDISTRIBUTE_DELETE,
172 zclient, AFI_IP6, i, 0,
173 VRF_DEFAULT);
d62a17ae 174
db2038c7 175 vrf_bitmap_unset(zclient->redist[AFI_IP6][i], VRF_DEFAULT);
718e3744 176
db2038c7
RW
177 /* Remove the routes from RIP table. */
178 ripng_redistribute_withdraw(i);
d62a17ae 179 }
718e3744 180}
181
db2038c7 182void ripng_redistribute_write(struct vty *vty)
718e3744 183{
d62a17ae 184 int i;
185
d00061ea
RW
186 for (i = 0; i < ZEBRA_ROUTE_MAX; i++) {
187 if (i == zclient->redist_default
188 || !vrf_bitmap_check(zclient->redist[AFI_IP6][i],
189 VRF_DEFAULT))
190 continue;
191
db2038c7 192 vty_out(vty, " %s", zebra_route_string(i));
d00061ea 193 }
718e3744 194}
195
d62a17ae 196static void ripng_zebra_connected(struct zclient *zclient)
7076bb2f 197{
d62a17ae 198 zclient_send_reg_requests(zclient, VRF_DEFAULT);
7076bb2f
FL
199}
200
718e3744 201/* Initialize zebra structure and it's commands. */
d62a17ae 202void zebra_init(struct thread_master *master)
718e3744 203{
d62a17ae 204 /* Allocate zebra structure. */
26f63a1e 205 zclient = zclient_new(master, &zclient_options_default);
342213ea 206 zclient_init(zclient, ZEBRA_ROUTE_RIPNG, 0, &ripngd_privs);
d62a17ae 207
208 zclient->zebra_connected = ripng_zebra_connected;
209 zclient->interface_up = ripng_interface_up;
210 zclient->interface_down = ripng_interface_down;
211 zclient->interface_add = ripng_interface_add;
212 zclient->interface_delete = ripng_interface_delete;
213 zclient->interface_address_add = ripng_interface_address_add;
214 zclient->interface_address_delete = ripng_interface_address_delete;
74489921
RW
215 zclient->redistribute_route_add = ripng_zebra_read_route;
216 zclient->redistribute_route_del = ripng_zebra_read_route;
718e3744 217}
7feb9237 218
d62a17ae 219void ripng_zebra_stop(void)
7feb9237 220{
d62a17ae 221 zclient_stop(zclient);
222 zclient_free(zclient);
7feb9237 223}