]> git.proxmox.com Git - mirror_frr.git/blame - zebra/redistribute.c
Merge pull request #12798 from donaldsharp/rib_match_multicast
[mirror_frr.git] / zebra / redistribute.c
CommitLineData
acddc0ed 1// SPDX-License-Identifier: GPL-2.0-or-later
718e3744 2/* Redistribution Handler
3 * Copyright (C) 1998 Kunihiro Ishiguro
718e3744 4 */
5
6#include <zebra.h>
7
8#include "vector.h"
9#include "vty.h"
10#include "command.h"
11#include "prefix.h"
12#include "table.h"
13#include "stream.h"
14#include "zclient.h"
15#include "linklist.h"
16#include "log.h"
b72ede27 17#include "vrf.h"
05737783 18#include "srcdest_table.h"
718e3744 19
20#include "zebra/rib.h"
161e9ab7 21#include "zebra/zebra_router.h"
7c551956
DS
22#include "zebra/zebra_ns.h"
23#include "zebra/zebra_vrf.h"
8902474b 24#include "zebra/zebra_routemap.h"
718e3744 25#include "zebra/redistribute.h"
26#include "zebra/debug.h"
18a6dce6 27#include "zebra/router-id.h"
bf094f69 28#include "zebra/zapi_msg.h"
1a98c087 29#include "zebra/zebra_vxlan.h"
364fed6b 30#include "zebra/zebra_errors.h"
718e3744 31
244c1cdc
DS
32#define ZEBRA_PTM_SUPPORT
33
7a4bb9c5
DS
34/* array holding redistribute info about table redistribution */
35/* bit AFI is set if that AFI is redistributing routes from this table */
032bfaaf 36static int zebra_import_table_used[AFI_MAX][ZEBRA_KERNEL_TABLE_MAX];
d7c0a89a 37static uint32_t zebra_import_table_distance[AFI_MAX][ZEBRA_KERNEL_TABLE_MAX];
7a4bb9c5 38
fe257ae7 39int is_zebra_import_table_enabled(afi_t afi, vrf_id_t vrf_id, uint32_t table_id)
7a4bb9c5 40{
1e9f448f
DS
41 /*
42 * Make sure that what we are called with actualy makes sense
43 */
44 if (afi == AFI_MAX)
45 return 0;
46
95a29032
DS
47 if (is_zebra_valid_kernel_table(table_id) &&
48 table_id < ZEBRA_KERNEL_TABLE_MAX)
d62a17ae 49 return zebra_import_table_used[afi][table_id];
50 return 0;
7a4bb9c5
DS
51}
52
d62a17ae 53static void zebra_redistribute_default(struct zserv *client, vrf_id_t vrf_id)
718e3744 54{
d62a17ae 55 int afi;
56 struct prefix p;
57 struct route_table *table;
58 struct route_node *rn;
59 struct route_entry *newre;
60
61 for (afi = AFI_IP; afi <= AFI_IP6; afi++) {
29a35332
DS
62
63 if (!vrf_bitmap_check(client->redist_default[afi], vrf_id))
64 continue;
65
d62a17ae 66 /* Lookup table. */
67 table = zebra_vrf_table(afi, SAFI_UNICAST, vrf_id);
68 if (!table)
69 continue;
70
71 /* Lookup default route. */
72 memset(&p, 0, sizeof(p));
73 p.family = afi2family(afi);
74 rn = route_node_lookup(table, &p);
75 if (!rn)
76 continue;
77
a2addae8 78 RNODE_FOREACH_RE (rn, newre) {
c3d0d6e8 79 if (CHECK_FLAG(newre->flags, ZEBRA_FLAG_SELECTED))
407c87a6 80 zsend_redistribute_route(
a2addae8 81 ZEBRA_REDISTRIBUTE_ROUTE_ADD, client,
84faa420 82 rn, newre);
407c87a6 83 }
d62a17ae 84
85 route_unlock_node(rn);
86 }
718e3744 87}
88
89/* Redistribute routes. */
d7c0a89a
QY
90static void zebra_redistribute(struct zserv *client, int type,
91 unsigned short instance, vrf_id_t vrf_id,
92 int afi)
718e3744 93{
d62a17ae 94 struct route_entry *newre;
95 struct route_table *table;
96 struct route_node *rn;
97
98 table = zebra_vrf_table(afi, SAFI_UNICAST, vrf_id);
99 if (!table)
100 return;
101
f0c4b8e1 102 for (rn = route_top(table); rn; rn = srcdest_route_next(rn))
a2addae8 103 RNODE_FOREACH_RE (rn, newre) {
14a4d9d0 104 if (IS_ZEBRA_DEBUG_RIB)
d62a17ae 105 zlog_debug(
3fb48129 106 "%s: client %s %pRN(%u:%u) checking: selected=%d, type=%s, instance=%u, distance=%d, metric=%d zebra_check_addr=%d",
d62a17ae 107 __func__,
84faa420
DS
108 zebra_route_string(client->proto), rn,
109 vrf_id, newre->instance,
1945fb7a
DS
110 !!CHECK_FLAG(newre->flags,
111 ZEBRA_FLAG_SELECTED),
3fb48129
DS
112 zebra_route_string(newre->type),
113 newre->instance,
114 newre->distance,
84faa420
DS
115 newre->metric,
116 zebra_check_addr(&rn->p));
d62a17ae 117
118 if (!CHECK_FLAG(newre->flags, ZEBRA_FLAG_SELECTED))
119 continue;
120 if ((type != ZEBRA_ROUTE_ALL
121 && (newre->type != type
122 || newre->instance != instance)))
123 continue;
84faa420 124 if (!zebra_check_addr(&rn->p))
d62a17ae 125 continue;
126
74489921 127 zsend_redistribute_route(ZEBRA_REDISTRIBUTE_ROUTE_ADD,
84faa420 128 client, rn, newre);
d62a17ae 129 }
718e3744 130}
131
14fe366e
S
132/*
133 * Function to check if prefix is candidate for
134 * redistribute.
135 */
c8671e9f
DS
136static bool zebra_redistribute_check(const struct route_node *rn,
137 const struct route_entry *re,
138 struct zserv *client)
14fe366e 139{
79a9ad14 140 struct zebra_vrf *zvrf;
c8671e9f 141 afi_t afi;
79a9ad14 142
14fe366e
S
143 /* Process only if there is valid re */
144 if (!re)
145 return false;
146
c8671e9f 147 afi = family2afi(rn->p.family);
79a9ad14
DS
148 zvrf = vrf_info_lookup(re->vrf_id);
149 if (re->vrf_id == VRF_DEFAULT && zvrf->table_id != re->table)
150 return false;
151
14fe366e 152 /* If default route and redistributed */
c8671e9f
DS
153 if (is_default_prefix(&rn->p) &&
154 vrf_bitmap_check(client->redist_default[afi], re->vrf_id))
14fe366e
S
155 return true;
156
157 /* If redistribute in enabled for zebra route all */
158 if (vrf_bitmap_check(client->redist[afi][ZEBRA_ROUTE_ALL], re->vrf_id))
159 return true;
160
161 /*
162 * If multi-instance then check for route
163 * redistribution for given instance.
164 */
deb39cca
DS
165 if (re->instance) {
166 if (redist_check_instance(&client->mi_redist[afi][re->type],
167 re->instance))
168 return true;
169 else
170 return false;
171 }
14fe366e
S
172
173 /* If redistribution is enabled for give route type. */
174 if (vrf_bitmap_check(client->redist[afi][re->type], re->vrf_id))
175 return true;
176
177 return false;
178}
179
c41fc67b 180/* Either advertise a route for redistribution to registered clients or */
181/* withdraw redistribution if add cannot be done for client */
ee78ed68 182void redistribute_update(const struct route_node *rn,
40f321c0
MS
183 const struct route_entry *re,
184 const struct route_entry *prev_re)
718e3744 185{
d62a17ae 186 struct listnode *node, *nnode;
187 struct zserv *client;
d62a17ae 188
2dbe669b 189 if (IS_ZEBRA_DEBUG_RIB)
d62a17ae 190 zlog_debug(
ee78ed68
DS
191 "(%u:%u):%pRN(%u): Redist update re %p (%s), old %p (%s)",
192 re->vrf_id, re->table, rn, re->instance, re,
2dbe669b 193 zebra_route_string(re->type), prev_re,
2da33d6b 194 prev_re ? zebra_route_string(prev_re->type) : "None");
d62a17ae 195
ee78ed68 196 if (!zebra_check_addr(&rn->p)) {
79becec8 197 if (IS_ZEBRA_DEBUG_RIB)
ee78ed68 198 zlog_debug("Redist update filter prefix %pRN", rn);
79becec8 199 return;
200 }
201
d62a17ae 202
161e9ab7 203 for (ALL_LIST_ELEMENTS(zrouter.client_list, node, nnode, client)) {
c8671e9f 204 if (zebra_redistribute_check(rn, re, client)) {
14a4d9d0 205 if (IS_ZEBRA_DEBUG_RIB) {
3e178809 206 zlog_debug(
ee78ed68 207 "%s: client %s %pRN(%u:%u), type=%d, distance=%d, metric=%d",
c2c02b76 208 __func__,
ee78ed68 209 zebra_route_string(client->proto), rn,
c2c02b76
DS
210 re->vrf_id, re->table, re->type,
211 re->distance, re->metric);
3e178809 212 }
74489921 213 zsend_redistribute_route(ZEBRA_REDISTRIBUTE_ROUTE_ADD,
84faa420 214 client, rn, re);
c8671e9f 215 } else if (zebra_redistribute_check(rn, prev_re, client))
74489921 216 zsend_redistribute_route(ZEBRA_REDISTRIBUTE_ROUTE_DEL,
84faa420 217 client, rn, prev_re);
c41fc67b 218 }
718e3744 219}
220
40f321c0
MS
221/*
222 * During a route delete, where 'new_re' is NULL, redist a delete to all
223 * clients registered for the type of 'old_re'.
224 * During a route update, redist a delete to any clients who will not see
225 * an update when the new route is installed. There are cases when a client
226 * may have seen a redist for 'old_re', but will not see
227 * the redist for 'new_re'.
228 */
b3a9fca1 229void redistribute_delete(const struct route_node *rn,
40f321c0
MS
230 const struct route_entry *old_re,
231 const struct route_entry *new_re)
718e3744 232{
d62a17ae 233 struct listnode *node, *nnode;
234 struct zserv *client;
40f321c0
MS
235 vrf_id_t vrfid;
236
237 if (old_re)
238 vrfid = old_re->vrf_id;
239 else if (new_re)
240 vrfid = new_re->vrf_id;
241 else
242 return;
d62a17ae 243
244 if (IS_ZEBRA_DEBUG_RIB) {
db80a7e2
DS
245 uint8_t old_inst, new_inst;
246 uint32_t table = 0;
247
248 old_inst = new_inst = 0;
249
250 if (old_re) {
251 old_inst = old_re->instance;
252 table = old_re->table;
253 }
254 if (new_re) {
255 new_inst = new_re->instance;
256 table = new_re->table;
257 }
258
259 zlog_debug(
260 "%u:%u%pRN: Redist del: re %p (%u:%s), new re %p (%u:%s)",
261 vrfid, table, rn, old_re, old_inst,
262 old_re ? zebra_route_string(old_re->type) : "None",
263 new_re, new_inst,
264 new_re ? zebra_route_string(new_re->type) : "None");
d62a17ae 265 }
266
40f321c0 267 /* Skip invalid (e.g. linklocal) prefix */
b3a9fca1 268 if (!zebra_check_addr(&rn->p)) {
40f321c0
MS
269 if (IS_ZEBRA_DEBUG_RIB) {
270 zlog_debug(
b3a9fca1
DS
271 "%u:%pRN: Redist del old: skipping invalid prefix",
272 vrfid, rn);
40f321c0 273 }
79becec8 274 return;
275 }
276
161e9ab7 277 for (ALL_LIST_ELEMENTS(zrouter.client_list, node, nnode, client)) {
17da84a4
KS
278 /* Do not send unsolicited messages to synchronous clients. */
279 if (client->synchronous)
280 continue;
14fe366e
S
281 /*
282 * Skip this client if it will receive an update for the
283 * 'new' re
284 */
c8671e9f 285 if (zebra_redistribute_check(rn, new_re, client))
14fe366e 286 continue;
40f321c0
MS
287
288 /* Send a delete for the 'old' re to any subscribed client. */
84faa420 289 if (zebra_redistribute_check(rn, old_re, client))
74489921 290 zsend_redistribute_route(ZEBRA_REDISTRIBUTE_ROUTE_DEL,
84faa420 291 client, rn, old_re);
1eb8ef25 292 }
718e3744 293}
294
14fe366e 295
89f4e507 296void zebra_redistribute_add(ZAPI_HANDLER_ARGS)
718e3744 297{
ec93aa12
DS
298 afi_t afi = 0;
299 int type = 0;
d7c0a89a 300 unsigned short instance;
d62a17ae 301
1002497a
QY
302 STREAM_GETC(msg, afi);
303 STREAM_GETC(msg, type);
304 STREAM_GETW(msg, instance);
d62a17ae 305
1b6e575b
PZ
306 if (IS_ZEBRA_DEBUG_EVENT)
307 zlog_debug(
c479e756 308 "%s: client proto %s afi=%d, wants %s, vrf %s(%u), instance=%d",
1b6e575b 309 __func__, zebra_route_string(client->proto), afi,
c479e756
DS
310 zebra_route_string(type), VRF_LOGNAME(zvrf->vrf),
311 zvrf_id(zvrf), instance);
1b6e575b 312
e1fa928d 313 if (afi == 0 || afi >= AFI_MAX) {
e914ccbe 314 flog_warn(EC_ZEBRA_REDISTRIBUTE_UNKNOWN_AF,
15569c58 315 "%s: Specified afi %d does not exist", __func__, afi);
d62a17ae 316 return;
ec93aa12
DS
317 }
318
319 if (type == 0 || type >= ZEBRA_ROUTE_MAX) {
9df414fe 320 zlog_debug("%s: Specified Route Type %d does not exist",
15569c58 321 __func__, type);
ec93aa12
DS
322 return;
323 }
d62a17ae 324
325 if (instance) {
326 if (!redist_check_instance(&client->mi_redist[afi][type],
327 instance)) {
328 redist_add_instance(&client->mi_redist[afi][type],
329 instance);
330 zebra_redistribute(client, type, instance,
331 zvrf_id(zvrf), afi);
332 }
333 } else {
d9083050
IR
334 if (!vrf_bitmap_check(client->redist[afi][type],
335 zvrf_id(zvrf))) {
336 if (IS_ZEBRA_DEBUG_EVENT)
337 zlog_debug(
338 "%s: setting vrf %s(%u) redist bitmap",
339 __func__, VRF_LOGNAME(zvrf->vrf),
340 zvrf_id(zvrf));
341 vrf_bitmap_set(client->redist[afi][type],
342 zvrf_id(zvrf));
343 zebra_redistribute(client, type, 0, zvrf_id(zvrf), afi);
344 }
4e1cadf0 345 }
ec93aa12
DS
346
347stream_failure:
348 return;
ebf08631 349}
718e3744 350
89f4e507 351void zebra_redistribute_delete(ZAPI_HANDLER_ARGS)
718e3744 352{
ec93aa12
DS
353 afi_t afi = 0;
354 int type = 0;
d7c0a89a 355 unsigned short instance;
d62a17ae 356
1002497a
QY
357 STREAM_GETC(msg, afi);
358 STREAM_GETC(msg, type);
359 STREAM_GETW(msg, instance);
d62a17ae 360
67da9573
EDP
361 if (IS_ZEBRA_DEBUG_EVENT)
362 zlog_debug(
363 "%s: client proto %s afi=%d, no longer wants %s, vrf %s(%u), instance=%d",
364 __func__, zebra_route_string(client->proto), afi,
365 zebra_route_string(type), VRF_LOGNAME(zvrf->vrf),
366 zvrf_id(zvrf), instance);
367
368
e1fa928d 369 if (afi == 0 || afi >= AFI_MAX) {
e914ccbe 370 flog_warn(EC_ZEBRA_REDISTRIBUTE_UNKNOWN_AF,
15569c58 371 "%s: Specified afi %d does not exist", __func__, afi);
d62a17ae 372 return;
ec93aa12
DS
373 }
374
375 if (type == 0 || type >= ZEBRA_ROUTE_MAX) {
9df414fe 376 zlog_debug("%s: Specified Route Type %d does not exist",
15569c58 377 __func__, type);
ec93aa12
DS
378 return;
379 }
d62a17ae 380
381 /*
382 * NOTE: no need to withdraw the previously advertised routes. The
383 * clients
384 * themselves should keep track of the received routes from zebra and
385 * withdraw them when necessary.
386 */
387 if (instance)
388 redist_del_instance(&client->mi_redist[afi][type], instance);
389 else
390 vrf_bitmap_unset(client->redist[afi][type], zvrf_id(zvrf));
ec93aa12
DS
391
392stream_failure:
393 return;
ebf08631 394}
718e3744 395
89f4e507 396void zebra_redistribute_default_add(ZAPI_HANDLER_ARGS)
718e3744 397{
49db7a7b
RW
398 afi_t afi = 0;
399
400 STREAM_GETC(msg, afi);
401
402 if (afi == 0 || afi >= AFI_MAX) {
403 flog_warn(EC_ZEBRA_REDISTRIBUTE_UNKNOWN_AF,
15569c58 404 "%s: Specified afi %u does not exist", __func__, afi);
49db7a7b
RW
405 return;
406 }
407
408 vrf_bitmap_set(client->redist_default[afi], zvrf_id(zvrf));
d62a17ae 409 zebra_redistribute_default(client, zvrf_id(zvrf));
49db7a7b
RW
410
411stream_failure:
412 return;
d62a17ae 413}
718e3744 414
89f4e507 415void zebra_redistribute_default_delete(ZAPI_HANDLER_ARGS)
718e3744 416{
49db7a7b
RW
417 afi_t afi = 0;
418
419 STREAM_GETC(msg, afi);
420
421 if (afi == 0 || afi >= AFI_MAX) {
422 flog_warn(EC_ZEBRA_REDISTRIBUTE_UNKNOWN_AF,
15569c58 423 "%s: Specified afi %u does not exist", __func__, afi);
49db7a7b
RW
424 return;
425 }
426
427 vrf_bitmap_unset(client->redist_default[afi], zvrf_id(zvrf));
428
429stream_failure:
430 return;
d62a17ae 431}
718e3744 432
433/* Interface up information. */
d62a17ae 434void zebra_interface_up_update(struct interface *ifp)
718e3744 435{
d62a17ae 436 struct listnode *node, *nnode;
437 struct zserv *client;
438
439 if (IS_ZEBRA_DEBUG_EVENT)
096f7609
IR
440 zlog_debug("MESSAGE: ZEBRA_INTERFACE_UP %s vrf %s(%u)",
441 ifp->name, ifp->vrf->name, ifp->vrf->vrf_id);
d62a17ae 442
443 if (ifp->ptm_status || !ifp->ptm_enable) {
161e9ab7 444 for (ALL_LIST_ELEMENTS(zrouter.client_list, node, nnode,
a8a20c4e 445 client)) {
17da84a4
KS
446 /* Do not send unsolicited messages to synchronous
447 * clients.
448 */
449 if (client->synchronous)
450 continue;
451
a8a20c4e
DS
452 zsend_interface_update(ZEBRA_INTERFACE_UP,
453 client, ifp);
454 zsend_interface_link_params(client, ifp);
455 }
16f1b9ee 456 }
718e3744 457}
458
459/* Interface down information. */
d62a17ae 460void zebra_interface_down_update(struct interface *ifp)
718e3744 461{
d62a17ae 462 struct listnode *node, *nnode;
463 struct zserv *client;
718e3744 464
d62a17ae 465 if (IS_ZEBRA_DEBUG_EVENT)
096f7609
IR
466 zlog_debug("MESSAGE: ZEBRA_INTERFACE_DOWN %s vrf %s(%u)",
467 ifp->name, ifp->vrf->name, ifp->vrf->vrf_id);
718e3744 468
161e9ab7 469 for (ALL_LIST_ELEMENTS(zrouter.client_list, node, nnode, client)) {
17da84a4
KS
470 /* Do not send unsolicited messages to synchronous clients. */
471 if (client->synchronous)
472 continue;
473
d62a17ae 474 zsend_interface_update(ZEBRA_INTERFACE_DOWN, client, ifp);
475 }
718e3744 476}
477
478/* Interface information update. */
d62a17ae 479void zebra_interface_add_update(struct interface *ifp)
718e3744 480{
d62a17ae 481 struct listnode *node, *nnode;
482 struct zserv *client;
483
484 if (IS_ZEBRA_DEBUG_EVENT)
096f7609
IR
485 zlog_debug("MESSAGE: ZEBRA_INTERFACE_ADD %s vrf %s(%u)",
486 ifp->name, ifp->vrf->name, ifp->vrf->vrf_id);
d62a17ae 487
a8a20c4e 488 for (ALL_LIST_ELEMENTS(zrouter.client_list, node, nnode, client)) {
17da84a4
KS
489 /* Do not send unsolicited messages to synchronous clients. */
490 if (client->synchronous)
491 continue;
492
a8a20c4e
DS
493 client->ifadd_cnt++;
494 zsend_interface_add(client, ifp);
495 zsend_interface_link_params(client, ifp);
496 }
718e3744 497}
498
d62a17ae 499void zebra_interface_delete_update(struct interface *ifp)
718e3744 500{
d62a17ae 501 struct listnode *node, *nnode;
502 struct zserv *client;
718e3744 503
d62a17ae 504 if (IS_ZEBRA_DEBUG_EVENT)
096f7609
IR
505 zlog_debug("MESSAGE: ZEBRA_INTERFACE_DELETE %s vrf %s(%u)",
506 ifp->name, ifp->vrf->name, ifp->vrf->vrf_id);
718e3744 507
161e9ab7 508 for (ALL_LIST_ELEMENTS(zrouter.client_list, node, nnode, client)) {
17da84a4
KS
509 /* Do not send unsolicited messages to synchronous clients. */
510 if (client->synchronous)
511 continue;
512
d62a17ae 513 client->ifdel_cnt++;
514 zsend_interface_delete(client, ifp);
515 }
718e3744 516}
517
518/* Interface address addition. */
d62a17ae 519void zebra_interface_address_add_update(struct interface *ifp,
520 struct connected *ifc)
718e3744 521{
d62a17ae 522 struct listnode *node, *nnode;
523 struct zserv *client;
d62a17ae 524
659ec5e9 525 if (IS_ZEBRA_DEBUG_EVENT)
2dbe669b 526 zlog_debug(
096f7609 527 "MESSAGE: ZEBRA_INTERFACE_ADDRESS_ADD %pFX on %s vrf %s(%u)",
659ec5e9
DS
528 ifc->address, ifp->name, ifp->vrf->name,
529 ifp->vrf->vrf_id);
d62a17ae 530
531 if (!CHECK_FLAG(ifc->conf, ZEBRA_IFC_REAL))
9df414fe 532 flog_warn(
e914ccbe 533 EC_ZEBRA_ADVERTISING_UNUSABLE_ADDR,
ad6f7449 534 "advertising address to clients that is not yet usable.");
d62a17ae 535
1a98c087
MK
536 zebra_vxlan_add_del_gw_macip(ifp, ifc->address, 1);
537
d62a17ae 538 router_id_add_address(ifc);
539
17da84a4
KS
540 for (ALL_LIST_ELEMENTS(zrouter.client_list, node, nnode, client)) {
541 /* Do not send unsolicited messages to synchronous clients. */
542 if (client->synchronous)
543 continue;
544
d62a17ae 545 if (CHECK_FLAG(ifc->conf, ZEBRA_IFC_REAL)) {
546 client->connected_rt_add_cnt++;
547 zsend_interface_address(ZEBRA_INTERFACE_ADDRESS_ADD,
548 client, ifp, ifc);
549 }
17da84a4 550 }
718e3744 551}
552
553/* Interface address deletion. */
d62a17ae 554void zebra_interface_address_delete_update(struct interface *ifp,
555 struct connected *ifc)
718e3744 556{
d62a17ae 557 struct listnode *node, *nnode;
558 struct zserv *client;
d62a17ae 559
659ec5e9 560 if (IS_ZEBRA_DEBUG_EVENT)
2dbe669b 561 zlog_debug(
096f7609 562 "MESSAGE: ZEBRA_INTERFACE_ADDRESS_DELETE %pFX on %s vrf %s(%u)",
659ec5e9
DS
563 ifc->address, ifp->name, ifp->vrf->name,
564 ifp->vrf->vrf_id);
d62a17ae 565
1a98c087
MK
566 zebra_vxlan_add_del_gw_macip(ifp, ifc->address, 0);
567
d62a17ae 568 router_id_del_address(ifc);
569
17da84a4
KS
570 for (ALL_LIST_ELEMENTS(zrouter.client_list, node, nnode, client)) {
571 /* Do not send unsolicited messages to synchronous clients. */
572 if (client->synchronous)
573 continue;
574
d62a17ae 575 if (CHECK_FLAG(ifc->conf, ZEBRA_IFC_REAL)) {
576 client->connected_rt_del_cnt++;
577 zsend_interface_address(ZEBRA_INTERFACE_ADDRESS_DELETE,
578 client, ifp, ifc);
579 }
17da84a4 580 }
718e3744 581}
d5a5c8f0 582
c8e264b6 583/* Interface VRF change. May need to delete from clients not interested in
584 * the new VRF. Note that this function is invoked *prior* to the VRF change.
585 */
d62a17ae 586void zebra_interface_vrf_update_del(struct interface *ifp, vrf_id_t new_vrf_id)
c8e264b6 587{
d62a17ae 588 struct listnode *node, *nnode;
589 struct zserv *client;
590
591 if (IS_ZEBRA_DEBUG_EVENT)
592 zlog_debug(
593 "MESSAGE: ZEBRA_INTERFACE_VRF_UPDATE/DEL %s VRF Id %u -> %u",
096f7609 594 ifp->name, ifp->vrf->vrf_id, new_vrf_id);
d62a17ae 595
161e9ab7 596 for (ALL_LIST_ELEMENTS(zrouter.client_list, node, nnode, client)) {
17da84a4
KS
597 /* Do not send unsolicited messages to synchronous clients. */
598 if (client->synchronous)
599 continue;
600
d62a17ae 601 /* Need to delete if the client is not interested in the new
602 * VRF. */
603 zsend_interface_update(ZEBRA_INTERFACE_DOWN, client, ifp);
604 client->ifdel_cnt++;
605 zsend_interface_delete(client, ifp);
606 zsend_interface_vrf_update(client, ifp, new_vrf_id);
607 }
c8e264b6 608}
609
610/* Interface VRF change. This function is invoked *post* VRF change and sends an
611 * add to clients who are interested in the new VRF but not in the old VRF.
612 */
d62a17ae 613void zebra_interface_vrf_update_add(struct interface *ifp, vrf_id_t old_vrf_id)
c8e264b6 614{
d62a17ae 615 struct listnode *node, *nnode;
616 struct zserv *client;
617
618 if (IS_ZEBRA_DEBUG_EVENT)
619 zlog_debug(
620 "MESSAGE: ZEBRA_INTERFACE_VRF_UPDATE/ADD %s VRF Id %u -> %u",
096f7609 621 ifp->name, old_vrf_id, ifp->vrf->vrf_id);
d62a17ae 622
161e9ab7 623 for (ALL_LIST_ELEMENTS(zrouter.client_list, node, nnode, client)) {
17da84a4
KS
624 /* Do not send unsolicited messages to synchronous clients. */
625 if (client->synchronous)
626 continue;
627
d62a17ae 628 /* Need to add if the client is interested in the new VRF. */
629 client->ifadd_cnt++;
630 zsend_interface_add(client, ifp);
631 zsend_interface_addresses(client, ifp);
632 }
c8e264b6 633}
634
fe257ae7
DS
635int zebra_add_import_table_entry(struct zebra_vrf *zvrf, struct route_node *rn,
636 struct route_entry *re, const char *rmap_name)
7a4bb9c5 637{
d62a17ae 638 struct route_entry *newre;
639 struct route_entry *same;
640 struct prefix p;
0eb97b86 641 struct nexthop_group *ng;
b68885f9 642 route_map_result_t ret = RMAP_PERMITMATCH;
f8c175f3 643 afi_t afi;
d62a17ae 644
f8c175f3 645 afi = family2afi(rn->p.family);
d62a17ae 646 if (rmap_name)
647 ret = zebra_import_table_route_map_check(
0eb97b86 648 afi, re->type, re->instance, &rn->p,
c415d895 649 re->nhe->nhg.nexthop,
fe257ae7 650 zvrf->vrf->vrf_id, re->tag, rmap_name);
d62a17ae 651
b68885f9 652 if (ret != RMAP_PERMITMATCH) {
85c615ac 653 UNSET_FLAG(re->flags, ZEBRA_FLAG_SELECTED);
fe257ae7 654 zebra_del_import_table_entry(zvrf, rn, re);
20796bc3
DS
655 return 0;
656 }
d62a17ae 657
f8c175f3 658 prefix_copy(&p, &rn->p);
d62a17ae 659
a2addae8
RW
660 RNODE_FOREACH_RE (rn, same) {
661 if (CHECK_FLAG(same->status, ROUTE_ENTRY_REMOVED))
f8c175f3 662 continue;
20796bc3 663
996c9314 664 if (same->type == re->type && same->instance == re->instance
f8c175f3
DS
665 && same->table == re->table
666 && same->type != ZEBRA_ROUTE_CONNECT)
667 break;
668 }
20796bc3 669
e71c84ca
DS
670 if (same) {
671 UNSET_FLAG(same->flags, ZEBRA_FLAG_SELECTED);
fe257ae7 672 zebra_del_import_table_entry(zvrf, rn, same);
e71c84ca 673 }
f8c175f3 674
b0385873
DS
675 newre = zebra_rib_route_entry_new(
676 0, ZEBRA_ROUTE_TABLE, re->table, re->flags, re->nhe_id,
677 zvrf->table_id, re->metric, re->mtu,
678 zebra_import_table_distance[afi][re->table], re->tag);
5c4b6e57 679
0eb97b86 680 ng = nexthop_group_new();
c415d895 681 copy_nexthops(&ng->nexthop, re->nhe->nhg.nexthop, NULL);
0eb97b86 682
c6eee91f 683 rib_add_multipath(afi, SAFI_UNICAST, &p, NULL, newre, ng, false);
5c4b6e57 684
d62a17ae 685 return 0;
7a4bb9c5
DS
686}
687
fe257ae7
DS
688int zebra_del_import_table_entry(struct zebra_vrf *zvrf, struct route_node *rn,
689 struct route_entry *re)
7a4bb9c5 690{
d62a17ae 691 struct prefix p;
f8c175f3 692 afi_t afi;
7a4bb9c5 693
f8c175f3
DS
694 afi = family2afi(rn->p.family);
695 prefix_copy(&p, &rn->p);
7a4bb9c5 696
fe257ae7 697 rib_delete(afi, SAFI_UNICAST, zvrf->vrf->vrf_id, ZEBRA_ROUTE_TABLE,
c415d895 698 re->table, re->flags, &p, NULL, re->nhe->nhg.nexthop,
0eb97b86 699 re->nhe_id, zvrf->table_id, re->metric, re->distance,
3ceae22b 700 false);
7a4bb9c5 701
d62a17ae 702 return 0;
7a4bb9c5
DS
703}
704
705/* Assuming no one calls this with the main routing table */
fe257ae7
DS
706int zebra_import_table(afi_t afi, vrf_id_t vrf_id, uint32_t table_id,
707 uint32_t distance, const char *rmap_name, int add)
7a4bb9c5 708{
d62a17ae 709 struct route_table *table;
710 struct route_entry *re;
711 struct route_node *rn;
fe257ae7 712 struct zebra_vrf *zvrf = zebra_vrf_lookup_by_id(vrf_id);
d62a17ae 713
714 if (!is_zebra_valid_kernel_table(table_id)
c447ad08 715 || (table_id == RT_TABLE_MAIN))
95f7965d 716 return -1;
d62a17ae 717
718 if (afi >= AFI_MAX)
95f7965d 719 return -1;
d62a17ae 720
c7c0b007
SW
721 table = zebra_vrf_get_table_with_table_id(afi, SAFI_UNICAST, vrf_id,
722 table_id);
d62a17ae 723 if (table == NULL) {
724 return 0;
725 } else if (IS_ZEBRA_DEBUG_RIB) {
726 zlog_debug("%s routes from table %d",
727 add ? "Importing" : "Unimporting", table_id);
7a4bb9c5
DS
728 }
729
d62a17ae 730 if (add) {
731 if (rmap_name)
732 zebra_add_import_table_route_map(afi, rmap_name,
733 table_id);
734 else {
735 rmap_name =
736 zebra_get_import_table_route_map(afi, table_id);
3660beec 737 if (rmap_name) {
d62a17ae 738 zebra_del_import_table_route_map(afi, table_id);
3660beec
DS
739 rmap_name = NULL;
740 }
d62a17ae 741 }
7a4bb9c5 742
d62a17ae 743 zebra_import_table_used[afi][table_id] = 1;
744 zebra_import_table_distance[afi][table_id] = distance;
745 } else {
746 zebra_import_table_used[afi][table_id] = 0;
747 zebra_import_table_distance[afi][table_id] =
748 ZEBRA_TABLE_DISTANCE_DEFAULT;
749
750 rmap_name = zebra_get_import_table_route_map(afi, table_id);
3660beec 751 if (rmap_name) {
d62a17ae 752 zebra_del_import_table_route_map(afi, table_id);
3660beec
DS
753 rmap_name = NULL;
754 }
7a4bb9c5 755 }
7a4bb9c5 756
d62a17ae 757 for (rn = route_top(table); rn; rn = route_next(rn)) {
758 /* For each entry in the non-default routing table,
759 * add the entry in the main table
760 */
761 if (!rn->info)
762 continue;
763
a2addae8 764 RNODE_FOREACH_RE (rn, re) {
d62a17ae 765 if (CHECK_FLAG(re->status, ROUTE_ENTRY_REMOVED))
766 continue;
767 break;
7a4bb9c5 768 }
8902474b 769
d62a17ae 770 if (!re)
771 continue;
8902474b 772
d62a17ae 773 if (((afi == AFI_IP) && (rn->p.family == AF_INET))
774 || ((afi == AFI_IP6) && (rn->p.family == AF_INET6))) {
775 if (add)
fe257ae7
DS
776 zebra_add_import_table_entry(zvrf, rn, re,
777 rmap_name);
d62a17ae 778 else
fe257ae7 779 zebra_del_import_table_entry(zvrf, rn, re);
d62a17ae 780 }
781 }
782 return 0;
783}
784
fe257ae7 785int zebra_import_table_config(struct vty *vty, vrf_id_t vrf_id)
d62a17ae 786{
787 int i;
788 afi_t afi;
789 int write = 0;
790 char afi_str[AFI_MAX][10] = {"", "ip", "ipv6", "ethernet"};
791 const char *rmap_name;
792
793 for (afi = AFI_IP; afi < AFI_MAX; afi++) {
794 for (i = 1; i < ZEBRA_KERNEL_TABLE_MAX; i++) {
fe257ae7 795 if (!is_zebra_import_table_enabled(afi, vrf_id, i))
20796bc3 796 continue;
d62a17ae 797
20796bc3
DS
798 if (zebra_import_table_distance[afi][i]
799 != ZEBRA_TABLE_DISTANCE_DEFAULT) {
996c9314 800 vty_out(vty, "%s import-table %d distance %d",
20796bc3
DS
801 afi_str[afi], i,
802 zebra_import_table_distance[afi][i]);
803 } else {
996c9314
LB
804 vty_out(vty, "%s import-table %d", afi_str[afi],
805 i);
d62a17ae 806 }
20796bc3
DS
807
808 rmap_name = zebra_get_import_table_route_map(afi, i);
809 if (rmap_name)
996c9314 810 vty_out(vty, " route-map %s", rmap_name);
20796bc3
DS
811
812 vty_out(vty, "\n");
813 write = 1;
d62a17ae 814 }
7a4bb9c5 815 }
7a4bb9c5 816
d62a17ae 817 return write;
7a4bb9c5 818}
8902474b 819
fe257ae7
DS
820static void zebra_import_table_rm_update_vrf_afi(struct zebra_vrf *zvrf,
821 afi_t afi, int table_id,
822 const char *rmap)
8902474b 823{
d62a17ae 824 struct route_table *table;
825 struct route_entry *re;
826 struct route_node *rn;
827 const char *rmap_name;
828
fe257ae7
DS
829 rmap_name = zebra_get_import_table_route_map(afi, table_id);
830 if ((!rmap_name) || (strcmp(rmap_name, rmap) != 0))
831 return;
d62a17ae 832
c7c0b007
SW
833 table = zebra_vrf_get_table_with_table_id(afi, SAFI_UNICAST,
834 zvrf->vrf->vrf_id, table_id);
fe257ae7
DS
835 if (!table) {
836 if (IS_ZEBRA_DEBUG_RIB_DETAILED)
837 zlog_debug("%s: Table id=%d not found", __func__,
838 table_id);
839 return;
840 }
841
842 for (rn = route_top(table); rn; rn = route_next(rn)) {
843 /*
844 * For each entry in the non-default routing table,
845 * add the entry in the main table
846 */
847 if (!rn->info)
848 continue;
849
850 RNODE_FOREACH_RE (rn, re) {
851 if (CHECK_FLAG(re->status, ROUTE_ENTRY_REMOVED))
d5b8c216 852 continue;
fe257ae7
DS
853 break;
854 }
855
856 if (!re)
857 continue;
858
859 if (((afi == AFI_IP) && (rn->p.family == AF_INET))
860 || ((afi == AFI_IP6) && (rn->p.family == AF_INET6)))
861 zebra_add_import_table_entry(zvrf, rn, re, rmap_name);
862 }
863
864 return;
865}
866
867static void zebra_import_table_rm_update_vrf(struct zebra_vrf *zvrf,
868 const char *rmap)
869{
870 afi_t afi;
871 int i;
872
873 for (afi = AFI_IP; afi < AFI_MAX; afi++) {
874 for (i = 1; i < ZEBRA_KERNEL_TABLE_MAX; i++) {
875 if (!is_zebra_import_table_enabled(
876 afi, zvrf->vrf->vrf_id, i))
2c7ef20d 877 continue;
2c7ef20d 878
fe257ae7
DS
879 zebra_import_table_rm_update_vrf_afi(zvrf, afi, i,
880 rmap);
d62a17ae 881 }
8902474b 882 }
fe257ae7 883}
8902474b 884
fe257ae7
DS
885void zebra_import_table_rm_update(const char *rmap)
886{
887 struct vrf *vrf;
888 struct zebra_vrf *zvrf;
889
890 RB_FOREACH (vrf, vrf_name_head, &vrfs_by_name) {
891 zvrf = vrf->info;
892
893 if (!zvrf)
894 continue;
895
896 zebra_import_table_rm_update_vrf(zvrf, rmap);
897 }
8902474b 898}
16f1b9ee
OD
899
900/* Interface parameters update */
d62a17ae 901void zebra_interface_parameters_update(struct interface *ifp)
16f1b9ee 902{
d62a17ae 903 struct listnode *node, *nnode;
904 struct zserv *client;
16f1b9ee 905
d62a17ae 906 if (IS_ZEBRA_DEBUG_EVENT)
096f7609
IR
907 zlog_debug("MESSAGE: ZEBRA_INTERFACE_LINK_PARAMS %s vrf %s(%u)",
908 ifp->name, ifp->vrf->name, ifp->vrf->vrf_id);
16f1b9ee 909
17da84a4
KS
910 for (ALL_LIST_ELEMENTS(zrouter.client_list, node, nnode, client)) {
911 /* Do not send unsolicited messages to synchronous clients. */
912 if (client->synchronous)
913 continue;
914
a8a20c4e 915 zsend_interface_link_params(client, ifp);
17da84a4 916 }
16f1b9ee 917}