From 44f2b1782e3d7afe7ede3779e7b9896cbd6c26c7 Mon Sep 17 00:00:00 2001 From: Quentin Armitage Date: Fri, 15 Dec 2017 21:14:24 +0000 Subject: [PATCH] Fix removing left-over addresses if keepalived aborts Issue #718 reported that if keepalived terminates abnormally when it has vrrp instances in master state, it doesn't remove the left-over VIPs and eVIPs when it restarts. This is despite commit f4c10426c saying that it resolved this problem. It turns out that commit f4c10426c did resolve the problem for VIPs or eVIPs, although it did resolve the issue for iptables and ipset configuration. This commit now really resolves the problem, and residual VIPs and eVIPs are removed at startup. Signed-off-by: Quentin Armitage --- keepalived/include/vrrp_ipaddress.h | 2 +- keepalived/vrrp/vrrp.c | 16 ++++++++-------- keepalived/vrrp/vrrp_daemon.c | 6 +++--- keepalived/vrrp/vrrp_ipaddress.c | 6 +++--- 4 files changed, 15 insertions(+), 15 deletions(-) diff --git a/keepalived/include/vrrp_ipaddress.h b/keepalived/include/vrrp_ipaddress.h index 900dfd7f..4d613652 100644 --- a/keepalived/include/vrrp_ipaddress.h +++ b/keepalived/include/vrrp_ipaddress.h @@ -93,7 +93,7 @@ struct ipt_handle; // AAGH - TODO /* prototypes */ extern char *ipaddresstos(char *, ip_address_t *); extern int netlink_ipaddress(ip_address_t *, int); -extern bool netlink_iplist(list, int); +extern bool netlink_iplist(list, int, bool); extern void handle_iptable_rule_to_iplist(struct ipt_handle *, list, int, bool force); extern void free_ipaddress(void *); extern void dump_ipaddress(void *); diff --git a/keepalived/vrrp/vrrp.c b/keepalived/vrrp/vrrp.c index 3d2bfe41..d58c3690 100644 --- a/keepalived/vrrp/vrrp.c +++ b/keepalived/vrrp/vrrp.c @@ -74,13 +74,13 @@ /* add/remove Virtual IP addresses */ static bool -vrrp_handle_ipaddress(vrrp_t * vrrp, int cmd, int type) +vrrp_handle_ipaddress(vrrp_t * vrrp, int cmd, int type, bool force) { if (__test_bit(LOG_DETAIL_BIT, &debug)) log_message(LOG_INFO, "VRRP_Instance(%s) %s protocol %s", vrrp->iname, (cmd == IPADDRESS_ADD) ? "setting" : "removing", (type == VRRP_VIP_TYPE) ? "VIPs." : "E-VIPs."); - return netlink_iplist((type == VRRP_VIP_TYPE) ? vrrp->vip : vrrp->evip, cmd); + return netlink_iplist((type == VRRP_VIP_TYPE) ? vrrp->vip : vrrp->evip, cmd, force); } #ifdef _HAVE_FIB_ROUTING_ @@ -1283,9 +1283,9 @@ vrrp_state_become_master(vrrp_t * vrrp) /* add the ip addresses */ vrrp_handle_accept_mode(vrrp, IPADDRESS_ADD, false); if (!LIST_ISEMPTY(vrrp->vip)) - vrrp_handle_ipaddress(vrrp, IPADDRESS_ADD, VRRP_VIP_TYPE); + vrrp_handle_ipaddress(vrrp, IPADDRESS_ADD, VRRP_VIP_TYPE, false); if (!LIST_ISEMPTY(vrrp->evip)) - vrrp_handle_ipaddress(vrrp, IPADDRESS_ADD, VRRP_EVIP_TYPE); + vrrp_handle_ipaddress(vrrp, IPADDRESS_ADD, VRRP_EVIP_TYPE, false); vrrp->vipset = 1; #ifdef _HAVE_FIB_ROUTING_ @@ -1403,9 +1403,9 @@ vrrp_restore_interface(vrrp_t * vrrp, bool advF, bool force) __test_bit(DONT_RELEASE_VRRP_BIT, &debug) || __test_bit(RELEASE_VIPS_BIT, &debug)) { if (!LIST_ISEMPTY(vrrp->vip)) - vrrp_handle_ipaddress(vrrp, IPADDRESS_DEL, VRRP_VIP_TYPE); + vrrp_handle_ipaddress(vrrp, IPADDRESS_DEL, VRRP_VIP_TYPE, force); if (!LIST_ISEMPTY(vrrp->evip)) - vrrp_handle_ipaddress(vrrp, IPADDRESS_DEL, VRRP_EVIP_TYPE); + vrrp_handle_ipaddress(vrrp, IPADDRESS_DEL, VRRP_EVIP_TYPE, force); vrrp_handle_accept_mode(vrrp, IPADDRESS_DEL, force); vrrp->vipset = 0; } @@ -2740,9 +2740,9 @@ restore_vrrp_state(vrrp_t *old_vrrp, vrrp_t *vrrp) if (vrrp->vipset) { vrrp_handle_accept_mode(vrrp, IPADDRESS_ADD, false); if (!LIST_ISEMPTY(vrrp->vip)) - added_ip_addr = vrrp_handle_ipaddress(vrrp, IPADDRESS_ADD, VRRP_VIP_TYPE); + added_ip_addr = vrrp_handle_ipaddress(vrrp, IPADDRESS_ADD, VRRP_VIP_TYPE, false); if (!LIST_ISEMPTY(vrrp->evip)) { - if (vrrp_handle_ipaddress(vrrp, IPADDRESS_ADD, VRRP_EVIP_TYPE)) + if (vrrp_handle_ipaddress(vrrp, IPADDRESS_ADD, VRRP_EVIP_TYPE, false)) added_ip_addr = true; } #ifdef _HAVE_FIB_ROUTING_ diff --git a/keepalived/vrrp/vrrp_daemon.c b/keepalived/vrrp/vrrp_daemon.c index 1c2f9e89..32bf4560 100644 --- a/keepalived/vrrp/vrrp_daemon.c +++ b/keepalived/vrrp/vrrp_daemon.c @@ -103,7 +103,7 @@ stop_vrrp(int status) netlink_rulelist(vrrp_data->static_rules, IPRULE_DEL, false); netlink_rtlist(vrrp_data->static_routes, IPROUTE_DEL); #endif - netlink_iplist(vrrp_data->static_addresses, IPADDRESS_DEL); + netlink_iplist(vrrp_data->static_addresses, IPADDRESS_DEL, false); #ifdef _WITH_SNMP_ if (global_data->enable_snmp_keepalived || global_data->enable_snmp_rfcv2 || global_data->enable_snmp_rfcv3) @@ -245,7 +245,7 @@ start_vrrp(void) } else { /* Clear leftover static entries */ - netlink_iplist(vrrp_data->static_addresses, IPADDRESS_DEL); + netlink_iplist(vrrp_data->static_addresses, IPADDRESS_DEL, false); #ifdef _HAVE_FIB_ROUTING_ netlink_rtlist(vrrp_data->static_routes, IPROUTE_DEL); netlink_error_ignore = ENOENT; @@ -286,7 +286,7 @@ start_vrrp(void) #endif /* Set static entries */ - netlink_iplist(vrrp_data->static_addresses, IPADDRESS_ADD); + netlink_iplist(vrrp_data->static_addresses, IPADDRESS_ADD, false); #ifdef _HAVE_FIB_ROUTING_ netlink_rtlist(vrrp_data->static_routes, IPROUTE_ADD); netlink_rulelist(vrrp_data->static_rules, IPRULE_ADD, false); diff --git a/keepalived/vrrp/vrrp_ipaddress.c b/keepalived/vrrp/vrrp_ipaddress.c index eb332e72..e8dca912 100644 --- a/keepalived/vrrp/vrrp_ipaddress.c +++ b/keepalived/vrrp/vrrp_ipaddress.c @@ -143,7 +143,7 @@ netlink_ipaddress(ip_address_t *ipaddress, int cmd) /* Add/Delete a list of IP addresses */ bool -netlink_iplist(list ip_list, int cmd) +netlink_iplist(list ip_list, int cmd, bool force) { ip_address_t *ipaddr; element e; @@ -161,7 +161,7 @@ netlink_iplist(list ip_list, int cmd) ipaddr = ELEMENT_DATA(e); if ((cmd == IPADDRESS_ADD && !ipaddr->set) || (cmd == IPADDRESS_DEL && - (ipaddr->set || __test_bit(DONT_RELEASE_VRRP_BIT, &debug)))) { + (force || ipaddr->set || __test_bit(DONT_RELEASE_VRRP_BIT, &debug)))) { if (netlink_ipaddress(ipaddr, cmd) > 0) { ipaddr->set = !(cmd == IPADDRESS_DEL); changed_entries = true; @@ -581,7 +581,7 @@ clear_diff_address(struct ipt_handle *h, list l, list n) /* All addresses removed */ if (LIST_ISEMPTY(n)) { log_message(LOG_INFO, "Removing a complete VIP or e-VIP block"); - netlink_iplist(l, IPADDRESS_DEL); + netlink_iplist(l, IPADDRESS_DEL, false); handle_iptable_rule_to_iplist(h, l, IPADDRESS_DEL, false); return; } -- 2.25.1