diff options
author | Donald Sharp <sharpd@cumulusnetworks.com> | 2017-12-13 16:32:54 +0100 |
---|---|---|
committer | Donald Sharp <sharpd@cumulusnetworks.com> | 2017-12-14 16:43:53 +0100 |
commit | 070b4959fa6dcc6eb963f902a859f59ca9b55b83 (patch) | |
tree | 56cc70713833ae4076306fffa6356866ac6baaf5 /zebra/interface.c | |
parent | Merge pull request #1546 from pguibert6WIND/issue__1537 (diff) | |
download | frr-070b4959fa6dcc6eb963f902a859f59ca9b55b83.tar.xz frr-070b4959fa6dcc6eb963f902a859f59ca9b55b83.zip |
zebra: Remove possible NULL dereference in if_delete_connected
It is technically possible to attempt to use a NULL pointer.
Remove this from happening.
Additionally cleanup code indentation a small bit.
Signed-off-by: Donald Sharp <sharpd@cumulusnetworks.com>
Diffstat (limited to 'zebra/interface.c')
-rw-r--r-- | zebra/interface.c | 71 |
1 files changed, 36 insertions, 35 deletions
diff --git a/zebra/interface.c b/zebra/interface.c index dd1050ee7..18588ee52 100644 --- a/zebra/interface.c +++ b/zebra/interface.c @@ -561,33 +561,35 @@ static void if_delete_connected(struct interface *ifp) struct prefix cp; struct route_node *rn; struct zebra_if *zebra_if; + struct listnode *node; + struct listnode *last = NULL; zebra_if = ifp->info; - if (ifp->connected) { - struct listnode *node; - struct listnode *last = NULL; + if (!ifp->connected) + return; - while ((node = (last ? last->next - : listhead(ifp->connected)))) { - ifc = listgetdata(node); + while ((node = (last ? last->next + : listhead(ifp->connected)))) { + ifc = listgetdata(node); - cp = *CONNECTED_PREFIX(ifc); - apply_mask(&cp); + cp = *CONNECTED_PREFIX(ifc); + apply_mask(&cp); - if (cp.family == AF_INET - && (rn = route_node_lookup(zebra_if->ipv4_subnets, - &cp))) { - struct listnode *anode; - struct listnode *next; - struct listnode *first; - struct list *addr_list; + if (cp.family == AF_INET + && (rn = route_node_lookup(zebra_if->ipv4_subnets, + &cp))) { + struct listnode *anode; + struct listnode *next; + struct listnode *first; + struct list *addr_list; - route_unlock_node(rn); - addr_list = (struct list *)rn->info; + route_unlock_node(rn); + addr_list = (struct list *)rn->info; - /* Remove addresses, secondaries first. */ - first = listhead(addr_list); + /* Remove addresses, secondaries first. */ + first = listhead(addr_list); + if (first) for (anode = first->next; anode || first; anode = next) { if (!anode) { @@ -626,27 +628,26 @@ static void if_delete_connected(struct interface *ifp) last = node; } - /* Free chain list and respective route node. */ - list_delete_and_null(&addr_list); - rn->info = NULL; - route_unlock_node(rn); - } else if (cp.family == AF_INET6) { - connected_down(ifp, ifc); + /* Free chain list and respective route node. */ + list_delete_and_null(&addr_list); + rn->info = NULL; + route_unlock_node(rn); + } else if (cp.family == AF_INET6) { + connected_down(ifp, ifc); - zebra_interface_address_delete_update(ifp, ifc); + zebra_interface_address_delete_update(ifp, ifc); - UNSET_FLAG(ifc->conf, ZEBRA_IFC_REAL); - UNSET_FLAG(ifc->conf, ZEBRA_IFC_QUEUED); + UNSET_FLAG(ifc->conf, ZEBRA_IFC_REAL); + UNSET_FLAG(ifc->conf, ZEBRA_IFC_QUEUED); - if (CHECK_FLAG(ifc->conf, ZEBRA_IFC_CONFIGURED)) - last = node; - else { - listnode_delete(ifp->connected, ifc); - connected_free(ifc); - } - } else { + if (CHECK_FLAG(ifc->conf, ZEBRA_IFC_CONFIGURED)) last = node; + else { + listnode_delete(ifp->connected, ifc); + connected_free(ifc); } + } else { + last = node; } } } |