1 /*
2  * Zebra EVPN for VxLAN code
3  * Copyright (C) 2016, 2017 Cumulus Networks, Inc.
4  *
5  * This file is part of FRR.
6  *
7  * FRR 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  * FRR 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  *
17  * You should have received a copy of the GNU General Public License
18  * along with FRR; see the file COPYING.  If not, write to the Free
19  * Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
20  * 02111-1307, USA.
21  */
22 
23 #include <zebra.h>
24 
25 #include "hash.h"
26 #include "if.h"
27 #include "jhash.h"
28 #include "linklist.h"
29 #include "log.h"
30 #include "memory.h"
31 #include "prefix.h"
32 #include "stream.h"
33 #include "table.h"
34 #include "vlan.h"
35 #include "vxlan.h"
36 #ifdef GNU_LINUX
37 #include <linux/neighbour.h>
38 #endif
39 
40 #include "zebra/zebra_router.h"
41 #include "zebra/debug.h"
42 #include "zebra/interface.h"
43 #include "zebra/rib.h"
44 #include "zebra/rt.h"
45 #include "zebra/rt_netlink.h"
46 #include "zebra/zebra_errors.h"
47 #include "zebra/zebra_l2.h"
48 #include "zebra/zebra_memory.h"
49 #include "zebra/zebra_ns.h"
50 #include "zebra/zebra_vrf.h"
51 #include "zebra/zebra_vxlan.h"
52 #include "zebra/zebra_evpn.h"
53 #include "zebra/zebra_evpn_mac.h"
54 #include "zebra/zebra_evpn_neigh.h"
55 #include "zebra/zebra_vxlan_private.h"
56 #include "zebra/zebra_evpn_mh.h"
57 #include "zebra/zebra_evpn_vxlan.h"
58 #include "zebra/zebra_router.h"
59 
60 DEFINE_MTYPE_STATIC(ZEBRA, HOST_PREFIX, "host prefix");
61 DEFINE_MTYPE_STATIC(ZEBRA, ZL3VNI, "L3 VNI hash");
62 DEFINE_MTYPE_STATIC(ZEBRA, L3VNI_MAC, "EVPN L3VNI MAC");
63 DEFINE_MTYPE_STATIC(ZEBRA, L3NEIGH, "EVPN Neighbor");
64 DEFINE_MTYPE_STATIC(ZEBRA, ZVXLAN_SG, "zebra VxLAN multicast group");
65 
66 DEFINE_HOOK(zebra_rmac_update, (zebra_mac_t *rmac, zebra_l3vni_t *zl3vni,
67 	    bool delete, const char *reason), (rmac, zl3vni, delete, reason))
68 
69 /* static function declarations */
70 static void zevpn_print_neigh_hash_all_evpn(struct hash_bucket *bucket,
71 					    void **args);
72 static void zl3vni_print_nh(zebra_neigh_t *n, struct vty *vty,
73 			    json_object *json);
74 static void zl3vni_print_rmac(zebra_mac_t *zrmac, struct vty *vty,
75 			      json_object *json);
76 static void zevpn_print_mac_hash_all_evpn(struct hash_bucket *bucket, void *ctxt);
77 
78 /* l3-vni next-hop neigh related APIs */
79 static zebra_neigh_t *zl3vni_nh_lookup(zebra_l3vni_t *zl3vni,
80 				       const struct ipaddr *ip);
81 static void *zl3vni_nh_alloc(void *p);
82 static zebra_neigh_t *zl3vni_nh_add(zebra_l3vni_t *zl3vni,
83 				    const struct ipaddr *vtep_ip,
84 				    const struct ethaddr *rmac);
85 static int zl3vni_nh_del(zebra_l3vni_t *zl3vni, zebra_neigh_t *n);
86 static int zl3vni_nh_install(zebra_l3vni_t *zl3vni, zebra_neigh_t *n);
87 static int zl3vni_nh_uninstall(zebra_l3vni_t *zl3vni, zebra_neigh_t *n);
88 
89 /* l3-vni rmac related APIs */
90 static void zl3vni_print_rmac_hash(struct hash_bucket *, void *);
91 static zebra_mac_t *zl3vni_rmac_lookup(zebra_l3vni_t *zl3vni,
92 				       const struct ethaddr *rmac);
93 static void *zl3vni_rmac_alloc(void *p);
94 static zebra_mac_t *zl3vni_rmac_add(zebra_l3vni_t *zl3vni,
95 				    const struct ethaddr *rmac);
96 static int zl3vni_rmac_del(zebra_l3vni_t *zl3vni, zebra_mac_t *zrmac);
97 static int zl3vni_rmac_install(zebra_l3vni_t *zl3vni, zebra_mac_t *zrmac);
98 static int zl3vni_rmac_uninstall(zebra_l3vni_t *zl3vni, zebra_mac_t *zrmac);
99 
100 /* l3-vni related APIs*/
101 static void *zl3vni_alloc(void *p);
102 static zebra_l3vni_t *zl3vni_add(vni_t vni, vrf_id_t vrf_id);
103 static int zl3vni_del(zebra_l3vni_t *zl3vni);
104 static void zebra_vxlan_process_l3vni_oper_up(zebra_l3vni_t *zl3vni);
105 static void zebra_vxlan_process_l3vni_oper_down(zebra_l3vni_t *zl3vni);
106 
107 static void zevpn_build_hash_table(void);
108 static unsigned int zebra_vxlan_sg_hash_key_make(const void *p);
109 static bool zebra_vxlan_sg_hash_eq(const void *p1, const void *p2);
110 static void zebra_vxlan_sg_do_deref(struct zebra_vrf *zvrf,
111 		struct in_addr sip, struct in_addr mcast_grp);
112 static zebra_vxlan_sg_t *zebra_vxlan_sg_do_ref(struct zebra_vrf *vrf,
113 				struct in_addr sip, struct in_addr mcast_grp);
114 static void zebra_vxlan_sg_deref(struct in_addr local_vtep_ip,
115 				struct in_addr mcast_grp);
116 static void zebra_vxlan_sg_ref(struct in_addr local_vtep_ip,
117 				struct in_addr mcast_grp);
118 static void zebra_vxlan_sg_cleanup(struct hash_bucket *bucket, void *arg);
119 
120 /* Private functions */
host_rb_entry_compare(const struct host_rb_entry * hle1,const struct host_rb_entry * hle2)121 static int host_rb_entry_compare(const struct host_rb_entry *hle1,
122 				 const struct host_rb_entry *hle2)
123 {
124 	if (hle1->p.family < hle2->p.family)
125 		return -1;
126 
127 	if (hle1->p.family > hle2->p.family)
128 		return 1;
129 
130 	if (hle1->p.prefixlen < hle2->p.prefixlen)
131 		return -1;
132 
133 	if (hle1->p.prefixlen > hle2->p.prefixlen)
134 		return 1;
135 
136 	if (hle1->p.family == AF_INET) {
137 		if (hle1->p.u.prefix4.s_addr < hle2->p.u.prefix4.s_addr)
138 			return -1;
139 
140 		if (hle1->p.u.prefix4.s_addr > hle2->p.u.prefix4.s_addr)
141 			return 1;
142 
143 		return 0;
144 	} else if (hle1->p.family == AF_INET6) {
145 		return memcmp(&hle1->p.u.prefix6, &hle2->p.u.prefix6,
146 			      IPV6_MAX_BYTELEN);
147 	} else {
148 		zlog_debug("%s: Unexpected family type: %d", __func__,
149 			   hle1->p.family);
150 		return 0;
151 	}
152 }
153 RB_GENERATE(host_rb_tree_entry, host_rb_entry, hl_entry, host_rb_entry_compare);
154 
rb_host_count(struct host_rb_tree_entry * hrbe)155 static uint32_t rb_host_count(struct host_rb_tree_entry *hrbe)
156 {
157 	struct host_rb_entry *hle;
158 	uint32_t count = 0;
159 
160 	RB_FOREACH (hle, host_rb_tree_entry, hrbe)
161 		count++;
162 
163 	return count;
164 }
165 
166 /*
167  * Print neighbors for all EVPN.
168  */
zevpn_print_neigh_hash_all_evpn(struct hash_bucket * bucket,void ** args)169 static void zevpn_print_neigh_hash_all_evpn(struct hash_bucket *bucket,
170 					  void **args)
171 {
172 	struct vty *vty;
173 	json_object *json = NULL, *json_evpn = NULL;
174 	zebra_evpn_t *zevpn;
175 	uint32_t num_neigh;
176 	struct neigh_walk_ctx wctx;
177 	char vni_str[VNI_STR_LEN];
178 	uint32_t print_dup;
179 
180 	vty = (struct vty *)args[0];
181 	json = (json_object *)args[1];
182 	print_dup = (uint32_t)(uintptr_t)args[2];
183 
184 	zevpn = (zebra_evpn_t *)bucket->data;
185 
186 	num_neigh = hashcount(zevpn->neigh_table);
187 
188 	if (print_dup)
189 		num_neigh = num_dup_detected_neighs(zevpn);
190 
191 	if (json == NULL) {
192 		vty_out(vty,
193 			"\nVNI %u #ARP (IPv4 and IPv6, local and remote) %u\n\n",
194 			zevpn->vni, num_neigh);
195 	} else {
196 		json_evpn = json_object_new_object();
197 		json_object_int_add(json_evpn, "numArpNd", num_neigh);
198 		snprintf(vni_str, VNI_STR_LEN, "%u", zevpn->vni);
199 	}
200 
201 	if (!num_neigh) {
202 		if (json)
203 			json_object_object_add(json, vni_str, json_evpn);
204 		return;
205 	}
206 
207 	/* Since we have IPv6 addresses to deal with which can vary widely in
208 	 * size, we try to be a bit more elegant in display by first computing
209 	 * the maximum width.
210 	 */
211 	memset(&wctx, 0, sizeof(struct neigh_walk_ctx));
212 	wctx.zevpn = zevpn;
213 	wctx.vty = vty;
214 	wctx.addr_width = 15;
215 	wctx.json = json_evpn;
216 	hash_iterate(zevpn->neigh_table, zebra_evpn_find_neigh_addr_width,
217 		     &wctx);
218 
219 	if (json == NULL)
220 		zebra_evpn_print_neigh_hdr(vty, &wctx);
221 
222 	if (print_dup)
223 		hash_iterate(zevpn->neigh_table,
224 			     zebra_evpn_print_dad_neigh_hash, &wctx);
225 	else
226 		hash_iterate(zevpn->neigh_table, zebra_evpn_print_neigh_hash,
227 			     &wctx);
228 
229 	if (json)
230 		json_object_object_add(json, vni_str, json_evpn);
231 }
232 
233 /*
234  * Print neighbors for all EVPNs in detail.
235  */
zevpn_print_neigh_hash_all_evpn_detail(struct hash_bucket * bucket,void ** args)236 static void zevpn_print_neigh_hash_all_evpn_detail(struct hash_bucket *bucket,
237 						 void **args)
238 {
239 	struct vty *vty;
240 	json_object *json = NULL, *json_evpn = NULL;
241 	zebra_evpn_t *zevpn;
242 	uint32_t num_neigh;
243 	struct neigh_walk_ctx wctx;
244 	char vni_str[VNI_STR_LEN];
245 	uint32_t print_dup;
246 
247 	vty = (struct vty *)args[0];
248 	json = (json_object *)args[1];
249 	print_dup = (uint32_t)(uintptr_t)args[2];
250 
251 	zevpn = (zebra_evpn_t *)bucket->data;
252 	if (!zevpn) {
253 		if (json)
254 			vty_out(vty, "{}\n");
255 		return;
256 	}
257 	num_neigh = hashcount(zevpn->neigh_table);
258 
259 	if (print_dup && num_dup_detected_neighs(zevpn) == 0)
260 		return;
261 
262 	if (json == NULL) {
263 		vty_out(vty,
264 			"\nVNI %u #ARP (IPv4 and IPv6, local and remote) %u\n\n",
265 			zevpn->vni, num_neigh);
266 	} else {
267 		json_evpn = json_object_new_object();
268 		json_object_int_add(json_evpn, "numArpNd", num_neigh);
269 		snprintf(vni_str, VNI_STR_LEN, "%u", zevpn->vni);
270 	}
271 	if (!num_neigh) {
272 		if (json)
273 			json_object_object_add(json, vni_str, json_evpn);
274 		return;
275 	}
276 
277 	memset(&wctx, 0, sizeof(struct neigh_walk_ctx));
278 	wctx.zevpn = zevpn;
279 	wctx.vty = vty;
280 	wctx.addr_width = 15;
281 	wctx.json = json_evpn;
282 
283 	if (print_dup)
284 		hash_iterate(zevpn->neigh_table,
285 			     zebra_evpn_print_dad_neigh_hash_detail, &wctx);
286 	else
287 		hash_iterate(zevpn->neigh_table,
288 			     zebra_evpn_print_neigh_hash_detail, &wctx);
289 
290 	if (json)
291 		json_object_object_add(json, vni_str, json_evpn);
292 }
293 
294 /* print a specific next hop for an l3vni */
zl3vni_print_nh(zebra_neigh_t * n,struct vty * vty,json_object * json)295 static void zl3vni_print_nh(zebra_neigh_t *n, struct vty *vty,
296 			    json_object *json)
297 {
298 	char buf1[ETHER_ADDR_STRLEN];
299 	char buf2[INET6_ADDRSTRLEN];
300 	json_object *json_hosts = NULL;
301 	struct host_rb_entry *hle;
302 
303 	if (!json) {
304 		vty_out(vty, "Ip: %s\n",
305 			ipaddr2str(&n->ip, buf2, sizeof(buf2)));
306 		vty_out(vty, "  RMAC: %s\n",
307 			prefix_mac2str(&n->emac, buf1, sizeof(buf1)));
308 		vty_out(vty, "  Refcount: %d\n",
309 			rb_host_count(&n->host_rb));
310 		vty_out(vty, "  Prefixes:\n");
311 		RB_FOREACH (hle, host_rb_tree_entry, &n->host_rb)
312 			vty_out(vty, "    %s\n",
313 				prefix2str(&hle->p, buf2, sizeof(buf2)));
314 	} else {
315 		json_hosts = json_object_new_array();
316 		json_object_string_add(
317 			json, "ip", ipaddr2str(&(n->ip), buf2, sizeof(buf2)));
318 		json_object_string_add(
319 			json, "routerMac",
320 			prefix_mac2str(&n->emac, buf2, sizeof(buf2)));
321 		json_object_int_add(json, "refCount",
322 				    rb_host_count(&n->host_rb));
323 		RB_FOREACH (hle, host_rb_tree_entry, &n->host_rb)
324 			json_object_array_add(json_hosts,
325 					      json_object_new_string(prefix2str(
326 										&hle->p, buf2, sizeof(buf2))));
327 		json_object_object_add(json, "prefixList", json_hosts);
328 	}
329 }
330 
331 /* Print a specific RMAC entry */
zl3vni_print_rmac(zebra_mac_t * zrmac,struct vty * vty,json_object * json)332 static void zl3vni_print_rmac(zebra_mac_t *zrmac, struct vty *vty,
333 			      json_object *json)
334 {
335 	char buf1[ETHER_ADDR_STRLEN];
336 	char buf2[PREFIX_STRLEN];
337 	json_object *json_hosts = NULL;
338 	struct host_rb_entry *hle;
339 
340 	if (!json) {
341 		vty_out(vty, "MAC: %s\n",
342 			prefix_mac2str(&zrmac->macaddr, buf1, sizeof(buf1)));
343 		vty_out(vty, " Remote VTEP: %s\n",
344 			inet_ntoa(zrmac->fwd_info.r_vtep_ip));
345 		vty_out(vty, " Refcount: %d\n", rb_host_count(&zrmac->host_rb));
346 		vty_out(vty, "  Prefixes:\n");
347 		RB_FOREACH (hle, host_rb_tree_entry, &zrmac->host_rb)
348 			vty_out(vty, "    %s\n",
349 				prefix2str(&hle->p, buf2, sizeof(buf2)));
350 	} else {
351 		json_hosts = json_object_new_array();
352 		json_object_string_add(
353 			json, "routerMac",
354 			prefix_mac2str(&zrmac->macaddr, buf1, sizeof(buf1)));
355 		json_object_string_add(json, "vtepIp",
356 				       inet_ntoa(zrmac->fwd_info.r_vtep_ip));
357 		json_object_int_add(json, "refCount",
358 				    rb_host_count(&zrmac->host_rb));
359 		json_object_int_add(json, "localSequence", zrmac->loc_seq);
360 		json_object_int_add(json, "remoteSequence", zrmac->rem_seq);
361 		RB_FOREACH (hle, host_rb_tree_entry, &zrmac->host_rb)
362 			json_object_array_add(
363 				json_hosts,
364 				json_object_new_string(prefix2str(
365 					&hle->p, buf2, sizeof(buf2))));
366 		json_object_object_add(json, "prefixList", json_hosts);
367 	}
368 }
369 
370 /*
371  * Print MACs for all EVPNs.
372  */
zevpn_print_mac_hash_all_evpn(struct hash_bucket * bucket,void * ctxt)373 static void zevpn_print_mac_hash_all_evpn(struct hash_bucket *bucket, void *ctxt)
374 {
375 	struct vty *vty;
376 	json_object *json = NULL, *json_evpn = NULL;
377 	json_object *json_mac = NULL;
378 	zebra_evpn_t *zevpn;
379 	uint32_t num_macs;
380 	struct mac_walk_ctx *wctx = ctxt;
381 	char vni_str[VNI_STR_LEN];
382 
383 	vty = wctx->vty;
384 	json = wctx->json;
385 
386 	zevpn = (zebra_evpn_t *)bucket->data;
387 	wctx->zevpn = zevpn;
388 
389 	/*We are iterating over a new VNI, set the count to 0*/
390 	wctx->count = 0;
391 
392 	num_macs = num_valid_macs(zevpn);
393 	if (!num_macs)
394 		return;
395 
396 	if (wctx->print_dup)
397 		num_macs = num_dup_detected_macs(zevpn);
398 
399 	if (json) {
400 		json_evpn = json_object_new_object();
401 		json_mac = json_object_new_object();
402 		snprintf(vni_str, VNI_STR_LEN, "%u", zevpn->vni);
403 	}
404 
405 	if (!CHECK_FLAG(wctx->flags, SHOW_REMOTE_MAC_FROM_VTEP)) {
406 		if (json == NULL) {
407 			vty_out(vty, "\nVNI %u #MACs (local and remote) %u\n\n",
408 				zevpn->vni, num_macs);
409 			vty_out(vty,
410 				"Flags: N=sync-neighs, I=local-inactive, P=peer-active, X=peer-proxy\n");
411 			vty_out(vty, "%-17s %-6s %-5s %-30s %-5s %s\n", "MAC",
412 				"Type", "Flags", "Intf/Remote ES/VTEP",
413 				"VLAN", "Seq #'s");
414 		} else
415 			json_object_int_add(json_evpn, "numMacs", num_macs);
416 	}
417 
418 	if (!num_macs) {
419 		if (json) {
420 			json_object_int_add(json_evpn, "numMacs", num_macs);
421 			json_object_object_add(json, vni_str, json_evpn);
422 		}
423 		return;
424 	}
425 
426 	/* assign per-evpn to wctx->json object to fill macs
427 	 * under the evpn. Re-assign primary json object to fill
428 	 * next evpn information.
429 	 */
430 	wctx->json = json_mac;
431 	if (wctx->print_dup)
432 		hash_iterate(zevpn->mac_table, zebra_evpn_print_dad_mac_hash,
433 			     wctx);
434 	else
435 		hash_iterate(zevpn->mac_table, zebra_evpn_print_mac_hash, wctx);
436 	wctx->json = json;
437 	if (json) {
438 		if (wctx->count)
439 			json_object_object_add(json_evpn, "macs", json_mac);
440 		json_object_object_add(json, vni_str, json_evpn);
441 	}
442 }
443 
444 /*
445  * Print MACs in detail for all EVPNs.
446  */
zevpn_print_mac_hash_all_evpn_detail(struct hash_bucket * bucket,void * ctxt)447 static void zevpn_print_mac_hash_all_evpn_detail(struct hash_bucket *bucket,
448 					       void *ctxt)
449 {
450 	struct vty *vty;
451 	json_object *json = NULL, *json_evpn = NULL;
452 	json_object *json_mac = NULL;
453 	zebra_evpn_t *zevpn;
454 	uint32_t num_macs;
455 	struct mac_walk_ctx *wctx = ctxt;
456 	char vni_str[VNI_STR_LEN];
457 
458 	vty = wctx->vty;
459 	json = wctx->json;
460 
461 	zevpn = (zebra_evpn_t *)bucket->data;
462 	if (!zevpn) {
463 		if (json)
464 			vty_out(vty, "{}\n");
465 		return;
466 	}
467 	wctx->zevpn = zevpn;
468 
469 	/*We are iterating over a new EVPN, set the count to 0*/
470 	wctx->count = 0;
471 
472 	num_macs = num_valid_macs(zevpn);
473 	if (!num_macs)
474 		return;
475 
476 	if (wctx->print_dup && (num_dup_detected_macs(zevpn) == 0))
477 		return;
478 
479 	if (json) {
480 		json_evpn = json_object_new_object();
481 		json_mac = json_object_new_object();
482 		snprintf(vni_str, VNI_STR_LEN, "%u", zevpn->vni);
483 	}
484 
485 	if (!CHECK_FLAG(wctx->flags, SHOW_REMOTE_MAC_FROM_VTEP)) {
486 		if (json == NULL) {
487 			vty_out(vty, "\nVNI %u #MACs (local and remote) %u\n\n",
488 				zevpn->vni, num_macs);
489 		} else
490 			json_object_int_add(json_evpn, "numMacs", num_macs);
491 	}
492 	/* assign per-evpn to wctx->json object to fill macs
493 	 * under the evpn. Re-assign primary json object to fill
494 	 * next evpn information.
495 	 */
496 	wctx->json = json_mac;
497 	if (wctx->print_dup)
498 		hash_iterate(zevpn->mac_table,
499 			     zebra_evpn_print_dad_mac_hash_detail, wctx);
500 	else
501 		hash_iterate(zevpn->mac_table, zebra_evpn_print_mac_hash_detail,
502 			     wctx);
503 	wctx->json = json;
504 	if (json) {
505 		if (wctx->count)
506 			json_object_object_add(json_evpn, "macs", json_mac);
507 		json_object_object_add(json, vni_str, json_evpn);
508 	}
509 }
510 
zl3vni_print_nh_hash(struct hash_bucket * bucket,void * ctx)511 static void zl3vni_print_nh_hash(struct hash_bucket *bucket, void *ctx)
512 {
513 	struct nh_walk_ctx *wctx = NULL;
514 	struct vty *vty = NULL;
515 	struct json_object *json_evpn = NULL;
516 	struct json_object *json_nh = NULL;
517 	zebra_neigh_t *n = NULL;
518 	char buf1[ETHER_ADDR_STRLEN];
519 	char buf2[INET6_ADDRSTRLEN];
520 
521 	wctx = (struct nh_walk_ctx *)ctx;
522 	vty = wctx->vty;
523 	json_evpn = wctx->json;
524 	if (json_evpn)
525 		json_nh = json_object_new_object();
526 	n = (zebra_neigh_t *)bucket->data;
527 
528 	if (!json_evpn) {
529 		vty_out(vty, "%-15s %-17s\n",
530 			ipaddr2str(&(n->ip), buf2, sizeof(buf2)),
531 			prefix_mac2str(&n->emac, buf1, sizeof(buf1)));
532 	} else {
533 		json_object_string_add(json_nh, "nexthopIp",
534 				       ipaddr2str(&n->ip, buf2, sizeof(buf2)));
535 		json_object_string_add(
536 			json_nh, "routerMac",
537 			prefix_mac2str(&n->emac, buf1, sizeof(buf1)));
538 		json_object_object_add(json_evpn,
539 				       ipaddr2str(&(n->ip), buf2, sizeof(buf2)),
540 				       json_nh);
541 	}
542 }
543 
zl3vni_print_nh_hash_all_vni(struct hash_bucket * bucket,void ** args)544 static void zl3vni_print_nh_hash_all_vni(struct hash_bucket *bucket,
545 					 void **args)
546 {
547 	struct vty *vty = NULL;
548 	json_object *json = NULL;
549 	json_object *json_evpn = NULL;
550 	zebra_l3vni_t *zl3vni = NULL;
551 	uint32_t num_nh = 0;
552 	struct nh_walk_ctx wctx;
553 	char vni_str[VNI_STR_LEN];
554 
555 	vty = (struct vty *)args[0];
556 	json = (struct json_object *)args[1];
557 
558 	zl3vni = (zebra_l3vni_t *)bucket->data;
559 
560 	num_nh = hashcount(zl3vni->nh_table);
561 	if (!num_nh)
562 		return;
563 
564 	if (json) {
565 		json_evpn = json_object_new_object();
566 		snprintf(vni_str, VNI_STR_LEN, "%u", zl3vni->vni);
567 	}
568 
569 	if (json == NULL) {
570 		vty_out(vty, "\nVNI %u #Next-Hops %u\n\n", zl3vni->vni, num_nh);
571 		vty_out(vty, "%-15s %-17s\n", "IP", "RMAC");
572 	} else
573 		json_object_int_add(json_evpn, "numNextHops", num_nh);
574 
575 	memset(&wctx, 0, sizeof(struct nh_walk_ctx));
576 	wctx.vty = vty;
577 	wctx.json = json_evpn;
578 	hash_iterate(zl3vni->nh_table, zl3vni_print_nh_hash, &wctx);
579 	if (json)
580 		json_object_object_add(json, vni_str, json_evpn);
581 }
582 
zl3vni_print_rmac_hash_all_vni(struct hash_bucket * bucket,void ** args)583 static void zl3vni_print_rmac_hash_all_vni(struct hash_bucket *bucket,
584 					   void **args)
585 {
586 	struct vty *vty = NULL;
587 	json_object *json = NULL;
588 	json_object *json_evpn = NULL;
589 	zebra_l3vni_t *zl3vni = NULL;
590 	uint32_t num_rmacs;
591 	struct rmac_walk_ctx wctx;
592 	char vni_str[VNI_STR_LEN];
593 
594 	vty = (struct vty *)args[0];
595 	json = (struct json_object *)args[1];
596 
597 	zl3vni = (zebra_l3vni_t *)bucket->data;
598 
599 	num_rmacs = hashcount(zl3vni->rmac_table);
600 	if (!num_rmacs)
601 		return;
602 
603 	if (json) {
604 		json_evpn = json_object_new_object();
605 		snprintf(vni_str, VNI_STR_LEN, "%u", zl3vni->vni);
606 	}
607 
608 	if (json == NULL) {
609 		vty_out(vty, "\nVNI %u #RMACs %u\n\n", zl3vni->vni, num_rmacs);
610 		vty_out(vty, "%-17s %-21s\n", "RMAC", "Remote VTEP");
611 	} else
612 		json_object_int_add(json_evpn, "numRmacs", num_rmacs);
613 
614 	/* assign per-vni to wctx->json object to fill macs
615 	 * under the vni. Re-assign primary json object to fill
616 	 * next vni information.
617 	 */
618 	memset(&wctx, 0, sizeof(struct rmac_walk_ctx));
619 	wctx.vty = vty;
620 	wctx.json = json_evpn;
621 	hash_iterate(zl3vni->rmac_table, zl3vni_print_rmac_hash, &wctx);
622 	if (json)
623 		json_object_object_add(json, vni_str, json_evpn);
624 }
625 
zl3vni_print_rmac_hash(struct hash_bucket * bucket,void * ctx)626 static void zl3vni_print_rmac_hash(struct hash_bucket *bucket, void *ctx)
627 {
628 	zebra_mac_t *zrmac = NULL;
629 	struct rmac_walk_ctx *wctx = NULL;
630 	struct vty *vty = NULL;
631 	struct json_object *json = NULL;
632 	struct json_object *json_rmac = NULL;
633 	char buf[ETHER_ADDR_STRLEN];
634 
635 	wctx = (struct rmac_walk_ctx *)ctx;
636 	vty = wctx->vty;
637 	json = wctx->json;
638 	if (json)
639 		json_rmac = json_object_new_object();
640 	zrmac = (zebra_mac_t *)bucket->data;
641 
642 	if (!json) {
643 		vty_out(vty, "%-17s %-21s\n",
644 			prefix_mac2str(&zrmac->macaddr, buf, sizeof(buf)),
645 			inet_ntoa(zrmac->fwd_info.r_vtep_ip));
646 	} else {
647 		json_object_string_add(
648 			json_rmac, "routerMac",
649 			prefix_mac2str(&zrmac->macaddr, buf, sizeof(buf)));
650 		json_object_string_add(json_rmac, "vtepIp",
651 				       inet_ntoa(zrmac->fwd_info.r_vtep_ip));
652 		json_object_object_add(
653 			json, prefix_mac2str(&zrmac->macaddr, buf, sizeof(buf)),
654 			json_rmac);
655 	}
656 }
657 
658 /* print a specific L3 VNI entry */
zl3vni_print(zebra_l3vni_t * zl3vni,void ** ctx)659 static void zl3vni_print(zebra_l3vni_t *zl3vni, void **ctx)
660 {
661 	char buf[ETHER_ADDR_STRLEN];
662 	struct vty *vty = NULL;
663 	json_object *json = NULL;
664 	zebra_evpn_t *zevpn = NULL;
665 	json_object *json_evpn_list = NULL;
666 	struct listnode *node = NULL, *nnode = NULL;
667 
668 	vty = ctx[0];
669 	json = ctx[1];
670 
671 	if (!json) {
672 		vty_out(vty, "VNI: %u\n", zl3vni->vni);
673 		vty_out(vty, "  Type: %s\n", "L3");
674 		vty_out(vty, "  Tenant VRF: %s\n", zl3vni_vrf_name(zl3vni));
675 		vty_out(vty, "  Local Vtep Ip: %s\n",
676 			inet_ntoa(zl3vni->local_vtep_ip));
677 		vty_out(vty, "  Vxlan-Intf: %s\n",
678 			zl3vni_vxlan_if_name(zl3vni));
679 		vty_out(vty, "  SVI-If: %s\n", zl3vni_svi_if_name(zl3vni));
680 		vty_out(vty, "  State: %s\n", zl3vni_state2str(zl3vni));
681 		vty_out(vty, "  VNI Filter: %s\n",
682 			CHECK_FLAG(zl3vni->filter, PREFIX_ROUTES_ONLY)
683 				? "prefix-routes-only"
684 				: "none");
685 		vty_out(vty, "  System MAC: %s\n",
686 			zl3vni_sysmac2str(zl3vni, buf, sizeof(buf)));
687 		vty_out(vty, "  Router MAC: %s\n",
688 			zl3vni_rmac2str(zl3vni, buf, sizeof(buf)));
689 		vty_out(vty, "  L2 VNIs: ");
690 		for (ALL_LIST_ELEMENTS(zl3vni->l2vnis, node, nnode, zevpn))
691 			vty_out(vty, "%u ", zevpn->vni);
692 		vty_out(vty, "\n");
693 	} else {
694 		json_evpn_list = json_object_new_array();
695 		json_object_int_add(json, "vni", zl3vni->vni);
696 		json_object_string_add(json, "type", "L3");
697 		json_object_string_add(json, "localVtepIp",
698 				       inet_ntoa(zl3vni->local_vtep_ip));
699 		json_object_string_add(json, "vxlanIntf",
700 				       zl3vni_vxlan_if_name(zl3vni));
701 		json_object_string_add(json, "sviIntf",
702 				       zl3vni_svi_if_name(zl3vni));
703 		json_object_string_add(json, "state", zl3vni_state2str(zl3vni));
704 		json_object_string_add(json, "vrf", zl3vni_vrf_name(zl3vni));
705 		json_object_string_add(
706 			json, "sysMac",
707 			zl3vni_sysmac2str(zl3vni, buf, sizeof(buf)));
708 		json_object_string_add(
709 			json, "routerMac",
710 			zl3vni_rmac2str(zl3vni, buf, sizeof(buf)));
711 		json_object_string_add(
712 			json, "vniFilter",
713 			CHECK_FLAG(zl3vni->filter, PREFIX_ROUTES_ONLY)
714 				? "prefix-routes-only"
715 				: "none");
716 		for (ALL_LIST_ELEMENTS(zl3vni->l2vnis, node, nnode, zevpn)) {
717 			json_object_array_add(json_evpn_list,
718 					      json_object_new_int(zevpn->vni));
719 		}
720 		json_object_object_add(json, "l2Vnis", json_evpn_list);
721 	}
722 }
723 
724 /* print a L3 VNI hash entry */
zl3vni_print_hash(struct hash_bucket * bucket,void * ctx[])725 static void zl3vni_print_hash(struct hash_bucket *bucket, void *ctx[])
726 {
727 	struct vty *vty = NULL;
728 	json_object *json = NULL;
729 	json_object *json_evpn = NULL;
730 	zebra_l3vni_t *zl3vni = NULL;
731 
732 	vty = (struct vty *)ctx[0];
733 	json = (json_object *)ctx[1];
734 
735 	zl3vni = (zebra_l3vni_t *)bucket->data;
736 
737 	if (!json) {
738 		vty_out(vty, "%-10u %-4s %-21s %-8lu %-8lu %-15s %-37s\n",
739 			zl3vni->vni, "L3", zl3vni_vxlan_if_name(zl3vni),
740 			hashcount(zl3vni->rmac_table),
741 			hashcount(zl3vni->nh_table), "n/a",
742 			zl3vni_vrf_name(zl3vni));
743 	} else {
744 		char vni_str[VNI_STR_LEN];
745 
746 		snprintf(vni_str, VNI_STR_LEN, "%u", zl3vni->vni);
747 		json_evpn = json_object_new_object();
748 		json_object_int_add(json_evpn, "vni", zl3vni->vni);
749 		json_object_string_add(json_evpn, "vxlanIf",
750 				       zl3vni_vxlan_if_name(zl3vni));
751 		json_object_int_add(json_evpn, "numMacs",
752 				    hashcount(zl3vni->rmac_table));
753 		json_object_int_add(json_evpn, "numArpNd",
754 				    hashcount(zl3vni->nh_table));
755 		json_object_string_add(json_evpn, "numRemoteVteps", "n/a");
756 		json_object_string_add(json_evpn, "type", "L3");
757 		json_object_string_add(json_evpn, "tenantVrf",
758 				       zl3vni_vrf_name(zl3vni));
759 		json_object_object_add(json, vni_str, json_evpn);
760 	}
761 }
762 
763 /* print a L3 VNI hash entry in detail*/
zl3vni_print_hash_detail(struct hash_bucket * bucket,void * data)764 static void zl3vni_print_hash_detail(struct hash_bucket *bucket, void *data)
765 {
766 	struct vty *vty = NULL;
767 	zebra_l3vni_t *zl3vni = NULL;
768 	json_object *json_array = NULL;
769 	bool use_json = false;
770 	struct zebra_evpn_show *zes = data;
771 
772 	vty = zes->vty;
773 	json_array = zes->json;
774 	use_json = zes->use_json;
775 
776 	zl3vni = (zebra_l3vni_t *)bucket->data;
777 
778 	zebra_vxlan_print_vni(vty, zes->zvrf, zl3vni->vni,
779 		use_json, json_array);
780 
781 	if (!use_json)
782 		vty_out(vty, "\n");
783 }
784 
zvni_map_to_svi_ns(struct ns * ns,void * _in_param,void ** _p_ifp)785 static int zvni_map_to_svi_ns(struct ns *ns,
786 			      void *_in_param,
787 			      void **_p_ifp)
788 {
789 	struct zebra_ns *zns = ns->info;
790 	struct route_node *rn;
791 	struct zebra_from_svi_param *in_param =
792 		(struct zebra_from_svi_param *)_in_param;
793 	struct zebra_l2info_vlan *vl;
794 	struct interface *tmp_if = NULL;
795 	struct interface **p_ifp = (struct interface **)_p_ifp;
796 	struct zebra_if *zif;
797 
798 	if (!in_param)
799 		return NS_WALK_STOP;
800 
801 	/* TODO: Optimize with a hash. */
802 	for (rn = route_top(zns->if_table); rn; rn = route_next(rn)) {
803 		tmp_if = (struct interface *)rn->info;
804 		/* Check oper status of the SVI. */
805 		if (!tmp_if || !if_is_operative(tmp_if))
806 			continue;
807 		zif = tmp_if->info;
808 		if (!zif || zif->zif_type != ZEBRA_IF_VLAN
809 		    || zif->link != in_param->br_if)
810 			continue;
811 		vl = (struct zebra_l2info_vlan *)&zif->l2info.vl;
812 
813 		if (vl->vid == in_param->vid) {
814 			if (p_ifp)
815 				*p_ifp = tmp_if;
816 			return NS_WALK_STOP;
817 		}
818 	}
819 	return NS_WALK_CONTINUE;
820 }
821 
822 /* Map to SVI on bridge corresponding to specified VLAN. This can be one
823  * of two cases:
824  * (a) In the case of a VLAN-aware bridge, the SVI is a L3 VLAN interface
825  * linked to the bridge
826  * (b) In the case of a VLAN-unaware bridge, the SVI is the bridge interface
827  * itself
828  */
zvni_map_to_svi(vlanid_t vid,struct interface * br_if)829 struct interface *zvni_map_to_svi(vlanid_t vid, struct interface *br_if)
830 {
831 	struct interface *tmp_if = NULL;
832 	struct zebra_if *zif;
833 	struct zebra_l2info_bridge *br;
834 	struct zebra_from_svi_param in_param;
835 	struct interface **p_ifp;
836 	/* Defensive check, caller expected to invoke only with valid bridge. */
837 	if (!br_if)
838 		return NULL;
839 
840 	/* Determine if bridge is VLAN-aware or not */
841 	zif = br_if->info;
842 	assert(zif);
843 	br = &zif->l2info.br;
844 	in_param.bridge_vlan_aware = br->vlan_aware;
845 	/* Check oper status of the SVI. */
846 	if (!in_param.bridge_vlan_aware)
847 		return if_is_operative(br_if) ? br_if : NULL;
848 
849 	in_param.vid = vid;
850 	in_param.br_if = br_if;
851 	in_param.zif = NULL;
852 	p_ifp = &tmp_if;
853 	/* Identify corresponding VLAN interface. */
854 	ns_walk_func(zvni_map_to_svi_ns, (void *)&in_param,
855 		     (void **)p_ifp);
856 	return tmp_if;
857 }
858 
zebra_evpn_vxlan_del(zebra_evpn_t * zevpn)859 static int zebra_evpn_vxlan_del(zebra_evpn_t *zevpn)
860 {
861 	zevpn_vxlan_if_set(zevpn, zevpn->vxlan_if, false /* set */);
862 
863 	/* Remove references to the BUM mcast grp */
864 	zebra_vxlan_sg_deref(zevpn->local_vtep_ip, zevpn->mcast_grp);
865 
866 	return zebra_evpn_del(zevpn);
867 }
868 
zevpn_build_hash_table_zns(struct ns * ns,void * param_in,void ** param_out)869 static int zevpn_build_hash_table_zns(struct ns *ns,
870 				     void *param_in __attribute__((unused)),
871 				     void **param_out __attribute__((unused)))
872 {
873 	struct zebra_ns *zns = ns->info;
874 	struct route_node *rn;
875 	struct interface *ifp;
876 	struct zebra_vrf *zvrf;
877 
878 	zvrf = zebra_vrf_get_evpn();
879 
880 	if (!zvrf)
881 		return NS_WALK_STOP;
882 
883 	/* Walk VxLAN interfaces and create EVPN hash. */
884 	for (rn = route_top(zns->if_table); rn; rn = route_next(rn)) {
885 		vni_t vni;
886 		zebra_evpn_t *zevpn = NULL;
887 		zebra_l3vni_t *zl3vni = NULL;
888 		struct zebra_if *zif;
889 		struct zebra_l2info_vxlan *vxl;
890 
891 		ifp = (struct interface *)rn->info;
892 		if (!ifp)
893 			continue;
894 		zif = ifp->info;
895 		if (!zif || zif->zif_type != ZEBRA_IF_VXLAN)
896 			continue;
897 
898 		vxl = &zif->l2info.vxl;
899 		vni = vxl->vni;
900 		/* link of VXLAN interface should be in zebra_evpn_vrf */
901 		if (zvrf->zns->ns_id != vxl->link_nsid) {
902 			if (IS_ZEBRA_DEBUG_VXLAN)
903 				zlog_debug(
904 					"Intf %s(%u) VNI %u, link not in same "
905 					"namespace than BGP EVPN core instance ",
906 					ifp->name, ifp->ifindex, vni);
907 			continue;
908 		}
909 		/* L3-VNI and L2-VNI are handled seperately */
910 		zl3vni = zl3vni_lookup(vni);
911 		if (zl3vni) {
912 
913 			if (IS_ZEBRA_DEBUG_VXLAN)
914 				zlog_debug(
915 					"create L3-VNI hash for Intf %s(%u) L3-VNI %u",
916 					ifp->name, ifp->ifindex, vni);
917 
918 			/* associate with vxlan_if */
919 			zl3vni->local_vtep_ip = vxl->vtep_ip;
920 			zl3vni->vxlan_if = ifp;
921 
922 			/*
923 			 * we need to associate with SVI.
924 			 * we can associate with svi-if only after association
925 			 * with vxlan-intf is complete
926 			 */
927 			zl3vni->svi_if = zl3vni_map_to_svi_if(zl3vni);
928 
929 			/* Associate l3vni to mac-vlan and extract VRR MAC */
930 			zl3vni->mac_vlan_if = zl3vni_map_to_mac_vlan_if(zl3vni);
931 
932 			if (IS_ZEBRA_DEBUG_VXLAN)
933 				zlog_debug("create l3vni %u svi_if %s mac_vlan_if %s",
934 				   vni, zl3vni->svi_if ? zl3vni->svi_if->name
935 				   : "NIL",
936 				   zl3vni->mac_vlan_if ?
937 				   zl3vni->mac_vlan_if->name : "NIL");
938 
939 			if (is_l3vni_oper_up(zl3vni))
940 				zebra_vxlan_process_l3vni_oper_up(zl3vni);
941 
942 		} else {
943 			struct interface *vlan_if = NULL;
944 
945 			if (IS_ZEBRA_DEBUG_VXLAN)
946 				zlog_debug(
947 					"Create L2-VNI hash for intf %s(%u) L2-VNI %u local IP %s",
948 					ifp->name, ifp->ifindex, vni,
949 					inet_ntoa(vxl->vtep_ip));
950 
951 			/* EVPN hash entry is expected to exist, if the BGP process is killed */
952 			zevpn = zebra_evpn_lookup(vni);
953 			if (zevpn) {
954 				zlog_debug(
955 					"EVPN hash already present for IF %s(%u) L2-VNI %u",
956 					ifp->name, ifp->ifindex, vni);
957 
958 				/*
959 				 * Inform BGP if intf is up and mapped to
960 				 * bridge.
961 				 */
962 				if (if_is_operative(ifp) &&
963 					zif->brslave_info.br_if)
964 					zebra_evpn_send_add_to_client(zevpn);
965 
966 				/* Send Local MAC-entries to client */
967 				zebra_evpn_send_mac_list_to_client(zevpn);
968 
969 				/* Send Loval Neighbor entries to client */
970 				zebra_evpn_send_neigh_to_client(zevpn);
971 			} else {
972 				zevpn = zebra_evpn_add(vni);
973 				if (!zevpn) {
974 					zlog_debug(
975 						"Failed to add EVPN hash, IF %s(%u) L2-VNI %u",
976 						ifp->name, ifp->ifindex, vni);
977 					return NS_WALK_CONTINUE;
978 				}
979 
980 				if (zevpn->local_vtep_ip.s_addr !=
981 					vxl->vtep_ip.s_addr ||
982 					zevpn->mcast_grp.s_addr !=
983 					vxl->mcast_grp.s_addr) {
984 					zebra_vxlan_sg_deref(
985 						zevpn->local_vtep_ip,
986 						zevpn->mcast_grp);
987 					zebra_vxlan_sg_ref(vxl->vtep_ip,
988 						vxl->mcast_grp);
989 					zevpn->local_vtep_ip = vxl->vtep_ip;
990 					zevpn->mcast_grp = vxl->mcast_grp;
991 					/* on local vtep-ip check if ES
992 					 * orig-ip needs to be updated
993 					 */
994 					zebra_evpn_es_set_base_evpn(zevpn);
995 				}
996 				zevpn_vxlan_if_set(zevpn, ifp, true /* set */);
997 				vlan_if = zvni_map_to_svi(
998 					vxl->access_vlan,
999 					zif->brslave_info.br_if);
1000 				if (vlan_if) {
1001 					zevpn->vrf_id = vlan_if->vrf_id;
1002 					zl3vni = zl3vni_from_vrf(
1003 							vlan_if->vrf_id);
1004 					if (zl3vni)
1005 						listnode_add_sort(
1006 							zl3vni->l2vnis, zevpn);
1007 				}
1008 
1009 				/*
1010 				 * Inform BGP if intf is up and mapped to
1011 				 * bridge.
1012 				 */
1013 				if (if_is_operative(ifp) &&
1014 					zif->brslave_info.br_if)
1015 					zebra_evpn_send_add_to_client(zevpn);
1016 			}
1017 		}
1018 	}
1019 	return NS_WALK_CONTINUE;
1020 }
1021 
1022 /*
1023  * Build the VNI hash table by going over the VxLAN interfaces. This
1024  * is called when EVPN (advertise-all-vni) is enabled.
1025  */
1026 
zevpn_build_hash_table(void)1027 static void zevpn_build_hash_table(void)
1028 {
1029 	ns_walk_func(zevpn_build_hash_table_zns,
1030 		     (void *)NULL,
1031 		     (void **)NULL);
1032 }
1033 
1034 /*
1035  * Cleanup EVPN/VTEP and update kernel
1036  */
zebra_evpn_vxlan_cleanup_all(struct hash_bucket * bucket,void * arg)1037 static void zebra_evpn_vxlan_cleanup_all(struct hash_bucket *bucket, void *arg)
1038 {
1039 	zebra_evpn_t *zevpn = NULL;
1040 	zebra_l3vni_t *zl3vni = NULL;
1041 	struct zebra_vrf *zvrf = (struct zebra_vrf *)arg;
1042 
1043 	zevpn = (zebra_evpn_t *)bucket->data;
1044 
1045 	/* remove from l3-vni list */
1046 	if (zvrf->l3vni)
1047 		zl3vni = zl3vni_lookup(zvrf->l3vni);
1048 	if (zl3vni)
1049 		listnode_delete(zl3vni->l2vnis, zevpn);
1050 
1051 	zebra_evpn_cleanup_all(bucket, arg);
1052 }
1053 
1054 /* cleanup L3VNI */
zl3vni_cleanup_all(struct hash_bucket * bucket,void * args)1055 static void zl3vni_cleanup_all(struct hash_bucket *bucket, void *args)
1056 {
1057 	zebra_l3vni_t *zl3vni = NULL;
1058 
1059 	zl3vni = (zebra_l3vni_t *)bucket->data;
1060 
1061 	zebra_vxlan_process_l3vni_oper_down(zl3vni);
1062 }
1063 
rb_find_or_add_host(struct host_rb_tree_entry * hrbe,const struct prefix * host)1064 static void rb_find_or_add_host(struct host_rb_tree_entry *hrbe,
1065 				const struct prefix *host)
1066 {
1067 	struct host_rb_entry lookup;
1068 	struct host_rb_entry *hle;
1069 
1070 	memset(&lookup, 0, sizeof(lookup));
1071 	memcpy(&lookup.p, host, sizeof(*host));
1072 
1073 	hle = RB_FIND(host_rb_tree_entry, hrbe, &lookup);
1074 	if (hle)
1075 		return;
1076 
1077 	hle = XCALLOC(MTYPE_HOST_PREFIX, sizeof(struct host_rb_entry));
1078 	memcpy(hle, &lookup, sizeof(lookup));
1079 
1080 	RB_INSERT(host_rb_tree_entry, hrbe, hle);
1081 }
1082 
rb_delete_host(struct host_rb_tree_entry * hrbe,struct prefix * host)1083 static void rb_delete_host(struct host_rb_tree_entry *hrbe, struct prefix *host)
1084 {
1085 	struct host_rb_entry lookup;
1086 	struct host_rb_entry *hle;
1087 
1088 	memset(&lookup, 0, sizeof(lookup));
1089 	memcpy(&lookup.p, host, sizeof(*host));
1090 
1091 	hle = RB_FIND(host_rb_tree_entry, hrbe, &lookup);
1092 	if (hle) {
1093 		RB_REMOVE(host_rb_tree_entry, hrbe, hle);
1094 		XFREE(MTYPE_HOST_PREFIX, hle);
1095 	}
1096 
1097 	return;
1098 }
1099 
1100 /*
1101  * Look up MAC hash entry.
1102  */
zl3vni_rmac_lookup(zebra_l3vni_t * zl3vni,const struct ethaddr * rmac)1103 static zebra_mac_t *zl3vni_rmac_lookup(zebra_l3vni_t *zl3vni,
1104 				       const struct ethaddr *rmac)
1105 {
1106 	zebra_mac_t tmp;
1107 	zebra_mac_t *pmac;
1108 
1109 	memset(&tmp, 0, sizeof(tmp));
1110 	memcpy(&tmp.macaddr, rmac, ETH_ALEN);
1111 	pmac = hash_lookup(zl3vni->rmac_table, &tmp);
1112 
1113 	return pmac;
1114 }
1115 
1116 /*
1117  * Callback to allocate RMAC hash entry.
1118  */
zl3vni_rmac_alloc(void * p)1119 static void *zl3vni_rmac_alloc(void *p)
1120 {
1121 	const zebra_mac_t *tmp_rmac = p;
1122 	zebra_mac_t *zrmac;
1123 
1124 	zrmac = XCALLOC(MTYPE_L3VNI_MAC, sizeof(zebra_mac_t));
1125 	*zrmac = *tmp_rmac;
1126 
1127 	return ((void *)zrmac);
1128 }
1129 
1130 /*
1131  * Add RMAC entry to l3-vni
1132  */
zl3vni_rmac_add(zebra_l3vni_t * zl3vni,const struct ethaddr * rmac)1133 static zebra_mac_t *zl3vni_rmac_add(zebra_l3vni_t *zl3vni,
1134 				    const struct ethaddr *rmac)
1135 {
1136 	zebra_mac_t tmp_rmac;
1137 	zebra_mac_t *zrmac = NULL;
1138 
1139 	memset(&tmp_rmac, 0, sizeof(zebra_mac_t));
1140 	memcpy(&tmp_rmac.macaddr, rmac, ETH_ALEN);
1141 	zrmac = hash_get(zl3vni->rmac_table, &tmp_rmac, zl3vni_rmac_alloc);
1142 	assert(zrmac);
1143 
1144 	RB_INIT(host_rb_tree_entry, &zrmac->host_rb);
1145 
1146 	SET_FLAG(zrmac->flags, ZEBRA_MAC_REMOTE);
1147 	SET_FLAG(zrmac->flags, ZEBRA_MAC_REMOTE_RMAC);
1148 
1149 	return zrmac;
1150 }
1151 
1152 /*
1153  * Delete MAC entry.
1154  */
zl3vni_rmac_del(zebra_l3vni_t * zl3vni,zebra_mac_t * zrmac)1155 static int zl3vni_rmac_del(zebra_l3vni_t *zl3vni, zebra_mac_t *zrmac)
1156 {
1157 	zebra_mac_t *tmp_rmac;
1158 	struct host_rb_entry *hle;
1159 
1160 	while (!RB_EMPTY(host_rb_tree_entry, &zrmac->host_rb)) {
1161 		hle = RB_ROOT(host_rb_tree_entry, &zrmac->host_rb);
1162 
1163 		RB_REMOVE(host_rb_tree_entry, &zrmac->host_rb, hle);
1164 		XFREE(MTYPE_HOST_PREFIX, hle);
1165 	}
1166 
1167 	tmp_rmac = hash_release(zl3vni->rmac_table, zrmac);
1168 	XFREE(MTYPE_L3VNI_MAC, tmp_rmac);
1169 
1170 	return 0;
1171 }
1172 
1173 /*
1174  * Install remote RMAC into the forwarding plane.
1175  */
zl3vni_rmac_install(zebra_l3vni_t * zl3vni,zebra_mac_t * zrmac)1176 static int zl3vni_rmac_install(zebra_l3vni_t *zl3vni, zebra_mac_t *zrmac)
1177 {
1178 	const struct zebra_if *zif = NULL, *br_zif = NULL;
1179 	const struct zebra_l2info_vxlan *vxl = NULL;
1180 	const struct interface *br_ifp;
1181 	enum zebra_dplane_result res;
1182 	vlanid_t vid;
1183 
1184 	if (!(CHECK_FLAG(zrmac->flags, ZEBRA_MAC_REMOTE))
1185 	    || !(CHECK_FLAG(zrmac->flags, ZEBRA_MAC_REMOTE_RMAC)))
1186 		return 0;
1187 
1188 	zif = zl3vni->vxlan_if->info;
1189 	if (!zif)
1190 		return -1;
1191 
1192 	br_ifp = zif->brslave_info.br_if;
1193 	if (br_ifp == NULL)
1194 		return -1;
1195 
1196 	vxl = &zif->l2info.vxl;
1197 
1198 	br_zif = (const struct zebra_if *)br_ifp->info;
1199 
1200 	if (IS_ZEBRA_IF_BRIDGE_VLAN_AWARE(br_zif))
1201 		vid = vxl->access_vlan;
1202 	else
1203 		vid = 0;
1204 
1205 	res = dplane_rem_mac_add(zl3vni->vxlan_if, br_ifp, vid,
1206 			     &zrmac->macaddr, zrmac->fwd_info.r_vtep_ip, 0, 0,
1207 				 false /*was_static*/);
1208 	if (res != ZEBRA_DPLANE_REQUEST_FAILURE)
1209 		return 0;
1210 	else
1211 		return -1;
1212 }
1213 
1214 /*
1215  * Uninstall remote RMAC from the forwarding plane.
1216  */
zl3vni_rmac_uninstall(zebra_l3vni_t * zl3vni,zebra_mac_t * zrmac)1217 static int zl3vni_rmac_uninstall(zebra_l3vni_t *zl3vni, zebra_mac_t *zrmac)
1218 {
1219 	char buf[ETHER_ADDR_STRLEN];
1220 	const struct zebra_if *zif = NULL, *br_zif;
1221 	const struct zebra_l2info_vxlan *vxl = NULL;
1222 	const struct interface *br_ifp;
1223 	vlanid_t vid;
1224 	enum zebra_dplane_result res;
1225 
1226 	if (!(CHECK_FLAG(zrmac->flags, ZEBRA_MAC_REMOTE))
1227 	    || !(CHECK_FLAG(zrmac->flags, ZEBRA_MAC_REMOTE_RMAC)))
1228 		return 0;
1229 
1230 	if (!zl3vni->vxlan_if) {
1231 		if (IS_ZEBRA_DEBUG_VXLAN)
1232 			zlog_debug(
1233 				"RMAC %s on L3-VNI %u hash %p couldn't be uninstalled - no vxlan_if",
1234 				prefix_mac2str(&zrmac->macaddr,
1235 					       buf, sizeof(buf)),
1236 				zl3vni->vni, zl3vni);
1237 		return -1;
1238 	}
1239 
1240 	zif = zl3vni->vxlan_if->info;
1241 	if (!zif)
1242 		return -1;
1243 
1244 	br_ifp = zif->brslave_info.br_if;
1245 	if (br_ifp == NULL)
1246 		return -1;
1247 
1248 	vxl = &zif->l2info.vxl;
1249 
1250 	br_zif = (const struct zebra_if *)br_ifp->info;
1251 	if (IS_ZEBRA_IF_BRIDGE_VLAN_AWARE(br_zif))
1252 		vid = vxl->access_vlan;
1253 	else
1254 		vid = 0;
1255 
1256 	res = dplane_rem_mac_del(zl3vni->vxlan_if, br_ifp, vid,
1257 			     &zrmac->macaddr, zrmac->fwd_info.r_vtep_ip);
1258 	if (res != ZEBRA_DPLANE_REQUEST_FAILURE)
1259 		return 0;
1260 	else
1261 		return -1;
1262 }
1263 
1264 /* handle rmac add */
zl3vni_remote_rmac_add(zebra_l3vni_t * zl3vni,const struct ethaddr * rmac,const struct ipaddr * vtep_ip,const struct prefix * host_prefix)1265 static int zl3vni_remote_rmac_add(zebra_l3vni_t *zl3vni,
1266 				  const struct ethaddr *rmac,
1267 				  const struct ipaddr *vtep_ip,
1268 				  const struct prefix *host_prefix)
1269 {
1270 	char buf[ETHER_ADDR_STRLEN];
1271 	char buf1[INET6_ADDRSTRLEN];
1272 	char buf2[PREFIX_STRLEN];
1273 	zebra_mac_t *zrmac = NULL;
1274 
1275 	zrmac = zl3vni_rmac_lookup(zl3vni, rmac);
1276 	if (!zrmac) {
1277 
1278 		 /* Create the RMAC entry, or update its vtep, if necessary. */
1279 		zrmac = zl3vni_rmac_add(zl3vni, rmac);
1280 		if (!zrmac) {
1281 			zlog_debug(
1282 				"Failed to add RMAC %s L3VNI %u Remote VTEP %s, prefix %s",
1283 				prefix_mac2str(rmac, buf, sizeof(buf)),
1284 				zl3vni->vni,
1285 				ipaddr2str(vtep_ip, buf1, sizeof(buf1)),
1286 				prefix2str(host_prefix, buf2, sizeof(buf2)));
1287 			return -1;
1288 		}
1289 		memset(&zrmac->fwd_info, 0, sizeof(zrmac->fwd_info));
1290 		zrmac->fwd_info.r_vtep_ip = vtep_ip->ipaddr_v4;
1291 
1292 		/* Send RMAC for FPM processing */
1293 		hook_call(zebra_rmac_update, zrmac, zl3vni, false,
1294 			  "new RMAC added");
1295 
1296 		/* install rmac in kernel */
1297 		zl3vni_rmac_install(zl3vni, zrmac);
1298 	} else if (!IPV4_ADDR_SAME(&zrmac->fwd_info.r_vtep_ip,
1299 				   &vtep_ip->ipaddr_v4)) {
1300 		if (IS_ZEBRA_DEBUG_VXLAN)
1301 			zlog_debug(
1302 				"L3VNI %u Remote VTEP change(%s -> %s) for RMAC %s, prefix %s",
1303 				zl3vni->vni,
1304 				inet_ntoa(zrmac->fwd_info.r_vtep_ip),
1305 				ipaddr2str(vtep_ip, buf1, sizeof(buf1)),
1306 				prefix_mac2str(rmac, buf, sizeof(buf)),
1307 				prefix2str(host_prefix, buf2, sizeof(buf2)));
1308 
1309 		zrmac->fwd_info.r_vtep_ip = vtep_ip->ipaddr_v4;
1310 
1311 		/* install rmac in kernel */
1312 		zl3vni_rmac_install(zl3vni, zrmac);
1313 	}
1314 
1315 	rb_find_or_add_host(&zrmac->host_rb, host_prefix);
1316 
1317 	return 0;
1318 }
1319 
1320 
1321 /* handle rmac delete */
zl3vni_remote_rmac_del(zebra_l3vni_t * zl3vni,zebra_mac_t * zrmac,struct prefix * host_prefix)1322 static void zl3vni_remote_rmac_del(zebra_l3vni_t *zl3vni, zebra_mac_t *zrmac,
1323 				  struct prefix *host_prefix)
1324 {
1325 	rb_delete_host(&zrmac->host_rb, host_prefix);
1326 
1327 	if (RB_EMPTY(host_rb_tree_entry, &zrmac->host_rb)) {
1328 		/* uninstall from kernel */
1329 		zl3vni_rmac_uninstall(zl3vni, zrmac);
1330 
1331 		/* Send RMAC for FPM processing */
1332 		hook_call(zebra_rmac_update, zrmac, zl3vni, true,
1333 			  "RMAC deleted");
1334 
1335 		/* del the rmac entry */
1336 		zl3vni_rmac_del(zl3vni, zrmac);
1337 	}
1338 }
1339 
1340 /*
1341  * Look up nh hash entry on a l3-vni.
1342  */
zl3vni_nh_lookup(zebra_l3vni_t * zl3vni,const struct ipaddr * ip)1343 static zebra_neigh_t *zl3vni_nh_lookup(zebra_l3vni_t *zl3vni,
1344 				       const struct ipaddr *ip)
1345 {
1346 	zebra_neigh_t tmp;
1347 	zebra_neigh_t *n;
1348 
1349 	memset(&tmp, 0, sizeof(tmp));
1350 	memcpy(&tmp.ip, ip, sizeof(struct ipaddr));
1351 	n = hash_lookup(zl3vni->nh_table, &tmp);
1352 
1353 	return n;
1354 }
1355 
1356 
1357 /*
1358  * Callback to allocate NH hash entry on L3-VNI.
1359  */
zl3vni_nh_alloc(void * p)1360 static void *zl3vni_nh_alloc(void *p)
1361 {
1362 	const zebra_neigh_t *tmp_n = p;
1363 	zebra_neigh_t *n;
1364 
1365 	n = XCALLOC(MTYPE_L3NEIGH, sizeof(zebra_neigh_t));
1366 	*n = *tmp_n;
1367 
1368 	return ((void *)n);
1369 }
1370 
1371 /*
1372  * Add neighbor entry.
1373  */
zl3vni_nh_add(zebra_l3vni_t * zl3vni,const struct ipaddr * ip,const struct ethaddr * mac)1374 static zebra_neigh_t *zl3vni_nh_add(zebra_l3vni_t *zl3vni,
1375 				    const struct ipaddr *ip,
1376 				    const struct ethaddr *mac)
1377 {
1378 	zebra_neigh_t tmp_n;
1379 	zebra_neigh_t *n = NULL;
1380 
1381 	memset(&tmp_n, 0, sizeof(zebra_neigh_t));
1382 	memcpy(&tmp_n.ip, ip, sizeof(struct ipaddr));
1383 	n = hash_get(zl3vni->nh_table, &tmp_n, zl3vni_nh_alloc);
1384 	assert(n);
1385 
1386 	RB_INIT(host_rb_tree_entry, &n->host_rb);
1387 
1388 	memcpy(&n->emac, mac, ETH_ALEN);
1389 	SET_FLAG(n->flags, ZEBRA_NEIGH_REMOTE);
1390 	SET_FLAG(n->flags, ZEBRA_NEIGH_REMOTE_NH);
1391 
1392 	return n;
1393 }
1394 
1395 /*
1396  * Delete neighbor entry.
1397  */
zl3vni_nh_del(zebra_l3vni_t * zl3vni,zebra_neigh_t * n)1398 static int zl3vni_nh_del(zebra_l3vni_t *zl3vni, zebra_neigh_t *n)
1399 {
1400 	zebra_neigh_t *tmp_n;
1401 	struct host_rb_entry *hle;
1402 
1403 	while (!RB_EMPTY(host_rb_tree_entry, &n->host_rb)) {
1404 		hle = RB_ROOT(host_rb_tree_entry, &n->host_rb);
1405 
1406 		RB_REMOVE(host_rb_tree_entry, &n->host_rb, hle);
1407 		XFREE(MTYPE_HOST_PREFIX, hle);
1408 	}
1409 
1410 	tmp_n = hash_release(zl3vni->nh_table, n);
1411 	XFREE(MTYPE_L3NEIGH, tmp_n);
1412 
1413 	return 0;
1414 }
1415 
1416 /*
1417  * Install remote nh as neigh into the kernel.
1418  */
zl3vni_nh_install(zebra_l3vni_t * zl3vni,zebra_neigh_t * n)1419 static int zl3vni_nh_install(zebra_l3vni_t *zl3vni, zebra_neigh_t *n)
1420 {
1421 	uint8_t flags;
1422 	int ret = 0;
1423 
1424 	if (!is_l3vni_oper_up(zl3vni))
1425 		return -1;
1426 
1427 	if (!(n->flags & ZEBRA_NEIGH_REMOTE)
1428 	    || !(n->flags & ZEBRA_NEIGH_REMOTE_NH))
1429 		return 0;
1430 
1431 	flags = DPLANE_NTF_EXT_LEARNED;
1432 	if (n->flags & ZEBRA_NEIGH_ROUTER_FLAG)
1433 		flags |= DPLANE_NTF_ROUTER;
1434 
1435 	dplane_rem_neigh_add(zl3vni->svi_if, &n->ip, &n->emac, flags,
1436 			false /*was_static*/);
1437 
1438 	return ret;
1439 }
1440 
1441 /*
1442  * Uninstall remote nh from the kernel.
1443  */
zl3vni_nh_uninstall(zebra_l3vni_t * zl3vni,zebra_neigh_t * n)1444 static int zl3vni_nh_uninstall(zebra_l3vni_t *zl3vni, zebra_neigh_t *n)
1445 {
1446 	if (!(n->flags & ZEBRA_NEIGH_REMOTE)
1447 	    || !(n->flags & ZEBRA_NEIGH_REMOTE_NH))
1448 		return 0;
1449 
1450 	if (!zl3vni->svi_if || !if_is_operative(zl3vni->svi_if))
1451 		return 0;
1452 
1453 	dplane_rem_neigh_delete(zl3vni->svi_if, &n->ip);
1454 
1455 	return 0;
1456 }
1457 
1458 /* add remote vtep as a neigh entry */
zl3vni_remote_nh_add(zebra_l3vni_t * zl3vni,const struct ipaddr * vtep_ip,const struct ethaddr * rmac,const struct prefix * host_prefix)1459 static int zl3vni_remote_nh_add(zebra_l3vni_t *zl3vni,
1460 				const struct ipaddr *vtep_ip,
1461 				const struct ethaddr *rmac,
1462 				const struct prefix *host_prefix)
1463 {
1464 	char buf[ETHER_ADDR_STRLEN];
1465 	char buf1[ETHER_ADDR_STRLEN];
1466 	char buf2[INET6_ADDRSTRLEN];
1467 	char buf3[PREFIX_STRLEN];
1468 	zebra_neigh_t *nh = NULL;
1469 
1470 	/* Create the next hop entry, or update its mac, if necessary. */
1471 	nh = zl3vni_nh_lookup(zl3vni, vtep_ip);
1472 	if (!nh) {
1473 		nh = zl3vni_nh_add(zl3vni, vtep_ip, rmac);
1474 		if (!nh) {
1475 			zlog_debug(
1476 				"Failed to add NH %s as Neigh (RMAC %s L3-VNI %u prefix %s)",
1477 				ipaddr2str(vtep_ip, buf1, sizeof(buf2)),
1478 				prefix_mac2str(rmac, buf, sizeof(buf)),
1479 				zl3vni->vni,
1480 				prefix2str(host_prefix, buf2, sizeof(buf2)));
1481 			return -1;
1482 		}
1483 
1484 		/* install the nh neigh in kernel */
1485 		zl3vni_nh_install(zl3vni, nh);
1486 	} else if (memcmp(&nh->emac, rmac, ETH_ALEN) != 0) {
1487 		if (IS_ZEBRA_DEBUG_VXLAN)
1488 			zlog_debug("L3VNI %u RMAC change(%s --> %s) for nexthop %s, prefix %s",
1489 				   zl3vni->vni,
1490 				   prefix_mac2str(&nh->emac, buf, sizeof(buf)),
1491 				   prefix_mac2str(rmac, buf1, sizeof(buf1)),
1492 				   ipaddr2str(vtep_ip, buf2, sizeof(buf2)),
1493 				   prefix2str(host_prefix, buf3, sizeof(buf3)));
1494 
1495 		memcpy(&nh->emac, rmac, ETH_ALEN);
1496 		/* install (update) the nh neigh in kernel */
1497 		zl3vni_nh_install(zl3vni, nh);
1498 	}
1499 
1500 	rb_find_or_add_host(&nh->host_rb, host_prefix);
1501 
1502 	return 0;
1503 }
1504 
1505 /* handle nh neigh delete */
zl3vni_remote_nh_del(zebra_l3vni_t * zl3vni,zebra_neigh_t * nh,struct prefix * host_prefix)1506 static void zl3vni_remote_nh_del(zebra_l3vni_t *zl3vni, zebra_neigh_t *nh,
1507 				 struct prefix *host_prefix)
1508 {
1509 	rb_delete_host(&nh->host_rb, host_prefix);
1510 
1511 	if (RB_EMPTY(host_rb_tree_entry, &nh->host_rb)) {
1512 		/* uninstall from kernel */
1513 		zl3vni_nh_uninstall(zl3vni, nh);
1514 
1515 		/* delete the nh entry */
1516 		zl3vni_nh_del(zl3vni, nh);
1517 	}
1518 }
1519 
1520 /* handle neigh update from kernel - the only thing of interest is to
1521  * readd stale entries.
1522  */
zl3vni_local_nh_add_update(zebra_l3vni_t * zl3vni,struct ipaddr * ip,uint16_t state)1523 static int zl3vni_local_nh_add_update(zebra_l3vni_t *zl3vni, struct ipaddr *ip,
1524 				      uint16_t state)
1525 {
1526 #ifdef GNU_LINUX
1527 	zebra_neigh_t *n = NULL;
1528 
1529 	n = zl3vni_nh_lookup(zl3vni, ip);
1530 	if (!n)
1531 		return 0;
1532 
1533 	/* all next hop neigh are remote and installed by frr.
1534 	 * If the kernel has aged this entry, re-install.
1535 	 */
1536 	if (state & NUD_STALE)
1537 		zl3vni_nh_install(zl3vni, n);
1538 #endif
1539 	return 0;
1540 }
1541 
1542 /* handle neigh delete from kernel */
zl3vni_local_nh_del(zebra_l3vni_t * zl3vni,struct ipaddr * ip)1543 static int zl3vni_local_nh_del(zebra_l3vni_t *zl3vni, struct ipaddr *ip)
1544 {
1545 	zebra_neigh_t *n = NULL;
1546 
1547 	n = zl3vni_nh_lookup(zl3vni, ip);
1548 	if (!n)
1549 		return 0;
1550 
1551 	/* all next hop neigh are remote and installed by frr.
1552 	 * If we get an age out notification for these neigh entries, we have to
1553 	 * install it back
1554 	 */
1555 	zl3vni_nh_install(zl3vni, n);
1556 
1557 	return 0;
1558 }
1559 
1560 /*
1561  * Hash function for L3 VNI.
1562  */
l3vni_hash_keymake(const void * p)1563 static unsigned int l3vni_hash_keymake(const void *p)
1564 {
1565 	const zebra_l3vni_t *zl3vni = p;
1566 
1567 	return jhash_1word(zl3vni->vni, 0);
1568 }
1569 
1570 /*
1571  * Compare 2 L3 VNI hash entries.
1572  */
l3vni_hash_cmp(const void * p1,const void * p2)1573 static bool l3vni_hash_cmp(const void *p1, const void *p2)
1574 {
1575 	const zebra_l3vni_t *zl3vni1 = p1;
1576 	const zebra_l3vni_t *zl3vni2 = p2;
1577 
1578 	return (zl3vni1->vni == zl3vni2->vni);
1579 }
1580 
1581 /*
1582  * Callback to allocate L3 VNI hash entry.
1583  */
zl3vni_alloc(void * p)1584 static void *zl3vni_alloc(void *p)
1585 {
1586 	zebra_l3vni_t *zl3vni = NULL;
1587 	const zebra_l3vni_t *tmp_l3vni = p;
1588 
1589 	zl3vni = XCALLOC(MTYPE_ZL3VNI, sizeof(zebra_l3vni_t));
1590 	zl3vni->vni = tmp_l3vni->vni;
1591 	return ((void *)zl3vni);
1592 }
1593 
1594 /*
1595  * Look up L3 VNI hash entry.
1596  */
zl3vni_lookup(vni_t vni)1597 zebra_l3vni_t *zl3vni_lookup(vni_t vni)
1598 {
1599 	zebra_l3vni_t tmp_l3vni;
1600 	zebra_l3vni_t *zl3vni = NULL;
1601 
1602 	memset(&tmp_l3vni, 0, sizeof(zebra_l3vni_t));
1603 	tmp_l3vni.vni = vni;
1604 	zl3vni = hash_lookup(zrouter.l3vni_table, &tmp_l3vni);
1605 
1606 	return zl3vni;
1607 }
1608 
1609 /*
1610  * Add L3 VNI hash entry.
1611  */
zl3vni_add(vni_t vni,vrf_id_t vrf_id)1612 static zebra_l3vni_t *zl3vni_add(vni_t vni, vrf_id_t vrf_id)
1613 {
1614 	zebra_l3vni_t tmp_zl3vni;
1615 	zebra_l3vni_t *zl3vni = NULL;
1616 
1617 	memset(&tmp_zl3vni, 0, sizeof(zebra_l3vni_t));
1618 	tmp_zl3vni.vni = vni;
1619 
1620 	zl3vni = hash_get(zrouter.l3vni_table, &tmp_zl3vni, zl3vni_alloc);
1621 	assert(zl3vni);
1622 
1623 	zl3vni->vrf_id = vrf_id;
1624 	zl3vni->svi_if = NULL;
1625 	zl3vni->vxlan_if = NULL;
1626 	zl3vni->l2vnis = list_new();
1627 	zl3vni->l2vnis->cmp = zebra_evpn_list_cmp;
1628 
1629 	/* Create hash table for remote RMAC */
1630 	zl3vni->rmac_table = zebra_mac_db_create("Zebra L3-VNI RMAC-Table");
1631 
1632 	/* Create hash table for neighbors */
1633 	zl3vni->nh_table = zebra_neigh_db_create("Zebra L3-VNI next-hop table");
1634 
1635 	return zl3vni;
1636 }
1637 
1638 /*
1639  * Delete L3 VNI hash entry.
1640  */
zl3vni_del(zebra_l3vni_t * zl3vni)1641 static int zl3vni_del(zebra_l3vni_t *zl3vni)
1642 {
1643 	zebra_l3vni_t *tmp_zl3vni;
1644 
1645 	/* free the list of l2vnis */
1646 	list_delete(&zl3vni->l2vnis);
1647 	zl3vni->l2vnis = NULL;
1648 
1649 	/* Free the rmac table */
1650 	hash_free(zl3vni->rmac_table);
1651 	zl3vni->rmac_table = NULL;
1652 
1653 	/* Free the nh table */
1654 	hash_free(zl3vni->nh_table);
1655 	zl3vni->nh_table = NULL;
1656 
1657 	/* Free the VNI hash entry and allocated memory. */
1658 	tmp_zl3vni = hash_release(zrouter.l3vni_table, zl3vni);
1659 	XFREE(MTYPE_ZL3VNI, tmp_zl3vni);
1660 
1661 	return 0;
1662 }
1663 
zl3vni_map_to_vxlan_if_ns(struct ns * ns,void * _zl3vni,void ** _pifp)1664 static int zl3vni_map_to_vxlan_if_ns(struct ns *ns,
1665 				     void *_zl3vni,
1666 				     void **_pifp)
1667 {
1668 	struct zebra_ns *zns = ns->info;
1669 	zebra_l3vni_t *zl3vni = (zebra_l3vni_t *)_zl3vni;
1670 	struct route_node *rn = NULL;
1671 	struct interface *ifp = NULL;
1672 	struct zebra_vrf *zvrf;
1673 
1674 	zvrf = zebra_vrf_get_evpn();
1675 
1676 	if (!zvrf)
1677 		return NS_WALK_STOP;
1678 
1679 	/* loop through all vxlan-interface */
1680 	for (rn = route_top(zns->if_table); rn; rn = route_next(rn)) {
1681 
1682 		struct zebra_if *zif = NULL;
1683 		struct zebra_l2info_vxlan *vxl = NULL;
1684 
1685 		ifp = (struct interface *)rn->info;
1686 		if (!ifp)
1687 			continue;
1688 
1689 		zif = ifp->info;
1690 		if (!zif || zif->zif_type != ZEBRA_IF_VXLAN)
1691 			continue;
1692 
1693 		vxl = &zif->l2info.vxl;
1694 		if (vxl->vni != zl3vni->vni)
1695 			continue;
1696 
1697 		/* link of VXLAN interface should be in zebra_evpn_vrf */
1698 		if (zvrf->zns->ns_id != vxl->link_nsid) {
1699 			if (IS_ZEBRA_DEBUG_VXLAN)
1700 				zlog_debug(
1701 					"Intf %s(%u) VNI %u, link not in same "
1702 					"namespace than BGP EVPN core instance ",
1703 					ifp->name, ifp->ifindex, vxl->vni);
1704 			continue;
1705 		}
1706 
1707 
1708 		zl3vni->local_vtep_ip = vxl->vtep_ip;
1709 		if (_pifp)
1710 			*_pifp = (void *)ifp;
1711 		return NS_WALK_STOP;
1712 	}
1713 
1714 	return NS_WALK_CONTINUE;
1715 }
1716 
zl3vni_map_to_vxlan_if(zebra_l3vni_t * zl3vni)1717 struct interface *zl3vni_map_to_vxlan_if(zebra_l3vni_t *zl3vni)
1718 {
1719 	struct interface **p_ifp;
1720 	struct interface *ifp = NULL;
1721 
1722 	p_ifp = &ifp;
1723 
1724 	ns_walk_func(zl3vni_map_to_vxlan_if_ns,
1725 		     (void *)zl3vni, (void **)p_ifp);
1726 	return ifp;
1727 }
1728 
zl3vni_map_to_svi_if(zebra_l3vni_t * zl3vni)1729 struct interface *zl3vni_map_to_svi_if(zebra_l3vni_t *zl3vni)
1730 {
1731 	struct zebra_if *zif = NULL;	   /* zebra_if for vxlan_if */
1732 	struct zebra_l2info_vxlan *vxl = NULL; /* l2 info for vxlan_if */
1733 
1734 	if (!zl3vni)
1735 		return NULL;
1736 
1737 	if (!zl3vni->vxlan_if)
1738 		return NULL;
1739 
1740 	zif = zl3vni->vxlan_if->info;
1741 	if (!zif)
1742 		return NULL;
1743 
1744 	vxl = &zif->l2info.vxl;
1745 
1746 	return zvni_map_to_svi(vxl->access_vlan, zif->brslave_info.br_if);
1747 }
1748 
zl3vni_map_to_mac_vlan_if(zebra_l3vni_t * zl3vni)1749 struct interface *zl3vni_map_to_mac_vlan_if(zebra_l3vni_t *zl3vni)
1750 {
1751 	struct zebra_if *zif = NULL;	   /* zebra_if for vxlan_if */
1752 
1753 	if (!zl3vni)
1754 		return NULL;
1755 
1756 	if (!zl3vni->vxlan_if)
1757 		return NULL;
1758 
1759 	zif = zl3vni->vxlan_if->info;
1760 	if (!zif)
1761 		return NULL;
1762 
1763 	return zebra_evpn_map_to_macvlan(zif->brslave_info.br_if,
1764 					 zl3vni->svi_if);
1765 }
1766 
1767 
zl3vni_from_vrf(vrf_id_t vrf_id)1768 zebra_l3vni_t *zl3vni_from_vrf(vrf_id_t vrf_id)
1769 {
1770 	struct zebra_vrf *zvrf = NULL;
1771 
1772 	zvrf = zebra_vrf_lookup_by_id(vrf_id);
1773 	if (!zvrf)
1774 		return NULL;
1775 
1776 	return zl3vni_lookup(zvrf->l3vni);
1777 }
1778 
1779 /*
1780  * Map SVI and associated bridge to a VNI. This is invoked upon getting
1781  * neighbor notifications, to see if they are of interest.
1782  */
zl3vni_from_svi(struct interface * ifp,struct interface * br_if)1783 static zebra_l3vni_t *zl3vni_from_svi(struct interface *ifp,
1784 				      struct interface *br_if)
1785 {
1786 	int found = 0;
1787 	vlanid_t vid = 0;
1788 	uint8_t bridge_vlan_aware = 0;
1789 	zebra_l3vni_t *zl3vni = NULL;
1790 	struct zebra_ns *zns = NULL;
1791 	struct route_node *rn = NULL;
1792 	struct zebra_if *zif = NULL;
1793 	struct interface *tmp_if = NULL;
1794 	struct zebra_l2info_bridge *br = NULL;
1795 	struct zebra_l2info_vxlan *vxl = NULL;
1796 
1797 	if (!br_if)
1798 		return NULL;
1799 
1800 	/* Make sure the linked interface is a bridge. */
1801 	if (!IS_ZEBRA_IF_BRIDGE(br_if))
1802 		return NULL;
1803 
1804 	/* Determine if bridge is VLAN-aware or not */
1805 	zif = br_if->info;
1806 	assert(zif);
1807 	br = &zif->l2info.br;
1808 	bridge_vlan_aware = br->vlan_aware;
1809 	if (bridge_vlan_aware) {
1810 		struct zebra_l2info_vlan *vl;
1811 
1812 		if (!IS_ZEBRA_IF_VLAN(ifp))
1813 			return NULL;
1814 
1815 		zif = ifp->info;
1816 		assert(zif);
1817 		vl = &zif->l2info.vl;
1818 		vid = vl->vid;
1819 	}
1820 
1821 	/* See if this interface (or interface plus VLAN Id) maps to a VxLAN */
1822 	/* TODO: Optimize with a hash. */
1823 	zns = zebra_ns_lookup(NS_DEFAULT);
1824 	for (rn = route_top(zns->if_table); rn; rn = route_next(rn)) {
1825 		tmp_if = (struct interface *)rn->info;
1826 		if (!tmp_if)
1827 			continue;
1828 		zif = tmp_if->info;
1829 		if (!zif || zif->zif_type != ZEBRA_IF_VXLAN)
1830 			continue;
1831 		if (!if_is_operative(tmp_if))
1832 			continue;
1833 		vxl = &zif->l2info.vxl;
1834 
1835 		if (zif->brslave_info.br_if != br_if)
1836 			continue;
1837 
1838 		if (!bridge_vlan_aware || vxl->access_vlan == vid) {
1839 			found = 1;
1840 			break;
1841 		}
1842 	}
1843 
1844 	if (!found)
1845 		return NULL;
1846 
1847 	zl3vni = zl3vni_lookup(vxl->vni);
1848 	return zl3vni;
1849 }
1850 
zl3vni_get_vrr_rmac(zebra_l3vni_t * zl3vni,struct ethaddr * rmac)1851 static inline void zl3vni_get_vrr_rmac(zebra_l3vni_t *zl3vni,
1852 				       struct ethaddr *rmac)
1853 {
1854 	if (!zl3vni)
1855 		return;
1856 
1857 	if (!is_l3vni_oper_up(zl3vni))
1858 		return;
1859 
1860 	if (zl3vni->mac_vlan_if && if_is_operative(zl3vni->mac_vlan_if))
1861 		memcpy(rmac->octet, zl3vni->mac_vlan_if->hw_addr, ETH_ALEN);
1862 }
1863 
1864 /*
1865  * Inform BGP about l3-vni.
1866  */
zl3vni_send_add_to_client(zebra_l3vni_t * zl3vni)1867 static int zl3vni_send_add_to_client(zebra_l3vni_t *zl3vni)
1868 {
1869 	struct stream *s = NULL;
1870 	struct zserv *client = NULL;
1871 	struct ethaddr svi_rmac, vrr_rmac = {.octet = {0} };
1872 	struct zebra_vrf *zvrf;
1873 	char buf[ETHER_ADDR_STRLEN];
1874 	char buf1[ETHER_ADDR_STRLEN];
1875 	bool is_anycast_mac = true;
1876 
1877 	client = zserv_find_client(ZEBRA_ROUTE_BGP, 0);
1878 	/* BGP may not be running. */
1879 	if (!client)
1880 		return 0;
1881 
1882 	zvrf = zebra_vrf_lookup_by_id(zl3vni->vrf_id);
1883 	assert(zvrf);
1884 
1885 	/* get the svi and vrr rmac values */
1886 	memset(&svi_rmac, 0, sizeof(struct ethaddr));
1887 	zl3vni_get_svi_rmac(zl3vni, &svi_rmac);
1888 	zl3vni_get_vrr_rmac(zl3vni, &vrr_rmac);
1889 
1890 	/* In absence of vrr mac use svi mac as anycast MAC value */
1891 	if (is_zero_mac(&vrr_rmac)) {
1892 		memcpy(&vrr_rmac, &svi_rmac, ETH_ALEN);
1893 		is_anycast_mac = false;
1894 	}
1895 
1896 	s = stream_new(ZEBRA_MAX_PACKET_SIZ);
1897 
1898 	/* The message is used for both vni add and/or update like
1899 	 * vrr mac is added for l3vni SVI.
1900 	 */
1901 	zclient_create_header(s, ZEBRA_L3VNI_ADD, zl3vni_vrf_id(zl3vni));
1902 	stream_putl(s, zl3vni->vni);
1903 	stream_put(s, &svi_rmac, sizeof(struct ethaddr));
1904 	stream_put_in_addr(s, &zl3vni->local_vtep_ip);
1905 	stream_put(s, &zl3vni->filter, sizeof(int));
1906 	stream_putl(s, zl3vni->svi_if->ifindex);
1907 	stream_put(s, &vrr_rmac, sizeof(struct ethaddr));
1908 	stream_putl(s, is_anycast_mac);
1909 
1910 	/* Write packet size. */
1911 	stream_putw_at(s, 0, stream_get_endp(s));
1912 
1913 	if (IS_ZEBRA_DEBUG_VXLAN)
1914 		zlog_debug(
1915 			"Send L3_VNI_ADD %u VRF %s RMAC %s VRR %s local-ip %s filter %s to %s",
1916 			zl3vni->vni, vrf_id_to_name(zl3vni_vrf_id(zl3vni)),
1917 			prefix_mac2str(&svi_rmac, buf, sizeof(buf)),
1918 			prefix_mac2str(&vrr_rmac, buf1, sizeof(buf1)),
1919 			inet_ntoa(zl3vni->local_vtep_ip),
1920 			CHECK_FLAG(zl3vni->filter, PREFIX_ROUTES_ONLY)
1921 				? "prefix-routes-only"
1922 				: "none",
1923 			zebra_route_string(client->proto));
1924 
1925 	client->l3vniadd_cnt++;
1926 	return zserv_send_message(client, s);
1927 }
1928 
1929 /*
1930  * Inform BGP about local l3-VNI deletion.
1931  */
zl3vni_send_del_to_client(zebra_l3vni_t * zl3vni)1932 static int zl3vni_send_del_to_client(zebra_l3vni_t *zl3vni)
1933 {
1934 	struct stream *s = NULL;
1935 	struct zserv *client = NULL;
1936 
1937 	client = zserv_find_client(ZEBRA_ROUTE_BGP, 0);
1938 	/* BGP may not be running. */
1939 	if (!client)
1940 		return 0;
1941 
1942 	s = stream_new(ZEBRA_MAX_PACKET_SIZ);
1943 
1944 	zclient_create_header(s, ZEBRA_L3VNI_DEL, zl3vni_vrf_id(zl3vni));
1945 	stream_putl(s, zl3vni->vni);
1946 
1947 	/* Write packet size. */
1948 	stream_putw_at(s, 0, stream_get_endp(s));
1949 
1950 	if (IS_ZEBRA_DEBUG_VXLAN)
1951 		zlog_debug("Send L3_VNI_DEL %u VRF %s to %s", zl3vni->vni,
1952 			   vrf_id_to_name(zl3vni_vrf_id(zl3vni)),
1953 			   zebra_route_string(client->proto));
1954 
1955 	client->l3vnidel_cnt++;
1956 	return zserv_send_message(client, s);
1957 }
1958 
zebra_vxlan_process_l3vni_oper_up(zebra_l3vni_t * zl3vni)1959 static void zebra_vxlan_process_l3vni_oper_up(zebra_l3vni_t *zl3vni)
1960 {
1961 	if (!zl3vni)
1962 		return;
1963 
1964 	/* send l3vni add to BGP */
1965 	zl3vni_send_add_to_client(zl3vni);
1966 }
1967 
zebra_vxlan_process_l3vni_oper_down(zebra_l3vni_t * zl3vni)1968 static void zebra_vxlan_process_l3vni_oper_down(zebra_l3vni_t *zl3vni)
1969 {
1970 	if (!zl3vni)
1971 		return;
1972 
1973 	/* send l3-vni del to BGP*/
1974 	zl3vni_send_del_to_client(zl3vni);
1975 }
1976 
zevpn_add_to_l3vni_list(struct hash_bucket * bucket,void * ctxt)1977 static void zevpn_add_to_l3vni_list(struct hash_bucket *bucket, void *ctxt)
1978 {
1979 	zebra_evpn_t *zevpn = (zebra_evpn_t *)bucket->data;
1980 	zebra_l3vni_t *zl3vni = (zebra_l3vni_t *)ctxt;
1981 
1982 	if (zevpn->vrf_id == zl3vni_vrf_id(zl3vni))
1983 		listnode_add_sort(zl3vni->l2vnis, zevpn);
1984 }
1985 
1986 /*
1987  *  handle transition of vni from l2 to l3 and vice versa
1988  */
zebra_vxlan_handle_vni_transition(struct zebra_vrf * zvrf,vni_t vni,int add)1989 static int zebra_vxlan_handle_vni_transition(struct zebra_vrf *zvrf, vni_t vni,
1990 					     int add)
1991 {
1992 	zebra_evpn_t *zevpn = NULL;
1993 
1994 	/* There is a possibility that VNI notification was already received
1995 	 * from kernel and we programmed it as L2-VNI
1996 	 * In such a case we need to delete this L2-VNI first, so
1997 	 * that it can be reprogrammed as L3-VNI in the system. It is also
1998 	 * possible that the vrf-vni mapping is removed from FRR while the vxlan
1999 	 * interface is still present in kernel. In this case to keep it
2000 	 * symmetric, we will delete the l3-vni and reprogram it as l2-vni
2001 	 */
2002 	if (add) {
2003 		/* Locate hash entry */
2004 		zevpn = zebra_evpn_lookup(vni);
2005 		if (!zevpn)
2006 			return 0;
2007 
2008 		if (IS_ZEBRA_DEBUG_VXLAN)
2009 			zlog_debug("Del L2-VNI %u - transition to L3-VNI", vni);
2010 
2011 		/* Delete EVPN from BGP. */
2012 		zebra_evpn_send_del_to_client(zevpn);
2013 
2014 		zebra_evpn_neigh_del_all(zevpn, 0, 0, DEL_ALL_NEIGH);
2015 		zebra_evpn_mac_del_all(zevpn, 0, 0, DEL_ALL_MAC);
2016 
2017 		/* Free up all remote VTEPs, if any. */
2018 		zebra_evpn_vtep_del_all(zevpn, 0);
2019 
2020 		/* Delete the hash entry. */
2021 		if (zebra_evpn_vxlan_del(zevpn)) {
2022 			flog_err(EC_ZEBRA_VNI_DEL_FAILED,
2023 				 "Failed to del EVPN hash %p, VNI %u", zevpn,
2024 				 zevpn->vni);
2025 			return -1;
2026 		}
2027 	} else {
2028 		/* TODO_MITESH: This needs to be thought through. We don't have
2029 		 * enough information at this point to reprogram the vni as
2030 		 * l2-vni. One way is to store the required info in l3-vni and
2031 		 * used it solely for this purpose
2032 		 */
2033 	}
2034 
2035 	return 0;
2036 }
2037 
2038 /* delete and uninstall rmac hash entry */
zl3vni_del_rmac_hash_entry(struct hash_bucket * bucket,void * ctx)2039 static void zl3vni_del_rmac_hash_entry(struct hash_bucket *bucket, void *ctx)
2040 {
2041 	zebra_mac_t *zrmac = NULL;
2042 	zebra_l3vni_t *zl3vni = NULL;
2043 
2044 	zrmac = (zebra_mac_t *)bucket->data;
2045 	zl3vni = (zebra_l3vni_t *)ctx;
2046 	zl3vni_rmac_uninstall(zl3vni, zrmac);
2047 
2048 	/* Send RMAC for FPM processing */
2049 	hook_call(zebra_rmac_update, zrmac, zl3vni, true, "RMAC deleted");
2050 
2051 	zl3vni_rmac_del(zl3vni, zrmac);
2052 }
2053 
2054 /* delete and uninstall nh hash entry */
zl3vni_del_nh_hash_entry(struct hash_bucket * bucket,void * ctx)2055 static void zl3vni_del_nh_hash_entry(struct hash_bucket *bucket, void *ctx)
2056 {
2057 	zebra_neigh_t *n = NULL;
2058 	zebra_l3vni_t *zl3vni = NULL;
2059 
2060 	n = (zebra_neigh_t *)bucket->data;
2061 	zl3vni = (zebra_l3vni_t *)ctx;
2062 	zl3vni_nh_uninstall(zl3vni, n);
2063 	zl3vni_nh_del(zl3vni, n);
2064 }
2065 
2066 /* re-add remote rmac if needed */
zebra_vxlan_readd_remote_rmac(zebra_l3vni_t * zl3vni,struct ethaddr * rmac)2067 static int zebra_vxlan_readd_remote_rmac(zebra_l3vni_t *zl3vni,
2068 					 struct ethaddr *rmac)
2069 {
2070 	char buf[ETHER_ADDR_STRLEN];
2071 	zebra_mac_t *zrmac = NULL;
2072 
2073 	zrmac = zl3vni_rmac_lookup(zl3vni, rmac);
2074 	if (!zrmac)
2075 		return 0;
2076 
2077 	if (IS_ZEBRA_DEBUG_VXLAN)
2078 		zlog_debug("Del remote RMAC %s L3VNI %u - readd",
2079 			   prefix_mac2str(rmac, buf, sizeof(buf)), zl3vni->vni);
2080 
2081 	zl3vni_rmac_install(zl3vni, zrmac);
2082 	return 0;
2083 }
2084 
2085 /* Public functions */
2086 
is_l3vni_for_prefix_routes_only(vni_t vni)2087 int is_l3vni_for_prefix_routes_only(vni_t vni)
2088 {
2089 	zebra_l3vni_t *zl3vni = NULL;
2090 
2091 	zl3vni = zl3vni_lookup(vni);
2092 	if (!zl3vni)
2093 		return 0;
2094 
2095 	return CHECK_FLAG(zl3vni->filter, PREFIX_ROUTES_ONLY) ? 1 : 0;
2096 }
2097 
2098 /* handle evpn route in vrf table */
zebra_vxlan_evpn_vrf_route_add(vrf_id_t vrf_id,const struct ethaddr * rmac,const struct ipaddr * vtep_ip,const struct prefix * host_prefix)2099 void zebra_vxlan_evpn_vrf_route_add(vrf_id_t vrf_id, const struct ethaddr *rmac,
2100 				    const struct ipaddr *vtep_ip,
2101 				    const struct prefix *host_prefix)
2102 {
2103 	zebra_l3vni_t *zl3vni = NULL;
2104 	struct ipaddr ipv4_vtep;
2105 
2106 	zl3vni = zl3vni_from_vrf(vrf_id);
2107 	if (!zl3vni || !is_l3vni_oper_up(zl3vni))
2108 		return;
2109 
2110 	/*
2111 	 * add the next hop neighbor -
2112 	 * neigh to be installed is the ipv6 nexthop neigh
2113 	 */
2114 	zl3vni_remote_nh_add(zl3vni, vtep_ip, rmac, host_prefix);
2115 
2116 	/*
2117 	 * if the remote vtep is a ipv4 mapped ipv6 address convert it to ipv4
2118 	 * address. Rmac is programmed against the ipv4 vtep because we only
2119 	 * support ipv4 tunnels in the h/w right now
2120 	 */
2121 	memset(&ipv4_vtep, 0, sizeof(struct ipaddr));
2122 	ipv4_vtep.ipa_type = IPADDR_V4;
2123 	if (vtep_ip->ipa_type == IPADDR_V6)
2124 		ipv4_mapped_ipv6_to_ipv4(&vtep_ip->ipaddr_v6,
2125 					 &(ipv4_vtep.ipaddr_v4));
2126 	else
2127 		memcpy(&(ipv4_vtep.ipaddr_v4), &vtep_ip->ipaddr_v4,
2128 		       sizeof(struct in_addr));
2129 
2130 	/*
2131 	 * add the rmac - remote rmac to be installed is against the ipv4
2132 	 * nexthop address
2133 	 */
2134 	zl3vni_remote_rmac_add(zl3vni, rmac, &ipv4_vtep, host_prefix);
2135 }
2136 
2137 /* handle evpn vrf route delete */
zebra_vxlan_evpn_vrf_route_del(vrf_id_t vrf_id,struct ipaddr * vtep_ip,struct prefix * host_prefix)2138 void zebra_vxlan_evpn_vrf_route_del(vrf_id_t vrf_id,
2139 				    struct ipaddr *vtep_ip,
2140 				    struct prefix *host_prefix)
2141 {
2142 	zebra_l3vni_t *zl3vni = NULL;
2143 	zebra_neigh_t *nh = NULL;
2144 	zebra_mac_t *zrmac = NULL;
2145 
2146 	zl3vni = zl3vni_from_vrf(vrf_id);
2147 	if (!zl3vni)
2148 		return;
2149 
2150 	/* find the next hop entry and rmac entry */
2151 	nh = zl3vni_nh_lookup(zl3vni, vtep_ip);
2152 	if (!nh)
2153 		return;
2154 	zrmac = zl3vni_rmac_lookup(zl3vni, &nh->emac);
2155 
2156 	/* delete the next hop entry */
2157 	zl3vni_remote_nh_del(zl3vni, nh, host_prefix);
2158 
2159 	/* delete the rmac entry */
2160 	if (zrmac)
2161 		zl3vni_remote_rmac_del(zl3vni, zrmac, host_prefix);
2162 
2163 }
2164 
zebra_vxlan_print_specific_rmac_l3vni(struct vty * vty,vni_t l3vni,struct ethaddr * rmac,bool use_json)2165 void zebra_vxlan_print_specific_rmac_l3vni(struct vty *vty, vni_t l3vni,
2166 					   struct ethaddr *rmac, bool use_json)
2167 {
2168 	zebra_l3vni_t *zl3vni = NULL;
2169 	zebra_mac_t *zrmac = NULL;
2170 	json_object *json = NULL;
2171 
2172 	if (!is_evpn_enabled()) {
2173 		if (use_json)
2174 			vty_out(vty, "{}\n");
2175 		return;
2176 	}
2177 
2178 	if (use_json)
2179 		json = json_object_new_object();
2180 
2181 	zl3vni = zl3vni_lookup(l3vni);
2182 	if (!zl3vni) {
2183 		if (use_json)
2184 			vty_out(vty, "{}\n");
2185 		else
2186 			vty_out(vty, "%% L3-VNI %u doesn't exist\n", l3vni);
2187 		return;
2188 	}
2189 
2190 	zrmac = zl3vni_rmac_lookup(zl3vni, rmac);
2191 	if (!zrmac) {
2192 		if (use_json)
2193 			vty_out(vty, "{}\n");
2194 		else
2195 			vty_out(vty,
2196 				"%% Requested RMAC doesn't exist in L3-VNI %u",
2197 				l3vni);
2198 		return;
2199 	}
2200 
2201 	zl3vni_print_rmac(zrmac, vty, json);
2202 
2203 	if (use_json) {
2204 		vty_out(vty, "%s\n", json_object_to_json_string_ext(
2205 					     json, JSON_C_TO_STRING_PRETTY));
2206 		json_object_free(json);
2207 	}
2208 }
2209 
zebra_vxlan_print_rmacs_l3vni(struct vty * vty,vni_t l3vni,bool use_json)2210 void zebra_vxlan_print_rmacs_l3vni(struct vty *vty, vni_t l3vni, bool use_json)
2211 {
2212 	zebra_l3vni_t *zl3vni;
2213 	uint32_t num_rmacs;
2214 	struct rmac_walk_ctx wctx;
2215 	json_object *json = NULL;
2216 
2217 	if (!is_evpn_enabled())
2218 		return;
2219 
2220 	zl3vni = zl3vni_lookup(l3vni);
2221 	if (!zl3vni) {
2222 		if (use_json)
2223 			vty_out(vty, "{}\n");
2224 		else
2225 			vty_out(vty, "%% L3-VNI %u does not exist\n", l3vni);
2226 		return;
2227 	}
2228 	num_rmacs = hashcount(zl3vni->rmac_table);
2229 	if (!num_rmacs)
2230 		return;
2231 
2232 	if (use_json)
2233 		json = json_object_new_object();
2234 
2235 	memset(&wctx, 0, sizeof(struct rmac_walk_ctx));
2236 	wctx.vty = vty;
2237 	wctx.json = json;
2238 	if (!use_json) {
2239 		vty_out(vty, "Number of Remote RMACs known for this VNI: %u\n",
2240 			num_rmacs);
2241 		vty_out(vty, "%-17s %-21s\n", "MAC", "Remote VTEP");
2242 	} else
2243 		json_object_int_add(json, "numRmacs", num_rmacs);
2244 
2245 	hash_iterate(zl3vni->rmac_table, zl3vni_print_rmac_hash, &wctx);
2246 
2247 	if (use_json) {
2248 		vty_out(vty, "%s\n", json_object_to_json_string_ext(
2249 					     json, JSON_C_TO_STRING_PRETTY));
2250 		json_object_free(json);
2251 	}
2252 }
2253 
zebra_vxlan_print_rmacs_all_l3vni(struct vty * vty,bool use_json)2254 void zebra_vxlan_print_rmacs_all_l3vni(struct vty *vty, bool use_json)
2255 {
2256 	json_object *json = NULL;
2257 	void *args[2];
2258 
2259 	if (!is_evpn_enabled()) {
2260 		if (use_json)
2261 			vty_out(vty, "{}\n");
2262 		return;
2263 	}
2264 
2265 	if (use_json)
2266 		json = json_object_new_object();
2267 
2268 	args[0] = vty;
2269 	args[1] = json;
2270 	hash_iterate(zrouter.l3vni_table,
2271 		     (void (*)(struct hash_bucket *,
2272 			       void *))zl3vni_print_rmac_hash_all_vni,
2273 		     args);
2274 
2275 	if (use_json) {
2276 		vty_out(vty, "%s\n", json_object_to_json_string_ext(
2277 					     json, JSON_C_TO_STRING_PRETTY));
2278 		json_object_free(json);
2279 	}
2280 }
2281 
zebra_vxlan_print_specific_nh_l3vni(struct vty * vty,vni_t l3vni,struct ipaddr * ip,bool use_json)2282 void zebra_vxlan_print_specific_nh_l3vni(struct vty *vty, vni_t l3vni,
2283 					 struct ipaddr *ip, bool use_json)
2284 {
2285 	zebra_l3vni_t *zl3vni = NULL;
2286 	zebra_neigh_t *n = NULL;
2287 	json_object *json = NULL;
2288 
2289 	if (!is_evpn_enabled()) {
2290 		if (use_json)
2291 			vty_out(vty, "{}\n");
2292 		return;
2293 	}
2294 
2295 	if (use_json)
2296 		json = json_object_new_object();
2297 
2298 	zl3vni = zl3vni_lookup(l3vni);
2299 	if (!zl3vni) {
2300 		if (use_json)
2301 			vty_out(vty, "{}\n");
2302 		else
2303 			vty_out(vty, "%% L3-VNI %u does not exist\n", l3vni);
2304 		return;
2305 	}
2306 
2307 	n = zl3vni_nh_lookup(zl3vni, ip);
2308 	if (!n) {
2309 		if (use_json)
2310 			vty_out(vty, "{}\n");
2311 		else
2312 			vty_out(vty,
2313 				"%% Requested next-hop not present for L3-VNI %u",
2314 				l3vni);
2315 		return;
2316 	}
2317 
2318 	zl3vni_print_nh(n, vty, json);
2319 
2320 	if (use_json) {
2321 		vty_out(vty, "%s\n", json_object_to_json_string_ext(
2322 					     json, JSON_C_TO_STRING_PRETTY));
2323 		json_object_free(json);
2324 	}
2325 }
2326 
zebra_vxlan_print_nh_l3vni(struct vty * vty,vni_t l3vni,bool use_json)2327 void zebra_vxlan_print_nh_l3vni(struct vty *vty, vni_t l3vni, bool use_json)
2328 {
2329 	uint32_t num_nh;
2330 	struct nh_walk_ctx wctx;
2331 	json_object *json = NULL;
2332 	zebra_l3vni_t *zl3vni = NULL;
2333 
2334 	if (!is_evpn_enabled())
2335 		return;
2336 
2337 	zl3vni = zl3vni_lookup(l3vni);
2338 	if (!zl3vni) {
2339 		if (use_json)
2340 			vty_out(vty, "{}\n");
2341 		else
2342 			vty_out(vty, "%% L3-VNI %u does not exist\n", l3vni);
2343 		return;
2344 	}
2345 
2346 	num_nh = hashcount(zl3vni->nh_table);
2347 	if (!num_nh)
2348 		return;
2349 
2350 	if (use_json)
2351 		json = json_object_new_object();
2352 
2353 	wctx.vty = vty;
2354 	wctx.json = json;
2355 	if (!use_json) {
2356 		vty_out(vty, "Number of NH Neighbors known for this VNI: %u\n",
2357 			num_nh);
2358 		vty_out(vty, "%-15s %-17s\n", "IP", "RMAC");
2359 	} else
2360 		json_object_int_add(json, "numNextHops", num_nh);
2361 
2362 	hash_iterate(zl3vni->nh_table, zl3vni_print_nh_hash, &wctx);
2363 
2364 	if (use_json) {
2365 		vty_out(vty, "%s\n", json_object_to_json_string_ext(
2366 					     json, JSON_C_TO_STRING_PRETTY));
2367 		json_object_free(json);
2368 	}
2369 }
2370 
zebra_vxlan_print_nh_all_l3vni(struct vty * vty,bool use_json)2371 void zebra_vxlan_print_nh_all_l3vni(struct vty *vty, bool use_json)
2372 {
2373 	json_object *json = NULL;
2374 	void *args[2];
2375 
2376 	if (!is_evpn_enabled()) {
2377 		if (use_json)
2378 			vty_out(vty, "{}\n");
2379 		return;
2380 	}
2381 
2382 	if (use_json)
2383 		json = json_object_new_object();
2384 
2385 	args[0] = vty;
2386 	args[1] = json;
2387 	hash_iterate(zrouter.l3vni_table,
2388 		     (void (*)(struct hash_bucket *,
2389 			       void *))zl3vni_print_nh_hash_all_vni,
2390 		     args);
2391 
2392 	if (use_json) {
2393 		vty_out(vty, "%s\n", json_object_to_json_string_ext(
2394 					     json, JSON_C_TO_STRING_PRETTY));
2395 		json_object_free(json);
2396 	}
2397 }
2398 
2399 /*
2400  * Display L3 VNI information (VTY command handler).
2401  */
zebra_vxlan_print_l3vni(struct vty * vty,vni_t vni,bool use_json)2402 void zebra_vxlan_print_l3vni(struct vty *vty, vni_t vni, bool use_json)
2403 {
2404 	void *args[2];
2405 	json_object *json = NULL;
2406 	zebra_l3vni_t *zl3vni = NULL;
2407 
2408 	if (!is_evpn_enabled()) {
2409 		if (use_json)
2410 			vty_out(vty, "{}\n");
2411 		return;
2412 	}
2413 
2414 	zl3vni = zl3vni_lookup(vni);
2415 	if (!zl3vni) {
2416 		if (use_json)
2417 			vty_out(vty, "{}\n");
2418 		else
2419 			vty_out(vty, "%% VNI %u does not exist\n", vni);
2420 		return;
2421 	}
2422 
2423 	if (use_json)
2424 		json = json_object_new_object();
2425 
2426 	args[0] = vty;
2427 	args[1] = json;
2428 	zl3vni_print(zl3vni, (void *)args);
2429 
2430 	if (use_json) {
2431 		vty_out(vty, "%s\n", json_object_to_json_string_ext(
2432 					     json, JSON_C_TO_STRING_PRETTY));
2433 		json_object_free(json);
2434 	}
2435 }
2436 
zebra_vxlan_print_vrf_vni(struct vty * vty,struct zebra_vrf * zvrf,json_object * json_vrfs)2437 void zebra_vxlan_print_vrf_vni(struct vty *vty, struct zebra_vrf *zvrf,
2438 			       json_object *json_vrfs)
2439 {
2440 	char buf[ETHER_ADDR_STRLEN];
2441 	zebra_l3vni_t *zl3vni = NULL;
2442 
2443 	zl3vni = zl3vni_lookup(zvrf->l3vni);
2444 	if (!zl3vni)
2445 		return;
2446 
2447 	if (!json_vrfs) {
2448 		vty_out(vty, "%-37s %-10u %-20s %-20s %-5s %-18s\n",
2449 			zvrf_name(zvrf), zl3vni->vni,
2450 			zl3vni_vxlan_if_name(zl3vni),
2451 			zl3vni_svi_if_name(zl3vni), zl3vni_state2str(zl3vni),
2452 			zl3vni_rmac2str(zl3vni, buf, sizeof(buf)));
2453 	} else {
2454 		json_object *json_vrf = NULL;
2455 
2456 		json_vrf = json_object_new_object();
2457 		json_object_string_add(json_vrf, "vrf", zvrf_name(zvrf));
2458 		json_object_int_add(json_vrf, "vni", zl3vni->vni);
2459 		json_object_string_add(json_vrf, "vxlanIntf",
2460 				       zl3vni_vxlan_if_name(zl3vni));
2461 		json_object_string_add(json_vrf, "sviIntf",
2462 				       zl3vni_svi_if_name(zl3vni));
2463 		json_object_string_add(json_vrf, "state",
2464 				       zl3vni_state2str(zl3vni));
2465 		json_object_string_add(
2466 			json_vrf, "routerMac",
2467 			zl3vni_rmac2str(zl3vni, buf, sizeof(buf)));
2468 		json_object_array_add(json_vrfs, json_vrf);
2469 	}
2470 }
2471 
2472 /*
2473  * Display Neighbors for a VNI (VTY command handler).
2474  */
zebra_vxlan_print_neigh_vni(struct vty * vty,struct zebra_vrf * zvrf,vni_t vni,bool use_json)2475 void zebra_vxlan_print_neigh_vni(struct vty *vty, struct zebra_vrf *zvrf,
2476 				 vni_t vni, bool use_json)
2477 {
2478 	zebra_evpn_t *zevpn;
2479 	uint32_t num_neigh;
2480 	struct neigh_walk_ctx wctx;
2481 	json_object *json = NULL;
2482 
2483 	if (!is_evpn_enabled())
2484 		return;
2485 	zevpn = zebra_evpn_lookup(vni);
2486 	if (!zevpn) {
2487 		if (use_json)
2488 			vty_out(vty, "{}\n");
2489 		else
2490 			vty_out(vty, "%% VNI %u does not exist\n", vni);
2491 		return;
2492 	}
2493 	num_neigh = hashcount(zevpn->neigh_table);
2494 	if (!num_neigh)
2495 		return;
2496 
2497 	if (use_json)
2498 		json = json_object_new_object();
2499 
2500 	/* Since we have IPv6 addresses to deal with which can vary widely in
2501 	 * size, we try to be a bit more elegant in display by first computing
2502 	 * the maximum width.
2503 	 */
2504 	memset(&wctx, 0, sizeof(struct neigh_walk_ctx));
2505 	wctx.zevpn = zevpn;
2506 	wctx.vty = vty;
2507 	wctx.addr_width = 15;
2508 	wctx.json = json;
2509 	hash_iterate(zevpn->neigh_table, zebra_evpn_find_neigh_addr_width,
2510 		     &wctx);
2511 
2512 	if (!use_json) {
2513 		vty_out(vty,
2514 			"Number of ARPs (local and remote) known for this VNI: %u\n",
2515 			num_neigh);
2516 		zebra_evpn_print_neigh_hdr(vty, &wctx);
2517 	} else
2518 		json_object_int_add(json, "numArpNd", num_neigh);
2519 
2520 	hash_iterate(zevpn->neigh_table, zebra_evpn_print_neigh_hash, &wctx);
2521 	if (use_json) {
2522 		vty_out(vty, "%s\n", json_object_to_json_string_ext(
2523 					     json, JSON_C_TO_STRING_PRETTY));
2524 		json_object_free(json);
2525 	}
2526 }
2527 
2528 /*
2529  * Display neighbors across all VNIs (VTY command handler).
2530  */
zebra_vxlan_print_neigh_all_vni(struct vty * vty,struct zebra_vrf * zvrf,bool print_dup,bool use_json)2531 void zebra_vxlan_print_neigh_all_vni(struct vty *vty, struct zebra_vrf *zvrf,
2532 				     bool print_dup, bool use_json)
2533 {
2534 	json_object *json = NULL;
2535 	void *args[3];
2536 
2537 	if (!is_evpn_enabled())
2538 		return;
2539 
2540 	if (use_json)
2541 		json = json_object_new_object();
2542 
2543 	args[0] = vty;
2544 	args[1] = json;
2545 	args[2] = (void *)(ptrdiff_t)print_dup;
2546 
2547 	hash_iterate(zvrf->evpn_table,
2548 		     (void (*)(struct hash_bucket *,
2549 			       void *))zevpn_print_neigh_hash_all_evpn,
2550 		     args);
2551 	if (use_json) {
2552 		vty_out(vty, "%s\n", json_object_to_json_string_ext(
2553 					     json, JSON_C_TO_STRING_PRETTY));
2554 		json_object_free(json);
2555 	}
2556 }
2557 
2558 /*
2559  * Display neighbors across all VNIs in detail(VTY command handler).
2560  */
zebra_vxlan_print_neigh_all_vni_detail(struct vty * vty,struct zebra_vrf * zvrf,bool print_dup,bool use_json)2561 void zebra_vxlan_print_neigh_all_vni_detail(struct vty *vty,
2562 					    struct zebra_vrf *zvrf,
2563 					    bool print_dup, bool use_json)
2564 {
2565 	json_object *json = NULL;
2566 	void *args[3];
2567 
2568 	if (!is_evpn_enabled())
2569 		return;
2570 
2571 	if (use_json)
2572 		json = json_object_new_object();
2573 
2574 	args[0] = vty;
2575 	args[1] = json;
2576 	args[2] = (void *)(ptrdiff_t)print_dup;
2577 
2578 	hash_iterate(zvrf->evpn_table,
2579 		     (void (*)(struct hash_bucket *,
2580 			       void *))zevpn_print_neigh_hash_all_evpn_detail,
2581 		     args);
2582 	if (use_json) {
2583 		vty_out(vty, "%s\n", json_object_to_json_string_ext(
2584 					     json, JSON_C_TO_STRING_PRETTY));
2585 		json_object_free(json);
2586 	}
2587 }
2588 
2589 /*
2590  * Display specific neighbor for a VNI, if present (VTY command handler).
2591  */
zebra_vxlan_print_specific_neigh_vni(struct vty * vty,struct zebra_vrf * zvrf,vni_t vni,struct ipaddr * ip,bool use_json)2592 void zebra_vxlan_print_specific_neigh_vni(struct vty *vty,
2593 					  struct zebra_vrf *zvrf, vni_t vni,
2594 					  struct ipaddr *ip, bool use_json)
2595 {
2596 	zebra_evpn_t *zevpn;
2597 	zebra_neigh_t *n;
2598 	json_object *json = NULL;
2599 
2600 	if (!is_evpn_enabled())
2601 		return;
2602 	zevpn = zebra_evpn_lookup(vni);
2603 	if (!zevpn) {
2604 		if (use_json)
2605 			vty_out(vty, "{}\n");
2606 		else
2607 			vty_out(vty, "%% VNI %u does not exist\n", vni);
2608 		return;
2609 	}
2610 	n = zebra_evpn_neigh_lookup(zevpn, ip);
2611 	if (!n) {
2612 		if (!use_json)
2613 			vty_out(vty,
2614 				"%% Requested neighbor does not exist in VNI %u\n",
2615 				vni);
2616 		return;
2617 	}
2618 	if (use_json)
2619 		json = json_object_new_object();
2620 
2621 	zebra_evpn_print_neigh(n, vty, json);
2622 
2623 	if (use_json) {
2624 		vty_out(vty, "%s\n", json_object_to_json_string_ext(
2625 					     json, JSON_C_TO_STRING_PRETTY));
2626 		json_object_free(json);
2627 	}
2628 }
2629 
2630 /*
2631  * Display neighbors for a VNI from specific VTEP (VTY command handler).
2632  * By definition, these are remote neighbors.
2633  */
zebra_vxlan_print_neigh_vni_vtep(struct vty * vty,struct zebra_vrf * zvrf,vni_t vni,struct in_addr vtep_ip,bool use_json)2634 void zebra_vxlan_print_neigh_vni_vtep(struct vty *vty, struct zebra_vrf *zvrf,
2635 				      vni_t vni, struct in_addr vtep_ip,
2636 				      bool use_json)
2637 {
2638 	zebra_evpn_t *zevpn;
2639 	uint32_t num_neigh;
2640 	struct neigh_walk_ctx wctx;
2641 	json_object *json = NULL;
2642 
2643 	if (!is_evpn_enabled())
2644 		return;
2645 	zevpn = zebra_evpn_lookup(vni);
2646 	if (!zevpn) {
2647 		if (use_json)
2648 			vty_out(vty, "{}\n");
2649 		else
2650 			vty_out(vty, "%% VNI %u does not exist\n", vni);
2651 		return;
2652 	}
2653 	num_neigh = hashcount(zevpn->neigh_table);
2654 	if (!num_neigh)
2655 		return;
2656 
2657 	if (use_json)
2658 		json = json_object_new_object();
2659 
2660 	memset(&wctx, 0, sizeof(struct neigh_walk_ctx));
2661 	wctx.zevpn = zevpn;
2662 	wctx.vty = vty;
2663 	wctx.addr_width = 15;
2664 	wctx.flags = SHOW_REMOTE_NEIGH_FROM_VTEP;
2665 	wctx.r_vtep_ip = vtep_ip;
2666 	wctx.json = json;
2667 	hash_iterate(zevpn->neigh_table, zebra_evpn_find_neigh_addr_width,
2668 		     &wctx);
2669 	hash_iterate(zevpn->neigh_table, zebra_evpn_print_neigh_hash, &wctx);
2670 
2671 	if (use_json) {
2672 		vty_out(vty, "%s\n", json_object_to_json_string_ext(
2673 					     json, JSON_C_TO_STRING_PRETTY));
2674 		json_object_free(json);
2675 	}
2676 }
2677 
2678 /*
2679  * Display Duplicate detected Neighbors for a VNI
2680  * (VTY command handler).
2681  */
zebra_vxlan_print_neigh_vni_dad(struct vty * vty,struct zebra_vrf * zvrf,vni_t vni,bool use_json)2682 void zebra_vxlan_print_neigh_vni_dad(struct vty *vty,
2683 				     struct zebra_vrf *zvrf,
2684 				     vni_t vni,
2685 				     bool use_json)
2686 {
2687 	zebra_evpn_t *zevpn;
2688 	uint32_t num_neigh;
2689 	struct neigh_walk_ctx wctx;
2690 	json_object *json = NULL;
2691 
2692 	if (!is_evpn_enabled())
2693 		return;
2694 
2695 	zevpn = zebra_evpn_lookup(vni);
2696 	if (!zevpn) {
2697 		vty_out(vty, "%% VNI %u does not exist\n", vni);
2698 		return;
2699 	}
2700 
2701 	num_neigh = hashcount(zevpn->neigh_table);
2702 	if (!num_neigh)
2703 		return;
2704 
2705 	num_neigh = num_dup_detected_neighs(zevpn);
2706 	if (!num_neigh)
2707 		return;
2708 
2709 	if (use_json)
2710 		json = json_object_new_object();
2711 
2712 	/* Since we have IPv6 addresses to deal with which can vary widely in
2713 	 * size, we try to be a bit more elegant in display by first computing
2714 	 * the maximum width.
2715 	 */
2716 	memset(&wctx, 0, sizeof(struct neigh_walk_ctx));
2717 	wctx.zevpn = zevpn;
2718 	wctx.vty = vty;
2719 	wctx.addr_width = 15;
2720 	wctx.json = json;
2721 	hash_iterate(zevpn->neigh_table, zebra_evpn_find_neigh_addr_width,
2722 		     &wctx);
2723 
2724 	if (!use_json) {
2725 		vty_out(vty,
2726 			"Number of ARPs (local and remote) known for this VNI: %u\n",
2727 			num_neigh);
2728 		vty_out(vty, "%*s %-6s %-8s %-17s %-30s\n",
2729 			-wctx.addr_width, "IP", "Type",
2730 			"State", "MAC", "Remote ES/VTEP");
2731 	} else
2732 		json_object_int_add(json, "numArpNd", num_neigh);
2733 
2734 	hash_iterate(zevpn->neigh_table, zebra_evpn_print_dad_neigh_hash,
2735 		     &wctx);
2736 
2737 	if (use_json) {
2738 		vty_out(vty, "%s\n", json_object_to_json_string_ext(
2739 					     json, JSON_C_TO_STRING_PRETTY));
2740 		json_object_free(json);
2741 	}
2742 }
2743 
2744 /*
2745  * Display MACs for a VNI (VTY command handler).
2746  */
zebra_vxlan_print_macs_vni(struct vty * vty,struct zebra_vrf * zvrf,vni_t vni,bool use_json)2747 void zebra_vxlan_print_macs_vni(struct vty *vty, struct zebra_vrf *zvrf,
2748 				vni_t vni, bool use_json)
2749 {
2750 	zebra_evpn_t *zevpn;
2751 	uint32_t num_macs;
2752 	struct mac_walk_ctx wctx;
2753 	json_object *json = NULL;
2754 	json_object *json_mac = NULL;
2755 
2756 	if (!is_evpn_enabled())
2757 		return;
2758 	zevpn = zebra_evpn_lookup(vni);
2759 	if (!zevpn) {
2760 		if (use_json)
2761 			vty_out(vty, "{}\n");
2762 		else
2763 			vty_out(vty, "%% VNI %u does not exist\n", vni);
2764 		return;
2765 	}
2766 	num_macs = num_valid_macs(zevpn);
2767 	if (!num_macs)
2768 		return;
2769 
2770 	if (use_json) {
2771 		json = json_object_new_object();
2772 		json_mac = json_object_new_object();
2773 	}
2774 
2775 	memset(&wctx, 0, sizeof(struct mac_walk_ctx));
2776 	wctx.zevpn = zevpn;
2777 	wctx.vty = vty;
2778 	wctx.json = json_mac;
2779 
2780 	if (!use_json) {
2781 		vty_out(vty,
2782 			"Number of MACs (local and remote) known for this VNI: %u\n",
2783 			num_macs);
2784 			vty_out(vty,
2785 				"Flags: N=sync-neighs, I=local-inactive, P=peer-active, X=peer-proxy\n");
2786 			vty_out(vty, "%-17s %-6s %-5s %-30s %-5s %s\n", "MAC",
2787 				"Type", "Flags", "Intf/Remote ES/VTEP",
2788 				"VLAN", "Seq #'s");
2789 	} else
2790 		json_object_int_add(json, "numMacs", num_macs);
2791 
2792 	hash_iterate(zevpn->mac_table, zebra_evpn_print_mac_hash, &wctx);
2793 
2794 	if (use_json) {
2795 		json_object_object_add(json, "macs", json_mac);
2796 		vty_out(vty, "%s\n", json_object_to_json_string_ext(
2797 					     json, JSON_C_TO_STRING_PRETTY));
2798 		json_object_free(json);
2799 	}
2800 }
2801 
2802 /*
2803  * Display MACs for all VNIs (VTY command handler).
2804  */
zebra_vxlan_print_macs_all_vni(struct vty * vty,struct zebra_vrf * zvrf,bool print_dup,bool use_json)2805 void zebra_vxlan_print_macs_all_vni(struct vty *vty, struct zebra_vrf *zvrf,
2806 				    bool print_dup, bool use_json)
2807 {
2808 	struct mac_walk_ctx wctx;
2809 	json_object *json = NULL;
2810 
2811 	if (!is_evpn_enabled()) {
2812 		if (use_json)
2813 			vty_out(vty, "{}\n");
2814 		return;
2815 	}
2816 	if (use_json)
2817 		json = json_object_new_object();
2818 
2819 	memset(&wctx, 0, sizeof(struct mac_walk_ctx));
2820 	wctx.vty = vty;
2821 	wctx.json = json;
2822 	wctx.print_dup = print_dup;
2823 	hash_iterate(zvrf->evpn_table, zevpn_print_mac_hash_all_evpn, &wctx);
2824 
2825 	if (use_json) {
2826 		vty_out(vty, "%s\n", json_object_to_json_string_ext(
2827 					     json, JSON_C_TO_STRING_PRETTY));
2828 		json_object_free(json);
2829 	}
2830 }
2831 
2832 /*
2833  * Display MACs in detail for all VNIs (VTY command handler).
2834  */
zebra_vxlan_print_macs_all_vni_detail(struct vty * vty,struct zebra_vrf * zvrf,bool print_dup,bool use_json)2835 void zebra_vxlan_print_macs_all_vni_detail(struct vty *vty,
2836 					   struct zebra_vrf *zvrf,
2837 					   bool print_dup, bool use_json)
2838 {
2839 	struct mac_walk_ctx wctx;
2840 	json_object *json = NULL;
2841 
2842 	if (!is_evpn_enabled()) {
2843 		if (use_json)
2844 			vty_out(vty, "{}\n");
2845 		return;
2846 	}
2847 	if (use_json)
2848 		json = json_object_new_object();
2849 
2850 	memset(&wctx, 0, sizeof(struct mac_walk_ctx));
2851 	wctx.vty = vty;
2852 	wctx.json = json;
2853 	wctx.print_dup = print_dup;
2854 	hash_iterate(zvrf->evpn_table, zevpn_print_mac_hash_all_evpn_detail,
2855 		     &wctx);
2856 
2857 	if (use_json) {
2858 		vty_out(vty, "%s\n", json_object_to_json_string_ext(
2859 					     json, JSON_C_TO_STRING_PRETTY));
2860 		json_object_free(json);
2861 	}
2862 }
2863 
2864 /*
2865  * Display MACs for all VNIs (VTY command handler).
2866  */
zebra_vxlan_print_macs_all_vni_vtep(struct vty * vty,struct zebra_vrf * zvrf,struct in_addr vtep_ip,bool use_json)2867 void zebra_vxlan_print_macs_all_vni_vtep(struct vty *vty,
2868 					 struct zebra_vrf *zvrf,
2869 					 struct in_addr vtep_ip, bool use_json)
2870 {
2871 	struct mac_walk_ctx wctx;
2872 	json_object *json = NULL;
2873 
2874 	if (!is_evpn_enabled())
2875 		return;
2876 
2877 	if (use_json)
2878 		json = json_object_new_object();
2879 
2880 	memset(&wctx, 0, sizeof(struct mac_walk_ctx));
2881 	wctx.vty = vty;
2882 	wctx.flags = SHOW_REMOTE_MAC_FROM_VTEP;
2883 	wctx.r_vtep_ip = vtep_ip;
2884 	wctx.json = json;
2885 	hash_iterate(zvrf->evpn_table, zevpn_print_mac_hash_all_evpn, &wctx);
2886 
2887 	if (use_json) {
2888 		vty_out(vty, "%s\n", json_object_to_json_string_ext(
2889 					     json, JSON_C_TO_STRING_PRETTY));
2890 		json_object_free(json);
2891 	}
2892 }
2893 
2894 /*
2895  * Display specific MAC for a VNI, if present (VTY command handler).
2896  */
zebra_vxlan_print_specific_mac_vni(struct vty * vty,struct zebra_vrf * zvrf,vni_t vni,struct ethaddr * macaddr,bool use_json)2897 void zebra_vxlan_print_specific_mac_vni(struct vty *vty, struct zebra_vrf *zvrf,
2898 					vni_t vni, struct ethaddr *macaddr,
2899 					bool use_json)
2900 {
2901 	zebra_evpn_t *zevpn;
2902 	zebra_mac_t *mac;
2903 	json_object *json = NULL;
2904 
2905 	if (!is_evpn_enabled())
2906 		return;
2907 
2908 	zevpn = zebra_evpn_lookup(vni);
2909 	if (!zevpn) {
2910 		if (use_json)
2911 			vty_out(vty, "{}\n");
2912 		else
2913 			vty_out(vty, "%% VNI %u does not exist\n", vni);
2914 		return;
2915 	}
2916 	mac = zebra_evpn_mac_lookup(zevpn, macaddr);
2917 	if (!mac) {
2918 		if (use_json)
2919 			vty_out(vty, "{}\n");
2920 		else
2921 			vty_out(vty,
2922 				"%% Requested MAC does not exist in VNI %u\n",
2923 				vni);
2924 		return;
2925 	}
2926 
2927 	if (use_json)
2928 		json = json_object_new_object();
2929 
2930 	zebra_evpn_print_mac(mac, vty, json);
2931 	if (use_json) {
2932 		vty_out(vty, "%s\n", json_object_to_json_string_ext(
2933 					     json, JSON_C_TO_STRING_PRETTY));
2934 		json_object_free(json);
2935 	}
2936 }
2937 
2938 /* Print Duplicate MACs per VNI */
zebra_vxlan_print_macs_vni_dad(struct vty * vty,struct zebra_vrf * zvrf,vni_t vni,bool use_json)2939 void zebra_vxlan_print_macs_vni_dad(struct vty *vty,
2940 				    struct zebra_vrf *zvrf,
2941 				    vni_t vni, bool use_json)
2942 {
2943 	zebra_evpn_t *zevpn;
2944 	struct mac_walk_ctx wctx;
2945 	uint32_t num_macs;
2946 	json_object *json = NULL;
2947 	json_object *json_mac = NULL;
2948 
2949 	if (!is_evpn_enabled())
2950 		return;
2951 
2952 	zevpn = zebra_evpn_lookup(vni);
2953 	if (!zevpn) {
2954 		vty_out(vty, "%% VNI %u does not exist\n", vni);
2955 		return;
2956 	}
2957 
2958 	num_macs = num_valid_macs(zevpn);
2959 	if (!num_macs)
2960 		return;
2961 
2962 	num_macs = num_dup_detected_macs(zevpn);
2963 	if (!num_macs)
2964 		return;
2965 
2966 	if (use_json) {
2967 		json = json_object_new_object();
2968 		json_mac = json_object_new_object();
2969 	}
2970 
2971 	memset(&wctx, 0, sizeof(struct mac_walk_ctx));
2972 	wctx.zevpn = zevpn;
2973 	wctx.vty = vty;
2974 	wctx.json = json_mac;
2975 
2976 	if (!use_json) {
2977 		vty_out(vty,
2978 		"Number of MACs (local and remote) known for this VNI: %u\n",
2979 			num_macs);
2980 		vty_out(vty, "%-17s %-6s %-5s %-30s %-5s\n", "MAC", "Type",
2981 			"Flags", "Intf/Remote ES/VTEP", "VLAN");
2982 	} else
2983 		json_object_int_add(json, "numMacs", num_macs);
2984 
2985 	hash_iterate(zevpn->mac_table, zebra_evpn_print_dad_mac_hash, &wctx);
2986 
2987 	if (use_json) {
2988 		json_object_object_add(json, "macs", json_mac);
2989 		vty_out(vty, "%s\n", json_object_to_json_string_ext(
2990 					     json, JSON_C_TO_STRING_PRETTY));
2991 		json_object_free(json);
2992 	}
2993 
2994 }
2995 
zebra_vxlan_clear_dup_detect_vni_mac(struct zebra_vrf * zvrf,vni_t vni,struct ethaddr * macaddr)2996 int zebra_vxlan_clear_dup_detect_vni_mac(struct zebra_vrf *zvrf, vni_t vni,
2997 					 struct ethaddr *macaddr)
2998 {
2999 	zebra_evpn_t *zevpn;
3000 	zebra_mac_t *mac;
3001 	struct listnode *node = NULL;
3002 	zebra_neigh_t *nbr = NULL;
3003 
3004 	if (!is_evpn_enabled())
3005 		return 0;
3006 
3007 	zevpn = zebra_evpn_lookup(vni);
3008 	if (!zevpn) {
3009 		zlog_warn("VNI %u does not exist\n", vni);
3010 		return -1;
3011 	}
3012 
3013 	mac = zebra_evpn_mac_lookup(zevpn, macaddr);
3014 	if (!mac) {
3015 		zlog_warn("Requested MAC does not exist in VNI %u\n", vni);
3016 		return -1;
3017 	}
3018 
3019 	if (!CHECK_FLAG(mac->flags, ZEBRA_MAC_DUPLICATE)) {
3020 		zlog_warn("Requested MAC is not duplicate detected\n");
3021 		return -1;
3022 	}
3023 
3024 	/* Remove all IPs as duplicate associcated with this MAC */
3025 	for (ALL_LIST_ELEMENTS_RO(mac->neigh_list, node, nbr)) {
3026 		/* For local neigh mark inactive so MACIP update is generated
3027 		 * to BGP. This is a scenario where MAC update received
3028 		 * and detected as duplicate which marked neigh as duplicate.
3029 		 * Later local neigh update did not get a chance to relay
3030 		 * to BGP. Similarly remote macip update, neigh needs to be
3031 		 * installed locally.
3032 		 */
3033 		if (zvrf->dad_freeze &&
3034 		    CHECK_FLAG(nbr->flags, ZEBRA_NEIGH_DUPLICATE)) {
3035 			if (CHECK_FLAG(nbr->flags, ZEBRA_NEIGH_LOCAL))
3036 				ZEBRA_NEIGH_SET_INACTIVE(nbr);
3037 			else if (CHECK_FLAG(nbr->flags, ZEBRA_NEIGH_REMOTE))
3038 				zebra_evpn_rem_neigh_install(
3039 					zevpn, nbr, false /*was_static*/);
3040 		}
3041 
3042 		UNSET_FLAG(nbr->flags, ZEBRA_NEIGH_DUPLICATE);
3043 		nbr->dad_count = 0;
3044 		nbr->detect_start_time.tv_sec = 0;
3045 		nbr->dad_dup_detect_time = 0;
3046 	}
3047 
3048 	UNSET_FLAG(mac->flags, ZEBRA_MAC_DUPLICATE);
3049 	mac->dad_count = 0;
3050 	mac->detect_start_time.tv_sec = 0;
3051 	mac->detect_start_time.tv_usec = 0;
3052 	mac->dad_dup_detect_time = 0;
3053 	THREAD_OFF(mac->dad_mac_auto_recovery_timer);
3054 
3055 	/* warn-only action return */
3056 	if (!zvrf->dad_freeze)
3057 		return 0;
3058 
3059 	/* Local: Notify Peer VTEPs, Remote: Install the entry */
3060 	if (CHECK_FLAG(mac->flags, ZEBRA_MAC_LOCAL)) {
3061 		/* Inform to BGP */
3062 		if (zebra_evpn_mac_send_add_to_client(zevpn->vni, &mac->macaddr,
3063 						      mac->flags, mac->loc_seq,
3064 						      mac->es))
3065 			return 0;
3066 
3067 		/* Process all neighbors associated with this MAC. */
3068 		zebra_evpn_process_neigh_on_local_mac_change(zevpn, mac, 0,
3069 							     0 /*es_change*/);
3070 
3071 	} else if (CHECK_FLAG(mac->flags, ZEBRA_MAC_REMOTE)) {
3072 		zebra_evpn_process_neigh_on_remote_mac_add(zevpn, mac);
3073 
3074 		/* Install the entry. */
3075 		zebra_evpn_rem_mac_install(zevpn, mac, false /* was_static */);
3076 	}
3077 
3078 	return 0;
3079 }
3080 
zebra_vxlan_clear_dup_detect_vni_ip(struct zebra_vrf * zvrf,vni_t vni,struct ipaddr * ip)3081 int zebra_vxlan_clear_dup_detect_vni_ip(struct zebra_vrf *zvrf, vni_t vni,
3082 					struct ipaddr *ip)
3083 {
3084 	zebra_evpn_t *zevpn;
3085 	zebra_neigh_t *nbr;
3086 	zebra_mac_t *mac;
3087 	char buf[INET6_ADDRSTRLEN];
3088 	char buf2[ETHER_ADDR_STRLEN];
3089 
3090 	if (!is_evpn_enabled())
3091 		return 0;
3092 
3093 	zevpn = zebra_evpn_lookup(vni);
3094 	if (!zevpn) {
3095 		zlog_debug("VNI %u does not exist\n", vni);
3096 		return -1;
3097 	}
3098 
3099 	nbr = zebra_evpn_neigh_lookup(zevpn, ip);
3100 	if (!nbr) {
3101 		zlog_warn("Requested host IP does not exist in VNI %u\n", vni);
3102 		return -1;
3103 	}
3104 
3105 	ipaddr2str(&nbr->ip, buf, sizeof(buf));
3106 
3107 	if (!CHECK_FLAG(nbr->flags, ZEBRA_NEIGH_DUPLICATE)) {
3108 		zlog_warn("Requested host IP %s is not duplicate detected\n",
3109 			  buf);
3110 		return -1;
3111 	}
3112 
3113 	mac = zebra_evpn_mac_lookup(zevpn, &nbr->emac);
3114 
3115 	if (CHECK_FLAG(mac->flags, ZEBRA_MAC_DUPLICATE)) {
3116 		zlog_warn(
3117 			"Requested IP's associated MAC %s is still in duplicate state\n",
3118 			prefix_mac2str(&nbr->emac, buf2, sizeof(buf2)));
3119 		return -1;
3120 	}
3121 
3122 	if (IS_ZEBRA_DEBUG_VXLAN)
3123 		zlog_debug("%s: clear neigh %s in dup state, flags 0x%x seq %u",
3124 			   __func__, buf, nbr->flags, nbr->loc_seq);
3125 
3126 	UNSET_FLAG(nbr->flags, ZEBRA_NEIGH_DUPLICATE);
3127 	nbr->dad_count = 0;
3128 	nbr->detect_start_time.tv_sec = 0;
3129 	nbr->detect_start_time.tv_usec = 0;
3130 	nbr->dad_dup_detect_time = 0;
3131 	THREAD_OFF(nbr->dad_ip_auto_recovery_timer);
3132 
3133 	if (!!CHECK_FLAG(nbr->flags, ZEBRA_NEIGH_LOCAL)) {
3134 		zebra_evpn_neigh_send_add_to_client(zevpn->vni, ip, &nbr->emac,
3135 						    nbr->mac, nbr->flags,
3136 						    nbr->loc_seq);
3137 	} else if (!!CHECK_FLAG(nbr->flags, ZEBRA_NEIGH_REMOTE)) {
3138 		zebra_evpn_rem_neigh_install(zevpn, nbr, false /*was_static*/);
3139 	}
3140 
3141 	return 0;
3142 }
3143 
zevpn_clear_dup_mac_hash(struct hash_bucket * bucket,void * ctxt)3144 static void zevpn_clear_dup_mac_hash(struct hash_bucket *bucket, void *ctxt)
3145 {
3146 	struct mac_walk_ctx *wctx = ctxt;
3147 	zebra_mac_t *mac;
3148 	zebra_evpn_t *zevpn;
3149 	struct listnode *node = NULL;
3150 	zebra_neigh_t *nbr = NULL;
3151 
3152 	mac = (zebra_mac_t *)bucket->data;
3153 	if (!mac)
3154 		return;
3155 
3156 	zevpn = wctx->zevpn;
3157 
3158 	if (!CHECK_FLAG(mac->flags, ZEBRA_MAC_DUPLICATE))
3159 		return;
3160 
3161 	UNSET_FLAG(mac->flags, ZEBRA_MAC_DUPLICATE);
3162 	mac->dad_count = 0;
3163 	mac->detect_start_time.tv_sec = 0;
3164 	mac->detect_start_time.tv_usec = 0;
3165 	mac->dad_dup_detect_time = 0;
3166 	THREAD_OFF(mac->dad_mac_auto_recovery_timer);
3167 
3168 	/* Remove all IPs as duplicate associcated with this MAC */
3169 	for (ALL_LIST_ELEMENTS_RO(mac->neigh_list, node, nbr)) {
3170 		if (CHECK_FLAG(nbr->flags, ZEBRA_NEIGH_LOCAL)
3171 		    && nbr->dad_count)
3172 			ZEBRA_NEIGH_SET_INACTIVE(nbr);
3173 
3174 		UNSET_FLAG(nbr->flags, ZEBRA_NEIGH_DUPLICATE);
3175 		nbr->dad_count = 0;
3176 		nbr->detect_start_time.tv_sec = 0;
3177 		nbr->dad_dup_detect_time = 0;
3178 	}
3179 
3180 	/* Local: Notify Peer VTEPs, Remote: Install the entry */
3181 	if (CHECK_FLAG(mac->flags, ZEBRA_MAC_LOCAL)) {
3182 		/* Inform to BGP */
3183 		if (zebra_evpn_mac_send_add_to_client(zevpn->vni, &mac->macaddr,
3184 						      mac->flags, mac->loc_seq,
3185 						      mac->es))
3186 			return;
3187 
3188 		/* Process all neighbors associated with this MAC. */
3189 		zebra_evpn_process_neigh_on_local_mac_change(zevpn, mac, 0,
3190 							     0 /*es_change*/);
3191 
3192 	} else if (CHECK_FLAG(mac->flags, ZEBRA_MAC_REMOTE)) {
3193 		zebra_evpn_process_neigh_on_remote_mac_add(zevpn, mac);
3194 
3195 		/* Install the entry. */
3196 		zebra_evpn_rem_mac_install(zevpn, mac, false /* was_static */);
3197 	}
3198 }
3199 
zevpn_clear_dup_detect_hash_vni_all(struct hash_bucket * bucket,void ** args)3200 static void zevpn_clear_dup_detect_hash_vni_all(struct hash_bucket *bucket,
3201 					    void **args)
3202 {
3203 	zebra_evpn_t *zevpn;
3204 	struct zebra_vrf *zvrf;
3205 	struct mac_walk_ctx m_wctx;
3206 	struct neigh_walk_ctx n_wctx;
3207 
3208 	zevpn = (zebra_evpn_t *)bucket->data;
3209 	if (!zevpn)
3210 		return;
3211 
3212 	zvrf = (struct zebra_vrf *)args[0];
3213 
3214 	if (hashcount(zevpn->neigh_table)) {
3215 		memset(&n_wctx, 0, sizeof(struct neigh_walk_ctx));
3216 		n_wctx.zevpn = zevpn;
3217 		n_wctx.zvrf = zvrf;
3218 		hash_iterate(zevpn->neigh_table,
3219 			     zebra_evpn_clear_dup_neigh_hash, &n_wctx);
3220 	}
3221 
3222 	if (num_valid_macs(zevpn)) {
3223 		memset(&m_wctx, 0, sizeof(struct mac_walk_ctx));
3224 		m_wctx.zevpn = zevpn;
3225 		m_wctx.zvrf = zvrf;
3226 		hash_iterate(zevpn->mac_table, zevpn_clear_dup_mac_hash, &m_wctx);
3227 	}
3228 
3229 }
3230 
zebra_vxlan_clear_dup_detect_vni_all(struct zebra_vrf * zvrf)3231 int zebra_vxlan_clear_dup_detect_vni_all(struct zebra_vrf *zvrf)
3232 {
3233 	void *args[1];
3234 
3235 	if (!is_evpn_enabled())
3236 		return 0;
3237 
3238 	args[0] = zvrf;
3239 
3240 	hash_iterate(zvrf->evpn_table,
3241 		     (void (*)(struct hash_bucket *, void *))
3242 		     zevpn_clear_dup_detect_hash_vni_all, args);
3243 
3244 	return 0;
3245 }
3246 
zebra_vxlan_clear_dup_detect_vni(struct zebra_vrf * zvrf,vni_t vni)3247 int zebra_vxlan_clear_dup_detect_vni(struct zebra_vrf *zvrf, vni_t vni)
3248 {
3249 	zebra_evpn_t *zevpn;
3250 	struct mac_walk_ctx m_wctx;
3251 	struct neigh_walk_ctx n_wctx;
3252 
3253 	if (!is_evpn_enabled())
3254 		return 0;
3255 
3256 	zevpn = zebra_evpn_lookup(vni);
3257 	if (!zevpn) {
3258 		zlog_warn("VNI %u does not exist\n", vni);
3259 		return CMD_WARNING;
3260 	}
3261 
3262 	if (hashcount(zevpn->neigh_table)) {
3263 		memset(&n_wctx, 0, sizeof(struct neigh_walk_ctx));
3264 		n_wctx.zevpn = zevpn;
3265 		n_wctx.zvrf = zvrf;
3266 		hash_iterate(zevpn->neigh_table,
3267 			     zebra_evpn_clear_dup_neigh_hash, &n_wctx);
3268 	}
3269 
3270 	if (num_valid_macs(zevpn)) {
3271 		memset(&m_wctx, 0, sizeof(struct mac_walk_ctx));
3272 		m_wctx.zevpn = zevpn;
3273 		m_wctx.zvrf = zvrf;
3274 		hash_iterate(zevpn->mac_table, zevpn_clear_dup_mac_hash, &m_wctx);
3275 	}
3276 
3277 	return 0;
3278 }
3279 
3280 /*
3281  * Display MACs for a VNI from specific VTEP (VTY command handler).
3282  */
zebra_vxlan_print_macs_vni_vtep(struct vty * vty,struct zebra_vrf * zvrf,vni_t vni,struct in_addr vtep_ip,bool use_json)3283 void zebra_vxlan_print_macs_vni_vtep(struct vty *vty, struct zebra_vrf *zvrf,
3284 				     vni_t vni, struct in_addr vtep_ip,
3285 				     bool use_json)
3286 {
3287 	zebra_evpn_t *zevpn;
3288 	uint32_t num_macs;
3289 	struct mac_walk_ctx wctx;
3290 	json_object *json = NULL;
3291 	json_object *json_mac = NULL;
3292 
3293 	if (!is_evpn_enabled())
3294 		return;
3295 	zevpn = zebra_evpn_lookup(vni);
3296 	if (!zevpn) {
3297 		if (use_json)
3298 			vty_out(vty, "{}\n");
3299 		else
3300 			vty_out(vty, "%% VNI %u does not exist\n", vni);
3301 		return;
3302 	}
3303 	num_macs = num_valid_macs(zevpn);
3304 	if (!num_macs)
3305 		return;
3306 
3307 	if (use_json) {
3308 		json = json_object_new_object();
3309 		json_mac = json_object_new_object();
3310 	}
3311 
3312 	memset(&wctx, 0, sizeof(struct mac_walk_ctx));
3313 	wctx.zevpn = zevpn;
3314 	wctx.vty = vty;
3315 	wctx.flags = SHOW_REMOTE_MAC_FROM_VTEP;
3316 	wctx.r_vtep_ip = vtep_ip;
3317 	wctx.json = json_mac;
3318 	hash_iterate(zevpn->mac_table, zebra_evpn_print_mac_hash, &wctx);
3319 
3320 	if (use_json) {
3321 		json_object_int_add(json, "numMacs", wctx.count);
3322 		if (wctx.count)
3323 			json_object_object_add(json, "macs", json_mac);
3324 		vty_out(vty, "%s\n", json_object_to_json_string_ext(
3325 					     json, JSON_C_TO_STRING_PRETTY));
3326 		json_object_free(json);
3327 	}
3328 }
3329 
3330 
3331 /*
3332  * Display VNI information (VTY command handler).
3333  *
3334  * use_json flag indicates that output should be in JSON format.
3335  * json_array is non NULL when JSON output needs to be aggregated (by the
3336  * caller) and then printed, otherwise, JSON evpn vni info is printed
3337  * right away.
3338  */
zebra_vxlan_print_vni(struct vty * vty,struct zebra_vrf * zvrf,vni_t vni,bool use_json,json_object * json_array)3339 void zebra_vxlan_print_vni(struct vty *vty, struct zebra_vrf *zvrf, vni_t vni,
3340 			   bool use_json, json_object *json_array)
3341 {
3342 	json_object *json = NULL;
3343 	void *args[2];
3344 	zebra_l3vni_t *zl3vni = NULL;
3345 	zebra_evpn_t *zevpn = NULL;
3346 
3347 	if (!is_evpn_enabled())
3348 		return;
3349 
3350 	if (use_json)
3351 		json = json_object_new_object();
3352 
3353 	args[0] = vty;
3354 	args[1] = json;
3355 
3356 	zl3vni = zl3vni_lookup(vni);
3357 	if (zl3vni) {
3358 		zl3vni_print(zl3vni, (void *)args);
3359 	} else {
3360 		zevpn = zebra_evpn_lookup(vni);
3361 		if (zevpn)
3362 			zebra_evpn_print(zevpn, (void *)args);
3363 		else if (!json)
3364 			vty_out(vty, "%% VNI %u does not exist\n", vni);
3365 	}
3366 
3367 	if (use_json) {
3368 		/*
3369 		 * Each "json" object contains info about 1 VNI.
3370 		 * When "json_array" is non-null, we aggreggate the json output
3371 		 * into json_array and print it as a JSON array.
3372 		 */
3373 		if (json_array)
3374 			json_object_array_add(json_array, json);
3375 		else {
3376 			vty_out(vty, "%s\n", json_object_to_json_string_ext(
3377 				json, JSON_C_TO_STRING_PRETTY));
3378 			json_object_free(json);
3379 		}
3380 	}
3381 }
3382 
3383 /* Display all global details for EVPN */
zebra_vxlan_print_evpn(struct vty * vty,bool uj)3384 void zebra_vxlan_print_evpn(struct vty *vty, bool uj)
3385 {
3386 	int num_l2vnis = 0;
3387 	int num_l3vnis = 0;
3388 	int num_vnis = 0;
3389 	json_object *json = NULL;
3390 	struct zebra_vrf *zvrf = NULL;
3391 
3392 	if (!is_evpn_enabled())
3393 		return;
3394 
3395 	zvrf = zebra_vrf_get_evpn();
3396 	if (!zvrf)
3397 		return;
3398 
3399 	num_l3vnis = hashcount(zrouter.l3vni_table);
3400 	num_l2vnis = hashcount(zvrf->evpn_table);
3401 	num_vnis = num_l2vnis + num_l3vnis;
3402 
3403 	if (uj) {
3404 		json = json_object_new_object();
3405 		json_object_string_add(json, "advertiseGatewayMacip",
3406 				       zvrf->advertise_gw_macip ? "Yes" : "No");
3407 		json_object_int_add(json, "numVnis", num_vnis);
3408 		json_object_int_add(json, "numL2Vnis", num_l2vnis);
3409 		json_object_int_add(json, "numL3Vnis", num_l3vnis);
3410 		if (zvrf->dup_addr_detect)
3411 			json_object_boolean_true_add(json,
3412 						"isDuplicateAddrDetection");
3413 		else
3414 			json_object_boolean_false_add(json,
3415 						"isDuplicateAddrDetection");
3416 		json_object_int_add(json, "maxMoves", zvrf->dad_max_moves);
3417 		json_object_int_add(json, "detectionTime", zvrf->dad_time);
3418 		json_object_int_add(json, "detectionFreezeTime",
3419 				    zvrf->dad_freeze_time);
3420 
3421 	} else {
3422 		vty_out(vty, "L2 VNIs: %u\n", num_l2vnis);
3423 		vty_out(vty, "L3 VNIs: %u\n", num_l3vnis);
3424 		vty_out(vty, "Advertise gateway mac-ip: %s\n",
3425 			zvrf->advertise_gw_macip ? "Yes" : "No");
3426 		vty_out(vty, "Advertise svi mac-ip: %s\n",
3427 			zvrf->advertise_svi_macip ? "Yes" : "No");
3428 		vty_out(vty, "Duplicate address detection: %s\n",
3429 			zvrf->dup_addr_detect ? "Enable" : "Disable");
3430 		vty_out(vty, "  Detection max-moves %u, time %d\n",
3431 			zvrf->dad_max_moves, zvrf->dad_time);
3432 		if (zvrf->dad_freeze) {
3433 			if (zvrf->dad_freeze_time)
3434 				vty_out(vty, "  Detection freeze %u\n",
3435 					zvrf->dad_freeze_time);
3436 			else
3437 				vty_out(vty, "  Detection freeze %s\n",
3438 					"permanent");
3439 		}
3440 	}
3441 
3442 	if (uj) {
3443 		vty_out(vty, "%s\n", json_object_to_json_string_ext(
3444 					     json, JSON_C_TO_STRING_PRETTY));
3445 		json_object_free(json);
3446 	}
3447 }
3448 
3449 /*
3450  * Display VNI hash table (VTY command handler).
3451  */
zebra_vxlan_print_vnis(struct vty * vty,struct zebra_vrf * zvrf,bool use_json)3452 void zebra_vxlan_print_vnis(struct vty *vty, struct zebra_vrf *zvrf,
3453 			    bool use_json)
3454 {
3455 	json_object *json = NULL;
3456 	void *args[2];
3457 
3458 	if (!is_evpn_enabled())
3459 		return;
3460 
3461 	if (use_json)
3462 		json = json_object_new_object();
3463 	else
3464 		vty_out(vty, "%-10s %-4s %-21s %-8s %-8s %-15s %-37s\n", "VNI",
3465 			"Type", "VxLAN IF", "# MACs", "# ARPs",
3466 			"# Remote VTEPs", "Tenant VRF");
3467 
3468 	args[0] = vty;
3469 	args[1] = json;
3470 
3471 	/* Display all L2-VNIs */
3472 	hash_iterate(
3473 		zvrf->evpn_table,
3474 		(void (*)(struct hash_bucket *, void *))zebra_evpn_print_hash,
3475 		args);
3476 
3477 	/* Display all L3-VNIs */
3478 	hash_iterate(zrouter.l3vni_table,
3479 		     (void (*)(struct hash_bucket *, void *))zl3vni_print_hash,
3480 		     args);
3481 
3482 	if (use_json) {
3483 		vty_out(vty, "%s\n", json_object_to_json_string_ext(
3484 					     json, JSON_C_TO_STRING_PRETTY));
3485 		json_object_free(json);
3486 	}
3487 }
3488 
zebra_vxlan_dup_addr_detection(ZAPI_HANDLER_ARGS)3489 void zebra_vxlan_dup_addr_detection(ZAPI_HANDLER_ARGS)
3490 {
3491 	struct stream *s;
3492 	int time = 0;
3493 	uint32_t max_moves = 0;
3494 	uint32_t freeze_time = 0;
3495 	bool dup_addr_detect = false;
3496 	bool freeze = false;
3497 
3498 	s = msg;
3499 	STREAM_GETL(s, dup_addr_detect);
3500 	STREAM_GETL(s, time);
3501 	STREAM_GETL(s, max_moves);
3502 	STREAM_GETL(s, freeze);
3503 	STREAM_GETL(s, freeze_time);
3504 
3505 	/* DAD previous state was enabled, and new state is disable,
3506 	 * clear all duplicate detected addresses.
3507 	 */
3508 	if (zvrf->dup_addr_detect && !dup_addr_detect)
3509 		zebra_vxlan_clear_dup_detect_vni_all(zvrf);
3510 
3511 	zvrf->dup_addr_detect = dup_addr_detect;
3512 	zvrf->dad_time = time;
3513 	zvrf->dad_max_moves = max_moves;
3514 	zvrf->dad_freeze = freeze;
3515 	zvrf->dad_freeze_time = freeze_time;
3516 
3517 	if (IS_ZEBRA_DEBUG_VXLAN)
3518 		zlog_debug(
3519 			"VRF %s duplicate detect %s max_moves %u timeout %u freeze %s freeze_time %u",
3520 			vrf_id_to_name(zvrf->vrf->vrf_id),
3521 			zvrf->dup_addr_detect ? "enable" : "disable",
3522 			zvrf->dad_max_moves,
3523 			zvrf->dad_time,
3524 			zvrf->dad_freeze ? "enable" : "disable",
3525 			zvrf->dad_freeze_time);
3526 
3527 stream_failure:
3528 	return;
3529 }
3530 
3531 /*
3532  * Display VNI hash table in detail(VTY command handler).
3533  */
zebra_vxlan_print_vnis_detail(struct vty * vty,struct zebra_vrf * zvrf,bool use_json)3534 void zebra_vxlan_print_vnis_detail(struct vty *vty, struct zebra_vrf *zvrf,
3535 				   bool use_json)
3536 {
3537 	json_object *json_array = NULL;
3538 	struct zebra_ns *zns = NULL;
3539 	struct zebra_evpn_show zes;
3540 
3541 	if (!is_evpn_enabled())
3542 		return;
3543 
3544 	zns = zebra_ns_lookup(NS_DEFAULT);
3545 	if (!zns)
3546 		return;
3547 
3548 	if (use_json)
3549 		json_array = json_object_new_array();
3550 
3551 	zes.vty = vty;
3552 	zes.json = json_array;
3553 	zes.zvrf = zvrf;
3554 	zes.use_json = use_json;
3555 
3556 	/* Display all L2-VNIs */
3557 	hash_iterate(zvrf->evpn_table,
3558 		     (void (*)(struct hash_bucket *,
3559 			       void *))zebra_evpn_print_hash_detail,
3560 		     &zes);
3561 
3562 	/* Display all L3-VNIs */
3563 	hash_iterate(zrouter.l3vni_table,
3564 		     (void (*)(struct hash_bucket *,
3565 			       void *))zl3vni_print_hash_detail,
3566 		     &zes);
3567 
3568 	if (use_json) {
3569 		vty_out(vty, "%s\n",
3570 			json_object_to_json_string_ext(
3571 				json_array, JSON_C_TO_STRING_PRETTY));
3572 		json_object_free(json_array);
3573 	}
3574 }
3575 
3576 /*
3577  * Handle neighbor delete notification from the kernel (on a VLAN device
3578  * / L3 interface). This may result in either the neighbor getting deleted
3579  * from our database or being re-added to the kernel (if it is a valid
3580  * remote neighbor).
3581  */
zebra_vxlan_handle_kernel_neigh_del(struct interface * ifp,struct interface * link_if,struct ipaddr * ip)3582 int zebra_vxlan_handle_kernel_neigh_del(struct interface *ifp,
3583 					struct interface *link_if,
3584 					struct ipaddr *ip)
3585 {
3586 	char buf[INET6_ADDRSTRLEN];
3587 	zebra_evpn_t *zevpn = NULL;
3588 	zebra_l3vni_t *zl3vni = NULL;
3589 
3590 	/* check if this is a remote neigh entry corresponding to remote
3591 	 * next-hop
3592 	 */
3593 	zl3vni = zl3vni_from_svi(ifp, link_if);
3594 	if (zl3vni)
3595 		return zl3vni_local_nh_del(zl3vni, ip);
3596 
3597 	/* We are only interested in neighbors on an SVI that resides on top
3598 	 * of a VxLAN bridge.
3599 	 */
3600 	zevpn = zebra_evpn_from_svi(ifp, link_if);
3601 	if (!zevpn) {
3602 		if (IS_ZEBRA_DEBUG_VXLAN)
3603 			zlog_debug(
3604 				"%s: Del neighbor %s EVPN is not present for interface %s",
3605 				__func__, ipaddr2str(ip, buf, sizeof(buf)),
3606 				ifp->name);
3607 		return 0;
3608 	}
3609 
3610 	if (!zevpn->vxlan_if) {
3611 		zlog_debug(
3612 			"VNI %u hash %p doesn't have intf upon local neighbor DEL",
3613 			zevpn->vni, zevpn);
3614 		return -1;
3615 	}
3616 
3617 	if (IS_ZEBRA_DEBUG_VXLAN)
3618 		zlog_debug("Del neighbor %s intf %s(%u) -> L2-VNI %u",
3619 			   ipaddr2str(ip, buf, sizeof(buf)), ifp->name,
3620 			   ifp->ifindex, zevpn->vni);
3621 
3622 	return zebra_evpn_neigh_del_ip(zevpn, ip);
3623 }
3624 
3625 /*
3626  * Handle neighbor add or update notification from the kernel (on a VLAN
3627  * device / L3 interface). This is typically for a local neighbor but can
3628  * also be for a remote neighbor (e.g., ageout notification). It could
3629  * also be a "move" scenario.
3630  */
zebra_vxlan_handle_kernel_neigh_update(struct interface * ifp,struct interface * link_if,struct ipaddr * ip,struct ethaddr * macaddr,uint16_t state,bool is_ext,bool is_router,bool local_inactive,bool dp_static)3631 int zebra_vxlan_handle_kernel_neigh_update(struct interface *ifp,
3632 					   struct interface *link_if,
3633 					   struct ipaddr *ip,
3634 					   struct ethaddr *macaddr,
3635 					   uint16_t state,
3636 					   bool is_ext,
3637 					   bool is_router,
3638 					   bool local_inactive, bool dp_static)
3639 {
3640 	char buf[ETHER_ADDR_STRLEN];
3641 	char buf2[INET6_ADDRSTRLEN];
3642 	zebra_evpn_t *zevpn = NULL;
3643 	zebra_l3vni_t *zl3vni = NULL;
3644 
3645 	/* check if this is a remote neigh entry corresponding to remote
3646 	 * next-hop
3647 	 */
3648 	zl3vni = zl3vni_from_svi(ifp, link_if);
3649 	if (zl3vni)
3650 		return zl3vni_local_nh_add_update(zl3vni, ip, state);
3651 
3652 	/* We are only interested in neighbors on an SVI that resides on top
3653 	 * of a VxLAN bridge.
3654 	 */
3655 	zevpn = zebra_evpn_from_svi(ifp, link_if);
3656 	if (!zevpn)
3657 		return 0;
3658 
3659 	if (IS_ZEBRA_DEBUG_VXLAN || IS_ZEBRA_DEBUG_EVPN_MH_NEIGH)
3660 		zlog_debug(
3661 			"Add/Update neighbor %s MAC %s intf %s(%u) state 0x%x %s%s%s-> L2-VNI %u",
3662 			ipaddr2str(ip, buf2, sizeof(buf2)),
3663 			prefix_mac2str(macaddr, buf, sizeof(buf)), ifp->name,
3664 			ifp->ifindex, state, is_ext ? "ext-learned " : "",
3665 			is_router ? "router " : "",
3666 			local_inactive ? "local_inactive " : "",
3667 			zevpn->vni);
3668 
3669 	/* Is this about a local neighbor or a remote one? */
3670 	if (!is_ext)
3671 		return zebra_evpn_local_neigh_update(zevpn, ifp, ip, macaddr,
3672 						     is_router, local_inactive,
3673 						     dp_static);
3674 
3675 	return zebra_evpn_remote_neigh_update(zevpn, ifp, ip, macaddr, state);
3676 }
3677 
3678 static int32_t
zebra_vxlan_remote_macip_helper(bool add,struct stream * s,vni_t * vni,struct ethaddr * macaddr,uint16_t * ipa_len,struct ipaddr * ip,struct in_addr * vtep_ip,uint8_t * flags,uint32_t * seq,esi_t * esi)3679 zebra_vxlan_remote_macip_helper(bool add, struct stream *s, vni_t *vni,
3680 				struct ethaddr *macaddr, uint16_t *ipa_len,
3681 				struct ipaddr *ip, struct in_addr *vtep_ip,
3682 				uint8_t *flags, uint32_t *seq, esi_t *esi)
3683 {
3684 	uint16_t l = 0;
3685 
3686 	/*
3687 	 * Obtain each remote MACIP and process.
3688 	 * Message contains VNI, followed by MAC followed by IP (if any)
3689 	 * followed by remote VTEP IP.
3690 	 */
3691 	memset(ip, 0, sizeof(*ip));
3692 	STREAM_GETL(s, *vni);
3693 	STREAM_GET(macaddr->octet, s, ETH_ALEN);
3694 	STREAM_GETL(s, *ipa_len);
3695 
3696 	if (*ipa_len) {
3697 		if (*ipa_len == IPV4_MAX_BYTELEN)
3698 			ip->ipa_type = IPADDR_V4;
3699 		else if (*ipa_len == IPV6_MAX_BYTELEN)
3700 			ip->ipa_type = IPADDR_V6;
3701 		else {
3702 			if (IS_ZEBRA_DEBUG_VXLAN)
3703 				zlog_debug(
3704 					"ipa_len *must* be %d or %d bytes in length not %d",
3705 					IPV4_MAX_BYTELEN, IPV6_MAX_BYTELEN,
3706 					*ipa_len);
3707 			goto stream_failure;
3708 		}
3709 
3710 		STREAM_GET(&ip->ip.addr, s, *ipa_len);
3711 	}
3712 	l += 4 + ETH_ALEN + 4 + *ipa_len;
3713 	STREAM_GET(&vtep_ip->s_addr, s, IPV4_MAX_BYTELEN);
3714 	l += IPV4_MAX_BYTELEN;
3715 
3716 	if (add) {
3717 		STREAM_GETC(s, *flags);
3718 		STREAM_GETL(s, *seq);
3719 		l += 5;
3720 		STREAM_GET(esi, s, sizeof(esi_t));
3721 		l += sizeof(esi_t);
3722 	}
3723 
3724 	return l;
3725 
3726 stream_failure:
3727 	return -1;
3728 }
3729 
3730 /*
3731  * Handle message from client to delete a remote MACIP for a VNI.
3732  */
zebra_vxlan_remote_macip_del(ZAPI_HANDLER_ARGS)3733 void zebra_vxlan_remote_macip_del(ZAPI_HANDLER_ARGS)
3734 {
3735 	struct stream *s;
3736 	vni_t vni;
3737 	struct ethaddr macaddr;
3738 	struct ipaddr ip;
3739 	struct in_addr vtep_ip;
3740 	uint16_t l = 0, ipa_len;
3741 	char buf[ETHER_ADDR_STRLEN];
3742 	char buf1[INET6_ADDRSTRLEN];
3743 
3744 	memset(&macaddr, 0, sizeof(struct ethaddr));
3745 	memset(&ip, 0, sizeof(struct ipaddr));
3746 	memset(&vtep_ip, 0, sizeof(struct in_addr));
3747 
3748 	s = msg;
3749 
3750 	while (l < hdr->length) {
3751 		int res_length = zebra_vxlan_remote_macip_helper(
3752 			false, s, &vni, &macaddr, &ipa_len, &ip, &vtep_ip, NULL,
3753 			NULL, NULL);
3754 
3755 		if (res_length == -1)
3756 			goto stream_failure;
3757 
3758 		l += res_length;
3759 		if (IS_ZEBRA_DEBUG_VXLAN)
3760 			zlog_debug(
3761 				"Recv MACIP DEL VNI %u MAC %s%s%s Remote VTEP %s from %s",
3762 				vni,
3763 				prefix_mac2str(&macaddr, buf, sizeof(buf)),
3764 				ipa_len ? " IP " : "",
3765 				ipa_len ?
3766 				ipaddr2str(&ip, buf1, sizeof(buf1)) : "",
3767 				inet_ntoa(vtep_ip),
3768 				zebra_route_string(client->proto));
3769 
3770 		process_remote_macip_del(vni, &macaddr, ipa_len, &ip, vtep_ip);
3771 	}
3772 
3773 stream_failure:
3774 	return;
3775 }
3776 
3777 /*
3778  * Handle message from client to add a remote MACIP for a VNI. This
3779  * could be just the add of a MAC address or the add of a neighbor
3780  * (IP+MAC).
3781  */
zebra_vxlan_remote_macip_add(ZAPI_HANDLER_ARGS)3782 void zebra_vxlan_remote_macip_add(ZAPI_HANDLER_ARGS)
3783 {
3784 	struct stream *s;
3785 	vni_t vni;
3786 	struct ethaddr macaddr;
3787 	struct ipaddr ip;
3788 	struct in_addr vtep_ip;
3789 	uint16_t l = 0, ipa_len;
3790 	uint8_t flags = 0;
3791 	uint32_t seq;
3792 	char buf[ETHER_ADDR_STRLEN];
3793 	char buf1[INET6_ADDRSTRLEN];
3794 	esi_t esi;
3795 	char esi_buf[ESI_STR_LEN];
3796 
3797 	memset(&macaddr, 0, sizeof(struct ethaddr));
3798 	memset(&ip, 0, sizeof(struct ipaddr));
3799 	memset(&vtep_ip, 0, sizeof(struct in_addr));
3800 
3801 	if (!EVPN_ENABLED(zvrf)) {
3802 		zlog_debug("EVPN not enabled, ignoring remote MACIP ADD");
3803 		return;
3804 	}
3805 
3806 	s = msg;
3807 
3808 	while (l < hdr->length) {
3809 		int res_length = zebra_vxlan_remote_macip_helper(
3810 			true, s, &vni, &macaddr, &ipa_len, &ip, &vtep_ip,
3811 			&flags, &seq, &esi);
3812 
3813 		if (res_length == -1)
3814 			goto stream_failure;
3815 
3816 		l += res_length;
3817 		if (IS_ZEBRA_DEBUG_VXLAN) {
3818 			if (memcmp(&esi, zero_esi, sizeof(esi_t)))
3819 				esi_to_str(&esi, esi_buf, sizeof(esi_buf));
3820 			else
3821 				strlcpy(esi_buf, "-", ESI_STR_LEN);
3822 			zlog_debug(
3823 				"Recv %sMACIP ADD VNI %u MAC %s%s%s flags 0x%x seq %u VTEP %s ESI %s from %s",
3824 				(flags & ZEBRA_MACIP_TYPE_SYNC_PATH) ?
3825 				"sync-" : "",
3826 				vni,
3827 				prefix_mac2str(&macaddr, buf, sizeof(buf)),
3828 				ipa_len ? " IP " : "",
3829 				ipa_len ?
3830 				ipaddr2str(&ip, buf1, sizeof(buf1)) : "",
3831 				flags, seq, inet_ntoa(vtep_ip), esi_buf,
3832 				zebra_route_string(client->proto));
3833 		}
3834 
3835 		process_remote_macip_add(vni, &macaddr, ipa_len, &ip,
3836 					 flags, seq, vtep_ip, &esi);
3837 	}
3838 
3839 stream_failure:
3840 	return;
3841 }
3842 
3843 /*
3844  * Handle remote vtep delete by kernel; re-add the vtep if we have it
3845  */
zebra_vxlan_check_readd_vtep(struct interface * ifp,struct in_addr vtep_ip)3846 int zebra_vxlan_check_readd_vtep(struct interface *ifp,
3847 				 struct in_addr vtep_ip)
3848 {
3849 	struct zebra_if *zif;
3850 	struct zebra_vrf *zvrf = NULL;
3851 	struct zebra_l2info_vxlan *vxl;
3852 	vni_t vni;
3853 	zebra_evpn_t *zevpn = NULL;
3854 	zebra_vtep_t *zvtep = NULL;
3855 
3856 	zif = ifp->info;
3857 	assert(zif);
3858 	vxl = &zif->l2info.vxl;
3859 	vni = vxl->vni;
3860 
3861 	/* If EVPN is not enabled, nothing to do. */
3862 	if (!is_evpn_enabled())
3863 		return 0;
3864 
3865 	/* Locate VRF corresponding to interface. */
3866 	zvrf = vrf_info_lookup(ifp->vrf_id);
3867 	if (!zvrf)
3868 		return -1;
3869 
3870 	/* Locate hash entry; it is expected to exist. */
3871 	zevpn = zebra_evpn_lookup(vni);
3872 	if (!zevpn)
3873 		return 0;
3874 
3875 	/* If the remote vtep entry doesn't exists nothing to do */
3876 	zvtep = zebra_evpn_vtep_find(zevpn, &vtep_ip);
3877 	if (!zvtep)
3878 		return 0;
3879 
3880 	if (IS_ZEBRA_DEBUG_VXLAN)
3881 		zlog_debug(
3882 			"Del MAC for remote VTEP %s intf %s(%u) VNI %u - readd",
3883 			inet_ntoa(vtep_ip), ifp->name, ifp->ifindex, vni);
3884 
3885 	zebra_evpn_vtep_install(zevpn, zvtep);
3886 	return 0;
3887 }
3888 
3889 /*
3890  * Handle notification of MAC add/update over VxLAN. If the kernel is notifying
3891  * us, this must involve a multihoming scenario. Treat this as implicit delete
3892  * of any prior local MAC.
3893  */
zebra_vxlan_check_del_local_mac(struct interface * ifp,struct interface * br_if,struct ethaddr * macaddr,vlanid_t vid)3894 int zebra_vxlan_check_del_local_mac(struct interface *ifp,
3895 				    struct interface *br_if,
3896 				    struct ethaddr *macaddr, vlanid_t vid)
3897 {
3898 	struct zebra_if *zif;
3899 	struct zebra_l2info_vxlan *vxl;
3900 	vni_t vni;
3901 	zebra_evpn_t *zevpn;
3902 	zebra_mac_t *mac;
3903 	char buf[ETHER_ADDR_STRLEN];
3904 
3905 	zif = ifp->info;
3906 	assert(zif);
3907 	vxl = &zif->l2info.vxl;
3908 	vni = vxl->vni;
3909 
3910 	/* Check if EVPN is enabled. */
3911 	if (!is_evpn_enabled())
3912 		return 0;
3913 
3914 	/* Locate hash entry; it is expected to exist. */
3915 	zevpn = zebra_evpn_lookup(vni);
3916 	if (!zevpn)
3917 		return 0;
3918 
3919 	/* If entry doesn't exist, nothing to do. */
3920 	mac = zebra_evpn_mac_lookup(zevpn, macaddr);
3921 	if (!mac)
3922 		return 0;
3923 
3924 	/* Is it a local entry? */
3925 	if (!CHECK_FLAG(mac->flags, ZEBRA_MAC_LOCAL))
3926 		return 0;
3927 
3928 	if (IS_ZEBRA_DEBUG_VXLAN)
3929 		zlog_debug(
3930 			"Add/update remote MAC %s intf %s(%u) VNI %u flags 0x%x - del local",
3931 			prefix_mac2str(macaddr, buf, sizeof(buf)), ifp->name,
3932 			ifp->ifindex, vni, mac->flags);
3933 
3934 	/* Remove MAC from BGP. */
3935 	zebra_evpn_mac_send_del_to_client(zevpn->vni, macaddr, mac->flags,
3936 					  false /* force */);
3937 
3938 	/*
3939 	 * If there are no neigh associated with the mac delete the mac
3940 	 * else mark it as AUTO for forward reference
3941 	 */
3942 	if (!listcount(mac->neigh_list)) {
3943 		zebra_evpn_mac_del(zevpn, mac);
3944 	} else {
3945 		UNSET_FLAG(mac->flags, ZEBRA_MAC_ALL_LOCAL_FLAGS);
3946 		UNSET_FLAG(mac->flags, ZEBRA_MAC_STICKY);
3947 		SET_FLAG(mac->flags, ZEBRA_MAC_AUTO);
3948 	}
3949 
3950 	return 0;
3951 }
3952 
3953 /*
3954  * Handle remote MAC delete by kernel; readd the remote MAC if we have it.
3955  * This can happen because the remote MAC entries are also added as "dynamic",
3956  * so the kernel can ageout the entry.
3957  */
zebra_vxlan_check_readd_remote_mac(struct interface * ifp,struct interface * br_if,struct ethaddr * macaddr,vlanid_t vid)3958 int zebra_vxlan_check_readd_remote_mac(struct interface *ifp,
3959 				       struct interface *br_if,
3960 				       struct ethaddr *macaddr, vlanid_t vid)
3961 {
3962 	struct zebra_if *zif = NULL;
3963 	struct zebra_l2info_vxlan *vxl = NULL;
3964 	vni_t vni;
3965 	zebra_evpn_t *zevpn = NULL;
3966 	zebra_l3vni_t *zl3vni = NULL;
3967 	zebra_mac_t *mac = NULL;
3968 	char buf[ETHER_ADDR_STRLEN];
3969 
3970 	zif = ifp->info;
3971 	assert(zif);
3972 	vxl = &zif->l2info.vxl;
3973 	vni = vxl->vni;
3974 
3975 	/* Check if EVPN is enabled. */
3976 	if (!is_evpn_enabled())
3977 		return 0;
3978 
3979 	/* check if this is a remote RMAC and readd simillar to remote macs */
3980 	zl3vni = zl3vni_lookup(vni);
3981 	if (zl3vni)
3982 		return zebra_vxlan_readd_remote_rmac(zl3vni, macaddr);
3983 
3984 	/* Locate hash entry; it is expected to exist. */
3985 	zevpn = zebra_evpn_lookup(vni);
3986 	if (!zevpn)
3987 		return 0;
3988 
3989 	/* If entry doesn't exist, nothing to do. */
3990 	mac = zebra_evpn_mac_lookup(zevpn, macaddr);
3991 	if (!mac)
3992 		return 0;
3993 
3994 	/* Is it a remote entry? */
3995 	if (!CHECK_FLAG(mac->flags, ZEBRA_MAC_REMOTE))
3996 		return 0;
3997 
3998 	if (IS_ZEBRA_DEBUG_VXLAN)
3999 		zlog_debug("Del remote MAC %s intf %s(%u) VNI %u - readd",
4000 			   prefix_mac2str(macaddr, buf, sizeof(buf)), ifp->name,
4001 			   ifp->ifindex, vni);
4002 
4003 	zebra_evpn_rem_mac_install(zevpn, mac, false /* was_static */);
4004 	return 0;
4005 }
4006 
4007 /*
4008  * Handle local MAC delete (on a port or VLAN corresponding to this VNI).
4009  */
zebra_vxlan_local_mac_del(struct interface * ifp,struct interface * br_if,struct ethaddr * macaddr,vlanid_t vid)4010 int zebra_vxlan_local_mac_del(struct interface *ifp, struct interface *br_if,
4011 			      struct ethaddr *macaddr, vlanid_t vid)
4012 {
4013 	zebra_evpn_t *zevpn;
4014 
4015 	/* We are interested in MACs only on ports or (port, VLAN) that
4016 	 * map to a VNI.
4017 	 */
4018 	zevpn = zebra_evpn_map_vlan(ifp, br_if, vid);
4019 	if (!zevpn)
4020 		return 0;
4021 	if (!zevpn->vxlan_if) {
4022 		zlog_debug(
4023 			"VNI %u hash %p doesn't have intf upon local MAC DEL",
4024 			zevpn->vni, zevpn);
4025 		return -1;
4026 	}
4027 
4028 	return zebra_evpn_del_local_mac(zevpn, macaddr, ifp);
4029 }
4030 
4031 /*
4032  * Handle local MAC add (on a port or VLAN corresponding to this VNI).
4033  */
zebra_vxlan_local_mac_add_update(struct interface * ifp,struct interface * br_if,struct ethaddr * macaddr,vlanid_t vid,bool sticky,bool local_inactive,bool dp_static)4034 int zebra_vxlan_local_mac_add_update(struct interface *ifp,
4035 				     struct interface *br_if,
4036 				     struct ethaddr *macaddr, vlanid_t vid,
4037 					 bool sticky, bool local_inactive,
4038 					 bool dp_static)
4039 {
4040 	zebra_evpn_t *zevpn;
4041 	struct zebra_vrf *zvrf;
4042 	char buf[ETHER_ADDR_STRLEN];
4043 
4044 	assert(ifp);
4045 
4046 	/* We are interested in MACs only on ports or (port, VLAN) that
4047 	 * map to an EVPN.
4048 	 */
4049 	zevpn = zebra_evpn_map_vlan(ifp, br_if, vid);
4050 	if (!zevpn) {
4051 		if (IS_ZEBRA_DEBUG_VXLAN)
4052 			zlog_debug(
4053 				"        Add/Update %sMAC %s intf %s(%u) VID %u, could not find EVPN",
4054 				sticky ? "sticky " : "",
4055 				prefix_mac2str(macaddr, buf, sizeof(buf)),
4056 				ifp->name, ifp->ifindex, vid);
4057 		return 0;
4058 	}
4059 
4060 	if (!zevpn->vxlan_if) {
4061 		if (IS_ZEBRA_DEBUG_VXLAN)
4062 			zlog_debug(
4063 				"        VNI %u hash %p doesn't have intf upon local MAC ADD",
4064 				zevpn->vni, zevpn);
4065 		return -1;
4066 	}
4067 
4068 	zvrf = zebra_vrf_get_evpn();
4069 	if (!zvrf) {
4070 		if (IS_ZEBRA_DEBUG_VXLAN)
4071 			zlog_debug("        No Evpn Global Vrf found");
4072 		return -1;
4073 	}
4074 
4075 	return zebra_evpn_add_update_local_mac(zvrf, zevpn, ifp, macaddr, vid,
4076 					       sticky, local_inactive,
4077 					       dp_static);
4078 }
4079 
4080 /*
4081  * Handle message from client to delete a remote VTEP for an EVPN.
4082  */
zebra_vxlan_remote_vtep_del(ZAPI_HANDLER_ARGS)4083 void zebra_vxlan_remote_vtep_del(ZAPI_HANDLER_ARGS)
4084 {
4085 	struct stream *s;
4086 	unsigned short l = 0;
4087 	vni_t vni;
4088 	struct in_addr vtep_ip;
4089 	zebra_evpn_t *zevpn;
4090 	zebra_vtep_t *zvtep;
4091 	struct interface *ifp;
4092 	struct zebra_if *zif;
4093 
4094 	if (!is_evpn_enabled()) {
4095 		zlog_debug(
4096 			"%s: EVPN is not enabled yet we have received a vtep del command",
4097 			__func__);
4098 		return;
4099 	}
4100 
4101 	if (!EVPN_ENABLED(zvrf)) {
4102 		zlog_debug("Recv MACIP DEL for non-EVPN VRF %u",
4103 			  zvrf_id(zvrf));
4104 		return;
4105 	}
4106 
4107 	s = msg;
4108 
4109 	while (l < hdr->length) {
4110 		int flood_control __attribute__((unused));
4111 
4112 		/* Obtain each remote VTEP and process. */
4113 		STREAM_GETL(s, vni);
4114 		l += 4;
4115 		STREAM_GET(&vtep_ip.s_addr, s, IPV4_MAX_BYTELEN);
4116 		l += IPV4_MAX_BYTELEN;
4117 
4118 		/* Flood control is intentionally ignored right now */
4119 		STREAM_GETL(s, flood_control);
4120 		l += 4;
4121 
4122 		if (IS_ZEBRA_DEBUG_VXLAN)
4123 			zlog_debug("Recv VTEP_DEL %s VNI %u from %s",
4124 				   inet_ntoa(vtep_ip), vni,
4125 				   zebra_route_string(client->proto));
4126 
4127 		/* Locate VNI hash entry - expected to exist. */
4128 		zevpn = zebra_evpn_lookup(vni);
4129 		if (!zevpn) {
4130 			if (IS_ZEBRA_DEBUG_VXLAN)
4131 				zlog_debug(
4132 					"Failed to locate VNI hash upon remote VTEP DEL, VNI %u",
4133 					vni);
4134 			continue;
4135 		}
4136 
4137 		ifp = zevpn->vxlan_if;
4138 		if (!ifp) {
4139 			zlog_debug(
4140 				"VNI %u hash %p doesn't have intf upon remote VTEP DEL",
4141 				zevpn->vni, zevpn);
4142 			continue;
4143 		}
4144 		zif = ifp->info;
4145 
4146 		/* If down or not mapped to a bridge, we're done. */
4147 		if (!if_is_operative(ifp) || !zif->brslave_info.br_if)
4148 			continue;
4149 
4150 		/* If the remote VTEP does not exist, there's nothing more to
4151 		 * do.
4152 		 * Otherwise, uninstall any remote MACs pointing to this VTEP
4153 		 * and
4154 		 * then, the VTEP entry itself and remove it.
4155 		 */
4156 		zvtep = zebra_evpn_vtep_find(zevpn, &vtep_ip);
4157 		if (!zvtep)
4158 			continue;
4159 
4160 		zebra_evpn_vtep_uninstall(zevpn, &vtep_ip);
4161 		zebra_evpn_vtep_del(zevpn, zvtep);
4162 	}
4163 
4164 stream_failure:
4165 	return;
4166 }
4167 
4168 /*
4169  * Handle message from client to add a remote VTEP for an EVPN.
4170  */
zebra_vxlan_remote_vtep_add(ZAPI_HANDLER_ARGS)4171 void zebra_vxlan_remote_vtep_add(ZAPI_HANDLER_ARGS)
4172 {
4173 	struct stream *s;
4174 	unsigned short l = 0;
4175 	vni_t vni;
4176 	struct in_addr vtep_ip;
4177 	zebra_evpn_t *zevpn;
4178 	struct interface *ifp;
4179 	struct zebra_if *zif;
4180 	int flood_control;
4181 	zebra_vtep_t *zvtep;
4182 
4183 	if (!is_evpn_enabled()) {
4184 		zlog_debug(
4185 			"%s: EVPN not enabled yet we received a vtep_add zapi call",
4186 			__func__);
4187 		return;
4188 	}
4189 
4190 	if (!EVPN_ENABLED(zvrf)) {
4191 		zlog_debug("Recv MACIP ADD for non-EVPN VRF %u",
4192 			  zvrf_id(zvrf));
4193 		return;
4194 	}
4195 
4196 	s = msg;
4197 
4198 	while (l < hdr->length) {
4199 		/* Obtain each remote VTEP and process. */
4200 		STREAM_GETL(s, vni);
4201 		l += 4;
4202 		STREAM_GET(&vtep_ip.s_addr, s, IPV4_MAX_BYTELEN);
4203 		STREAM_GETL(s, flood_control);
4204 		l += IPV4_MAX_BYTELEN + 4;
4205 
4206 		if (IS_ZEBRA_DEBUG_VXLAN)
4207 			zlog_debug("Recv VTEP_ADD %s VNI %u flood %d from %s",
4208 					inet_ntoa(vtep_ip), vni, flood_control,
4209 					zebra_route_string(client->proto));
4210 
4211 		/* Locate VNI hash entry - expected to exist. */
4212 		zevpn = zebra_evpn_lookup(vni);
4213 		if (!zevpn) {
4214 			flog_err(
4215 				EC_ZEBRA_VTEP_ADD_FAILED,
4216 				"Failed to locate EVPN hash upon remote VTEP ADD, VNI %u",
4217 				vni);
4218 			continue;
4219 		}
4220 
4221 		ifp = zevpn->vxlan_if;
4222 		if (!ifp) {
4223 			flog_err(
4224 				EC_ZEBRA_VTEP_ADD_FAILED,
4225 				"VNI %u hash %p doesn't have intf upon remote VTEP ADD",
4226 				zevpn->vni, zevpn);
4227 			continue;
4228 		}
4229 
4230 		zif = ifp->info;
4231 
4232 		/* If down or not mapped to a bridge, we're done. */
4233 		if (!if_is_operative(ifp) || !zif->brslave_info.br_if)
4234 			continue;
4235 
4236 		zvtep = zebra_evpn_vtep_find(zevpn, &vtep_ip);
4237 		if (zvtep) {
4238 			/* If the remote VTEP already exists check if
4239 			 * the flood mode has changed
4240 			 */
4241 			if (zvtep->flood_control != flood_control) {
4242 				if (zvtep->flood_control
4243 						== VXLAN_FLOOD_DISABLED)
4244 					/* old mode was head-end-replication but
4245 					 * is no longer; get rid of the HER fdb
4246 					 * entry installed before
4247 					 */
4248 					zebra_evpn_vtep_uninstall(zevpn,
4249 								  &vtep_ip);
4250 				zvtep->flood_control = flood_control;
4251 				zebra_evpn_vtep_install(zevpn, zvtep);
4252 			}
4253 		} else {
4254 			zvtep = zebra_evpn_vtep_add(zevpn, &vtep_ip,
4255 						    flood_control);
4256 			if (zvtep)
4257 				zebra_evpn_vtep_install(zevpn, zvtep);
4258 			else
4259 				flog_err(EC_ZEBRA_VTEP_ADD_FAILED,
4260 					"Failed to add remote VTEP, VNI %u zevpn %p",
4261 					vni, zevpn);
4262 		}
4263 	}
4264 
4265 stream_failure:
4266 	return;
4267 }
4268 
4269 /*
4270  * Add/Del gateway macip to evpn
4271  * g/w can be:
4272  *  1. SVI interface on a vlan aware bridge
4273  *  2. SVI interface on a vlan unaware bridge
4274  *  3. vrr interface (MACVLAN) associated to a SVI
4275  * We advertise macip routes for an interface if it is associated to VxLan vlan
4276  */
zebra_vxlan_add_del_gw_macip(struct interface * ifp,struct prefix * p,int add)4277 int zebra_vxlan_add_del_gw_macip(struct interface *ifp, struct prefix *p,
4278 				 int add)
4279 {
4280 	struct ipaddr ip;
4281 	struct ethaddr macaddr;
4282 	zebra_evpn_t *zevpn = NULL;
4283 
4284 	memset(&ip, 0, sizeof(struct ipaddr));
4285 	memset(&macaddr, 0, sizeof(struct ethaddr));
4286 
4287 	/* Check if EVPN is enabled. */
4288 	if (!is_evpn_enabled())
4289 		return 0;
4290 
4291 	if (IS_ZEBRA_IF_MACVLAN(ifp)) {
4292 		struct interface *svi_if =
4293 			NULL; /* SVI corresponding to the MACVLAN */
4294 		struct zebra_if *ifp_zif =
4295 			NULL; /* Zebra daemon specific info for MACVLAN */
4296 		struct zebra_if *svi_if_zif =
4297 			NULL; /* Zebra daemon specific info for SVI*/
4298 
4299 		ifp_zif = ifp->info;
4300 		if (!ifp_zif)
4301 			return -1;
4302 
4303 		/*
4304 		 * for a MACVLAN interface the link represents the svi_if
4305 		 */
4306 		svi_if = if_lookup_by_index_per_ns(zebra_ns_lookup(NS_DEFAULT),
4307 						   ifp_zif->link_ifindex);
4308 		if (!svi_if) {
4309 			zlog_debug("MACVLAN %s(%u) without link information",
4310 				   ifp->name, ifp->ifindex);
4311 			return -1;
4312 		}
4313 
4314 		if (IS_ZEBRA_IF_VLAN(svi_if)) {
4315 			/*
4316 			 * If it is a vlan aware bridge then the link gives the
4317 			 * bridge information
4318 			 */
4319 			struct interface *svi_if_link = NULL;
4320 
4321 			svi_if_zif = svi_if->info;
4322 			if (svi_if_zif) {
4323 				svi_if_link = if_lookup_by_index_per_ns(
4324 					zebra_ns_lookup(NS_DEFAULT),
4325 					svi_if_zif->link_ifindex);
4326 				zevpn = zebra_evpn_from_svi(svi_if,
4327 							    svi_if_link);
4328 			}
4329 		} else if (IS_ZEBRA_IF_BRIDGE(svi_if)) {
4330 			/*
4331 			 * If it is a vlan unaware bridge then svi is the bridge
4332 			 * itself
4333 			 */
4334 			zevpn = zebra_evpn_from_svi(svi_if, svi_if);
4335 		}
4336 	} else if (IS_ZEBRA_IF_VLAN(ifp)) {
4337 		struct zebra_if *svi_if_zif =
4338 			NULL; /* Zebra daemon specific info for SVI */
4339 		struct interface *svi_if_link =
4340 			NULL; /* link info for the SVI = bridge info */
4341 
4342 		svi_if_zif = ifp->info;
4343 		if (svi_if_zif) {
4344 			svi_if_link = if_lookup_by_index_per_ns(
4345 				zebra_ns_lookup(NS_DEFAULT),
4346 				svi_if_zif->link_ifindex);
4347 			if (svi_if_link)
4348 				zevpn = zebra_evpn_from_svi(ifp, svi_if_link);
4349 		}
4350 	} else if (IS_ZEBRA_IF_BRIDGE(ifp)) {
4351 		zevpn = zebra_evpn_from_svi(ifp, ifp);
4352 	}
4353 
4354 	if (!zevpn)
4355 		return 0;
4356 
4357 	if (!zevpn->vxlan_if) {
4358 		zlog_debug("VNI %u hash %p doesn't have intf upon MACVLAN up",
4359 			   zevpn->vni, zevpn);
4360 		return -1;
4361 	}
4362 
4363 
4364 	memcpy(&macaddr.octet, ifp->hw_addr, ETH_ALEN);
4365 
4366 	if (p->family == AF_INET) {
4367 		ip.ipa_type = IPADDR_V4;
4368 		memcpy(&(ip.ipaddr_v4), &(p->u.prefix4),
4369 		       sizeof(struct in_addr));
4370 	} else if (p->family == AF_INET6) {
4371 		ip.ipa_type = IPADDR_V6;
4372 		memcpy(&(ip.ipaddr_v6), &(p->u.prefix6),
4373 		       sizeof(struct in6_addr));
4374 	}
4375 
4376 
4377 	if (add)
4378 		zebra_evpn_gw_macip_add(ifp, zevpn, &macaddr, &ip);
4379 	else
4380 		zebra_evpn_gw_macip_del(ifp, zevpn, &ip);
4381 
4382 	return 0;
4383 }
4384 
4385 /*
4386  * Handle SVI interface going down.
4387  * SVI can be associated to either L3-VNI or L2-VNI.
4388  * For L2-VNI: At this point, this is a NOP since
4389  *	the kernel deletes the neighbor entries on this SVI (if any).
4390  *      We only need to update the vrf corresponding to zevpn.
4391  * For L3-VNI: L3-VNI is operationally down, update mac-ip routes and delete
4392  *	from bgp
4393  */
zebra_vxlan_svi_down(struct interface * ifp,struct interface * link_if)4394 int zebra_vxlan_svi_down(struct interface *ifp, struct interface *link_if)
4395 {
4396 	zebra_l3vni_t *zl3vni = NULL;
4397 
4398 	zl3vni = zl3vni_from_svi(ifp, link_if);
4399 	if (zl3vni) {
4400 
4401 		/* process l3-vni down */
4402 		zebra_vxlan_process_l3vni_oper_down(zl3vni);
4403 
4404 		/* remove association with svi-if */
4405 		zl3vni->svi_if = NULL;
4406 	} else {
4407 		zebra_evpn_t *zevpn = NULL;
4408 
4409 		/* since we dont have svi corresponding to zevpn, we associate it
4410 		 * to default vrf. Note: the corresponding neigh entries on the
4411 		 * SVI would have already been deleted */
4412 		zevpn = zebra_evpn_from_svi(ifp, link_if);
4413 		if (zevpn) {
4414 			zevpn->vrf_id = VRF_DEFAULT;
4415 
4416 			/* update the tenant vrf in BGP */
4417 			zebra_evpn_send_add_to_client(zevpn);
4418 		}
4419 	}
4420 	return 0;
4421 }
4422 
4423 /*
4424  * Handle SVI interface coming up.
4425  * SVI can be associated to L3-VNI (l3vni vxlan interface) or L2-VNI (l2-vni
4426  * vxlan intf).
4427  * For L2-VNI: we need to install any remote neighbors entried (used for
4428  * apr-suppression)
4429  * For L3-VNI: SVI will be used to get the rmac to be used with L3-VNI
4430  */
zebra_vxlan_svi_up(struct interface * ifp,struct interface * link_if)4431 int zebra_vxlan_svi_up(struct interface *ifp, struct interface *link_if)
4432 {
4433 	zebra_evpn_t *zevpn = NULL;
4434 	zebra_l3vni_t *zl3vni = NULL;
4435 
4436 	zl3vni = zl3vni_from_svi(ifp, link_if);
4437 	if (zl3vni) {
4438 
4439 		/* associate with svi */
4440 		zl3vni->svi_if = ifp;
4441 
4442 		/* process oper-up */
4443 		if (is_l3vni_oper_up(zl3vni))
4444 			zebra_vxlan_process_l3vni_oper_up(zl3vni);
4445 	} else {
4446 
4447 		/* process SVI up for l2-vni */
4448 		struct neigh_walk_ctx n_wctx;
4449 
4450 		zevpn = zebra_evpn_from_svi(ifp, link_if);
4451 		if (!zevpn)
4452 			return 0;
4453 
4454 		if (!zevpn->vxlan_if) {
4455 			zlog_debug(
4456 				"VNI %u hash %p doesn't have intf upon SVI up",
4457 				zevpn->vni, zevpn);
4458 			return -1;
4459 		}
4460 
4461 		if (IS_ZEBRA_DEBUG_VXLAN)
4462 			zlog_debug(
4463 				"SVI %s(%u) VNI %u VRF %s is UP, installing neighbors",
4464 				ifp->name, ifp->ifindex, zevpn->vni,
4465 				vrf_id_to_name(ifp->vrf_id));
4466 
4467 		/* update the vrf information for l2-vni and inform bgp */
4468 		zevpn->vrf_id = ifp->vrf_id;
4469 		zebra_evpn_send_add_to_client(zevpn);
4470 
4471 		/* Install any remote neighbors for this VNI. */
4472 		memset(&n_wctx, 0, sizeof(struct neigh_walk_ctx));
4473 		n_wctx.zevpn = zevpn;
4474 		hash_iterate(zevpn->neigh_table, zebra_evpn_install_neigh_hash,
4475 			     &n_wctx);
4476 	}
4477 
4478 	return 0;
4479 }
4480 
4481 /*
4482  * Handle MAC-VLAN interface going down.
4483  * L3VNI: When MAC-VLAN interface goes down,
4484  * find its associated SVI and update type2/type-5 routes
4485  * with SVI as RMAC
4486  */
zebra_vxlan_macvlan_down(struct interface * ifp)4487 void zebra_vxlan_macvlan_down(struct interface *ifp)
4488 {
4489 	zebra_l3vni_t *zl3vni = NULL;
4490 	struct zebra_if *zif, *link_zif;
4491 	struct interface *link_ifp, *link_if;
4492 
4493 	zif = ifp->info;
4494 	assert(zif);
4495 	link_ifp = zif->link;
4496 	if (!link_ifp) {
4497 		if (IS_ZEBRA_DEBUG_VXLAN) {
4498 			struct interface *ifp;
4499 
4500 			ifp = if_lookup_by_index_all_vrf(zif->link_ifindex);
4501 			zlog_debug("macvlan parent link is not found. Parent index %d ifp %s",
4502 				zif->link_ifindex, ifp ? ifp->name : " ");
4503 		}
4504 		return;
4505 	}
4506 	link_zif = link_ifp->info;
4507 	assert(link_zif);
4508 
4509 	link_if = if_lookup_by_index_per_ns(zebra_ns_lookup(NS_DEFAULT),
4510 					    link_zif->link_ifindex);
4511 
4512 	zl3vni = zl3vni_from_svi(link_ifp, link_if);
4513 	if (zl3vni) {
4514 		zl3vni->mac_vlan_if = NULL;
4515 		if (is_l3vni_oper_up(zl3vni))
4516 			zebra_vxlan_process_l3vni_oper_up(zl3vni);
4517 	}
4518 }
4519 
4520 /*
4521  * Handle MAC-VLAN interface going up.
4522  * L3VNI: When MAC-VLAN interface comes up,
4523  * find its associated SVI and update type-2 routes
4524  * with MAC-VLAN's MAC as RMAC and for type-5 routes
4525  * use SVI's MAC as RMAC.
4526  */
zebra_vxlan_macvlan_up(struct interface * ifp)4527 void zebra_vxlan_macvlan_up(struct interface *ifp)
4528 {
4529 	zebra_l3vni_t *zl3vni = NULL;
4530 	struct zebra_if *zif, *link_zif;
4531 	struct interface *link_ifp, *link_if;
4532 
4533 	zif = ifp->info;
4534 	assert(zif);
4535 	link_ifp = zif->link;
4536 	link_zif = link_ifp->info;
4537 	assert(link_zif);
4538 
4539 	link_if = if_lookup_by_index_per_ns(zebra_ns_lookup(NS_DEFAULT),
4540 					    link_zif->link_ifindex);
4541 	zl3vni = zl3vni_from_svi(link_ifp, link_if);
4542 	if (zl3vni) {
4543 		/* associate with macvlan (VRR) interface */
4544 		zl3vni->mac_vlan_if = ifp;
4545 
4546 		/* process oper-up */
4547 		if (is_l3vni_oper_up(zl3vni))
4548 			zebra_vxlan_process_l3vni_oper_up(zl3vni);
4549 	}
4550 }
4551 
4552 /*
4553  * Handle VxLAN interface down
4554  */
zebra_vxlan_if_down(struct interface * ifp)4555 int zebra_vxlan_if_down(struct interface *ifp)
4556 {
4557 	vni_t vni;
4558 	struct zebra_if *zif = NULL;
4559 	struct zebra_l2info_vxlan *vxl = NULL;
4560 	zebra_l3vni_t *zl3vni = NULL;
4561 	zebra_evpn_t *zevpn;
4562 
4563 	/* Check if EVPN is enabled. */
4564 	if (!is_evpn_enabled())
4565 		return 0;
4566 
4567 	zif = ifp->info;
4568 	assert(zif);
4569 	vxl = &zif->l2info.vxl;
4570 	vni = vxl->vni;
4571 
4572 	zl3vni = zl3vni_lookup(vni);
4573 	if (zl3vni) {
4574 		/* process-if-down for l3-vni */
4575 		if (IS_ZEBRA_DEBUG_VXLAN)
4576 			zlog_debug("Intf %s(%u) L3-VNI %u is DOWN", ifp->name,
4577 				   ifp->ifindex, vni);
4578 
4579 		zebra_vxlan_process_l3vni_oper_down(zl3vni);
4580 	} else {
4581 		/* process if-down for l2-vni */
4582 		if (IS_ZEBRA_DEBUG_VXLAN)
4583 			zlog_debug("Intf %s(%u) L2-VNI %u is DOWN", ifp->name,
4584 				   ifp->ifindex, vni);
4585 
4586 		/* Locate hash entry; it is expected to exist. */
4587 		zevpn = zebra_evpn_lookup(vni);
4588 		if (!zevpn) {
4589 			zlog_debug(
4590 				"Failed to locate VNI hash at DOWN, IF %s(%u) VNI %u",
4591 				ifp->name, ifp->ifindex, vni);
4592 			return -1;
4593 		}
4594 
4595 		assert(zevpn->vxlan_if == ifp);
4596 
4597 		/* remove from l3-vni list */
4598 		zl3vni = zl3vni_from_vrf(zevpn->vrf_id);
4599 		if (zl3vni)
4600 			listnode_delete(zl3vni->l2vnis, zevpn);
4601 
4602 		/* Delete this VNI from BGP. */
4603 		zebra_evpn_send_del_to_client(zevpn);
4604 
4605 		/* Free up all neighbors and MACs, if any. */
4606 		zebra_evpn_neigh_del_all(zevpn, 1, 0, DEL_ALL_NEIGH);
4607 		zebra_evpn_mac_del_all(zevpn, 1, 0, DEL_ALL_MAC);
4608 
4609 		/* Free up all remote VTEPs, if any. */
4610 		zebra_evpn_vtep_del_all(zevpn, 1);
4611 	}
4612 	return 0;
4613 }
4614 
4615 /*
4616  * Handle VxLAN interface up - update BGP if required.
4617  */
zebra_vxlan_if_up(struct interface * ifp)4618 int zebra_vxlan_if_up(struct interface *ifp)
4619 {
4620 	vni_t vni;
4621 	struct zebra_if *zif = NULL;
4622 	struct zebra_l2info_vxlan *vxl = NULL;
4623 	zebra_evpn_t *zevpn = NULL;
4624 	zebra_l3vni_t *zl3vni = NULL;
4625 
4626 	/* Check if EVPN is enabled. */
4627 	if (!is_evpn_enabled())
4628 		return 0;
4629 
4630 	zif = ifp->info;
4631 	assert(zif);
4632 	vxl = &zif->l2info.vxl;
4633 	vni = vxl->vni;
4634 
4635 	zl3vni = zl3vni_lookup(vni);
4636 	if (zl3vni) {
4637 		/* we need to associate with SVI, if any, we can associate with
4638 		 * svi-if only after association with vxlan-intf is complete
4639 		 */
4640 		zl3vni->svi_if = zl3vni_map_to_svi_if(zl3vni);
4641 		zl3vni->mac_vlan_if = zl3vni_map_to_mac_vlan_if(zl3vni);
4642 
4643 		if (IS_ZEBRA_DEBUG_VXLAN)
4644 			zlog_debug("Intf %s(%u) L3-VNI %u is UP svi_if %s mac_vlan_if %s"
4645 				, ifp->name, ifp->ifindex, vni,
4646 				zl3vni->svi_if ? zl3vni->svi_if->name : "NIL",
4647 				zl3vni->mac_vlan_if ?
4648 				zl3vni->mac_vlan_if->name : "NIL");
4649 
4650 		if (is_l3vni_oper_up(zl3vni))
4651 			zebra_vxlan_process_l3vni_oper_up(zl3vni);
4652 	} else {
4653 		/* Handle L2-VNI add */
4654 		struct interface *vlan_if = NULL;
4655 
4656 		if (IS_ZEBRA_DEBUG_VXLAN)
4657 			zlog_debug("Intf %s(%u) L2-VNI %u is UP", ifp->name,
4658 				   ifp->ifindex, vni);
4659 
4660 		/* Locate hash entry; it is expected to exist. */
4661 		zevpn = zebra_evpn_lookup(vni);
4662 		if (!zevpn) {
4663 			zlog_debug(
4664 				"Failed to locate EVPN hash at UP, IF %s(%u) VNI %u",
4665 				ifp->name, ifp->ifindex, vni);
4666 			return -1;
4667 		}
4668 
4669 		assert(zevpn->vxlan_if == ifp);
4670 		vlan_if = zvni_map_to_svi(vxl->access_vlan,
4671 					  zif->brslave_info.br_if);
4672 		if (vlan_if) {
4673 			zevpn->vrf_id = vlan_if->vrf_id;
4674 			zl3vni = zl3vni_from_vrf(vlan_if->vrf_id);
4675 			if (zl3vni)
4676 				listnode_add_sort_nodup(zl3vni->l2vnis, zevpn);
4677 		}
4678 
4679 		/* If part of a bridge, inform BGP about this VNI. */
4680 		/* Also, read and populate local MACs and neighbors. */
4681 		if (zif->brslave_info.br_if) {
4682 			zebra_evpn_send_add_to_client(zevpn);
4683 			zebra_evpn_read_mac_neigh(zevpn, ifp);
4684 		}
4685 	}
4686 
4687 	return 0;
4688 }
4689 
4690 /*
4691  * Handle VxLAN interface delete. Locate and remove entry in hash table
4692  * and update BGP, if required.
4693  */
zebra_vxlan_if_del(struct interface * ifp)4694 int zebra_vxlan_if_del(struct interface *ifp)
4695 {
4696 	vni_t vni;
4697 	struct zebra_if *zif = NULL;
4698 	struct zebra_l2info_vxlan *vxl = NULL;
4699 	zebra_evpn_t *zevpn = NULL;
4700 	zebra_l3vni_t *zl3vni = NULL;
4701 
4702 	/* Check if EVPN is enabled. */
4703 	if (!is_evpn_enabled())
4704 		return 0;
4705 
4706 	zif = ifp->info;
4707 	assert(zif);
4708 	vxl = &zif->l2info.vxl;
4709 	vni = vxl->vni;
4710 
4711 	zl3vni = zl3vni_lookup(vni);
4712 	if (zl3vni) {
4713 
4714 		if (IS_ZEBRA_DEBUG_VXLAN)
4715 			zlog_debug("Del L3-VNI %u intf %s(%u)", vni, ifp->name,
4716 				   ifp->ifindex);
4717 
4718 		/* process oper-down for l3-vni */
4719 		zebra_vxlan_process_l3vni_oper_down(zl3vni);
4720 
4721 		/* remove the association with vxlan_if */
4722 		memset(&zl3vni->local_vtep_ip, 0, sizeof(struct in_addr));
4723 		zl3vni->vxlan_if = NULL;
4724 	} else {
4725 
4726 		/* process if-del for l2-vni*/
4727 		if (IS_ZEBRA_DEBUG_VXLAN)
4728 			zlog_debug("Del L2-VNI %u intf %s(%u)", vni, ifp->name,
4729 				   ifp->ifindex);
4730 
4731 		/* Locate hash entry; it is expected to exist. */
4732 		zevpn = zebra_evpn_lookup(vni);
4733 		if (!zevpn) {
4734 			zlog_debug(
4735 				"Failed to locate VNI hash at del, IF %s(%u) VNI %u",
4736 				ifp->name, ifp->ifindex, vni);
4737 			return 0;
4738 		}
4739 
4740 		/* remove from l3-vni list */
4741 		zl3vni = zl3vni_from_vrf(zevpn->vrf_id);
4742 		if (zl3vni)
4743 			listnode_delete(zl3vni->l2vnis, zevpn);
4744 		/* Delete VNI from BGP. */
4745 		zebra_evpn_send_del_to_client(zevpn);
4746 
4747 		/* Free up all neighbors and MAC, if any. */
4748 		zebra_evpn_neigh_del_all(zevpn, 0, 0, DEL_ALL_NEIGH);
4749 		zebra_evpn_mac_del_all(zevpn, 0, 0, DEL_ALL_MAC);
4750 
4751 		/* Free up all remote VTEPs, if any. */
4752 		zebra_evpn_vtep_del_all(zevpn, 0);
4753 
4754 		/* Delete the hash entry. */
4755 		if (zebra_evpn_vxlan_del(zevpn)) {
4756 			flog_err(EC_ZEBRA_VNI_DEL_FAILED,
4757 				 "Failed to del EVPN hash %p, IF %s(%u) VNI %u",
4758 				 zevpn, ifp->name, ifp->ifindex, zevpn->vni);
4759 			return -1;
4760 		}
4761 	}
4762 	return 0;
4763 }
4764 
4765 /*
4766  * Handle VxLAN interface update - change to tunnel IP, master or VLAN.
4767  */
zebra_vxlan_if_update(struct interface * ifp,uint16_t chgflags)4768 int zebra_vxlan_if_update(struct interface *ifp, uint16_t chgflags)
4769 {
4770 	vni_t vni;
4771 	struct zebra_if *zif = NULL;
4772 	struct zebra_l2info_vxlan *vxl = NULL;
4773 	zebra_evpn_t *zevpn = NULL;
4774 	zebra_l3vni_t *zl3vni = NULL;
4775 
4776 	/* Check if EVPN is enabled. */
4777 	if (!is_evpn_enabled())
4778 		return 0;
4779 
4780 	zif = ifp->info;
4781 	assert(zif);
4782 	vxl = &zif->l2info.vxl;
4783 	vni = vxl->vni;
4784 
4785 	zl3vni = zl3vni_lookup(vni);
4786 	if (zl3vni) {
4787 
4788 		if (IS_ZEBRA_DEBUG_VXLAN)
4789 			zlog_debug(
4790 				"Update L3-VNI %u intf %s(%u) VLAN %u local IP %s master %u chg 0x%x",
4791 				vni, ifp->name, ifp->ifindex, vxl->access_vlan,
4792 				inet_ntoa(vxl->vtep_ip),
4793 				zif->brslave_info.bridge_ifindex, chgflags);
4794 
4795 		/* Removed from bridge? Cleanup and return */
4796 		if ((chgflags & ZEBRA_VXLIF_MASTER_CHANGE)
4797 		    && (zif->brslave_info.bridge_ifindex == IFINDEX_INTERNAL)) {
4798 			zebra_vxlan_process_l3vni_oper_down(zl3vni);
4799 			return 0;
4800 		}
4801 
4802 		/* access-vlan change - process oper down, associate with new
4803 		 * svi_if and then process oper up again
4804 		 */
4805 		if (chgflags & ZEBRA_VXLIF_VLAN_CHANGE) {
4806 			if (if_is_operative(ifp)) {
4807 				zebra_vxlan_process_l3vni_oper_down(zl3vni);
4808 				zl3vni->svi_if = NULL;
4809 				zl3vni->svi_if = zl3vni_map_to_svi_if(zl3vni);
4810 				zl3vni->mac_vlan_if =
4811 					zl3vni_map_to_mac_vlan_if(zl3vni);
4812 				zl3vni->local_vtep_ip = vxl->vtep_ip;
4813 				if (is_l3vni_oper_up(zl3vni))
4814 					zebra_vxlan_process_l3vni_oper_up(
4815 						zl3vni);
4816 			}
4817 		}
4818 
4819 		/*
4820 		 * local-ip change - process oper down, associate with new
4821 		 * local-ip and then process oper up again
4822 		 */
4823 		if (chgflags & ZEBRA_VXLIF_LOCAL_IP_CHANGE) {
4824 			if (if_is_operative(ifp)) {
4825 				zebra_vxlan_process_l3vni_oper_down(zl3vni);
4826 				zl3vni->local_vtep_ip = vxl->vtep_ip;
4827 				if (is_l3vni_oper_up(zl3vni))
4828 					zebra_vxlan_process_l3vni_oper_up(
4829 						zl3vni);
4830 			}
4831 		}
4832 
4833 		/* Update local tunnel IP. */
4834 		zl3vni->local_vtep_ip = vxl->vtep_ip;
4835 
4836 		/* if we have a valid new master, process l3-vni oper up */
4837 		if (chgflags & ZEBRA_VXLIF_MASTER_CHANGE) {
4838 			if (if_is_operative(ifp) && is_l3vni_oper_up(zl3vni))
4839 				zebra_vxlan_process_l3vni_oper_up(zl3vni);
4840 		}
4841 	} else {
4842 
4843 		/* Update VNI hash. */
4844 		zevpn = zebra_evpn_lookup(vni);
4845 		if (!zevpn) {
4846 			zlog_debug(
4847 				"Failed to find EVPN hash on update, IF %s(%u) VNI %u",
4848 				ifp->name, ifp->ifindex, vni);
4849 			return -1;
4850 		}
4851 
4852 		if (IS_ZEBRA_DEBUG_VXLAN)
4853 			zlog_debug(
4854 				"Update L2-VNI %u intf %s(%u) VLAN %u local IP %s master %u chg 0x%x",
4855 				vni, ifp->name, ifp->ifindex, vxl->access_vlan,
4856 				inet_ntoa(vxl->vtep_ip),
4857 				zif->brslave_info.bridge_ifindex, chgflags);
4858 
4859 		/* Removed from bridge? Cleanup and return */
4860 		if ((chgflags & ZEBRA_VXLIF_MASTER_CHANGE)
4861 		    && (zif->brslave_info.bridge_ifindex == IFINDEX_INTERNAL)) {
4862 			/* Delete from client, remove all remote VTEPs */
4863 			/* Also, free up all MACs and neighbors. */
4864 			zebra_evpn_send_del_to_client(zevpn);
4865 			zebra_evpn_neigh_del_all(zevpn, 1, 0, DEL_ALL_NEIGH);
4866 			zebra_evpn_mac_del_all(zevpn, 1, 0, DEL_ALL_MAC);
4867 			zebra_evpn_vtep_del_all(zevpn, 1);
4868 			return 0;
4869 		}
4870 
4871 		/* Handle other changes. */
4872 		if (chgflags & ZEBRA_VXLIF_VLAN_CHANGE) {
4873 			/* Remove all existing local neigh and MACs for this VNI
4874 			 * (including from BGP)
4875 			 */
4876 			zebra_evpn_neigh_del_all(zevpn, 0, 1, DEL_LOCAL_MAC);
4877 			zebra_evpn_mac_del_all(zevpn, 0, 1, DEL_LOCAL_MAC);
4878 		}
4879 
4880 		if (zevpn->local_vtep_ip.s_addr != vxl->vtep_ip.s_addr ||
4881 			zevpn->mcast_grp.s_addr != vxl->mcast_grp.s_addr) {
4882 			zebra_vxlan_sg_deref(zevpn->local_vtep_ip,
4883 				zevpn->mcast_grp);
4884 			zebra_vxlan_sg_ref(vxl->vtep_ip, vxl->mcast_grp);
4885 			zevpn->local_vtep_ip = vxl->vtep_ip;
4886 			zevpn->mcast_grp = vxl->mcast_grp;
4887 			/* on local vtep-ip check if ES orig-ip
4888 			 * needs to be updated
4889 			 */
4890 			zebra_evpn_es_set_base_evpn(zevpn);
4891 		}
4892 		zevpn_vxlan_if_set(zevpn, ifp, true /* set */);
4893 		/* Take further actions needed.
4894 		 * Note that if we are here, there is a change of interest.
4895 		 */
4896 		/* If down or not mapped to a bridge, we're done. */
4897 		if (!if_is_operative(ifp) || !zif->brslave_info.br_if)
4898 			return 0;
4899 
4900 		/* Inform BGP, if there is a change of interest. */
4901 		if (chgflags
4902 			& (ZEBRA_VXLIF_MASTER_CHANGE |
4903 			   ZEBRA_VXLIF_LOCAL_IP_CHANGE |
4904 			   ZEBRA_VXLIF_MCAST_GRP_CHANGE))
4905 			zebra_evpn_send_add_to_client(zevpn);
4906 
4907 		/* If there is a valid new master or a VLAN mapping change,
4908 		 * read and populate local MACs and neighbors.
4909 		 * Also, reinstall any remote MACs and neighbors
4910 		 * for this VNI (based on new VLAN).
4911 		 */
4912 		if (chgflags & ZEBRA_VXLIF_MASTER_CHANGE)
4913 			zebra_evpn_read_mac_neigh(zevpn, ifp);
4914 		else if (chgflags & ZEBRA_VXLIF_VLAN_CHANGE) {
4915 			struct mac_walk_ctx m_wctx;
4916 			struct neigh_walk_ctx n_wctx;
4917 
4918 			zebra_evpn_read_mac_neigh(zevpn, ifp);
4919 
4920 			memset(&m_wctx, 0, sizeof(struct mac_walk_ctx));
4921 			m_wctx.zevpn = zevpn;
4922 			hash_iterate(zevpn->mac_table,
4923 				     zebra_evpn_install_mac_hash, &m_wctx);
4924 
4925 			memset(&n_wctx, 0, sizeof(struct neigh_walk_ctx));
4926 			n_wctx.zevpn = zevpn;
4927 			hash_iterate(zevpn->neigh_table,
4928 				     zebra_evpn_install_neigh_hash, &n_wctx);
4929 		}
4930 	}
4931 
4932 	return 0;
4933 }
4934 
4935 /*
4936  * Handle VxLAN interface add.
4937  */
zebra_vxlan_if_add(struct interface * ifp)4938 int zebra_vxlan_if_add(struct interface *ifp)
4939 {
4940 	vni_t vni;
4941 	struct zebra_if *zif = NULL;
4942 	struct zebra_l2info_vxlan *vxl = NULL;
4943 	zebra_evpn_t *zevpn = NULL;
4944 	zebra_l3vni_t *zl3vni = NULL;
4945 
4946 	/* Check if EVPN is enabled. */
4947 	if (!is_evpn_enabled())
4948 		return 0;
4949 
4950 	zif = ifp->info;
4951 	assert(zif);
4952 	vxl = &zif->l2info.vxl;
4953 	vni = vxl->vni;
4954 
4955 	zl3vni = zl3vni_lookup(vni);
4956 	if (zl3vni) {
4957 
4958 		/* process if-add for l3-vni*/
4959 		if (IS_ZEBRA_DEBUG_VXLAN)
4960 			zlog_debug(
4961 				"Add L3-VNI %u intf %s(%u) VLAN %u local IP %s master %u",
4962 				vni, ifp->name, ifp->ifindex, vxl->access_vlan,
4963 				inet_ntoa(vxl->vtep_ip),
4964 				zif->brslave_info.bridge_ifindex);
4965 
4966 		/* associate with vxlan_if */
4967 		zl3vni->local_vtep_ip = vxl->vtep_ip;
4968 		zl3vni->vxlan_if = ifp;
4969 
4970 		/* Associate with SVI, if any. We can associate with svi-if only
4971 		 * after association with vxlan_if is complete */
4972 		zl3vni->svi_if = zl3vni_map_to_svi_if(zl3vni);
4973 
4974 		zl3vni->mac_vlan_if = zl3vni_map_to_mac_vlan_if(zl3vni);
4975 
4976 		if (is_l3vni_oper_up(zl3vni))
4977 			zebra_vxlan_process_l3vni_oper_up(zl3vni);
4978 	} else {
4979 
4980 		/* process if-add for l2-vni */
4981 		struct interface *vlan_if = NULL;
4982 
4983 		/* Create or update EVPN hash. */
4984 		zevpn = zebra_evpn_lookup(vni);
4985 		if (!zevpn) {
4986 			zevpn = zebra_evpn_add(vni);
4987 			if (!zevpn) {
4988 				flog_err(
4989 					EC_ZEBRA_VNI_ADD_FAILED,
4990 					"Failed to add EVPN hash, IF %s(%u) VNI %u",
4991 					ifp->name, ifp->ifindex, vni);
4992 				return -1;
4993 			}
4994 		}
4995 
4996 		if (zevpn->local_vtep_ip.s_addr != vxl->vtep_ip.s_addr ||
4997 			zevpn->mcast_grp.s_addr != vxl->mcast_grp.s_addr) {
4998 			zebra_vxlan_sg_deref(zevpn->local_vtep_ip,
4999 				zevpn->mcast_grp);
5000 			zebra_vxlan_sg_ref(vxl->vtep_ip, vxl->mcast_grp);
5001 			zevpn->local_vtep_ip = vxl->vtep_ip;
5002 			zevpn->mcast_grp = vxl->mcast_grp;
5003 			/* on local vtep-ip check if ES orig-ip
5004 			 * needs to be updated
5005 			 */
5006 			zebra_evpn_es_set_base_evpn(zevpn);
5007 		}
5008 		zevpn_vxlan_if_set(zevpn, ifp, true /* set */);
5009 		vlan_if = zvni_map_to_svi(vxl->access_vlan,
5010 					  zif->brslave_info.br_if);
5011 		if (vlan_if) {
5012 			zevpn->vrf_id = vlan_if->vrf_id;
5013 			zl3vni = zl3vni_from_vrf(vlan_if->vrf_id);
5014 			if (zl3vni)
5015 				listnode_add_sort_nodup(zl3vni->l2vnis, zevpn);
5016 		}
5017 
5018 		if (IS_ZEBRA_DEBUG_VXLAN) {
5019 			char addr_buf1[INET_ADDRSTRLEN];
5020 			char addr_buf2[INET_ADDRSTRLEN];
5021 
5022 			inet_ntop(AF_INET, &vxl->vtep_ip,
5023 					addr_buf1, INET_ADDRSTRLEN);
5024 			inet_ntop(AF_INET, &vxl->mcast_grp,
5025 					addr_buf2, INET_ADDRSTRLEN);
5026 
5027 			zlog_debug(
5028 				"Add L2-VNI %u VRF %s intf %s(%u) VLAN %u local IP %s mcast_grp %s master %u",
5029 				vni,
5030 				vlan_if ? vrf_id_to_name(vlan_if->vrf_id)
5031 					: VRF_DEFAULT_NAME,
5032 				ifp->name, ifp->ifindex, vxl->access_vlan,
5033 				addr_buf1, addr_buf2,
5034 				zif->brslave_info.bridge_ifindex);
5035 		}
5036 
5037 		/* If down or not mapped to a bridge, we're done. */
5038 		if (!if_is_operative(ifp) || !zif->brslave_info.br_if)
5039 			return 0;
5040 
5041 		/* Inform BGP */
5042 		zebra_evpn_send_add_to_client(zevpn);
5043 
5044 		/* Read and populate local MACs and neighbors */
5045 		zebra_evpn_read_mac_neigh(zevpn, ifp);
5046 	}
5047 
5048 	return 0;
5049 }
5050 
zebra_vxlan_process_vrf_vni_cmd(struct zebra_vrf * zvrf,vni_t vni,char * err,int err_str_sz,int filter,int add)5051 int zebra_vxlan_process_vrf_vni_cmd(struct zebra_vrf *zvrf, vni_t vni,
5052 				    char *err, int err_str_sz, int filter,
5053 				    int add)
5054 {
5055 	zebra_l3vni_t *zl3vni = NULL;
5056 	struct zebra_vrf *zvrf_evpn = NULL;
5057 
5058 	zvrf_evpn = zebra_vrf_get_evpn();
5059 	if (!zvrf_evpn)
5060 		return -1;
5061 
5062 	if (IS_ZEBRA_DEBUG_VXLAN)
5063 		zlog_debug("vrf %s vni %u %s", zvrf_name(zvrf), vni,
5064 			   add ? "ADD" : "DEL");
5065 
5066 	if (add) {
5067 
5068 		zebra_vxlan_handle_vni_transition(zvrf, vni, add);
5069 
5070 		/* check if the vni is already present under zvrf */
5071 		if (zvrf->l3vni) {
5072 			snprintf(err, err_str_sz,
5073 				 "VNI is already configured under the vrf");
5074 			return -1;
5075 		}
5076 
5077 		/* check if this VNI is already present in the system */
5078 		zl3vni = zl3vni_lookup(vni);
5079 		if (zl3vni) {
5080 			snprintf(err, err_str_sz,
5081 				 "VNI is already configured as L3-VNI");
5082 			return -1;
5083 		}
5084 
5085 		/* add the L3-VNI to the global table */
5086 		zl3vni = zl3vni_add(vni, zvrf_id(zvrf));
5087 		if (!zl3vni) {
5088 			snprintf(err, err_str_sz, "Could not add L3-VNI");
5089 			return -1;
5090 		}
5091 
5092 		/* associate the vrf with vni */
5093 		zvrf->l3vni = vni;
5094 
5095 		/* set the filter in l3vni to denote if we are using l3vni only
5096 		 * for prefix routes
5097 		 */
5098 		if (filter)
5099 			SET_FLAG(zl3vni->filter, PREFIX_ROUTES_ONLY);
5100 
5101 		/* associate with vxlan-intf;
5102 		 * we need to associate with the vxlan-intf first
5103 		 */
5104 		zl3vni->vxlan_if = zl3vni_map_to_vxlan_if(zl3vni);
5105 
5106 		/* associate with corresponding SVI interface, we can associate
5107 		 * with svi-if only after vxlan interface association is
5108 		 * complete
5109 		 */
5110 		zl3vni->svi_if = zl3vni_map_to_svi_if(zl3vni);
5111 
5112 		zl3vni->mac_vlan_if = zl3vni_map_to_mac_vlan_if(zl3vni);
5113 
5114 		if (IS_ZEBRA_DEBUG_VXLAN)
5115 			zlog_debug(
5116 				"%s: l3vni %u svi_if %s mac_vlan_if %s",
5117 				__func__, vni,
5118 				zl3vni->svi_if ? zl3vni->svi_if->name : "NIL",
5119 				zl3vni->mac_vlan_if ? zl3vni->mac_vlan_if->name
5120 						    : "NIL");
5121 
5122 		/* formulate l2vni list */
5123 		hash_iterate(zvrf_evpn->evpn_table, zevpn_add_to_l3vni_list,
5124 			     zl3vni);
5125 
5126 		if (is_l3vni_oper_up(zl3vni))
5127 			zebra_vxlan_process_l3vni_oper_up(zl3vni);
5128 
5129 	} else {
5130 		zl3vni = zl3vni_lookup(vni);
5131 		if (!zl3vni) {
5132 			snprintf(err, err_str_sz, "VNI doesn't exist");
5133 			return -1;
5134 		}
5135 
5136 		if (zvrf->l3vni != vni) {
5137 			snprintf(err, err_str_sz,
5138 					"VNI %d doesn't exist in VRF: %s",
5139 					vni, zvrf->vrf->name);
5140 			return -1;
5141 		}
5142 
5143 		if (filter && !CHECK_FLAG(zl3vni->filter, PREFIX_ROUTES_ONLY)) {
5144 			snprintf(err, ERR_STR_SZ,
5145 				 "prefix-routes-only is not set for the vni");
5146 			return -1;
5147 		}
5148 
5149 		zebra_vxlan_process_l3vni_oper_down(zl3vni);
5150 
5151 		/* delete and uninstall all rmacs */
5152 		hash_iterate(zl3vni->rmac_table, zl3vni_del_rmac_hash_entry,
5153 			     zl3vni);
5154 
5155 		/* delete and uninstall all next-hops */
5156 		hash_iterate(zl3vni->nh_table, zl3vni_del_nh_hash_entry,
5157 			     zl3vni);
5158 
5159 		zvrf->l3vni = 0;
5160 		zl3vni_del(zl3vni);
5161 
5162 		zebra_vxlan_handle_vni_transition(zvrf, vni, add);
5163 	}
5164 	return 0;
5165 }
5166 
zebra_vxlan_vrf_enable(struct zebra_vrf * zvrf)5167 int zebra_vxlan_vrf_enable(struct zebra_vrf *zvrf)
5168 {
5169 	zebra_l3vni_t *zl3vni = NULL;
5170 
5171 	if (zvrf->l3vni)
5172 		zl3vni = zl3vni_lookup(zvrf->l3vni);
5173 	if (!zl3vni)
5174 		return 0;
5175 
5176 	zl3vni->vrf_id = zvrf_id(zvrf);
5177 	if (is_l3vni_oper_up(zl3vni))
5178 		zebra_vxlan_process_l3vni_oper_up(zl3vni);
5179 	return 0;
5180 }
5181 
zebra_vxlan_vrf_disable(struct zebra_vrf * zvrf)5182 int zebra_vxlan_vrf_disable(struct zebra_vrf *zvrf)
5183 {
5184 	zebra_l3vni_t *zl3vni = NULL;
5185 
5186 	if (zvrf->l3vni)
5187 		zl3vni = zl3vni_lookup(zvrf->l3vni);
5188 	if (!zl3vni)
5189 		return 0;
5190 
5191 	zebra_vxlan_process_l3vni_oper_down(zl3vni);
5192 
5193 	/* delete and uninstall all rmacs */
5194 	hash_iterate(zl3vni->rmac_table, zl3vni_del_rmac_hash_entry, zl3vni);
5195 	/* delete and uninstall all next-hops */
5196 	hash_iterate(zl3vni->nh_table, zl3vni_del_nh_hash_entry, zl3vni);
5197 
5198 	zl3vni->vrf_id = VRF_UNKNOWN;
5199 
5200 	return 0;
5201 }
5202 
zebra_vxlan_vrf_delete(struct zebra_vrf * zvrf)5203 int zebra_vxlan_vrf_delete(struct zebra_vrf *zvrf)
5204 {
5205 	zebra_l3vni_t *zl3vni = NULL;
5206 	vni_t vni;
5207 
5208 	if (zvrf->l3vni)
5209 		zl3vni = zl3vni_lookup(zvrf->l3vni);
5210 	if (!zl3vni)
5211 		return 0;
5212 
5213 	vni = zl3vni->vni;
5214 	zl3vni_del(zl3vni);
5215 	zebra_vxlan_handle_vni_transition(zvrf, vni, 0);
5216 
5217 	return 0;
5218 }
5219 
5220 /*
5221  * Handle message from client to specify the flooding mechanism for
5222  * BUM packets. The default is to do head-end (ingress) replication
5223  * and the other supported option is to disable it. This applies to
5224  * all BUM traffic and disabling it applies to both the transmit and
5225  * receive direction.
5226  */
zebra_vxlan_flood_control(ZAPI_HANDLER_ARGS)5227 void zebra_vxlan_flood_control(ZAPI_HANDLER_ARGS)
5228 {
5229 	struct stream *s;
5230 	enum vxlan_flood_control flood_ctrl;
5231 
5232 	if (!EVPN_ENABLED(zvrf)) {
5233 		zlog_err("EVPN flood control for non-EVPN VRF %u",
5234 			 zvrf_id(zvrf));
5235 		return;
5236 	}
5237 
5238 	s = msg;
5239 	STREAM_GETC(s, flood_ctrl);
5240 
5241 	if (IS_ZEBRA_DEBUG_VXLAN)
5242 		zlog_debug("EVPN flood control %u, currently %u",
5243 			   flood_ctrl, zvrf->vxlan_flood_ctrl);
5244 
5245 	if (zvrf->vxlan_flood_ctrl == flood_ctrl)
5246 		return;
5247 
5248 	zvrf->vxlan_flood_ctrl = flood_ctrl;
5249 
5250 	/* Install or uninstall flood entries corresponding to
5251 	 * remote VTEPs.
5252 	 */
5253 	hash_iterate(zvrf->evpn_table, zebra_evpn_handle_flooding_remote_vteps,
5254 		     zvrf);
5255 
5256 stream_failure:
5257 	return;
5258 }
5259 
5260 /*
5261  * Handle message from client to enable/disable advertisement of svi macip
5262  * routes
5263  */
zebra_vxlan_advertise_svi_macip(ZAPI_HANDLER_ARGS)5264 void zebra_vxlan_advertise_svi_macip(ZAPI_HANDLER_ARGS)
5265 {
5266 	struct stream *s;
5267 	int advertise;
5268 	vni_t vni = 0;
5269 	zebra_evpn_t *zevpn = NULL;
5270 	struct interface *ifp = NULL;
5271 
5272 	if (!EVPN_ENABLED(zvrf)) {
5273 		zlog_debug("EVPN SVI-MACIP Adv for non-EVPN VRF %u",
5274 			  zvrf_id(zvrf));
5275 		return;
5276 	}
5277 
5278 	s = msg;
5279 	STREAM_GETC(s, advertise);
5280 	STREAM_GETL(s, vni);
5281 
5282 	if (!vni) {
5283 		if (IS_ZEBRA_DEBUG_VXLAN)
5284 			zlog_debug("EVPN SVI-MACIP Adv %s, currently %s",
5285 				   advertise ? "enabled" : "disabled",
5286 				   advertise_svi_macip_enabled(NULL)
5287 					   ? "enabled"
5288 					   : "disabled");
5289 
5290 		if (zvrf->advertise_svi_macip == advertise)
5291 			return;
5292 
5293 
5294 		if (advertise) {
5295 			zvrf->advertise_svi_macip = advertise;
5296 			hash_iterate(zvrf->evpn_table,
5297 				     zebra_evpn_gw_macip_add_for_evpn_hash,
5298 				     NULL);
5299 		} else {
5300 			hash_iterate(zvrf->evpn_table,
5301 				     zebra_evpn_svi_macip_del_for_evpn_hash,
5302 				     NULL);
5303 			zvrf->advertise_svi_macip = advertise;
5304 		}
5305 
5306 	} else {
5307 		struct zebra_if *zif = NULL;
5308 		struct zebra_l2info_vxlan zl2_info;
5309 		struct interface *vlan_if = NULL;
5310 
5311 		zevpn = zebra_evpn_lookup(vni);
5312 		if (!zevpn)
5313 			return;
5314 
5315 		if (IS_ZEBRA_DEBUG_VXLAN)
5316 			zlog_debug(
5317 				"EVPN SVI macip Adv %s on VNI %d , currently %s",
5318 				advertise ? "enabled" : "disabled", vni,
5319 				advertise_svi_macip_enabled(zevpn)
5320 					? "enabled"
5321 					: "disabled");
5322 
5323 		if (zevpn->advertise_svi_macip == advertise)
5324 			return;
5325 
5326 		/* Store flag even though SVI is not present.
5327 		 * Once SVI comes up triggers self MAC-IP route add.
5328 		 */
5329 		zevpn->advertise_svi_macip = advertise;
5330 
5331 		ifp = zevpn->vxlan_if;
5332 		if (!ifp)
5333 			return;
5334 
5335 		zif = ifp->info;
5336 
5337 		/* If down or not mapped to a bridge, we're done. */
5338 		if (!if_is_operative(ifp) || !zif->brslave_info.br_if)
5339 			return;
5340 
5341 		zl2_info = zif->l2info.vxl;
5342 		vlan_if = zvni_map_to_svi(zl2_info.access_vlan,
5343 					  zif->brslave_info.br_if);
5344 		if (!vlan_if)
5345 			return;
5346 
5347 		if (advertise) {
5348 			/* Add primary SVI MAC-IP */
5349 			zebra_evpn_add_macip_for_intf(vlan_if, zevpn);
5350 		} else {
5351 			/* Del primary SVI MAC-IP */
5352 			zebra_evpn_del_macip_for_intf(vlan_if, zevpn);
5353 		}
5354 	}
5355 
5356 stream_failure:
5357 	return;
5358 }
5359 
5360 /*
5361  * Handle message from client to enable/disable advertisement of g/w macip
5362  * routes
5363  */
zebra_vxlan_advertise_subnet(ZAPI_HANDLER_ARGS)5364 void zebra_vxlan_advertise_subnet(ZAPI_HANDLER_ARGS)
5365 {
5366 	struct stream *s;
5367 	int advertise;
5368 	vni_t vni = 0;
5369 	zebra_evpn_t *zevpn = NULL;
5370 	struct interface *ifp = NULL;
5371 	struct zebra_if *zif = NULL;
5372 	struct zebra_l2info_vxlan zl2_info;
5373 	struct interface *vlan_if = NULL;
5374 
5375 	if (!EVPN_ENABLED(zvrf)) {
5376 		zlog_debug("EVPN GW-MACIP Adv for non-EVPN VRF %u",
5377 			  zvrf_id(zvrf));
5378 		return;
5379 	}
5380 
5381 	s = msg;
5382 	STREAM_GETC(s, advertise);
5383 	STREAM_GET(&vni, s, 3);
5384 
5385 	zevpn = zebra_evpn_lookup(vni);
5386 	if (!zevpn)
5387 		return;
5388 
5389 	if (zevpn->advertise_subnet == advertise)
5390 		return;
5391 
5392 	if (IS_ZEBRA_DEBUG_VXLAN)
5393 		zlog_debug("EVPN subnet Adv %s on VNI %d , currently %s",
5394 			   advertise ? "enabled" : "disabled", vni,
5395 			   zevpn->advertise_subnet ? "enabled" : "disabled");
5396 
5397 
5398 	zevpn->advertise_subnet = advertise;
5399 
5400 	ifp = zevpn->vxlan_if;
5401 	if (!ifp)
5402 		return;
5403 
5404 	zif = ifp->info;
5405 
5406 	/* If down or not mapped to a bridge, we're done. */
5407 	if (!if_is_operative(ifp) || !zif->brslave_info.br_if)
5408 		return;
5409 
5410 	zl2_info = zif->l2info.vxl;
5411 
5412 	vlan_if =
5413 		zvni_map_to_svi(zl2_info.access_vlan, zif->brslave_info.br_if);
5414 	if (!vlan_if)
5415 		return;
5416 
5417 	if (zevpn->advertise_subnet)
5418 		zebra_evpn_advertise_subnet(zevpn, vlan_if, 1);
5419 	else
5420 		zebra_evpn_advertise_subnet(zevpn, vlan_if, 0);
5421 
5422 stream_failure:
5423 	return;
5424 }
5425 
5426 /*
5427  * Handle message from client to enable/disable advertisement of g/w macip
5428  * routes
5429  */
zebra_vxlan_advertise_gw_macip(ZAPI_HANDLER_ARGS)5430 void zebra_vxlan_advertise_gw_macip(ZAPI_HANDLER_ARGS)
5431 {
5432 	struct stream *s;
5433 	int advertise;
5434 	vni_t vni = 0;
5435 	zebra_evpn_t *zevpn = NULL;
5436 	struct interface *ifp = NULL;
5437 
5438 	if (!EVPN_ENABLED(zvrf)) {
5439 		zlog_debug("EVPN GW-MACIP Adv for non-EVPN VRF %u",
5440 			   zvrf_id(zvrf));
5441 		return;
5442 	}
5443 
5444 	s = msg;
5445 	STREAM_GETC(s, advertise);
5446 	STREAM_GETL(s, vni);
5447 
5448 	if (!vni) {
5449 		if (IS_ZEBRA_DEBUG_VXLAN)
5450 			zlog_debug("EVPN gateway macip Adv %s, currently %s",
5451 				   advertise ? "enabled" : "disabled",
5452 				   advertise_gw_macip_enabled(NULL)
5453 					   ? "enabled"
5454 					   : "disabled");
5455 
5456 		if (zvrf->advertise_gw_macip == advertise)
5457 			return;
5458 
5459 		zvrf->advertise_gw_macip = advertise;
5460 
5461 		if (advertise_gw_macip_enabled(zevpn))
5462 			hash_iterate(zvrf->evpn_table,
5463 				     zebra_evpn_gw_macip_add_for_evpn_hash,
5464 				     NULL);
5465 		else
5466 			hash_iterate(zvrf->evpn_table,
5467 				     zebra_evpn_gw_macip_del_for_evpn_hash,
5468 				     NULL);
5469 
5470 	} else {
5471 		struct zebra_if *zif = NULL;
5472 		struct zebra_l2info_vxlan zl2_info;
5473 		struct interface *vlan_if = NULL;
5474 		struct interface *vrr_if = NULL;
5475 
5476 		zevpn = zebra_evpn_lookup(vni);
5477 		if (!zevpn)
5478 			return;
5479 
5480 		if (IS_ZEBRA_DEBUG_VXLAN)
5481 			zlog_debug(
5482 				"EVPN gateway macip Adv %s on VNI %d , currently %s",
5483 				advertise ? "enabled" : "disabled", vni,
5484 				advertise_gw_macip_enabled(zevpn) ? "enabled"
5485 								 : "disabled");
5486 
5487 		if (zevpn->advertise_gw_macip == advertise)
5488 			return;
5489 
5490 		zevpn->advertise_gw_macip = advertise;
5491 
5492 		ifp = zevpn->vxlan_if;
5493 		if (!ifp)
5494 			return;
5495 
5496 		zif = ifp->info;
5497 
5498 		/* If down or not mapped to a bridge, we're done. */
5499 		if (!if_is_operative(ifp) || !zif->brslave_info.br_if)
5500 			return;
5501 
5502 		zl2_info = zif->l2info.vxl;
5503 
5504 		vlan_if = zvni_map_to_svi(zl2_info.access_vlan,
5505 					  zif->brslave_info.br_if);
5506 		if (!vlan_if)
5507 			return;
5508 
5509 		if (advertise_gw_macip_enabled(zevpn)) {
5510 			/* Add primary SVI MAC-IP */
5511 			zebra_evpn_add_macip_for_intf(vlan_if, zevpn);
5512 
5513 			/* Add VRR MAC-IP - if any*/
5514 			vrr_if = zebra_get_vrr_intf_for_svi(vlan_if);
5515 			if (vrr_if)
5516 				zebra_evpn_add_macip_for_intf(vrr_if, zevpn);
5517 		} else {
5518 			/* Del primary MAC-IP */
5519 			zebra_evpn_del_macip_for_intf(vlan_if, zevpn);
5520 
5521 			/* Del VRR MAC-IP - if any*/
5522 			vrr_if = zebra_get_vrr_intf_for_svi(vlan_if);
5523 			if (vrr_if)
5524 				zebra_evpn_del_macip_for_intf(vrr_if, zevpn);
5525 		}
5526 	}
5527 
5528 stream_failure:
5529 	return;
5530 }
5531 
macfdb_read_ns(struct ns * ns,void * _in_param,void ** out_param)5532 static int macfdb_read_ns(struct ns *ns,
5533 			  void *_in_param __attribute__((unused)),
5534 			  void **out_param __attribute__((unused)))
5535 {
5536 	struct zebra_ns *zns = ns->info;
5537 
5538 	macfdb_read(zns);
5539 	return NS_WALK_CONTINUE;
5540 }
5541 
neigh_read_ns(struct ns * ns,void * _in_param,void ** out_param)5542 static int neigh_read_ns(struct ns *ns,
5543 			 void *_in_param __attribute__((unused)),
5544 			 void **out_param __attribute__((unused)))
5545 {
5546 	struct zebra_ns *zns = ns->info;
5547 
5548 	neigh_read(zns);
5549 	return NS_WALK_CONTINUE;
5550 }
5551 
5552 /*
5553  * Handle message from client to learn (or stop learning) about VNIs and MACs.
5554  * When enabled, the VNI hash table will be built and MAC FDB table read;
5555  * when disabled, the entries should be deleted and remote VTEPs and MACs
5556  * uninstalled from the kernel.
5557  * This also informs the setting for BUM handling at the time this change
5558  * occurs; it is relevant only when specifying "learn".
5559  */
zebra_vxlan_advertise_all_vni(ZAPI_HANDLER_ARGS)5560 void zebra_vxlan_advertise_all_vni(ZAPI_HANDLER_ARGS)
5561 {
5562 	struct stream *s = NULL;
5563 	int advertise = 0;
5564 	enum vxlan_flood_control flood_ctrl;
5565 
5566 	/* Mismatch between EVPN VRF and current VRF (should be prevented by
5567 	 * bgpd's cli) */
5568 	if (is_evpn_enabled() && !EVPN_ENABLED(zvrf))
5569 		return;
5570 
5571 	s = msg;
5572 	STREAM_GETC(s, advertise);
5573 	STREAM_GETC(s, flood_ctrl);
5574 
5575 	if (IS_ZEBRA_DEBUG_VXLAN)
5576 		zlog_debug("EVPN VRF %s(%u) VNI Adv %s, currently %s, flood control %u",
5577 			   zvrf_name(zvrf), zvrf_id(zvrf),
5578 			   advertise ? "enabled" : "disabled",
5579 			   is_evpn_enabled() ? "enabled" : "disabled",
5580 			   flood_ctrl);
5581 
5582 	if (zvrf->advertise_all_vni == advertise)
5583 		return;
5584 
5585 	zvrf->advertise_all_vni = advertise;
5586 	if (EVPN_ENABLED(zvrf)) {
5587 		zrouter.evpn_vrf = zvrf;
5588 
5589 		/* Note BUM handling */
5590 		zvrf->vxlan_flood_ctrl = flood_ctrl;
5591 
5592 		/* Replay all ESs */
5593 		zebra_evpn_es_send_all_to_client(true /* add */);
5594 
5595 		/* Build EVPN hash table and inform BGP. */
5596 		zevpn_build_hash_table();
5597 
5598 		/* Add all SVI (L3 GW) MACs to BGP*/
5599 		hash_iterate(zvrf->evpn_table,
5600 			     zebra_evpn_gw_macip_add_for_evpn_hash, NULL);
5601 
5602 		/* Read the MAC FDB */
5603 		ns_walk_func(macfdb_read_ns, NULL, NULL);
5604 
5605 		/* Read neighbors */
5606 		ns_walk_func(neigh_read_ns, NULL, NULL);
5607 	} else {
5608 		/* Cleanup VTEPs for all EVPNs - uninstall from
5609 		 * kernel and free entries.
5610 		 */
5611 		hash_iterate(zvrf->evpn_table, zebra_evpn_vxlan_cleanup_all,
5612 			     zvrf);
5613 
5614 		/* Delete all ESs in BGP */
5615 		zebra_evpn_es_send_all_to_client(false /* add */);
5616 
5617 		/* cleanup all l3vnis */
5618 		hash_iterate(zrouter.l3vni_table, zl3vni_cleanup_all, NULL);
5619 
5620 		/* Mark as "no EVPN VRF" */
5621 		zrouter.evpn_vrf = NULL;
5622 	}
5623 
5624 stream_failure:
5625 	return;
5626 }
5627 
5628 /*
5629  * Allocate EVPN hash table for this VRF and do other initialization.
5630  * NOTE: Currently supported only for default VRF.
5631  */
zebra_vxlan_init_tables(struct zebra_vrf * zvrf)5632 void zebra_vxlan_init_tables(struct zebra_vrf *zvrf)
5633 {
5634 	if (!zvrf)
5635 		return;
5636 	zvrf->evpn_table =
5637 		hash_create(zebra_evpn_hash_keymake, zebra_evpn_hash_cmp,
5638 			    "Zebra VRF EVPN Table");
5639 	zvrf->vxlan_sg_table = hash_create(zebra_vxlan_sg_hash_key_make,
5640 			zebra_vxlan_sg_hash_eq, "Zebra VxLAN SG Table");
5641 }
5642 
5643 /* Cleanup EVPN info, but don't free the table. */
zebra_vxlan_cleanup_tables(struct zebra_vrf * zvrf)5644 void zebra_vxlan_cleanup_tables(struct zebra_vrf *zvrf)
5645 {
5646 	struct zebra_vrf *evpn_zvrf = zebra_vrf_get_evpn();
5647 
5648 	if (!zvrf)
5649 		return;
5650 	hash_iterate(zvrf->evpn_table, zebra_evpn_vxlan_cleanup_all, zvrf);
5651 	hash_iterate(zvrf->vxlan_sg_table, zebra_vxlan_sg_cleanup, NULL);
5652 
5653 	if (zvrf == evpn_zvrf)
5654 		zebra_evpn_es_cleanup();
5655 }
5656 
5657 /* Close all EVPN handling */
zebra_vxlan_close_tables(struct zebra_vrf * zvrf)5658 void zebra_vxlan_close_tables(struct zebra_vrf *zvrf)
5659 {
5660 	if (!zvrf)
5661 		return;
5662 	hash_iterate(zvrf->evpn_table, zebra_evpn_vxlan_cleanup_all, zvrf);
5663 	hash_free(zvrf->evpn_table);
5664 }
5665 
5666 /* init the l3vni table */
zebra_vxlan_init(void)5667 void zebra_vxlan_init(void)
5668 {
5669 	zrouter.l3vni_table = hash_create(l3vni_hash_keymake, l3vni_hash_cmp,
5670 					  "Zebra VRF L3 VNI table");
5671 	zrouter.evpn_vrf = NULL;
5672 	zebra_evpn_mh_init();
5673 }
5674 
5675 /* free l3vni table */
zebra_vxlan_disable(void)5676 void zebra_vxlan_disable(void)
5677 {
5678 	hash_free(zrouter.l3vni_table);
5679 	zebra_evpn_mh_terminate();
5680 }
5681 
5682 /* get the l3vni svi ifindex */
get_l3vni_svi_ifindex(vrf_id_t vrf_id)5683 ifindex_t get_l3vni_svi_ifindex(vrf_id_t vrf_id)
5684 {
5685 	zebra_l3vni_t *zl3vni = NULL;
5686 
5687 	zl3vni = zl3vni_from_vrf(vrf_id);
5688 	if (!zl3vni || !is_l3vni_oper_up(zl3vni))
5689 		return 0;
5690 
5691 	return zl3vni->svi_if->ifindex;
5692 }
5693 
5694 /************************** vxlan SG cache management ************************/
5695 /* Inform PIM about the mcast group */
zebra_vxlan_sg_send(struct zebra_vrf * zvrf,struct prefix_sg * sg,char * sg_str,uint16_t cmd)5696 static int zebra_vxlan_sg_send(struct zebra_vrf *zvrf,
5697 		struct prefix_sg *sg,
5698 		char *sg_str, uint16_t cmd)
5699 {
5700 	struct zserv *client = NULL;
5701 	struct stream *s = NULL;
5702 
5703 	client = zserv_find_client(ZEBRA_ROUTE_PIM, 0);
5704 	if (!client)
5705 		return 0;
5706 
5707 	if (!CHECK_FLAG(zvrf->flags, ZEBRA_PIM_SEND_VXLAN_SG))
5708 		return 0;
5709 
5710 	s = stream_new(ZEBRA_MAX_PACKET_SIZ);
5711 
5712 	zclient_create_header(s, cmd, VRF_DEFAULT);
5713 	stream_putl(s, IPV4_MAX_BYTELEN);
5714 	stream_put(s, &sg->src.s_addr, IPV4_MAX_BYTELEN);
5715 	stream_put(s, &sg->grp.s_addr, IPV4_MAX_BYTELEN);
5716 
5717 	/* Write packet size. */
5718 	stream_putw_at(s, 0, stream_get_endp(s));
5719 
5720 	if (IS_ZEBRA_DEBUG_VXLAN)
5721 		zlog_debug(
5722 			"Send %s %s to %s",
5723 			(cmd == ZEBRA_VXLAN_SG_ADD) ? "add" : "del", sg_str,
5724 			zebra_route_string(client->proto));
5725 
5726 	if (cmd == ZEBRA_VXLAN_SG_ADD)
5727 		client->vxlan_sg_add_cnt++;
5728 	else
5729 		client->vxlan_sg_del_cnt++;
5730 
5731 	return zserv_send_message(client, s);
5732 }
5733 
zebra_vxlan_sg_hash_key_make(const void * p)5734 static unsigned int zebra_vxlan_sg_hash_key_make(const void *p)
5735 {
5736 	const zebra_vxlan_sg_t *vxlan_sg = p;
5737 
5738 	return (jhash_2words(vxlan_sg->sg.src.s_addr,
5739 				vxlan_sg->sg.grp.s_addr, 0));
5740 }
5741 
zebra_vxlan_sg_hash_eq(const void * p1,const void * p2)5742 static bool zebra_vxlan_sg_hash_eq(const void *p1, const void *p2)
5743 {
5744 	const zebra_vxlan_sg_t *sg1 = p1;
5745 	const zebra_vxlan_sg_t *sg2 = p2;
5746 
5747 	return ((sg1->sg.src.s_addr == sg2->sg.src.s_addr)
5748 		&& (sg1->sg.grp.s_addr == sg2->sg.grp.s_addr));
5749 }
5750 
zebra_vxlan_sg_new(struct zebra_vrf * zvrf,struct prefix_sg * sg)5751 static zebra_vxlan_sg_t *zebra_vxlan_sg_new(struct zebra_vrf *zvrf,
5752 		struct prefix_sg *sg)
5753 {
5754 	zebra_vxlan_sg_t *vxlan_sg;
5755 
5756 	vxlan_sg = XCALLOC(MTYPE_ZVXLAN_SG, sizeof(*vxlan_sg));
5757 
5758 	vxlan_sg->zvrf = zvrf;
5759 	vxlan_sg->sg = *sg;
5760 	prefix_sg2str(sg, vxlan_sg->sg_str);
5761 
5762 	vxlan_sg = hash_get(zvrf->vxlan_sg_table, vxlan_sg, hash_alloc_intern);
5763 
5764 	if (IS_ZEBRA_DEBUG_VXLAN)
5765 		zlog_debug("vxlan SG %s created", vxlan_sg->sg_str);
5766 
5767 	return vxlan_sg;
5768 }
5769 
zebra_vxlan_sg_find(struct zebra_vrf * zvrf,struct prefix_sg * sg)5770 static zebra_vxlan_sg_t *zebra_vxlan_sg_find(struct zebra_vrf *zvrf,
5771 					    struct prefix_sg *sg)
5772 {
5773 	zebra_vxlan_sg_t lookup;
5774 
5775 	lookup.sg = *sg;
5776 	return hash_lookup(zvrf->vxlan_sg_table, &lookup);
5777 }
5778 
zebra_vxlan_sg_add(struct zebra_vrf * zvrf,struct prefix_sg * sg)5779 static zebra_vxlan_sg_t *zebra_vxlan_sg_add(struct zebra_vrf *zvrf,
5780 					   struct prefix_sg *sg)
5781 {
5782 	zebra_vxlan_sg_t *vxlan_sg;
5783 	zebra_vxlan_sg_t *parent = NULL;
5784 	struct in_addr sip;
5785 
5786 	vxlan_sg = zebra_vxlan_sg_find(zvrf, sg);
5787 	if (vxlan_sg)
5788 		return vxlan_sg;
5789 
5790 	/* create a *G entry for every BUM group implicitly -
5791 	 * 1. The SG entry is used by pimd to setup the vxlan-origination-mroute
5792 	 * 2. the XG entry is used by pimd to setup the
5793 	 * vxlan-termination-mroute
5794 	 */
5795 	if (sg->src.s_addr != INADDR_ANY) {
5796 		memset(&sip, 0, sizeof(sip));
5797 		parent = zebra_vxlan_sg_do_ref(zvrf, sip, sg->grp);
5798 		if (!parent)
5799 			return NULL;
5800 	}
5801 
5802 	vxlan_sg = zebra_vxlan_sg_new(zvrf, sg);
5803 	if (!vxlan_sg) {
5804 		if (parent)
5805 			zebra_vxlan_sg_do_deref(zvrf, sip, sg->grp);
5806 		return vxlan_sg;
5807 	}
5808 
5809 	zebra_vxlan_sg_send(zvrf, sg, vxlan_sg->sg_str,
5810 			ZEBRA_VXLAN_SG_ADD);
5811 
5812 	return vxlan_sg;
5813 }
5814 
zebra_vxlan_sg_del(zebra_vxlan_sg_t * vxlan_sg)5815 static void zebra_vxlan_sg_del(zebra_vxlan_sg_t *vxlan_sg)
5816 {
5817 	struct in_addr sip;
5818 	struct zebra_vrf *zvrf;
5819 
5820 	zvrf = vrf_info_lookup(VRF_DEFAULT);
5821 	if (!zvrf)
5822 		return;
5823 
5824 	/* On SG entry deletion remove the reference to its parent XG
5825 	 * entry
5826 	 */
5827 	if (vxlan_sg->sg.src.s_addr != INADDR_ANY) {
5828 		memset(&sip, 0, sizeof(sip));
5829 		zebra_vxlan_sg_do_deref(zvrf, sip, vxlan_sg->sg.grp);
5830 	}
5831 
5832 	zebra_vxlan_sg_send(zvrf, &vxlan_sg->sg,
5833 			vxlan_sg->sg_str, ZEBRA_VXLAN_SG_DEL);
5834 
5835 	hash_release(vxlan_sg->zvrf->vxlan_sg_table, vxlan_sg);
5836 
5837 	if (IS_ZEBRA_DEBUG_VXLAN)
5838 		zlog_debug("VXLAN SG %s deleted", vxlan_sg->sg_str);
5839 
5840 	XFREE(MTYPE_ZVXLAN_SG, vxlan_sg);
5841 }
5842 
zebra_vxlan_sg_do_deref(struct zebra_vrf * zvrf,struct in_addr sip,struct in_addr mcast_grp)5843 static void zebra_vxlan_sg_do_deref(struct zebra_vrf *zvrf,
5844 		struct in_addr sip, struct in_addr mcast_grp)
5845 {
5846 	zebra_vxlan_sg_t *vxlan_sg;
5847 	struct prefix_sg sg;
5848 
5849 	sg.family = AF_INET;
5850 	sg.prefixlen = IPV4_MAX_BYTELEN;
5851 	sg.src = sip;
5852 	sg.grp = mcast_grp;
5853 	vxlan_sg = zebra_vxlan_sg_find(zvrf, &sg);
5854 	if (!vxlan_sg)
5855 		return;
5856 
5857 	if (vxlan_sg->ref_cnt)
5858 		--vxlan_sg->ref_cnt;
5859 
5860 	if (!vxlan_sg->ref_cnt)
5861 		zebra_vxlan_sg_del(vxlan_sg);
5862 }
5863 
zebra_vxlan_sg_do_ref(struct zebra_vrf * zvrf,struct in_addr sip,struct in_addr mcast_grp)5864 static zebra_vxlan_sg_t *zebra_vxlan_sg_do_ref(struct zebra_vrf *zvrf,
5865 				struct in_addr sip, struct in_addr mcast_grp)
5866 {
5867 	zebra_vxlan_sg_t *vxlan_sg;
5868 	struct prefix_sg sg;
5869 
5870 	sg.family = AF_INET;
5871 	sg.prefixlen = IPV4_MAX_BYTELEN;
5872 	sg.src = sip;
5873 	sg.grp = mcast_grp;
5874 	vxlan_sg = zebra_vxlan_sg_add(zvrf, &sg);
5875 	if (vxlan_sg)
5876 		++vxlan_sg->ref_cnt;
5877 
5878 	return vxlan_sg;
5879 }
5880 
zebra_vxlan_sg_deref(struct in_addr local_vtep_ip,struct in_addr mcast_grp)5881 static void zebra_vxlan_sg_deref(struct in_addr local_vtep_ip,
5882 		struct in_addr mcast_grp)
5883 {
5884 	struct zebra_vrf *zvrf;
5885 
5886 	if (local_vtep_ip.s_addr == INADDR_ANY
5887 	    || mcast_grp.s_addr == INADDR_ANY)
5888 		return;
5889 
5890 	zvrf = vrf_info_lookup(VRF_DEFAULT);
5891 	if (!zvrf)
5892 		return;
5893 
5894 	zebra_vxlan_sg_do_deref(zvrf, local_vtep_ip, mcast_grp);
5895 }
5896 
zebra_vxlan_sg_ref(struct in_addr local_vtep_ip,struct in_addr mcast_grp)5897 static void zebra_vxlan_sg_ref(struct in_addr local_vtep_ip,
5898 				struct in_addr mcast_grp)
5899 {
5900 	struct zebra_vrf *zvrf;
5901 
5902 	if (local_vtep_ip.s_addr == INADDR_ANY
5903 	    || mcast_grp.s_addr == INADDR_ANY)
5904 		return;
5905 
5906 	zvrf = vrf_info_lookup(VRF_DEFAULT);
5907 	if (!zvrf)
5908 		return;
5909 	zebra_vxlan_sg_do_ref(zvrf, local_vtep_ip, mcast_grp);
5910 }
5911 
zebra_vxlan_sg_cleanup(struct hash_bucket * backet,void * arg)5912 static void zebra_vxlan_sg_cleanup(struct hash_bucket *backet, void *arg)
5913 {
5914 	zebra_vxlan_sg_t *vxlan_sg = (zebra_vxlan_sg_t *)backet->data;
5915 
5916 	zebra_vxlan_sg_del(vxlan_sg);
5917 }
5918 
zebra_vxlan_sg_replay_send(struct hash_bucket * backet,void * arg)5919 static void zebra_vxlan_sg_replay_send(struct hash_bucket *backet, void *arg)
5920 {
5921 	zebra_vxlan_sg_t *vxlan_sg = (zebra_vxlan_sg_t *)backet->data;
5922 
5923 	zebra_vxlan_sg_send(vxlan_sg->zvrf, &vxlan_sg->sg,
5924 			vxlan_sg->sg_str, ZEBRA_VXLAN_SG_ADD);
5925 }
5926 
5927 /* Handle message from client to replay vxlan SG entries */
zebra_vxlan_sg_replay(ZAPI_HANDLER_ARGS)5928 void zebra_vxlan_sg_replay(ZAPI_HANDLER_ARGS)
5929 {
5930 	if (IS_ZEBRA_DEBUG_VXLAN)
5931 		zlog_debug("VxLAN SG updates to PIM, start");
5932 
5933 	SET_FLAG(zvrf->flags, ZEBRA_PIM_SEND_VXLAN_SG);
5934 
5935 	if (!EVPN_ENABLED(zvrf)) {
5936 		if (IS_ZEBRA_DEBUG_VXLAN)
5937 			zlog_debug("VxLAN SG replay request on unexpected vrf %d",
5938 				   zvrf->vrf->vrf_id);
5939 		return;
5940 	}
5941 
5942 	hash_iterate(zvrf->vxlan_sg_table, zebra_vxlan_sg_replay_send, NULL);
5943 }
5944 
5945 
5946 /* Cleanup EVPN configuration of a specific VRF */
zebra_evpn_vrf_cfg_cleanup(struct zebra_vrf * zvrf)5947 static void zebra_evpn_vrf_cfg_cleanup(struct zebra_vrf *zvrf)
5948 {
5949 	zebra_l3vni_t *zl3vni = NULL;
5950 
5951 	zvrf->advertise_all_vni = 0;
5952 	zvrf->advertise_gw_macip = 0;
5953 	zvrf->advertise_svi_macip = 0;
5954 	zvrf->vxlan_flood_ctrl = VXLAN_FLOOD_HEAD_END_REPL;
5955 
5956 	hash_iterate(zvrf->evpn_table, zebra_evpn_cfg_cleanup, NULL);
5957 
5958 	if (zvrf->l3vni)
5959 		zl3vni = zl3vni_lookup(zvrf->l3vni);
5960 	if (zl3vni) {
5961 		/* delete and uninstall all rmacs */
5962 		hash_iterate(zl3vni->rmac_table, zl3vni_del_rmac_hash_entry,
5963 			     zl3vni);
5964 		/* delete and uninstall all next-hops */
5965 		hash_iterate(zl3vni->nh_table, zl3vni_del_nh_hash_entry,
5966 			     zl3vni);
5967 	}
5968 }
5969 
5970 /* Cleanup BGP EVPN configuration upon client disconnect */
zebra_evpn_bgp_cfg_clean_up(struct zserv * client)5971 static int zebra_evpn_bgp_cfg_clean_up(struct zserv *client)
5972 {
5973 	struct vrf *vrf;
5974 	struct zebra_vrf *zvrf;
5975 
5976 	RB_FOREACH (vrf, vrf_id_head, &vrfs_by_id) {
5977 		zvrf = vrf->info;
5978 		if (zvrf)
5979 			zebra_evpn_vrf_cfg_cleanup(zvrf);
5980 	}
5981 
5982 	return 0;
5983 }
5984 
zebra_evpn_pim_cfg_clean_up(struct zserv * client)5985 static int zebra_evpn_pim_cfg_clean_up(struct zserv *client)
5986 {
5987 	struct zebra_vrf *zvrf = zebra_vrf_get_evpn();
5988 
5989 	if (zvrf && CHECK_FLAG(zvrf->flags, ZEBRA_PIM_SEND_VXLAN_SG)) {
5990 		if (IS_ZEBRA_DEBUG_VXLAN)
5991 			zlog_debug("VxLAN SG updates to PIM, stop");
5992 		UNSET_FLAG(zvrf->flags, ZEBRA_PIM_SEND_VXLAN_SG);
5993 	}
5994 
5995 	return 0;
5996 }
5997 
zebra_evpn_cfg_clean_up(struct zserv * client)5998 static int zebra_evpn_cfg_clean_up(struct zserv *client)
5999 {
6000 	if (client->proto == ZEBRA_ROUTE_BGP)
6001 		return zebra_evpn_bgp_cfg_clean_up(client);
6002 
6003 	if (client->proto == ZEBRA_ROUTE_PIM)
6004 		return zebra_evpn_pim_cfg_clean_up(client);
6005 
6006 	return 0;
6007 }
6008 
6009 /*
6010  * Handle results for vxlan dataplane operations.
6011  */
zebra_vxlan_handle_result(struct zebra_dplane_ctx * ctx)6012 extern void zebra_vxlan_handle_result(struct zebra_dplane_ctx *ctx)
6013 {
6014 	/* TODO -- anything other than freeing the context? */
6015 	dplane_ctx_fini(&ctx);
6016 }
6017 
6018 /* Cleanup BGP EVPN configuration upon client disconnect */
zebra_evpn_init(void)6019 extern void zebra_evpn_init(void)
6020 {
6021 	hook_register(zserv_client_close, zebra_evpn_cfg_clean_up);
6022 }
6023