]> git.proxmox.com Git - mirror_frr.git/blob - ripd/rip_interface.c
sharpd, staticd: Add access_list_init
[mirror_frr.git] / ripd / rip_interface.c
1 /* Interface related function for RIP.
2 * Copyright (C) 1997, 98 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 along
17 * with this program; see the file COPYING; if not, write to the Free Software
18 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
19 */
20
21 #include <zebra.h>
22
23 #include "command.h"
24 #include "if.h"
25 #include "sockunion.h"
26 #include "prefix.h"
27 #include "memory.h"
28 #include "network.h"
29 #include "table.h"
30 #include "log.h"
31 #include "stream.h"
32 #include "thread.h"
33 #include "zclient.h"
34 #include "filter.h"
35 #include "sockopt.h"
36 #include "privs.h"
37
38 #include "zebra/connected.h"
39
40 #include "ripd/ripd.h"
41 #include "ripd/rip_debug.h"
42 #include "ripd/rip_interface.h"
43
44 DEFINE_HOOK(rip_ifaddr_add, (struct connected * ifc), (ifc))
45 DEFINE_HOOK(rip_ifaddr_del, (struct connected * ifc), (ifc))
46
47 /* static prototypes */
48 static void rip_enable_apply(struct interface *);
49 static void rip_passive_interface_apply(struct interface *);
50 static int rip_if_down(struct interface *ifp);
51 static int rip_enable_if_lookup(const char *ifname);
52 static int rip_enable_network_lookup2(struct connected *connected);
53 static void rip_enable_apply_all(void);
54
55 const struct message ri_version_msg[] = {{RI_RIP_VERSION_1, "1"},
56 {RI_RIP_VERSION_2, "2"},
57 {RI_RIP_VERSION_1_AND_2, "1 2"},
58 {RI_RIP_VERSION_NONE, "none"},
59 {0}};
60
61 /* RIP enabled network vector. */
62 vector rip_enable_interface;
63
64 /* RIP enabled interface table. */
65 struct route_table *rip_enable_network;
66
67 /* Vector to store passive-interface name. */
68 static int passive_default; /* are we in passive-interface default mode? */
69 vector Vrip_passive_nondefault;
70
71 /* Join to the RIP version 2 multicast group. */
72 static int ipv4_multicast_join(int sock, struct in_addr group,
73 struct in_addr ifa, ifindex_t ifindex)
74 {
75 int ret;
76
77 ret = setsockopt_ipv4_multicast(sock, IP_ADD_MEMBERSHIP, ifa,
78 group.s_addr, ifindex);
79
80 if (ret < 0)
81 zlog_info("can't setsockopt IP_ADD_MEMBERSHIP %s",
82 safe_strerror(errno));
83
84 return ret;
85 }
86
87 /* Leave from the RIP version 2 multicast group. */
88 static int ipv4_multicast_leave(int sock, struct in_addr group,
89 struct in_addr ifa, ifindex_t ifindex)
90 {
91 int ret;
92
93 ret = setsockopt_ipv4_multicast(sock, IP_DROP_MEMBERSHIP, ifa,
94 group.s_addr, ifindex);
95
96 if (ret < 0)
97 zlog_info("can't setsockopt IP_DROP_MEMBERSHIP");
98
99 return ret;
100 }
101
102 static void rip_interface_reset(struct rip_interface *);
103
104 /* Allocate new RIP's interface configuration. */
105 static struct rip_interface *rip_interface_new(void)
106 {
107 struct rip_interface *ri;
108
109 ri = XCALLOC(MTYPE_RIP_INTERFACE, sizeof(struct rip_interface));
110
111 rip_interface_reset(ri);
112
113 return ri;
114 }
115
116 void rip_interface_multicast_set(int sock, struct connected *connected)
117 {
118 struct in_addr addr;
119
120 assert(connected != NULL);
121
122 addr = CONNECTED_ID(connected)->u.prefix4;
123
124 if (setsockopt_ipv4_multicast_if(sock, addr, connected->ifp->ifindex)
125 < 0) {
126 zlog_warn(
127 "Can't setsockopt IP_MULTICAST_IF on fd %d to "
128 "ifindex %d for interface %s",
129 sock, connected->ifp->ifindex, connected->ifp->name);
130 }
131
132 return;
133 }
134
135 /* Send RIP request packet to specified interface. */
136 static void rip_request_interface_send(struct interface *ifp, uint8_t version)
137 {
138 struct sockaddr_in to;
139
140 /* RIPv2 support multicast. */
141 if (version == RIPv2 && if_is_multicast(ifp)) {
142
143 if (IS_RIP_DEBUG_EVENT)
144 zlog_debug("multicast request on %s", ifp->name);
145
146 rip_request_send(NULL, ifp, version, NULL);
147 return;
148 }
149
150 /* RIPv1 and non multicast interface. */
151 if (if_is_pointopoint(ifp) || if_is_broadcast(ifp)) {
152 struct listnode *cnode, *cnnode;
153 struct connected *connected;
154
155 if (IS_RIP_DEBUG_EVENT)
156 zlog_debug("broadcast request to %s", ifp->name);
157
158 for (ALL_LIST_ELEMENTS(ifp->connected, cnode, cnnode,
159 connected)) {
160 if (connected->address->family == AF_INET) {
161 memset(&to, 0, sizeof(struct sockaddr_in));
162 to.sin_port = htons(RIP_PORT_DEFAULT);
163 if (connected->destination)
164 /* use specified broadcast or peer
165 * destination addr */
166 to.sin_addr = connected->destination->u
167 .prefix4;
168 else if (connected->address->prefixlen
169 < IPV4_MAX_PREFIXLEN)
170 /* calculate the appropriate broadcast
171 * address */
172 to.sin_addr
173 .s_addr = ipv4_broadcast_addr(
174 connected->address->u.prefix4
175 .s_addr,
176 connected->address->prefixlen);
177 else
178 /* do not know where to send the packet
179 */
180 continue;
181
182 if (IS_RIP_DEBUG_EVENT)
183 zlog_debug("SEND request to %s",
184 inet_ntoa(to.sin_addr));
185
186 rip_request_send(&to, ifp, version, connected);
187 }
188 }
189 }
190 }
191
192 /* This will be executed when interface goes up. */
193 static void rip_request_interface(struct interface *ifp)
194 {
195 struct rip_interface *ri;
196
197 /* In default ripd doesn't send RIP_REQUEST to the loopback interface.
198 */
199 if (if_is_loopback(ifp))
200 return;
201
202 /* If interface is down, don't send RIP packet. */
203 if (!if_is_operative(ifp))
204 return;
205
206 /* Fetch RIP interface information. */
207 ri = ifp->info;
208
209
210 /* If there is no version configuration in the interface,
211 use rip's version setting. */
212 {
213 int vsend = ((ri->ri_send == RI_RIP_UNSPEC) ? rip->version_send
214 : ri->ri_send);
215 if (vsend & RIPv1)
216 rip_request_interface_send(ifp, RIPv1);
217 if (vsend & RIPv2)
218 rip_request_interface_send(ifp, RIPv2);
219 }
220 }
221
222 #if 0
223 /* Send RIP request to the neighbor. */
224 static void
225 rip_request_neighbor (struct in_addr addr)
226 {
227 struct sockaddr_in to;
228
229 memset (&to, 0, sizeof (struct sockaddr_in));
230 to.sin_port = htons (RIP_PORT_DEFAULT);
231 to.sin_addr = addr;
232
233 rip_request_send (&to, NULL, rip->version_send, NULL);
234 }
235
236 /* Request routes at all interfaces. */
237 static void
238 rip_request_neighbor_all (void)
239 {
240 struct route_node *rp;
241
242 if (! rip)
243 return;
244
245 if (IS_RIP_DEBUG_EVENT)
246 zlog_debug ("request to the all neighbor");
247
248 /* Send request to all neighbor. */
249 for (rp = route_top (rip->neighbor); rp; rp = route_next (rp))
250 if (rp->info)
251 rip_request_neighbor (rp->p.u.prefix4);
252 }
253 #endif
254
255 /* Multicast packet receive socket. */
256 static int rip_multicast_join(struct interface *ifp, int sock)
257 {
258 struct listnode *cnode;
259 struct connected *ifc;
260
261 if (if_is_operative(ifp) && if_is_multicast(ifp)) {
262 if (IS_RIP_DEBUG_EVENT)
263 zlog_debug("multicast join at %s", ifp->name);
264
265 for (ALL_LIST_ELEMENTS_RO(ifp->connected, cnode, ifc)) {
266 struct prefix_ipv4 *p;
267 struct in_addr group;
268
269 p = (struct prefix_ipv4 *)ifc->address;
270
271 if (p->family != AF_INET)
272 continue;
273
274 group.s_addr = htonl(INADDR_RIP_GROUP);
275 if (ipv4_multicast_join(sock, group, p->prefix,
276 ifp->ifindex)
277 < 0)
278 return -1;
279 else
280 return 0;
281 }
282 }
283 return 0;
284 }
285
286 /* Leave from multicast group. */
287 static void rip_multicast_leave(struct interface *ifp, int sock)
288 {
289 struct listnode *cnode;
290 struct connected *connected;
291
292 if (if_is_up(ifp) && if_is_multicast(ifp)) {
293 if (IS_RIP_DEBUG_EVENT)
294 zlog_debug("multicast leave from %s", ifp->name);
295
296 for (ALL_LIST_ELEMENTS_RO(ifp->connected, cnode, connected)) {
297 struct prefix_ipv4 *p;
298 struct in_addr group;
299
300 p = (struct prefix_ipv4 *)connected->address;
301
302 if (p->family != AF_INET)
303 continue;
304
305 group.s_addr = htonl(INADDR_RIP_GROUP);
306 if (ipv4_multicast_leave(sock, group, p->prefix,
307 ifp->ifindex)
308 == 0)
309 return;
310 }
311 }
312 }
313
314 /* Is there and address on interface that I could use ? */
315 static int rip_if_ipv4_address_check(struct interface *ifp)
316 {
317 struct listnode *nn;
318 struct connected *connected;
319 int count = 0;
320
321 for (ALL_LIST_ELEMENTS_RO(ifp->connected, nn, connected)) {
322 struct prefix *p;
323
324 p = connected->address;
325
326 if (p->family == AF_INET)
327 count++;
328 }
329
330 return count;
331 }
332
333
334 /* Does this address belongs to me ? */
335 int if_check_address(struct in_addr addr)
336 {
337 struct vrf *vrf = vrf_lookup_by_id(VRF_DEFAULT);
338 struct interface *ifp;
339
340 FOR_ALL_INTERFACES (vrf, ifp) {
341 struct listnode *cnode;
342 struct connected *connected;
343
344 for (ALL_LIST_ELEMENTS_RO(ifp->connected, cnode, connected)) {
345 struct prefix_ipv4 *p;
346
347 p = (struct prefix_ipv4 *)connected->address;
348
349 if (p->family != AF_INET)
350 continue;
351
352 if (IPV4_ADDR_CMP(&p->prefix, &addr) == 0)
353 return 1;
354 }
355 }
356 return 0;
357 }
358
359 /* Inteface link down message processing. */
360 int rip_interface_down(int command, struct zclient *zclient,
361 zebra_size_t length, vrf_id_t vrf_id)
362 {
363 struct interface *ifp;
364 struct stream *s;
365
366 s = zclient->ibuf;
367
368 /* zebra_interface_state_read() updates interface structure in
369 iflist. */
370 ifp = zebra_interface_state_read(s, vrf_id);
371
372 if (ifp == NULL)
373 return 0;
374
375 rip_if_down(ifp);
376
377 if (IS_RIP_DEBUG_ZEBRA)
378 zlog_debug(
379 "interface %s index %d flags %llx metric %d mtu %d is down",
380 ifp->name, ifp->ifindex, (unsigned long long)ifp->flags,
381 ifp->metric, ifp->mtu);
382
383 return 0;
384 }
385
386 /* Inteface link up message processing */
387 int rip_interface_up(int command, struct zclient *zclient, zebra_size_t length,
388 vrf_id_t vrf_id)
389 {
390 struct interface *ifp;
391
392 /* zebra_interface_state_read () updates interface structure in
393 iflist. */
394 ifp = zebra_interface_state_read(zclient->ibuf, vrf_id);
395
396 if (ifp == NULL)
397 return 0;
398
399 if (IS_RIP_DEBUG_ZEBRA)
400 zlog_debug(
401 "interface %s index %d flags %#llx metric %d mtu %d is up",
402 ifp->name, ifp->ifindex, (unsigned long long)ifp->flags,
403 ifp->metric, ifp->mtu);
404
405 /* Check if this interface is RIP enabled or not.*/
406 rip_enable_apply(ifp);
407
408 /* Check for a passive interface */
409 rip_passive_interface_apply(ifp);
410
411 /* Apply distribute list to the all interface. */
412 rip_distribute_update_interface(ifp);
413
414 return 0;
415 }
416
417 /* Inteface addition message from zebra. */
418 int rip_interface_add(int command, struct zclient *zclient, zebra_size_t length,
419 vrf_id_t vrf_id)
420 {
421 struct interface *ifp;
422
423 ifp = zebra_interface_add_read(zclient->ibuf, vrf_id);
424
425 if (IS_RIP_DEBUG_ZEBRA)
426 zlog_debug(
427 "interface add %s index %d flags %#llx metric %d mtu %d",
428 ifp->name, ifp->ifindex, (unsigned long long)ifp->flags,
429 ifp->metric, ifp->mtu);
430
431 /* Check if this interface is RIP enabled or not.*/
432 rip_enable_apply(ifp);
433
434 /* Check for a passive interface */
435 rip_passive_interface_apply(ifp);
436
437 /* Apply distribute list to the all interface. */
438 rip_distribute_update_interface(ifp);
439
440 /* rip_request_neighbor_all (); */
441
442 /* Check interface routemap. */
443 rip_if_rmap_update_interface(ifp);
444
445 return 0;
446 }
447
448 int rip_interface_delete(int command, struct zclient *zclient,
449 zebra_size_t length, vrf_id_t vrf_id)
450 {
451 struct interface *ifp;
452 struct stream *s;
453
454
455 s = zclient->ibuf;
456 /* zebra_interface_state_read() updates interface structure in iflist */
457 ifp = zebra_interface_state_read(s, vrf_id);
458
459 if (ifp == NULL)
460 return 0;
461
462 if (if_is_up(ifp)) {
463 rip_if_down(ifp);
464 }
465
466 zlog_info("interface delete %s index %d flags %#llx metric %d mtu %d",
467 ifp->name, ifp->ifindex, (unsigned long long)ifp->flags,
468 ifp->metric, ifp->mtu);
469
470 /* To support pseudo interface do not free interface structure. */
471 /* if_delete(ifp); */
472 if_set_index(ifp, IFINDEX_INTERNAL);
473
474 return 0;
475 }
476
477 static void rip_interface_clean(struct rip_interface *ri)
478 {
479 ri->enable_network = 0;
480 ri->enable_interface = 0;
481 ri->running = 0;
482
483 if (ri->t_wakeup) {
484 thread_cancel(ri->t_wakeup);
485 ri->t_wakeup = NULL;
486 }
487 }
488
489 void rip_interfaces_clean(void)
490 {
491 struct vrf *vrf = vrf_lookup_by_id(VRF_DEFAULT);
492 struct interface *ifp;
493
494 FOR_ALL_INTERFACES (vrf, ifp)
495 rip_interface_clean(ifp->info);
496 }
497
498 static void rip_interface_reset(struct rip_interface *ri)
499 {
500 /* Default authentication type is simple password for Cisco
501 compatibility. */
502 ri->auth_type = RIP_NO_AUTH;
503 ri->md5_auth_len = RIP_AUTH_MD5_COMPAT_SIZE;
504
505 /* Set default split-horizon behavior. If the interface is Frame
506 Relay or SMDS is enabled, the default value for split-horizon is
507 off. But currently Zebra does detect Frame Relay or SMDS
508 interface. So all interface is set to split horizon. */
509 ri->split_horizon_default = RIP_SPLIT_HORIZON;
510 ri->split_horizon = ri->split_horizon_default;
511
512 ri->ri_send = RI_RIP_UNSPEC;
513 ri->ri_receive = RI_RIP_UNSPEC;
514
515 ri->v2_broadcast = 0;
516
517 if (ri->auth_str)
518 XFREE(MTYPE_RIP_INTERFACE_STRING, ri->auth_str);
519
520 if (ri->key_chain)
521 XFREE(MTYPE_RIP_INTERFACE_STRING, ri->key_chain);
522
523
524 ri->list[RIP_FILTER_IN] = NULL;
525 ri->list[RIP_FILTER_OUT] = NULL;
526
527 ri->prefix[RIP_FILTER_IN] = NULL;
528 ri->prefix[RIP_FILTER_OUT] = NULL;
529
530 ri->recv_badpackets = 0;
531 ri->recv_badroutes = 0;
532 ri->sent_updates = 0;
533
534 ri->passive = 0;
535
536 rip_interface_clean(ri);
537 }
538
539 void rip_interfaces_reset(void)
540 {
541 struct vrf *vrf = vrf_lookup_by_id(VRF_DEFAULT);
542 struct interface *ifp;
543
544 FOR_ALL_INTERFACES (vrf, ifp)
545 rip_interface_reset(ifp->info);
546 }
547
548 int rip_if_down(struct interface *ifp)
549 {
550 struct route_node *rp;
551 struct rip_info *rinfo;
552 struct rip_interface *ri = NULL;
553 struct list *list = NULL;
554 struct listnode *listnode = NULL, *nextnode = NULL;
555 if (rip) {
556 for (rp = route_top(rip->table); rp; rp = route_next(rp))
557 if ((list = rp->info) != NULL)
558 for (ALL_LIST_ELEMENTS(list, listnode, nextnode,
559 rinfo))
560 if (rinfo->nh.ifindex == ifp->ifindex)
561 rip_ecmp_delete(rinfo);
562
563 ri = ifp->info;
564
565 if (ri->running) {
566 if (IS_RIP_DEBUG_EVENT)
567 zlog_debug("turn off %s", ifp->name);
568
569 /* Leave from multicast group. */
570 rip_multicast_leave(ifp, rip->sock);
571
572 ri->running = 0;
573 }
574 }
575
576 return 0;
577 }
578
579 /* Needed for stop RIP process. */
580 void rip_if_down_all()
581 {
582 struct vrf *vrf = vrf_lookup_by_id(VRF_DEFAULT);
583 struct interface *ifp;
584
585 FOR_ALL_INTERFACES (vrf, ifp)
586 rip_if_down(ifp);
587 }
588
589 static void rip_apply_address_add(struct connected *ifc)
590 {
591 struct prefix_ipv4 address;
592 struct nexthop nh;
593 struct prefix *p;
594
595 if (!rip)
596 return;
597
598 if (!if_is_up(ifc->ifp))
599 return;
600
601 p = ifc->address;
602
603 memset(&address, 0, sizeof(address));
604 memset(&nh, 0, sizeof(nh));
605
606 address.family = p->family;
607 address.prefix = p->u.prefix4;
608 address.prefixlen = p->prefixlen;
609 apply_mask_ipv4(&address);
610
611 nh.ifindex = ifc->ifp->ifindex;
612 nh.type = NEXTHOP_TYPE_IFINDEX;
613
614 /* Check if this interface is RIP enabled or not
615 or Check if this address's prefix is RIP enabled */
616 if ((rip_enable_if_lookup(ifc->ifp->name) >= 0)
617 || (rip_enable_network_lookup2(ifc) >= 0))
618 rip_redistribute_add(ZEBRA_ROUTE_CONNECT, RIP_ROUTE_INTERFACE,
619 &address, &nh, 0, 0, 0);
620 }
621
622 int rip_interface_address_add(int command, struct zclient *zclient,
623 zebra_size_t length, vrf_id_t vrf_id)
624 {
625 struct connected *ifc;
626 struct prefix *p;
627
628 ifc = zebra_interface_address_read(ZEBRA_INTERFACE_ADDRESS_ADD,
629 zclient->ibuf, vrf_id);
630
631 if (ifc == NULL)
632 return 0;
633
634 p = ifc->address;
635
636 if (p->family == AF_INET) {
637 if (IS_RIP_DEBUG_ZEBRA)
638 zlog_debug("connected address %s/%d is added",
639 inet_ntoa(p->u.prefix4), p->prefixlen);
640
641 rip_enable_apply(ifc->ifp);
642 /* Check if this prefix needs to be redistributed */
643 rip_apply_address_add(ifc);
644
645 hook_call(rip_ifaddr_add, ifc);
646 }
647
648 return 0;
649 }
650
651 static void rip_apply_address_del(struct connected *ifc)
652 {
653 struct prefix_ipv4 address;
654 struct prefix *p;
655
656 if (!rip)
657 return;
658
659 if (!if_is_up(ifc->ifp))
660 return;
661
662 p = ifc->address;
663
664 memset(&address, 0, sizeof(address));
665 address.family = p->family;
666 address.prefix = p->u.prefix4;
667 address.prefixlen = p->prefixlen;
668 apply_mask_ipv4(&address);
669
670 rip_redistribute_delete(ZEBRA_ROUTE_CONNECT, RIP_ROUTE_INTERFACE,
671 &address, ifc->ifp->ifindex);
672 }
673
674 int rip_interface_address_delete(int command, struct zclient *zclient,
675 zebra_size_t length, vrf_id_t vrf_id)
676 {
677 struct connected *ifc;
678 struct prefix *p;
679
680 ifc = zebra_interface_address_read(ZEBRA_INTERFACE_ADDRESS_DELETE,
681 zclient->ibuf, vrf_id);
682
683 if (ifc) {
684 p = ifc->address;
685 if (p->family == AF_INET) {
686 if (IS_RIP_DEBUG_ZEBRA)
687 zlog_debug("connected address %s/%d is deleted",
688 inet_ntoa(p->u.prefix4),
689 p->prefixlen);
690
691 hook_call(rip_ifaddr_del, ifc);
692
693 /* Chech wether this prefix needs to be removed */
694 rip_apply_address_del(ifc);
695 }
696
697 connected_free(ifc);
698 }
699
700 return 0;
701 }
702
703 /* Check interface is enabled by network statement. */
704 /* Check wether the interface has at least a connected prefix that
705 * is within the ripng_enable_network table. */
706 static int rip_enable_network_lookup_if(struct interface *ifp)
707 {
708 struct listnode *node, *nnode;
709 struct connected *connected;
710 struct prefix_ipv4 address;
711
712 for (ALL_LIST_ELEMENTS(ifp->connected, node, nnode, connected)) {
713 struct prefix *p;
714 struct route_node *node;
715
716 p = connected->address;
717
718 if (p->family == AF_INET) {
719 address.family = AF_INET;
720 address.prefix = p->u.prefix4;
721 address.prefixlen = IPV4_MAX_BITLEN;
722
723 node = route_node_match(rip_enable_network,
724 (struct prefix *)&address);
725 if (node) {
726 route_unlock_node(node);
727 return 1;
728 }
729 }
730 }
731 return -1;
732 }
733
734 /* Check wether connected is within the ripng_enable_network table. */
735 int rip_enable_network_lookup2(struct connected *connected)
736 {
737 struct prefix_ipv4 address;
738 struct prefix *p;
739
740 p = connected->address;
741
742 if (p->family == AF_INET) {
743 struct route_node *node;
744
745 address.family = p->family;
746 address.prefix = p->u.prefix4;
747 address.prefixlen = IPV4_MAX_BITLEN;
748
749 /* LPM on p->family, p->u.prefix4/IPV4_MAX_BITLEN within
750 * rip_enable_network */
751 node = route_node_match(rip_enable_network,
752 (struct prefix *)&address);
753
754 if (node) {
755 route_unlock_node(node);
756 return 1;
757 }
758 }
759
760 return -1;
761 }
762 /* Add RIP enable network. */
763 static int rip_enable_network_add(struct prefix *p)
764 {
765 struct route_node *node;
766
767 node = route_node_get(rip_enable_network, p);
768
769 if (node->info) {
770 route_unlock_node(node);
771 return -1;
772 } else
773 node->info = (void *)1;
774
775 /* XXX: One should find a better solution than a generic one */
776 rip_enable_apply_all();
777
778 return 1;
779 }
780
781 /* Delete RIP enable network. */
782 static int rip_enable_network_delete(struct prefix *p)
783 {
784 struct route_node *node;
785
786 node = route_node_lookup(rip_enable_network, p);
787 if (node) {
788 node->info = NULL;
789
790 /* Unlock info lock. */
791 route_unlock_node(node);
792
793 /* Unlock lookup lock. */
794 route_unlock_node(node);
795
796 /* XXX: One should find a better solution than a generic one */
797 rip_enable_apply_all();
798
799 return 1;
800 }
801 return -1;
802 }
803
804 /* Check interface is enabled by ifname statement. */
805 static int rip_enable_if_lookup(const char *ifname)
806 {
807 unsigned int i;
808 char *str;
809
810 for (i = 0; i < vector_active(rip_enable_interface); i++)
811 if ((str = vector_slot(rip_enable_interface, i)) != NULL)
812 if (strcmp(str, ifname) == 0)
813 return i;
814 return -1;
815 }
816
817 /* Add interface to rip_enable_if. */
818 static int rip_enable_if_add(const char *ifname)
819 {
820 int ret;
821
822 ret = rip_enable_if_lookup(ifname);
823 if (ret >= 0)
824 return -1;
825
826 vector_set(rip_enable_interface,
827 XSTRDUP(MTYPE_RIP_INTERFACE_STRING, ifname));
828
829 rip_enable_apply_all(); /* TODOVJ */
830
831 return 1;
832 }
833
834 /* Delete interface from rip_enable_if. */
835 static int rip_enable_if_delete(const char *ifname)
836 {
837 int index;
838 char *str;
839
840 index = rip_enable_if_lookup(ifname);
841 if (index < 0)
842 return -1;
843
844 str = vector_slot(rip_enable_interface, index);
845 XFREE(MTYPE_RIP_INTERFACE_STRING, str);
846 vector_unset(rip_enable_interface, index);
847
848 rip_enable_apply_all(); /* TODOVJ */
849
850 return 1;
851 }
852
853 /* Join to multicast group and send request to the interface. */
854 static int rip_interface_wakeup(struct thread *t)
855 {
856 struct interface *ifp;
857 struct rip_interface *ri;
858
859 /* Get interface. */
860 ifp = THREAD_ARG(t);
861
862 ri = ifp->info;
863 ri->t_wakeup = NULL;
864
865 /* Join to multicast group. */
866 if (rip_multicast_join(ifp, rip->sock) < 0) {
867 zlog_err("multicast join failed, interface %s not running",
868 ifp->name);
869 return 0;
870 }
871
872 /* Set running flag. */
873 ri->running = 1;
874
875 /* Send RIP request to the interface. */
876 rip_request_interface(ifp);
877
878 return 0;
879 }
880
881 static void rip_connect_set(struct interface *ifp, int set)
882 {
883 struct listnode *node, *nnode;
884 struct connected *connected;
885 struct prefix_ipv4 address;
886 struct nexthop nh;
887
888 memset(&nh, 0, sizeof(nh));
889
890 for (ALL_LIST_ELEMENTS(ifp->connected, node, nnode, connected)) {
891 struct prefix *p;
892 p = connected->address;
893
894 if (p->family != AF_INET)
895 continue;
896
897 address.family = AF_INET;
898 address.prefix = p->u.prefix4;
899 address.prefixlen = p->prefixlen;
900 apply_mask_ipv4(&address);
901
902 nh.ifindex = connected->ifp->ifindex;
903 nh.type = NEXTHOP_TYPE_IFINDEX;
904 if (set) {
905 /* Check once more wether this prefix is within a
906 * "network IF_OR_PREF" one */
907 if ((rip_enable_if_lookup(connected->ifp->name) >= 0)
908 || (rip_enable_network_lookup2(connected) >= 0))
909 rip_redistribute_add(ZEBRA_ROUTE_CONNECT,
910 RIP_ROUTE_INTERFACE,
911 &address, &nh, 0, 0, 0);
912 } else {
913 rip_redistribute_delete(ZEBRA_ROUTE_CONNECT,
914 RIP_ROUTE_INTERFACE, &address,
915 connected->ifp->ifindex);
916 if (rip_redistribute_check(ZEBRA_ROUTE_CONNECT))
917 rip_redistribute_add(ZEBRA_ROUTE_CONNECT,
918 RIP_ROUTE_REDISTRIBUTE,
919 &address, &nh, 0, 0, 0);
920 }
921 }
922 }
923
924 /* Update interface status. */
925 void rip_enable_apply(struct interface *ifp)
926 {
927 int ret;
928 struct rip_interface *ri = NULL;
929
930 /* Check interface. */
931 if (!if_is_operative(ifp))
932 return;
933
934 ri = ifp->info;
935
936 /* Check network configuration. */
937 ret = rip_enable_network_lookup_if(ifp);
938
939 /* If the interface is matched. */
940 if (ret > 0)
941 ri->enable_network = 1;
942 else
943 ri->enable_network = 0;
944
945 /* Check interface name configuration. */
946 ret = rip_enable_if_lookup(ifp->name);
947 if (ret >= 0)
948 ri->enable_interface = 1;
949 else
950 ri->enable_interface = 0;
951
952 /* any interface MUST have an IPv4 address */
953 if (!rip_if_ipv4_address_check(ifp)) {
954 ri->enable_network = 0;
955 ri->enable_interface = 0;
956 }
957
958 /* Update running status of the interface. */
959 if (ri->enable_network || ri->enable_interface) {
960 {
961 if (IS_RIP_DEBUG_EVENT)
962 zlog_debug("turn on %s", ifp->name);
963
964 /* Add interface wake up thread. */
965 thread_add_timer(master, rip_interface_wakeup, ifp, 1,
966 &ri->t_wakeup);
967 rip_connect_set(ifp, 1);
968 }
969 } else {
970 if (ri->running) {
971 /* Might as well clean up the route table as well
972 * rip_if_down sets to 0 ri->running, and displays "turn
973 *off %s"
974 **/
975 rip_if_down(ifp);
976
977 rip_connect_set(ifp, 0);
978 }
979 }
980 }
981
982 /* Apply network configuration to all interface. */
983 void rip_enable_apply_all()
984 {
985 struct vrf *vrf = vrf_lookup_by_id(VRF_DEFAULT);
986 struct interface *ifp;
987
988 /* Check each interface. */
989 FOR_ALL_INTERFACES (vrf, ifp)
990 rip_enable_apply(ifp);
991 }
992
993 int rip_neighbor_lookup(struct sockaddr_in *from)
994 {
995 struct prefix_ipv4 p;
996 struct route_node *node;
997
998 memset(&p, 0, sizeof(struct prefix_ipv4));
999 p.family = AF_INET;
1000 p.prefix = from->sin_addr;
1001 p.prefixlen = IPV4_MAX_BITLEN;
1002
1003 node = route_node_lookup(rip->neighbor, (struct prefix *)&p);
1004 if (node) {
1005 route_unlock_node(node);
1006 return 1;
1007 }
1008 return 0;
1009 }
1010
1011 /* Add new RIP neighbor to the neighbor tree. */
1012 static int rip_neighbor_add(struct prefix_ipv4 *p)
1013 {
1014 struct route_node *node;
1015
1016 node = route_node_get(rip->neighbor, (struct prefix *)p);
1017
1018 if (node->info)
1019 return -1;
1020
1021 node->info = rip->neighbor;
1022
1023 return 0;
1024 }
1025
1026 /* Delete RIP neighbor from the neighbor tree. */
1027 static int rip_neighbor_delete(struct prefix_ipv4 *p)
1028 {
1029 struct route_node *node;
1030
1031 /* Lock for look up. */
1032 node = route_node_lookup(rip->neighbor, (struct prefix *)p);
1033 if (!node)
1034 return -1;
1035
1036 node->info = NULL;
1037
1038 /* Unlock lookup lock. */
1039 route_unlock_node(node);
1040
1041 /* Unlock real neighbor information lock. */
1042 route_unlock_node(node);
1043
1044 return 0;
1045 }
1046
1047 /* Clear all network and neighbor configuration. */
1048 void rip_clean_network()
1049 {
1050 unsigned int i;
1051 char *str;
1052 struct route_node *rn;
1053
1054 /* rip_enable_network. */
1055 for (rn = route_top(rip_enable_network); rn; rn = route_next(rn))
1056 if (rn->info) {
1057 rn->info = NULL;
1058 route_unlock_node(rn);
1059 }
1060
1061 /* rip_enable_interface. */
1062 for (i = 0; i < vector_active(rip_enable_interface); i++)
1063 if ((str = vector_slot(rip_enable_interface, i)) != NULL) {
1064 XFREE(MTYPE_RIP_INTERFACE_STRING, str);
1065 vector_slot(rip_enable_interface, i) = NULL;
1066 }
1067 }
1068
1069 /* Utility function for looking up passive interface settings. */
1070 static int rip_passive_nondefault_lookup(const char *ifname)
1071 {
1072 unsigned int i;
1073 char *str;
1074
1075 for (i = 0; i < vector_active(Vrip_passive_nondefault); i++)
1076 if ((str = vector_slot(Vrip_passive_nondefault, i)) != NULL)
1077 if (strcmp(str, ifname) == 0)
1078 return i;
1079 return -1;
1080 }
1081
1082 void rip_passive_interface_apply(struct interface *ifp)
1083 {
1084 struct rip_interface *ri;
1085
1086 ri = ifp->info;
1087
1088 ri->passive = ((rip_passive_nondefault_lookup(ifp->name) < 0)
1089 ? passive_default
1090 : !passive_default);
1091
1092 if (IS_RIP_DEBUG_ZEBRA)
1093 zlog_debug("interface %s: passive = %d", ifp->name,
1094 ri->passive);
1095 }
1096
1097 static void rip_passive_interface_apply_all(void)
1098 {
1099 struct vrf *vrf = vrf_lookup_by_id(VRF_DEFAULT);
1100 struct interface *ifp;
1101
1102 FOR_ALL_INTERFACES (vrf, ifp)
1103 rip_passive_interface_apply(ifp);
1104 }
1105
1106 /* Passive interface. */
1107 static int rip_passive_nondefault_set(struct vty *vty, const char *ifname)
1108 {
1109 if (rip_passive_nondefault_lookup(ifname) >= 0)
1110 return CMD_WARNING_CONFIG_FAILED;
1111
1112 vector_set(Vrip_passive_nondefault,
1113 XSTRDUP(MTYPE_RIP_INTERFACE_STRING, ifname));
1114
1115 rip_passive_interface_apply_all();
1116
1117 return CMD_SUCCESS;
1118 }
1119
1120 static int rip_passive_nondefault_unset(struct vty *vty, const char *ifname)
1121 {
1122 int i;
1123 char *str;
1124
1125 i = rip_passive_nondefault_lookup(ifname);
1126 if (i < 0)
1127 return CMD_WARNING_CONFIG_FAILED;
1128
1129 str = vector_slot(Vrip_passive_nondefault, i);
1130 XFREE(MTYPE_RIP_INTERFACE_STRING, str);
1131 vector_unset(Vrip_passive_nondefault, i);
1132
1133 rip_passive_interface_apply_all();
1134
1135 return CMD_SUCCESS;
1136 }
1137
1138 /* Free all configured RIP passive-interface settings. */
1139 void rip_passive_nondefault_clean(void)
1140 {
1141 unsigned int i;
1142 char *str;
1143
1144 for (i = 0; i < vector_active(Vrip_passive_nondefault); i++)
1145 if ((str = vector_slot(Vrip_passive_nondefault, i)) != NULL) {
1146 XFREE(MTYPE_RIP_INTERFACE_STRING, str);
1147 vector_slot(Vrip_passive_nondefault, i) = NULL;
1148 }
1149 rip_passive_interface_apply_all();
1150 }
1151
1152 /* RIP enable network or interface configuration. */
1153 DEFUN (rip_network,
1154 rip_network_cmd,
1155 "network <A.B.C.D/M|WORD>",
1156 "Enable routing on an IP network\n"
1157 "IP prefix <network>/<length>, e.g., 35.0.0.0/8\n"
1158 "Interface name\n")
1159 {
1160 int idx_ipv4_word = 1;
1161 int ret;
1162 struct prefix_ipv4 p;
1163
1164 ret = str2prefix_ipv4(argv[idx_ipv4_word]->arg, &p);
1165
1166 if (ret)
1167 ret = rip_enable_network_add((struct prefix *)&p);
1168 else
1169 ret = rip_enable_if_add(argv[idx_ipv4_word]->arg);
1170
1171 if (ret < 0) {
1172 vty_out(vty, "There is a same network configuration %s\n",
1173 argv[idx_ipv4_word]->arg);
1174 return CMD_WARNING_CONFIG_FAILED;
1175 }
1176
1177 return CMD_SUCCESS;
1178 }
1179
1180 /* RIP enable network or interface configuration. */
1181 DEFUN (no_rip_network,
1182 no_rip_network_cmd,
1183 "no network <A.B.C.D/M|WORD>",
1184 NO_STR
1185 "Enable routing on an IP network\n"
1186 "IP prefix <network>/<length>, e.g., 35.0.0.0/8\n"
1187 "Interface name\n")
1188 {
1189 int idx_ipv4_word = 2;
1190 int ret;
1191 struct prefix_ipv4 p;
1192
1193 ret = str2prefix_ipv4(argv[idx_ipv4_word]->arg, &p);
1194
1195 if (ret)
1196 ret = rip_enable_network_delete((struct prefix *)&p);
1197 else
1198 ret = rip_enable_if_delete(argv[idx_ipv4_word]->arg);
1199
1200 if (ret < 0) {
1201 vty_out(vty, "Can't find network configuration %s\n",
1202 argv[idx_ipv4_word]->arg);
1203 return CMD_WARNING_CONFIG_FAILED;
1204 }
1205
1206 return CMD_SUCCESS;
1207 }
1208
1209 /* RIP neighbor configuration set. */
1210 DEFUN (rip_neighbor,
1211 rip_neighbor_cmd,
1212 "neighbor A.B.C.D",
1213 "Specify a neighbor router\n"
1214 "Neighbor address\n")
1215 {
1216 int idx_ipv4 = 1;
1217 int ret;
1218 struct prefix_ipv4 p;
1219
1220 ret = str2prefix_ipv4(argv[idx_ipv4]->arg, &p);
1221
1222 if (ret <= 0) {
1223 vty_out(vty, "Please specify address by A.B.C.D\n");
1224 return CMD_WARNING_CONFIG_FAILED;
1225 }
1226
1227 rip_neighbor_add(&p);
1228
1229 return CMD_SUCCESS;
1230 }
1231
1232 /* RIP neighbor configuration unset. */
1233 DEFUN (no_rip_neighbor,
1234 no_rip_neighbor_cmd,
1235 "no neighbor A.B.C.D",
1236 NO_STR
1237 "Specify a neighbor router\n"
1238 "Neighbor address\n")
1239 {
1240 int idx_ipv4 = 2;
1241 int ret;
1242 struct prefix_ipv4 p;
1243
1244 ret = str2prefix_ipv4(argv[idx_ipv4]->arg, &p);
1245
1246 if (ret <= 0) {
1247 vty_out(vty, "Please specify address by A.B.C.D\n");
1248 return CMD_WARNING_CONFIG_FAILED;
1249 }
1250
1251 rip_neighbor_delete(&p);
1252
1253 return CMD_SUCCESS;
1254 }
1255
1256 DEFUN (ip_rip_receive_version,
1257 ip_rip_receive_version_cmd,
1258 "ip rip receive version <(1-2)|none>",
1259 IP_STR
1260 "Routing Information Protocol\n"
1261 "Advertisement reception\n"
1262 "Version control\n"
1263 "RIP version\n"
1264 "None\n")
1265 {
1266 VTY_DECLVAR_CONTEXT(interface, ifp);
1267 int idx_type = 4;
1268 struct rip_interface *ri;
1269
1270 ri = ifp->info;
1271
1272 switch (argv[idx_type]->arg[0]) {
1273 case '1':
1274 ri->ri_receive = RI_RIP_VERSION_1;
1275 return CMD_SUCCESS;
1276 case '2':
1277 ri->ri_receive = RI_RIP_VERSION_2;
1278 return CMD_SUCCESS;
1279 case 'n':
1280 ri->ri_receive = RI_RIP_VERSION_NONE;
1281 return CMD_SUCCESS;
1282 default:
1283 break;
1284 }
1285
1286 return CMD_WARNING_CONFIG_FAILED;
1287 }
1288
1289 DEFUN (ip_rip_receive_version_1,
1290 ip_rip_receive_version_1_cmd,
1291 "ip rip receive version <1 2|2 1>",
1292 IP_STR
1293 "Routing Information Protocol\n"
1294 "Advertisement reception\n"
1295 "Version control\n"
1296 "RIP version 1\n"
1297 "RIP version 2\n"
1298 "RIP version 2\n"
1299 "RIP version 1\n")
1300 {
1301 VTY_DECLVAR_CONTEXT(interface, ifp);
1302 struct rip_interface *ri;
1303
1304 ri = ifp->info;
1305
1306 /* Version 1 and 2. */
1307 ri->ri_receive = RI_RIP_VERSION_1_AND_2;
1308 return CMD_SUCCESS;
1309 }
1310
1311 DEFUN (no_ip_rip_receive_version,
1312 no_ip_rip_receive_version_cmd,
1313 "no ip rip receive version [(1-2)]",
1314 NO_STR
1315 IP_STR
1316 "Routing Information Protocol\n"
1317 "Advertisement reception\n"
1318 "Version control\n"
1319 "RIP version\n")
1320 {
1321 VTY_DECLVAR_CONTEXT(interface, ifp);
1322 struct rip_interface *ri;
1323
1324 ri = ifp->info;
1325
1326 ri->ri_receive = RI_RIP_UNSPEC;
1327 return CMD_SUCCESS;
1328 }
1329
1330
1331 DEFUN (ip_rip_send_version,
1332 ip_rip_send_version_cmd,
1333 "ip rip send version (1-2)",
1334 IP_STR
1335 "Routing Information Protocol\n"
1336 "Advertisement transmission\n"
1337 "Version control\n"
1338 "RIP version\n")
1339 {
1340 VTY_DECLVAR_CONTEXT(interface, ifp);
1341 int idx_type = 4;
1342 struct rip_interface *ri;
1343
1344 ri = ifp->info;
1345
1346 /* Version 1. */
1347 if (atoi(argv[idx_type]->arg) == 1) {
1348 ri->ri_send = RI_RIP_VERSION_1;
1349 return CMD_SUCCESS;
1350 }
1351 if (atoi(argv[idx_type]->arg) == 2) {
1352 ri->ri_send = RI_RIP_VERSION_2;
1353 return CMD_SUCCESS;
1354 }
1355 return CMD_WARNING_CONFIG_FAILED;
1356 }
1357
1358 DEFUN (ip_rip_send_version_1,
1359 ip_rip_send_version_1_cmd,
1360 "ip rip send version <1 2|2 1>",
1361 IP_STR
1362 "Routing Information Protocol\n"
1363 "Advertisement transmission\n"
1364 "Version control\n"
1365 "RIP version 1\n"
1366 "RIP version 2\n"
1367 "RIP version 2\n"
1368 "RIP version 1\n")
1369 {
1370 VTY_DECLVAR_CONTEXT(interface, ifp);
1371 struct rip_interface *ri;
1372
1373 ri = ifp->info;
1374
1375 /* Version 1 and 2. */
1376 ri->ri_send = RI_RIP_VERSION_1_AND_2;
1377 return CMD_SUCCESS;
1378 }
1379
1380 DEFUN (no_ip_rip_send_version,
1381 no_ip_rip_send_version_cmd,
1382 "no ip rip send version [(1-2)]",
1383 NO_STR
1384 IP_STR
1385 "Routing Information Protocol\n"
1386 "Advertisement transmission\n"
1387 "Version control\n"
1388 "RIP version\n")
1389 {
1390 VTY_DECLVAR_CONTEXT(interface, ifp);
1391 struct rip_interface *ri;
1392
1393 ri = ifp->info;
1394
1395 ri->ri_send = RI_RIP_UNSPEC;
1396 return CMD_SUCCESS;
1397 }
1398
1399
1400 DEFUN (ip_rip_v2_broadcast,
1401 ip_rip_v2_broadcast_cmd,
1402 "ip rip v2-broadcast",
1403 IP_STR
1404 "Routing Information Protocol\n"
1405 "Send ip broadcast v2 update\n")
1406 {
1407 VTY_DECLVAR_CONTEXT(interface, ifp);
1408 struct rip_interface *ri;
1409
1410 ri = ifp->info;
1411
1412 ri->v2_broadcast = 1;
1413 return CMD_SUCCESS;
1414 }
1415
1416 DEFUN (no_ip_rip_v2_broadcast,
1417 no_ip_rip_v2_broadcast_cmd,
1418 "no ip rip v2-broadcast",
1419 NO_STR
1420 IP_STR
1421 "Routing Information Protocol\n"
1422 "Send ip broadcast v2 update\n")
1423 {
1424 VTY_DECLVAR_CONTEXT(interface, ifp);
1425 struct rip_interface *ri;
1426
1427 ri = ifp->info;
1428
1429 ri->v2_broadcast = 0;
1430 return CMD_SUCCESS;
1431 }
1432
1433 DEFUN (ip_rip_authentication_mode,
1434 ip_rip_authentication_mode_cmd,
1435 "ip rip authentication mode <md5|text> [auth-length <rfc|old-ripd>]",
1436 IP_STR
1437 "Routing Information Protocol\n"
1438 "Authentication control\n"
1439 "Authentication mode\n"
1440 "Keyed message digest\n"
1441 "Clear text authentication\n"
1442 "MD5 authentication data length\n"
1443 "RFC compatible\n"
1444 "Old ripd compatible\n")
1445 {
1446 VTY_DECLVAR_CONTEXT(interface, ifp);
1447 char *cryptmode = argv[4]->text;
1448 char *authlen = (argc > 5) ? argv[6]->text : NULL;
1449 struct rip_interface *ri;
1450 int auth_type;
1451
1452 ri = ifp->info;
1453
1454 if (strmatch("md5", cryptmode))
1455 auth_type = RIP_AUTH_MD5;
1456 else {
1457 assert(strmatch("text", cryptmode));
1458 auth_type = RIP_AUTH_SIMPLE_PASSWORD;
1459 }
1460
1461 ri->auth_type = auth_type;
1462
1463 if (argc > 5) {
1464 if (auth_type != RIP_AUTH_MD5) {
1465 vty_out(vty,
1466 "auth length argument only valid for md5\n");
1467 return CMD_WARNING_CONFIG_FAILED;
1468 }
1469 if (strmatch("rfc", authlen))
1470 ri->md5_auth_len = RIP_AUTH_MD5_SIZE;
1471 else {
1472 assert(strmatch("old-ripd", authlen));
1473 ri->md5_auth_len = RIP_AUTH_MD5_COMPAT_SIZE;
1474 }
1475 }
1476
1477 return CMD_SUCCESS;
1478 }
1479
1480 DEFUN (no_ip_rip_authentication_mode,
1481 no_ip_rip_authentication_mode_cmd,
1482 "no ip rip authentication mode [<md5|text> [auth-length <rfc|old-ripd>]]",
1483 NO_STR
1484 IP_STR
1485 "Routing Information Protocol\n"
1486 "Authentication control\n"
1487 "Authentication mode\n"
1488 "Keyed message digest\n"
1489 "Clear text authentication\n"
1490 "MD5 authentication data length\n"
1491 "RFC compatible\n"
1492 "Old ripd compatible\n")
1493 {
1494 VTY_DECLVAR_CONTEXT(interface, ifp);
1495 struct rip_interface *ri;
1496
1497 ri = ifp->info;
1498
1499 ri->auth_type = RIP_NO_AUTH;
1500 ri->md5_auth_len = RIP_AUTH_MD5_COMPAT_SIZE;
1501
1502 return CMD_SUCCESS;
1503 }
1504
1505 DEFUN (ip_rip_authentication_string,
1506 ip_rip_authentication_string_cmd,
1507 "ip rip authentication string LINE",
1508 IP_STR
1509 "Routing Information Protocol\n"
1510 "Authentication control\n"
1511 "Authentication string\n"
1512 "Authentication string\n")
1513 {
1514 VTY_DECLVAR_CONTEXT(interface, ifp);
1515 int idx_line = 4;
1516 struct rip_interface *ri;
1517
1518 ri = ifp->info;
1519
1520 if (strlen(argv[idx_line]->arg) > 16) {
1521 vty_out(vty,
1522 "%% RIPv2 authentication string must be shorter than 16\n");
1523 return CMD_WARNING_CONFIG_FAILED;
1524 }
1525
1526 if (ri->key_chain) {
1527 vty_out(vty, "%% key-chain configuration exists\n");
1528 return CMD_WARNING_CONFIG_FAILED;
1529 }
1530
1531 if (ri->auth_str)
1532 XFREE(MTYPE_RIP_INTERFACE_STRING, ri->auth_str);
1533
1534 ri->auth_str = XSTRDUP(MTYPE_RIP_INTERFACE_STRING, argv[idx_line]->arg);
1535
1536 return CMD_SUCCESS;
1537 }
1538
1539 DEFUN (no_ip_rip_authentication_string,
1540 no_ip_rip_authentication_string_cmd,
1541 "no ip rip authentication string [LINE]",
1542 NO_STR
1543 IP_STR
1544 "Routing Information Protocol\n"
1545 "Authentication control\n"
1546 "Authentication string\n"
1547 "Authentication string\n")
1548 {
1549 VTY_DECLVAR_CONTEXT(interface, ifp);
1550 struct rip_interface *ri;
1551
1552 ri = ifp->info;
1553
1554 if (ri->auth_str)
1555 XFREE(MTYPE_RIP_INTERFACE_STRING, ri->auth_str);
1556
1557 return CMD_SUCCESS;
1558 }
1559
1560
1561 DEFUN (ip_rip_authentication_key_chain,
1562 ip_rip_authentication_key_chain_cmd,
1563 "ip rip authentication key-chain LINE",
1564 IP_STR
1565 "Routing Information Protocol\n"
1566 "Authentication control\n"
1567 "Authentication key-chain\n"
1568 "name of key-chain\n")
1569 {
1570 VTY_DECLVAR_CONTEXT(interface, ifp);
1571 int idx_line = 4;
1572 struct rip_interface *ri;
1573
1574 ri = ifp->info;
1575
1576 if (ri->auth_str) {
1577 vty_out(vty, "%% authentication string configuration exists\n");
1578 return CMD_WARNING_CONFIG_FAILED;
1579 }
1580
1581 if (ri->key_chain)
1582 XFREE(MTYPE_RIP_INTERFACE_STRING, ri->key_chain);
1583
1584 ri->key_chain =
1585 XSTRDUP(MTYPE_RIP_INTERFACE_STRING, argv[idx_line]->arg);
1586
1587 return CMD_SUCCESS;
1588 }
1589
1590 DEFUN (no_ip_rip_authentication_key_chain,
1591 no_ip_rip_authentication_key_chain_cmd,
1592 "no ip rip authentication key-chain [LINE]",
1593 NO_STR
1594 IP_STR
1595 "Routing Information Protocol\n"
1596 "Authentication control\n"
1597 "Authentication key-chain\n"
1598 "name of key-chain\n")
1599 {
1600 VTY_DECLVAR_CONTEXT(interface, ifp);
1601 struct rip_interface *ri;
1602
1603 ri = ifp->info;
1604
1605 if (ri->key_chain)
1606 XFREE(MTYPE_RIP_INTERFACE_STRING, ri->key_chain);
1607
1608 return CMD_SUCCESS;
1609 }
1610
1611
1612 /* CHANGED: ip rip split-horizon
1613 Cisco and Zebra's command is
1614 ip split-horizon
1615 */
1616 DEFUN (ip_rip_split_horizon,
1617 ip_rip_split_horizon_cmd,
1618 "ip rip split-horizon",
1619 IP_STR
1620 "Routing Information Protocol\n"
1621 "Perform split horizon\n")
1622 {
1623 VTY_DECLVAR_CONTEXT(interface, ifp);
1624 struct rip_interface *ri;
1625
1626 ri = ifp->info;
1627
1628 ri->split_horizon = RIP_SPLIT_HORIZON;
1629 return CMD_SUCCESS;
1630 }
1631
1632 DEFUN (ip_rip_split_horizon_poisoned_reverse,
1633 ip_rip_split_horizon_poisoned_reverse_cmd,
1634 "ip rip split-horizon poisoned-reverse",
1635 IP_STR
1636 "Routing Information Protocol\n"
1637 "Perform split horizon\n"
1638 "With poisoned-reverse\n")
1639 {
1640 VTY_DECLVAR_CONTEXT(interface, ifp);
1641 struct rip_interface *ri;
1642
1643 ri = ifp->info;
1644
1645 ri->split_horizon = RIP_SPLIT_HORIZON_POISONED_REVERSE;
1646 return CMD_SUCCESS;
1647 }
1648
1649 /* CHANGED: no ip rip split-horizon
1650 Cisco and Zebra's command is
1651 no ip split-horizon
1652 */
1653 DEFUN (no_ip_rip_split_horizon,
1654 no_ip_rip_split_horizon_cmd,
1655 "no ip rip split-horizon",
1656 NO_STR
1657 IP_STR
1658 "Routing Information Protocol\n"
1659 "Perform split horizon\n")
1660 {
1661 VTY_DECLVAR_CONTEXT(interface, ifp);
1662 struct rip_interface *ri;
1663
1664 ri = ifp->info;
1665
1666 ri->split_horizon = RIP_NO_SPLIT_HORIZON;
1667 return CMD_SUCCESS;
1668 }
1669
1670 DEFUN (no_ip_rip_split_horizon_poisoned_reverse,
1671 no_ip_rip_split_horizon_poisoned_reverse_cmd,
1672 "no ip rip split-horizon poisoned-reverse",
1673 NO_STR
1674 IP_STR
1675 "Routing Information Protocol\n"
1676 "Perform split horizon\n"
1677 "With poisoned-reverse\n")
1678 {
1679 VTY_DECLVAR_CONTEXT(interface, ifp);
1680 struct rip_interface *ri;
1681
1682 ri = ifp->info;
1683
1684 switch (ri->split_horizon) {
1685 case RIP_SPLIT_HORIZON_POISONED_REVERSE:
1686 ri->split_horizon = RIP_SPLIT_HORIZON;
1687 default:
1688 break;
1689 }
1690
1691 return CMD_SUCCESS;
1692 }
1693
1694 DEFUN (rip_passive_interface,
1695 rip_passive_interface_cmd,
1696 "passive-interface <IFNAME|default>",
1697 "Suppress routing updates on an interface\n"
1698 "Interface name\n"
1699 "default for all interfaces\n")
1700 {
1701 if (argv[1]->type == WORD_TKN) { // user passed 'default'
1702 passive_default = 1;
1703 rip_passive_nondefault_clean();
1704 return CMD_SUCCESS;
1705 }
1706 if (passive_default)
1707 return rip_passive_nondefault_unset(vty, argv[1]->arg);
1708 else
1709 return rip_passive_nondefault_set(vty, argv[1]->arg);
1710 }
1711
1712 DEFUN (no_rip_passive_interface,
1713 no_rip_passive_interface_cmd,
1714 "no passive-interface <IFNAME|default>",
1715 NO_STR
1716 "Suppress routing updates on an interface\n"
1717 "Interface name\n"
1718 "default for all interfaces\n")
1719 {
1720 if (argv[2]->type == WORD_TKN) {
1721 passive_default = 0;
1722 rip_passive_nondefault_clean();
1723 return CMD_SUCCESS;
1724 }
1725 if (passive_default)
1726 return rip_passive_nondefault_set(vty, argv[2]->arg);
1727 else
1728 return rip_passive_nondefault_unset(vty, argv[2]->arg);
1729 }
1730
1731 /* Write rip configuration of each interface. */
1732 static int rip_interface_config_write(struct vty *vty)
1733 {
1734 struct vrf *vrf = vrf_lookup_by_id(VRF_DEFAULT);
1735 struct interface *ifp;
1736
1737 FOR_ALL_INTERFACES (vrf, ifp) {
1738 struct rip_interface *ri;
1739
1740 ri = ifp->info;
1741
1742 /* Do not display the interface if there is no
1743 * configuration about it.
1744 **/
1745 if ((!ifp->desc)
1746 && (ri->split_horizon == ri->split_horizon_default)
1747 && (ri->ri_send == RI_RIP_UNSPEC)
1748 && (ri->ri_receive == RI_RIP_UNSPEC)
1749 && (ri->auth_type != RIP_AUTH_MD5) && (!ri->v2_broadcast)
1750 && (ri->md5_auth_len != RIP_AUTH_MD5_SIZE)
1751 && (!ri->auth_str) && (!ri->key_chain))
1752 continue;
1753
1754 vty_frame(vty, "interface %s\n", ifp->name);
1755
1756 if (ifp->desc)
1757 vty_out(vty, " description %s\n", ifp->desc);
1758
1759 /* Split horizon. */
1760 if (ri->split_horizon != ri->split_horizon_default) {
1761 switch (ri->split_horizon) {
1762 case RIP_SPLIT_HORIZON:
1763 vty_out(vty, " ip rip split-horizon\n");
1764 break;
1765 case RIP_SPLIT_HORIZON_POISONED_REVERSE:
1766 vty_out(vty,
1767 " ip rip split-horizon poisoned-reverse\n");
1768 break;
1769 case RIP_NO_SPLIT_HORIZON:
1770 default:
1771 vty_out(vty, " no ip rip split-horizon\n");
1772 break;
1773 }
1774 }
1775
1776 /* RIP version setting. */
1777 if (ri->ri_send != RI_RIP_UNSPEC)
1778 vty_out(vty, " ip rip send version %s\n",
1779 lookup_msg(ri_version_msg, ri->ri_send, NULL));
1780
1781 if (ri->ri_receive != RI_RIP_UNSPEC)
1782 vty_out(vty, " ip rip receive version %s \n",
1783 lookup_msg(ri_version_msg, ri->ri_receive,
1784 NULL));
1785
1786 if (ri->v2_broadcast)
1787 vty_out(vty, " ip rip v2-broadcast\n");
1788
1789 /* RIP authentication. */
1790 if (ri->auth_type == RIP_AUTH_SIMPLE_PASSWORD)
1791 vty_out(vty, " ip rip authentication mode text\n");
1792
1793 if (ri->auth_type == RIP_AUTH_MD5) {
1794 vty_out(vty, " ip rip authentication mode md5");
1795 if (ri->md5_auth_len == RIP_AUTH_MD5_COMPAT_SIZE)
1796 vty_out(vty, " auth-length old-ripd");
1797 else
1798 vty_out(vty, " auth-length rfc");
1799 vty_out(vty, "\n");
1800 }
1801
1802 if (ri->auth_str)
1803 vty_out(vty, " ip rip authentication string %s\n",
1804 ri->auth_str);
1805
1806 if (ri->key_chain)
1807 vty_out(vty, " ip rip authentication key-chain %s\n",
1808 ri->key_chain);
1809
1810 vty_endframe(vty, "!\n");
1811 }
1812 return 0;
1813 }
1814
1815 int config_write_rip_network(struct vty *vty, int config_mode)
1816 {
1817 unsigned int i;
1818 char *ifname;
1819 struct route_node *node;
1820
1821 /* Network type RIP enable interface statement. */
1822 for (node = route_top(rip_enable_network); node;
1823 node = route_next(node))
1824 if (node->info)
1825 vty_out(vty, "%s%s/%d\n",
1826 config_mode ? " network " : " ",
1827 inet_ntoa(node->p.u.prefix4),
1828 node->p.prefixlen);
1829
1830 /* Interface name RIP enable statement. */
1831 for (i = 0; i < vector_active(rip_enable_interface); i++)
1832 if ((ifname = vector_slot(rip_enable_interface, i)) != NULL)
1833 vty_out(vty, "%s%s\n",
1834 config_mode ? " network " : " ", ifname);
1835
1836 /* RIP neighbors listing. */
1837 for (node = route_top(rip->neighbor); node; node = route_next(node))
1838 if (node->info)
1839 vty_out(vty, "%s%s\n",
1840 config_mode ? " neighbor " : " ",
1841 inet_ntoa(node->p.u.prefix4));
1842
1843 /* RIP passive interface listing. */
1844 if (config_mode) {
1845 if (passive_default)
1846 vty_out(vty, " passive-interface default\n");
1847 for (i = 0; i < vector_active(Vrip_passive_nondefault); i++)
1848 if ((ifname = vector_slot(Vrip_passive_nondefault, i))
1849 != NULL)
1850 vty_out(vty, " %spassive-interface %s\n",
1851 (passive_default ? "no " : ""), ifname);
1852 }
1853
1854 return 0;
1855 }
1856
1857 static struct cmd_node interface_node = {
1858 INTERFACE_NODE, "%s(config-if)# ", 1,
1859 };
1860
1861 /* Called when interface structure allocated. */
1862 static int rip_interface_new_hook(struct interface *ifp)
1863 {
1864 ifp->info = rip_interface_new();
1865 return 0;
1866 }
1867
1868 /* Called when interface structure deleted. */
1869 static int rip_interface_delete_hook(struct interface *ifp)
1870 {
1871 XFREE(MTYPE_RIP_INTERFACE, ifp->info);
1872 ifp->info = NULL;
1873 return 0;
1874 }
1875
1876 /* Allocate and initialize interface vector. */
1877 void rip_if_init(void)
1878 {
1879 /* Default initial size of interface vector. */
1880 hook_register_prio(if_add, 0, rip_interface_new_hook);
1881 hook_register_prio(if_del, 0, rip_interface_delete_hook);
1882
1883 /* RIP network init. */
1884 rip_enable_interface = vector_init(1);
1885 rip_enable_network = route_table_init();
1886
1887 /* RIP passive interface. */
1888 Vrip_passive_nondefault = vector_init(1);
1889
1890 /* Install interface node. */
1891 install_node(&interface_node, rip_interface_config_write);
1892 if_cmd_init();
1893
1894 /* Install commands. */
1895 install_element(RIP_NODE, &rip_network_cmd);
1896 install_element(RIP_NODE, &no_rip_network_cmd);
1897 install_element(RIP_NODE, &rip_neighbor_cmd);
1898 install_element(RIP_NODE, &no_rip_neighbor_cmd);
1899
1900 install_element(RIP_NODE, &rip_passive_interface_cmd);
1901 install_element(RIP_NODE, &no_rip_passive_interface_cmd);
1902
1903 install_element(INTERFACE_NODE, &ip_rip_send_version_cmd);
1904 install_element(INTERFACE_NODE, &ip_rip_send_version_1_cmd);
1905 install_element(INTERFACE_NODE, &no_ip_rip_send_version_cmd);
1906
1907 install_element(INTERFACE_NODE, &ip_rip_receive_version_cmd);
1908 install_element(INTERFACE_NODE, &ip_rip_receive_version_1_cmd);
1909 install_element(INTERFACE_NODE, &no_ip_rip_receive_version_cmd);
1910
1911 install_element(INTERFACE_NODE, &ip_rip_v2_broadcast_cmd);
1912 install_element(INTERFACE_NODE, &no_ip_rip_v2_broadcast_cmd);
1913
1914 install_element(INTERFACE_NODE, &ip_rip_authentication_mode_cmd);
1915 install_element(INTERFACE_NODE, &no_ip_rip_authentication_mode_cmd);
1916
1917 install_element(INTERFACE_NODE, &ip_rip_authentication_key_chain_cmd);
1918 install_element(INTERFACE_NODE,
1919 &no_ip_rip_authentication_key_chain_cmd);
1920
1921 install_element(INTERFACE_NODE, &ip_rip_authentication_string_cmd);
1922 install_element(INTERFACE_NODE, &no_ip_rip_authentication_string_cmd);
1923
1924 install_element(INTERFACE_NODE, &ip_rip_split_horizon_cmd);
1925 install_element(INTERFACE_NODE,
1926 &ip_rip_split_horizon_poisoned_reverse_cmd);
1927 install_element(INTERFACE_NODE, &no_ip_rip_split_horizon_cmd);
1928 install_element(INTERFACE_NODE,
1929 &no_ip_rip_split_horizon_poisoned_reverse_cmd);
1930 }