blob: 0b51af5a8c78b02b8d650cf9bb4c922238f76af4 [file] [log] [blame]
paul718e3742002-12-13 20:15:29 +00001/* RIPd and zebra interface.
2 * Copyright (C) 1997, 1999 Kunihiro Ishiguro <kunihiro@zebra.org>
3 *
4 * This file is part of GNU Zebra.
5 *
6 * GNU Zebra is free software; you can redistribute it and/or modify it
7 * under the terms of the GNU General Public License as published by the
8 * Free Software Foundation; either version 2, or (at your option) any
9 * later version.
10 *
11 * GNU Zebra is distributed in the hope that it will be useful, but
12 * WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * General Public License for more details.
15 *
16 * You should have received a copy of the GNU General Public License
17 * along with GNU Zebra; see the file COPYING. If not, write to the Free
18 * Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
19 * 02111-1307, USA.
20 */
21
22#include <zebra.h>
23
24#include "command.h"
25#include "prefix.h"
Lu Fengb397cf42014-07-18 06:13:18 +000026#include "table.h"
paul718e3742002-12-13 20:15:29 +000027#include "stream.h"
Lu Fengb397cf42014-07-18 06:13:18 +000028#include "memory.h"
paul718e3742002-12-13 20:15:29 +000029#include "routemap.h"
30#include "zclient.h"
31#include "log.h"
Feng Luc99f3482014-10-16 09:52:36 +080032#include "vrf.h"
paul718e3742002-12-13 20:15:29 +000033#include "ripd/ripd.h"
34#include "ripd/rip_debug.h"
pauldc63bfd2005-10-25 23:31:05 +000035#include "ripd/rip_interface.h"
paul718e3742002-12-13 20:15:29 +000036
37/* All information about zebra. */
38struct zclient *zclient = NULL;
David Lamparter6b0655a2014-06-04 06:53:35 +020039
Lu Fengb397cf42014-07-18 06:13:18 +000040/* Send ECMP routes to zebra. */
41static void
42rip_zebra_ipv4_send (struct route_node *rp, u_char cmd)
paul718e3742002-12-13 20:15:29 +000043{
Lu Fengb397cf42014-07-18 06:13:18 +000044 static struct in_addr **nexthops = NULL;
45 static unsigned int nexthops_len = 0;
46
47 struct list *list = (struct list *)rp->info;
paul718e3742002-12-13 20:15:29 +000048 struct zapi_ipv4 api;
Lu Fengb397cf42014-07-18 06:13:18 +000049 struct listnode *listnode = NULL;
50 struct rip_info *rinfo = NULL;
51 int count = 0;
paul718e3742002-12-13 20:15:29 +000052
Feng Luc99f3482014-10-16 09:52:36 +080053 if (vrf_bitmap_check (zclient->redist[ZEBRA_ROUTE_RIP], VRF_DEFAULT))
paul718e3742002-12-13 20:15:29 +000054 {
Feng Luc99f3482014-10-16 09:52:36 +080055 api.vrf_id = VRF_DEFAULT;
paul718e3742002-12-13 20:15:29 +000056 api.type = ZEBRA_ROUTE_RIP;
57 api.flags = 0;
58 api.message = 0;
Denis Ovsienkob4e45f62011-12-05 16:35:14 +040059 api.safi = SAFI_UNICAST;
Lu Fengb397cf42014-07-18 06:13:18 +000060
61 if (nexthops_len < listcount (list))
62 {
63 nexthops_len = listcount (list);
64 nexthops = XREALLOC (MTYPE_TMP, nexthops,
65 nexthops_len * sizeof (struct in_addr *));
66 }
67
paul718e3742002-12-13 20:15:29 +000068 SET_FLAG (api.message, ZAPI_MESSAGE_NEXTHOP);
Lu Fengb397cf42014-07-18 06:13:18 +000069 for (ALL_LIST_ELEMENTS_RO (list, listnode, rinfo))
70 {
71 nexthops[count++] = &rinfo->nexthop;
72 if (cmd == ZEBRA_IPV4_ROUTE_ADD)
73 SET_FLAG (rinfo->flags, RIP_RTF_FIB);
74 else
75 UNSET_FLAG (rinfo->flags, RIP_RTF_FIB);
76 }
77
78 api.nexthop = nexthops;
79 api.nexthop_num = count;
paul718e3742002-12-13 20:15:29 +000080 api.ifindex_num = 0;
Lu Fengb397cf42014-07-18 06:13:18 +000081
82 rinfo = listgetdata (listhead (list));
83
paul718e3742002-12-13 20:15:29 +000084 SET_FLAG (api.message, ZAPI_MESSAGE_METRIC);
Lu Fengb397cf42014-07-18 06:13:18 +000085 api.metric = rinfo->metric;
paul718e3742002-12-13 20:15:29 +000086
Lu Fengb397cf42014-07-18 06:13:18 +000087 if (rinfo->distance && rinfo->distance != ZEBRA_RIP_DISTANCE_DEFAULT)
88 {
89 SET_FLAG (api.message, ZAPI_MESSAGE_DISTANCE);
90 api.distance = rinfo->distance;
91 }
paul718e3742002-12-13 20:15:29 +000092
Christian Franke2bbacea2016-10-01 21:43:17 +020093 if (rinfo->tag)
94 {
95 SET_FLAG (api.message, ZAPI_MESSAGE_TAG);
96 api.tag = rinfo->tag;
97 }
98
Lu Fengb397cf42014-07-18 06:13:18 +000099 zapi_ipv4_route (cmd, zclient,
100 (struct prefix_ipv4 *)&rp->p, &api);
101
102 if (IS_RIP_DEBUG_ZEBRA)
Lu Feng0b74a0a2014-07-18 06:13:19 +0000103 {
104 if (rip->ecmp)
105 zlog_debug ("%s: %s/%d nexthops %d",
106 (cmd == ZEBRA_IPV4_ROUTE_ADD) ? \
107 "Install into zebra" : "Delete from zebra",
108 inet_ntoa (rp->p.u.prefix4), rp->p.prefixlen, count);
109 else
110 zlog_debug ("%s: %s/%d",
111 (cmd == ZEBRA_IPV4_ROUTE_ADD) ? \
112 "Install into zebra" : "Delete from zebra",
113 inet_ntoa (rp->p.u.prefix4), rp->p.prefixlen);
114 }
paul718e3742002-12-13 20:15:29 +0000115
116 rip_global_route_changes++;
117 }
118}
119
Lu Fengb397cf42014-07-18 06:13:18 +0000120/* Add/update ECMP routes to zebra. */
paul718e3742002-12-13 20:15:29 +0000121void
Lu Fengb397cf42014-07-18 06:13:18 +0000122rip_zebra_ipv4_add (struct route_node *rp)
paul718e3742002-12-13 20:15:29 +0000123{
Lu Fengb397cf42014-07-18 06:13:18 +0000124 rip_zebra_ipv4_send (rp, ZEBRA_IPV4_ROUTE_ADD);
125}
paul718e3742002-12-13 20:15:29 +0000126
Lu Fengb397cf42014-07-18 06:13:18 +0000127/* Delete ECMP routes from zebra. */
128void
129rip_zebra_ipv4_delete (struct route_node *rp)
130{
131 rip_zebra_ipv4_send (rp, ZEBRA_IPV4_ROUTE_DELETE);
paul718e3742002-12-13 20:15:29 +0000132}
133
134/* Zebra route add and delete treatment. */
pauldc63bfd2005-10-25 23:31:05 +0000135static int
Feng Luc99f3482014-10-16 09:52:36 +0800136rip_zebra_read_ipv4 (int command, struct zclient *zclient, zebra_size_t length,
137 vrf_id_t vrf_id)
paul718e3742002-12-13 20:15:29 +0000138{
139 struct stream *s;
140 struct zapi_ipv4 api;
141 unsigned long ifindex;
142 struct in_addr nexthop;
143 struct prefix_ipv4 p;
Donald Sharp5e57b5f2016-03-11 16:28:34 -0500144 unsigned char plength = 0;
145
paul718e3742002-12-13 20:15:29 +0000146 s = zclient->ibuf;
147 ifindex = 0;
148 nexthop.s_addr = 0;
149
150 /* Type, flags, message. */
151 api.type = stream_getc (s);
152 api.flags = stream_getc (s);
153 api.message = stream_getc (s);
154
155 /* IPv4 prefix. */
156 memset (&p, 0, sizeof (struct prefix_ipv4));
157 p.family = AF_INET;
Donald Sharp5e57b5f2016-03-11 16:28:34 -0500158 plength = stream_getc (s);
159 p.prefixlen = MIN(IPV4_MAX_PREFIXLEN, plength);
paul718e3742002-12-13 20:15:29 +0000160 stream_get (&p.prefix, s, PSIZE (p.prefixlen));
161
162 /* Nexthop, ifindex, distance, metric. */
163 if (CHECK_FLAG (api.message, ZAPI_MESSAGE_NEXTHOP))
164 {
165 api.nexthop_num = stream_getc (s);
166 nexthop.s_addr = stream_get_ipv4 (s);
167 }
168 if (CHECK_FLAG (api.message, ZAPI_MESSAGE_IFINDEX))
169 {
170 api.ifindex_num = stream_getc (s);
171 ifindex = stream_getl (s);
172 }
173 if (CHECK_FLAG (api.message, ZAPI_MESSAGE_DISTANCE))
174 api.distance = stream_getc (s);
vincentfbf5d032005-09-29 11:25:50 +0000175 else
176 api.distance = 255;
paul718e3742002-12-13 20:15:29 +0000177 if (CHECK_FLAG (api.message, ZAPI_MESSAGE_METRIC))
178 api.metric = stream_getl (s);
vincentfbf5d032005-09-29 11:25:50 +0000179 else
180 api.metric = 0;
paul718e3742002-12-13 20:15:29 +0000181
Christian Franke2bbacea2016-10-01 21:43:17 +0200182 if (CHECK_FLAG (api.message, ZAPI_MESSAGE_TAG))
183 api.tag = stream_getl (s);
184 else
185 api.tag = 0;
186
paul718e3742002-12-13 20:15:29 +0000187 /* Then fetch IPv4 prefixes. */
188 if (command == ZEBRA_IPV4_ROUTE_ADD)
vincentfbf5d032005-09-29 11:25:50 +0000189 rip_redistribute_add (api.type, RIP_ROUTE_REDISTRIBUTE, &p, ifindex,
Christian Franke2bbacea2016-10-01 21:43:17 +0200190 &nexthop, api.metric, api.distance, api.tag);
191 else
paul718e3742002-12-13 20:15:29 +0000192 rip_redistribute_delete (api.type, RIP_ROUTE_REDISTRIBUTE, &p, ifindex);
193
194 return 0;
195}
196
197void
pauldc63bfd2005-10-25 23:31:05 +0000198rip_zclient_reset (void)
paul718e3742002-12-13 20:15:29 +0000199{
200 zclient_reset (zclient);
201}
202
203/* RIP route-map set for redistribution */
pauldc63bfd2005-10-25 23:31:05 +0000204static void
hasso98b718a2004-10-11 12:57:57 +0000205rip_routemap_set (int type, const char *name)
paul718e3742002-12-13 20:15:29 +0000206{
207 if (rip->route_map[type].name)
208 free(rip->route_map[type].name);
209
210 rip->route_map[type].name = strdup (name);
211 rip->route_map[type].map = route_map_lookup_by_name (name);
212}
213
pauldc63bfd2005-10-25 23:31:05 +0000214static void
hasso8a676be2004-10-08 06:36:38 +0000215rip_redistribute_metric_set (int type, unsigned int metric)
paul718e3742002-12-13 20:15:29 +0000216{
217 rip->route_map[type].metric_config = 1;
218 rip->route_map[type].metric = metric;
219}
220
pauldc63bfd2005-10-25 23:31:05 +0000221static int
hasso8a676be2004-10-08 06:36:38 +0000222rip_metric_unset (int type, unsigned int metric)
paul718e3742002-12-13 20:15:29 +0000223{
224#define DONT_CARE_METRIC_RIP 17
225 if (metric != DONT_CARE_METRIC_RIP &&
226 rip->route_map[type].metric != metric)
227 return 1;
228 rip->route_map[type].metric_config = 0;
229 rip->route_map[type].metric = 0;
230 return 0;
231}
232
233/* RIP route-map unset for redistribution */
pauldc63bfd2005-10-25 23:31:05 +0000234static int
hasso98b718a2004-10-11 12:57:57 +0000235rip_routemap_unset (int type, const char *name)
paul718e3742002-12-13 20:15:29 +0000236{
237 if (! rip->route_map[type].name ||
238 (name != NULL && strcmp(rip->route_map[type].name,name)))
239 return 1;
240
241 free (rip->route_map[type].name);
242 rip->route_map[type].name = NULL;
243 rip->route_map[type].map = NULL;
244
245 return 0;
246}
David Lamparter6b0655a2014-06-04 06:53:35 +0200247
paul718e3742002-12-13 20:15:29 +0000248/* Redistribution types */
249static struct {
250 int type;
251 int str_min_len;
hasso8a676be2004-10-08 06:36:38 +0000252 const char *str;
paul718e3742002-12-13 20:15:29 +0000253} redist_type[] = {
254 {ZEBRA_ROUTE_KERNEL, 1, "kernel"},
255 {ZEBRA_ROUTE_CONNECT, 1, "connected"},
256 {ZEBRA_ROUTE_STATIC, 1, "static"},
257 {ZEBRA_ROUTE_OSPF, 1, "ospf"},
Matthieu Boutier9c58fbd2012-02-09 21:51:17 +0100258 {ZEBRA_ROUTE_BGP, 2, "bgp"},
259 {ZEBRA_ROUTE_BABEL, 2, "babel"},
paul718e3742002-12-13 20:15:29 +0000260 {0, 0, NULL}
261};
262
263DEFUN (router_zebra,
264 router_zebra_cmd,
265 "router zebra",
266 "Enable a routing process\n"
267 "Make connection to zebra daemon\n")
268{
269 vty->node = ZEBRA_NODE;
270 zclient->enable = 1;
271 zclient_start (zclient);
272 return CMD_SUCCESS;
273}
274
275DEFUN (no_router_zebra,
276 no_router_zebra_cmd,
277 "no router zebra",
278 NO_STR
279 "Enable a routing process\n"
280 "Make connection to zebra daemon\n")
281{
282 zclient->enable = 0;
283 zclient_stop (zclient);
284 return CMD_SUCCESS;
285}
286
Stephen Hemminger2c239702009-12-10 19:16:05 +0300287#if 0
pauldc63bfd2005-10-25 23:31:05 +0000288static int
paul718e3742002-12-13 20:15:29 +0000289rip_redistribute_set (int type)
290{
Feng Luc99f3482014-10-16 09:52:36 +0800291 if (vrf_bitmap_check (zclient->redist[type], VRF_DEFAULT))
paul718e3742002-12-13 20:15:29 +0000292 return CMD_SUCCESS;
293
Feng Luc99f3482014-10-16 09:52:36 +0800294 vrf_bitmap_set (zclient->redist[type], VRF_DEFAULT);
paul718e3742002-12-13 20:15:29 +0000295
296 if (zclient->sock > 0)
ajs634f9ea2005-04-11 15:51:40 +0000297 zebra_redistribute_send (ZEBRA_REDISTRIBUTE_ADD, zclient, type);
paul718e3742002-12-13 20:15:29 +0000298
299 return CMD_SUCCESS;
300}
Stephen Hemminger2c239702009-12-10 19:16:05 +0300301#endif
paul718e3742002-12-13 20:15:29 +0000302
pauldc63bfd2005-10-25 23:31:05 +0000303static int
paul718e3742002-12-13 20:15:29 +0000304rip_redistribute_unset (int type)
305{
Feng Luc99f3482014-10-16 09:52:36 +0800306 if (! vrf_bitmap_check (zclient->redist[type], VRF_DEFAULT))
paul718e3742002-12-13 20:15:29 +0000307 return CMD_SUCCESS;
308
Feng Luc99f3482014-10-16 09:52:36 +0800309 vrf_bitmap_unset (zclient->redist[type], VRF_DEFAULT);
paul718e3742002-12-13 20:15:29 +0000310
311 if (zclient->sock > 0)
Feng Luc99f3482014-10-16 09:52:36 +0800312 zebra_redistribute_send (ZEBRA_REDISTRIBUTE_DELETE, zclient, type,
313 VRF_DEFAULT);
paul718e3742002-12-13 20:15:29 +0000314
315 /* Remove the routes from RIP table. */
316 rip_redistribute_withdraw (type);
317
318 return CMD_SUCCESS;
319}
320
321int
322rip_redistribute_check (int type)
323{
Feng Luc99f3482014-10-16 09:52:36 +0800324 return vrf_bitmap_check (zclient->redist[type], VRF_DEFAULT);
paul718e3742002-12-13 20:15:29 +0000325}
326
327void
pauldc63bfd2005-10-25 23:31:05 +0000328rip_redistribute_clean (void)
paul718e3742002-12-13 20:15:29 +0000329{
330 int i;
331
332 for (i = 0; redist_type[i].str; i++)
333 {
Feng Luc99f3482014-10-16 09:52:36 +0800334 if (vrf_bitmap_check (zclient->redist[redist_type[i].type], VRF_DEFAULT))
paul718e3742002-12-13 20:15:29 +0000335 {
336 if (zclient->sock > 0)
337 zebra_redistribute_send (ZEBRA_REDISTRIBUTE_DELETE,
Feng Luc99f3482014-10-16 09:52:36 +0800338 zclient, redist_type[i].type,
339 VRF_DEFAULT);
paul718e3742002-12-13 20:15:29 +0000340
Feng Luc99f3482014-10-16 09:52:36 +0800341 vrf_bitmap_unset (zclient->redist[redist_type[i].type], VRF_DEFAULT);
paul718e3742002-12-13 20:15:29 +0000342
343 /* Remove the routes from RIP table. */
344 rip_redistribute_withdraw (redist_type[i].type);
345 }
346 }
347}
348
349DEFUN (rip_redistribute_rip,
350 rip_redistribute_rip_cmd,
351 "redistribute rip",
352 "Redistribute information from another routing protocol\n"
353 "Routing Information Protocol (RIP)\n")
354{
Feng Luc99f3482014-10-16 09:52:36 +0800355 vrf_bitmap_set (zclient->redist[ZEBRA_ROUTE_RIP], VRF_DEFAULT);
paul718e3742002-12-13 20:15:29 +0000356 return CMD_SUCCESS;
357}
358
359DEFUN (no_rip_redistribute_rip,
360 no_rip_redistribute_rip_cmd,
361 "no redistribute rip",
362 NO_STR
363 "Redistribute information from another routing protocol\n"
364 "Routing Information Protocol (RIP)\n")
365{
Feng Luc99f3482014-10-16 09:52:36 +0800366 vrf_bitmap_unset (zclient->redist[ZEBRA_ROUTE_RIP], VRF_DEFAULT);
paul718e3742002-12-13 20:15:29 +0000367 return CMD_SUCCESS;
368}
369
370DEFUN (rip_redistribute_type,
371 rip_redistribute_type_cmd,
Paul Jakma9a57dc62006-06-30 16:58:53 +0000372 "redistribute " QUAGGA_REDIST_STR_RIPD,
373 REDIST_STR
374 QUAGGA_REDIST_HELP_STR_RIPD)
paul718e3742002-12-13 20:15:29 +0000375{
376 int i;
377
378 for(i = 0; redist_type[i].str; i++)
379 {
380 if (strncmp (redist_type[i].str, argv[0],
381 redist_type[i].str_min_len) == 0)
382 {
paul0a589352004-05-08 11:48:26 +0000383 zclient_redistribute (ZEBRA_REDISTRIBUTE_ADD, zclient,
Feng Luc99f3482014-10-16 09:52:36 +0800384 redist_type[i].type, VRF_DEFAULT);
paul718e3742002-12-13 20:15:29 +0000385 return CMD_SUCCESS;
386 }
387 }
388
389 vty_out(vty, "Invalid type %s%s", argv[0],
390 VTY_NEWLINE);
391
392 return CMD_WARNING;
393}
394
395DEFUN (no_rip_redistribute_type,
396 no_rip_redistribute_type_cmd,
Paul Jakma9a57dc62006-06-30 16:58:53 +0000397 "no redistribute " QUAGGA_REDIST_STR_RIPD,
paul718e3742002-12-13 20:15:29 +0000398 NO_STR
Paul Jakma9a57dc62006-06-30 16:58:53 +0000399 REDIST_STR
400 QUAGGA_REDIST_HELP_STR_RIPD)
paul718e3742002-12-13 20:15:29 +0000401{
402 int i;
403
404 for (i = 0; redist_type[i].str; i++)
405 {
406 if (strncmp(redist_type[i].str, argv[0],
407 redist_type[i].str_min_len) == 0)
408 {
409 rip_metric_unset (redist_type[i].type, DONT_CARE_METRIC_RIP);
410 rip_routemap_unset (redist_type[i].type,NULL);
411 rip_redistribute_unset (redist_type[i].type);
412 return CMD_SUCCESS;
413 }
414 }
415
416 vty_out(vty, "Invalid type %s%s", argv[0],
417 VTY_NEWLINE);
418
419 return CMD_WARNING;
420}
421
422DEFUN (rip_redistribute_type_routemap,
423 rip_redistribute_type_routemap_cmd,
Paul Jakma9a57dc62006-06-30 16:58:53 +0000424 "redistribute " QUAGGA_REDIST_STR_RIPD " route-map WORD",
425 REDIST_STR
426 QUAGGA_REDIST_HELP_STR_RIPD
paul718e3742002-12-13 20:15:29 +0000427 "Route map reference\n"
428 "Pointer to route-map entries\n")
429{
430 int i;
431
432 for (i = 0; redist_type[i].str; i++) {
433 if (strncmp(redist_type[i].str, argv[0],
434 redist_type[i].str_min_len) == 0)
435 {
436 rip_routemap_set (redist_type[i].type, argv[1]);
Feng Luc99f3482014-10-16 09:52:36 +0800437 zclient_redistribute (ZEBRA_REDISTRIBUTE_ADD, zclient, redist_type[i].type,
438 VRF_DEFAULT);
paul718e3742002-12-13 20:15:29 +0000439 return CMD_SUCCESS;
440 }
441 }
442
443 vty_out(vty, "Invalid type %s%s", argv[0],
444 VTY_NEWLINE);
445
446 return CMD_WARNING;
447}
448
449DEFUN (no_rip_redistribute_type_routemap,
450 no_rip_redistribute_type_routemap_cmd,
Paul Jakma9a57dc62006-06-30 16:58:53 +0000451 "no redistribute " QUAGGA_REDIST_STR_RIPD " route-map WORD",
paul718e3742002-12-13 20:15:29 +0000452 NO_STR
Paul Jakma9a57dc62006-06-30 16:58:53 +0000453 REDIST_STR
454 QUAGGA_REDIST_HELP_STR_RIPD
paul718e3742002-12-13 20:15:29 +0000455 "Route map reference\n"
456 "Pointer to route-map entries\n")
457{
458 int i;
459
460 for (i = 0; redist_type[i].str; i++)
461 {
462 if (strncmp(redist_type[i].str, argv[0],
463 redist_type[i].str_min_len) == 0)
464 {
465 if (rip_routemap_unset (redist_type[i].type,argv[1]))
466 return CMD_WARNING;
467 rip_redistribute_unset (redist_type[i].type);
468 return CMD_SUCCESS;
469 }
470 }
471
472 vty_out(vty, "Invalid type %s%s", argv[0],
473 VTY_NEWLINE);
474
475 return CMD_WARNING;
476}
477
478DEFUN (rip_redistribute_type_metric,
479 rip_redistribute_type_metric_cmd,
Paul Jakma9a57dc62006-06-30 16:58:53 +0000480 "redistribute " QUAGGA_REDIST_STR_RIPD " metric <0-16>",
481 REDIST_STR
482 QUAGGA_REDIST_HELP_STR_RIPD
paul718e3742002-12-13 20:15:29 +0000483 "Metric\n"
484 "Metric value\n")
485{
486 int i;
487 int metric;
488
489 metric = atoi (argv[1]);
490
491 for (i = 0; redist_type[i].str; i++) {
492 if (strncmp(redist_type[i].str, argv[0],
493 redist_type[i].str_min_len) == 0)
494 {
495 rip_redistribute_metric_set (redist_type[i].type, metric);
Feng Luc99f3482014-10-16 09:52:36 +0800496 zclient_redistribute (ZEBRA_REDISTRIBUTE_ADD, zclient, redist_type[i].type,
497 VRF_DEFAULT);
paul718e3742002-12-13 20:15:29 +0000498 return CMD_SUCCESS;
499 }
500 }
501
502 vty_out(vty, "Invalid type %s%s", argv[0],
503 VTY_NEWLINE);
504
505 return CMD_WARNING;
506}
507
508DEFUN (no_rip_redistribute_type_metric,
509 no_rip_redistribute_type_metric_cmd,
Paul Jakma9a57dc62006-06-30 16:58:53 +0000510 "no redistribute " QUAGGA_REDIST_STR_RIPD " metric <0-16>",
paul718e3742002-12-13 20:15:29 +0000511 NO_STR
Paul Jakma9a57dc62006-06-30 16:58:53 +0000512 REDIST_STR
513 QUAGGA_REDIST_HELP_STR_RIPD
paul718e3742002-12-13 20:15:29 +0000514 "Metric\n"
515 "Metric value\n")
516{
517 int i;
518
519 for (i = 0; redist_type[i].str; i++)
520 {
521 if (strncmp(redist_type[i].str, argv[0],
522 redist_type[i].str_min_len) == 0)
523 {
524 if (rip_metric_unset (redist_type[i].type, atoi(argv[1])))
525 return CMD_WARNING;
526 rip_redistribute_unset (redist_type[i].type);
527 return CMD_SUCCESS;
528 }
529 }
530
531 vty_out(vty, "Invalid type %s%s", argv[0],
532 VTY_NEWLINE);
533
534 return CMD_WARNING;
535}
536
hasso16705132003-05-25 14:49:19 +0000537DEFUN (rip_redistribute_type_metric_routemap,
538 rip_redistribute_type_metric_routemap_cmd,
Paul Jakma9a57dc62006-06-30 16:58:53 +0000539 "redistribute " QUAGGA_REDIST_STR_RIPD " metric <0-16> route-map WORD",
540 REDIST_STR
541 QUAGGA_REDIST_HELP_STR_RIPD
hasso16705132003-05-25 14:49:19 +0000542 "Metric\n"
543 "Metric value\n"
544 "Route map reference\n"
545 "Pointer to route-map entries\n")
546{
547 int i;
548 int metric;
549
550 metric = atoi (argv[1]);
551
552 for (i = 0; redist_type[i].str; i++) {
553 if (strncmp(redist_type[i].str, argv[0],
554 redist_type[i].str_min_len) == 0)
555 {
556 rip_redistribute_metric_set (redist_type[i].type, metric);
557 rip_routemap_set (redist_type[i].type, argv[2]);
Feng Luc99f3482014-10-16 09:52:36 +0800558 zclient_redistribute (ZEBRA_REDISTRIBUTE_ADD, zclient, redist_type[i].type,
559 VRF_DEFAULT);
hasso16705132003-05-25 14:49:19 +0000560 return CMD_SUCCESS;
561 }
562 }
563
564 vty_out(vty, "Invalid type %s%s", argv[0],
565 VTY_NEWLINE);
566
567 return CMD_WARNING;
568}
569
570
paul718e3742002-12-13 20:15:29 +0000571DEFUN (no_rip_redistribute_type_metric_routemap,
572 no_rip_redistribute_type_metric_routemap_cmd,
Paul Jakma9a57dc62006-06-30 16:58:53 +0000573 "no redistribute " QUAGGA_REDIST_STR_RIPD
574 " metric <0-16> route-map WORD",
paul718e3742002-12-13 20:15:29 +0000575 NO_STR
Paul Jakma9a57dc62006-06-30 16:58:53 +0000576 REDIST_STR
577 QUAGGA_REDIST_HELP_STR_RIPD
paul718e3742002-12-13 20:15:29 +0000578 "Metric\n"
579 "Metric value\n"
580 "Route map reference\n"
581 "Pointer to route-map entries\n")
582{
583 int i;
584
585 for (i = 0; redist_type[i].str; i++)
586 {
587 if (strncmp(redist_type[i].str, argv[0],
588 redist_type[i].str_min_len) == 0)
589 {
590 if (rip_metric_unset (redist_type[i].type, atoi(argv[1])))
591 return CMD_WARNING;
592 if (rip_routemap_unset (redist_type[i].type, argv[2]))
593 {
594 rip_redistribute_metric_set(redist_type[i].type, atoi(argv[1]));
595 return CMD_WARNING;
596 }
597 rip_redistribute_unset (redist_type[i].type);
598 return CMD_SUCCESS;
599 }
600 }
601
602 vty_out(vty, "Invalid type %s%s", argv[0],
603 VTY_NEWLINE);
604
605 return CMD_WARNING;
606}
David Lamparter6b0655a2014-06-04 06:53:35 +0200607
paul718e3742002-12-13 20:15:29 +0000608/* Default information originate. */
609
610DEFUN (rip_default_information_originate,
611 rip_default_information_originate_cmd,
612 "default-information originate",
613 "Control distribution of default route\n"
614 "Distribute a default route\n")
615{
616 struct prefix_ipv4 p;
617
618 if (! rip->default_information)
619 {
620 memset (&p, 0, sizeof (struct prefix_ipv4));
621 p.family = AF_INET;
622
623 rip->default_information = 1;
624
vincentfbf5d032005-09-29 11:25:50 +0000625 rip_redistribute_add (ZEBRA_ROUTE_RIP, RIP_ROUTE_DEFAULT, &p, 0,
Christian Franke2bbacea2016-10-01 21:43:17 +0200626 NULL, 0, 0, 0);
paul718e3742002-12-13 20:15:29 +0000627 }
628
629 return CMD_SUCCESS;
630}
631
632DEFUN (no_rip_default_information_originate,
633 no_rip_default_information_originate_cmd,
634 "no default-information originate",
635 NO_STR
636 "Control distribution of default route\n"
637 "Distribute a default route\n")
638{
639 struct prefix_ipv4 p;
640
641 if (rip->default_information)
642 {
643 memset (&p, 0, sizeof (struct prefix_ipv4));
644 p.family = AF_INET;
645
646 rip->default_information = 0;
647
hasso16705132003-05-25 14:49:19 +0000648 rip_redistribute_delete (ZEBRA_ROUTE_RIP, RIP_ROUTE_DEFAULT, &p, 0);
paul718e3742002-12-13 20:15:29 +0000649 }
650
651 return CMD_SUCCESS;
652}
David Lamparter6b0655a2014-06-04 06:53:35 +0200653
paul718e3742002-12-13 20:15:29 +0000654/* RIP configuration write function. */
pauldc63bfd2005-10-25 23:31:05 +0000655static int
paul718e3742002-12-13 20:15:29 +0000656config_write_zebra (struct vty *vty)
657{
658 if (! zclient->enable)
659 {
660 vty_out (vty, "no router zebra%s", VTY_NEWLINE);
661 return 1;
662 }
Feng Luc99f3482014-10-16 09:52:36 +0800663 else if (! vrf_bitmap_check (zclient->redist[ZEBRA_ROUTE_RIP], VRF_DEFAULT))
paul718e3742002-12-13 20:15:29 +0000664 {
665 vty_out (vty, "router zebra%s", VTY_NEWLINE);
666 vty_out (vty, " no redistribute rip%s", VTY_NEWLINE);
667 return 1;
668 }
669 return 0;
670}
671
672int
673config_write_rip_redistribute (struct vty *vty, int config_mode)
674{
675 int i;
paul718e3742002-12-13 20:15:29 +0000676
677 for (i = 0; i < ZEBRA_ROUTE_MAX; i++)
Feng Luc99f3482014-10-16 09:52:36 +0800678 if (i != zclient->redist_default &&
679 vrf_bitmap_check (zclient->redist[i], VRF_DEFAULT))
paul718e3742002-12-13 20:15:29 +0000680 {
681 if (config_mode)
682 {
683 if (rip->route_map[i].metric_config)
684 {
685 if (rip->route_map[i].name)
686 vty_out (vty, " redistribute %s metric %d route-map %s%s",
ajsf52d13c2005-10-01 17:38:06 +0000687 zebra_route_string(i), rip->route_map[i].metric,
paul718e3742002-12-13 20:15:29 +0000688 rip->route_map[i].name,
689 VTY_NEWLINE);
690 else
691 vty_out (vty, " redistribute %s metric %d%s",
ajsf52d13c2005-10-01 17:38:06 +0000692 zebra_route_string(i), rip->route_map[i].metric,
paul718e3742002-12-13 20:15:29 +0000693 VTY_NEWLINE);
694 }
695 else
696 {
697 if (rip->route_map[i].name)
698 vty_out (vty, " redistribute %s route-map %s%s",
ajsf52d13c2005-10-01 17:38:06 +0000699 zebra_route_string(i), rip->route_map[i].name,
paul718e3742002-12-13 20:15:29 +0000700 VTY_NEWLINE);
701 else
ajsf52d13c2005-10-01 17:38:06 +0000702 vty_out (vty, " redistribute %s%s", zebra_route_string(i),
paul718e3742002-12-13 20:15:29 +0000703 VTY_NEWLINE);
704 }
705 }
706 else
ajsf52d13c2005-10-01 17:38:06 +0000707 vty_out (vty, " %s", zebra_route_string(i));
paul718e3742002-12-13 20:15:29 +0000708 }
709 return 0;
710}
711
712/* Zebra node structure. */
Stephen Hemminger7fc626d2008-12-01 11:10:34 -0800713static struct cmd_node zebra_node =
paul718e3742002-12-13 20:15:29 +0000714{
715 ZEBRA_NODE,
716 "%s(config-router)# ",
717};
718
Feng Luc99f3482014-10-16 09:52:36 +0800719static void
720rip_zebra_connected (struct zclient *zclient)
721{
722 zclient_send_requests (zclient, VRF_DEFAULT);
723}
724
paul718e3742002-12-13 20:15:29 +0000725void
Donald Sharp71252932015-09-24 09:25:19 -0400726rip_zclient_init (struct thread_master *master)
paul718e3742002-12-13 20:15:29 +0000727{
728 /* Set default value to the zebra client structure. */
Donald Sharp71252932015-09-24 09:25:19 -0400729 zclient = zclient_new (master);
paul718e3742002-12-13 20:15:29 +0000730 zclient_init (zclient, ZEBRA_ROUTE_RIP);
Feng Luc99f3482014-10-16 09:52:36 +0800731 zclient->zebra_connected = rip_zebra_connected;
paul718e3742002-12-13 20:15:29 +0000732 zclient->interface_add = rip_interface_add;
733 zclient->interface_delete = rip_interface_delete;
734 zclient->interface_address_add = rip_interface_address_add;
735 zclient->interface_address_delete = rip_interface_address_delete;
736 zclient->ipv4_route_add = rip_zebra_read_ipv4;
737 zclient->ipv4_route_delete = rip_zebra_read_ipv4;
738 zclient->interface_up = rip_interface_up;
739 zclient->interface_down = rip_interface_down;
740
741 /* Install zebra node. */
742 install_node (&zebra_node, config_write_zebra);
743
744 /* Install command elements to zebra node. */
745 install_element (CONFIG_NODE, &router_zebra_cmd);
746 install_element (CONFIG_NODE, &no_router_zebra_cmd);
747 install_default (ZEBRA_NODE);
748 install_element (ZEBRA_NODE, &rip_redistribute_rip_cmd);
749 install_element (ZEBRA_NODE, &no_rip_redistribute_rip_cmd);
750
751 /* Install command elements to rip node. */
752 install_element (RIP_NODE, &rip_redistribute_type_cmd);
753 install_element (RIP_NODE, &rip_redistribute_type_routemap_cmd);
754 install_element (RIP_NODE, &rip_redistribute_type_metric_cmd);
hasso16705132003-05-25 14:49:19 +0000755 install_element (RIP_NODE, &rip_redistribute_type_metric_routemap_cmd);
paul718e3742002-12-13 20:15:29 +0000756 install_element (RIP_NODE, &no_rip_redistribute_type_cmd);
757 install_element (RIP_NODE, &no_rip_redistribute_type_routemap_cmd);
758 install_element (RIP_NODE, &no_rip_redistribute_type_metric_cmd);
759 install_element (RIP_NODE, &no_rip_redistribute_type_metric_routemap_cmd);
760 install_element (RIP_NODE, &rip_default_information_originate_cmd);
761 install_element (RIP_NODE, &no_rip_default_information_originate_cmd);
762}