From 3f5682c88d6f4f0b85539a8776c9e869f1cbd4fa Mon Sep 17 00:00:00 2001 From: Donald Sharp Date: Wed, 15 Nov 2017 11:19:06 -0500 Subject: [PATCH] ripd: Allow rip_redistribute_add to know the nexthop type Allow rip_redistribute_add to receive and properly store the nexthop type passed up from zebra. Additionally display the different nexthop types appropriately. Signed-off-by: Donald Sharp --- ripd/rip_interface.c | 18 +++++++++++++---- ripd/rip_zebra.c | 23 +++++++++++++--------- ripd/ripd.c | 46 +++++++++++++++++++++++++++----------------- ripd/ripd.h | 8 +++++--- 4 files changed, 61 insertions(+), 34 deletions(-) diff --git a/ripd/rip_interface.c b/ripd/rip_interface.c index 184f2f2b81..d20954037d 100644 --- a/ripd/rip_interface.c +++ b/ripd/rip_interface.c @@ -591,6 +591,7 @@ void rip_if_down_all() static void rip_apply_address_add(struct connected *ifc) { struct prefix_ipv4 address; + struct nexthop nh; struct prefix *p; if (!rip) @@ -602,18 +603,22 @@ static void rip_apply_address_add(struct connected *ifc) p = ifc->address; memset(&address, 0, sizeof(address)); + memset(&nh, 0, sizeof(nh)); + address.family = p->family; address.prefix = p->u.prefix4; address.prefixlen = p->prefixlen; apply_mask_ipv4(&address); + nh.ifindex = ifc->ifp->ifindex; + nh.type = NEXTHOP_TYPE_IFINDEX; + /* Check if this interface is RIP enabled or not or Check if this address's prefix is RIP enabled */ if ((rip_enable_if_lookup(ifc->ifp->name) >= 0) || (rip_enable_network_lookup2(ifc) >= 0)) rip_redistribute_add(ZEBRA_ROUTE_CONNECT, RIP_ROUTE_INTERFACE, - &address, ifc->ifp->ifindex, NULL, 0, 0, - 0); + &address, &nh, 0, 0, 0); } int rip_interface_address_add(int command, struct zclient *zclient, @@ -879,6 +884,9 @@ static void rip_connect_set(struct interface *ifp, int set) struct listnode *node, *nnode; struct connected *connected; struct prefix_ipv4 address; + struct nexthop nh; + + memset(&nh, 0, sizeof(nh)); for (ALL_LIST_ELEMENTS(ifp->connected, node, nnode, connected)) { struct prefix *p; @@ -892,6 +900,8 @@ static void rip_connect_set(struct interface *ifp, int set) address.prefixlen = p->prefixlen; apply_mask_ipv4(&address); + nh.ifindex = connected->ifp->ifindex; + nh.type = NEXTHOP_TYPE_IFINDEX; if (set) { /* Check once more wether this prefix is within a * "network IF_OR_PREF" one */ @@ -900,7 +910,7 @@ static void rip_connect_set(struct interface *ifp, int set) rip_redistribute_add( ZEBRA_ROUTE_CONNECT, RIP_ROUTE_INTERFACE, &address, - connected->ifp->ifindex, NULL, 0, 0, 0); + &nh, 0, 0, 0); } else { rip_redistribute_delete(ZEBRA_ROUTE_CONNECT, RIP_ROUTE_INTERFACE, &address, @@ -909,7 +919,7 @@ static void rip_connect_set(struct interface *ifp, int set) rip_redistribute_add( ZEBRA_ROUTE_CONNECT, RIP_ROUTE_REDISTRIBUTE, &address, - connected->ifp->ifindex, NULL, 0, 0, 0); + &nh, 0, 0, 0); } } } diff --git a/ripd/rip_zebra.c b/ripd/rip_zebra.c index bd46f7e3e4..e479e2474d 100644 --- a/ripd/rip_zebra.c +++ b/ripd/rip_zebra.c @@ -121,8 +121,7 @@ static int rip_zebra_read_route(int command, struct zclient *zclient, zebra_size_t length, vrf_id_t vrf_id) { struct zapi_route api; - struct in_addr nexthop; - unsigned long ifindex; + struct nexthop nh; if (!rip) return 0; @@ -130,19 +129,21 @@ static int rip_zebra_read_route(int command, struct zclient *zclient, if (zapi_route_decode(zclient->ibuf, &api) < 0) return -1; - nexthop = api.nexthops[0].gate.ipv4; - ifindex = api.nexthops[0].ifindex; + memset(&nh, 0, sizeof(nh)); + nh.type = api.nexthops[0].type; + nh.gate.ipv4 = api.nexthops[0].gate.ipv4; + nh.ifindex = api.nexthops[0].ifindex; /* Then fetch IPv4 prefixes. */ if (command == ZEBRA_REDISTRIBUTE_ROUTE_ADD) rip_redistribute_add(api.type, RIP_ROUTE_REDISTRIBUTE, - (struct prefix_ipv4 *)&api.prefix, ifindex, - &nexthop, api.metric, api.distance, + (struct prefix_ipv4 *)&api.prefix, &nh, + api.metric, api.distance, api.tag); else if (command == ZEBRA_REDISTRIBUTE_ROUTE_DEL) rip_redistribute_delete(api.type, RIP_ROUTE_REDISTRIBUTE, (struct prefix_ipv4 *)&api.prefix, - ifindex); + nh.ifindex); return 0; } @@ -501,15 +502,19 @@ DEFUN (rip_default_information_originate, "Distribute a default route\n") { struct prefix_ipv4 p; + struct nexthop nh; if (!rip->default_information) { memset(&p, 0, sizeof(struct prefix_ipv4)); + memset(&nh, 0, sizeof(nh)); + p.family = AF_INET; + nh.type = NEXTHOP_TYPE_IPV4; rip->default_information = 1; - rip_redistribute_add(ZEBRA_ROUTE_RIP, RIP_ROUTE_DEFAULT, &p, 0, - NULL, 0, 0, 0); + rip_redistribute_add(ZEBRA_ROUTE_RIP, RIP_ROUTE_DEFAULT, &p, + &nh, 0, 0, 0); } return CMD_SUCCESS; diff --git a/ripd/ripd.c b/ripd/ripd.c index 0415c5ba9e..4c1a12b0d5 100644 --- a/ripd/ripd.c +++ b/ripd/ripd.c @@ -1463,7 +1463,7 @@ static int rip_send_packet(u_char *buf, int size, struct sockaddr_in *to, /* Add redistributed route to RIP table. */ void rip_redistribute_add(int type, int sub_type, struct prefix_ipv4 *p, - ifindex_t ifindex, struct in_addr *nexthop, + struct nexthop *nh, unsigned int metric, unsigned char distance, route_tag_t tag) { @@ -1482,15 +1482,13 @@ void rip_redistribute_add(int type, int sub_type, struct prefix_ipv4 *p, memset(&newinfo, 0, sizeof(struct rip_info)); newinfo.type = type; newinfo.sub_type = sub_type; - newinfo.nh.ifindex = ifindex; newinfo.metric = 1; newinfo.external_metric = metric; newinfo.distance = distance; if (tag <= UINT16_MAX) /* RIP only supports 16 bit tags */ newinfo.tag = tag; newinfo.rp = rp; - if (nexthop) - newinfo.nh.gate.ipv4 = *nexthop; + newinfo.nh = *nh; if ((list = rp->info) != NULL && listcount(list) != 0) { rinfo = listgetdata(listhead(list)); @@ -1520,17 +1518,9 @@ void rip_redistribute_add(int type, int sub_type, struct prefix_ipv4 *p, rinfo = rip_ecmp_add(&newinfo); if (IS_RIP_DEBUG_EVENT) { - if (!nexthop) - zlog_debug( - "Redistribute new prefix %s/%d on the interface %s", - inet_ntoa(p->prefix), p->prefixlen, - ifindex2ifname(ifindex, VRF_DEFAULT)); - else - zlog_debug( - "Redistribute new prefix %s/%d with nexthop %s on the interface %s", - inet_ntoa(p->prefix), p->prefixlen, - inet_ntoa(rinfo->nh.gate.ipv4), - ifindex2ifname(ifindex, VRF_DEFAULT)); + zlog_debug( + "Redistribute new prefix %s/%d", + inet_ntoa(p->prefix), p->prefixlen); } rip_event(RIP_TRIGGERED_UPDATE, 0); @@ -2864,9 +2854,13 @@ DEFUN (rip_route, { int idx_ipv4_prefixlen = 1; int ret; + struct nexthop nh; struct prefix_ipv4 p; struct route_node *node; + memset(&nh, 0, sizeof(nh)); + nh.type = NEXTHOP_TYPE_IPV4; + ret = str2prefix_ipv4(argv[idx_ipv4_prefixlen]->arg, &p); if (ret < 0) { vty_out(vty, "Malformed address\n"); @@ -2885,7 +2879,7 @@ DEFUN (rip_route, node->info = (void *)1; - rip_redistribute_add(ZEBRA_ROUTE_RIP, RIP_ROUTE_STATIC, &p, 0, NULL, 0, + rip_redistribute_add(ZEBRA_ROUTE_RIP, RIP_ROUTE_STATIC, &p, &nh, 0, 0, 0); return CMD_SUCCESS; @@ -3457,14 +3451,30 @@ DEFUN (show_ip_rip, if (len > 0) vty_out(vty, "%*s", len, " "); - if (rinfo->nh.gate.ipv4.s_addr) + switch(rinfo->nh.type) { + case NEXTHOP_TYPE_IPV4: + case NEXTHOP_TYPE_IPV4_IFINDEX: vty_out(vty, "%-20s %2d ", inet_ntoa(rinfo->nh.gate.ipv4), rinfo->metric); - else + break; + case NEXTHOP_TYPE_IFINDEX: vty_out(vty, "0.0.0.0 %2d ", rinfo->metric); + break; + case NEXTHOP_TYPE_BLACKHOLE: + vty_out(vty, + "blackhole %2d ", + rinfo->metric); + break; + case NEXTHOP_TYPE_IPV6: + case NEXTHOP_TYPE_IPV6_IFINDEX: + vty_out(vty, + "V6 Address Hidden %2d ", + rinfo->metric); + break; + } /* Route which exist in kernel routing table. */ if ((rinfo->type == ZEBRA_ROUTE_RIP) diff --git a/ripd/ripd.h b/ripd/ripd.h index a66f506f48..9a9c081bf9 100644 --- a/ripd/ripd.h +++ b/ripd/ripd.h @@ -385,9 +385,11 @@ extern int rip_request_send(struct sockaddr_in *, struct interface *, u_char, extern int rip_neighbor_lookup(struct sockaddr_in *); extern int rip_redistribute_check(int); -extern void rip_redistribute_add(int, int, struct prefix_ipv4 *, ifindex_t, - struct in_addr *, unsigned int, unsigned char, - route_tag_t); +extern void rip_redistribute_add(int type, int sub_type, + struct prefix_ipv4 *p, + struct nexthop *nh, + unsigned int metric, unsigned char distance, + route_tag_t tag); extern void rip_redistribute_delete(int, int, struct prefix_ipv4 *, ifindex_t); extern void rip_redistribute_withdraw(int); extern void rip_zebra_ipv4_add(struct route_node *); -- 2.39.5