From 37690195004301bfdb76f7f2d83bad2bb349c69c Mon Sep 17 00:00:00 2001 From: dougal seeley Date: Fri, 22 Sep 2017 12:38:27 +0100 Subject: [PATCH] Add ability to specify VRRP V2 (as opposed to default of 3). Current release has a problem with V3 when there are more than 2 nodes (https://github.com/acassen/keepalived/issues/642). This has been fixed in master, but not part of a release yet. Using VRRP V2 bypasses the issue. --- keepalived-vip/controller.go | 7 ++++++- keepalived-vip/keepalived.go | 2 ++ keepalived-vip/keepalived.tmpl | 2 +- keepalived-vip/main.go | 4 +++- keepalived-vip/vip-daemonset.yaml | 2 ++ 5 files changed, 14 insertions(+), 3 deletions(-) mode change 100644 => 100755 keepalived-vip/controller.go mode change 100644 => 100755 keepalived-vip/keepalived.go mode change 100644 => 100755 keepalived-vip/keepalived.tmpl mode change 100644 => 100755 keepalived-vip/main.go mode change 100644 => 100755 keepalived-vip/vip-daemonset.yaml diff --git a/keepalived-vip/controller.go b/keepalived-vip/controller.go old mode 100644 new mode 100755 index 394aea93b0..fab6cfaf20 --- a/keepalived-vip/controller.go +++ b/keepalived-vip/controller.go @@ -300,7 +300,7 @@ func (ipvsc *ipvsControllerController) Stop() error { } // newIPVSController creates a new controller from the given config. -func newIPVSController(kubeClient *unversioned.Client, namespace string, useUnicast bool, configMapName string, vrid int) *ipvsControllerController { +func newIPVSController(kubeClient *unversioned.Client, namespace string, useUnicast bool, configMapName string, vrid int, vrrpVersion int) *ipvsControllerController { ipvsc := ipvsControllerController{ client: kubeClient, reloadRateLimiter: flowcontrol.NewTokenBucketRateLimiter(reloadQPS, int(reloadQPS)), @@ -331,6 +331,10 @@ func newIPVSController(kubeClient *unversioned.Client, namespace string, useUnic glog.Fatalf("Error using VRID %d, only values between 0 and 255 are allowed.", vrid) } + if vrrpVersion < 2 || vrrpVersion > 3 { + glog.Fatalf("Error using VRRP %d, only values between 2 and 3 are allowed.", vrrpVersion) + } + neighbors := getNodeNeighbors(nodeInfo, clusterNodes) execer := exec.New() @@ -347,6 +351,7 @@ func newIPVSController(kubeClient *unversioned.Client, namespace string, useUnic useUnicast: useUnicast, ipt: iptInterface, vrid: vrid, + vrrpVersion: vrrpVersion, } ipvsc.syncQueue = NewTaskQueue(ipvsc.sync) diff --git a/keepalived-vip/keepalived.go b/keepalived-vip/keepalived.go old mode 100644 new mode 100755 index f57dea93da..f4ed7cafd3 --- a/keepalived-vip/keepalived.go +++ b/keepalived-vip/keepalived.go @@ -50,6 +50,7 @@ type keepalived struct { cmd *exec.Cmd ipt iptables.Interface vrid int + vrrpVersion int } // WriteCfg creates a new keepalived configuration file. @@ -74,6 +75,7 @@ func (k *keepalived) WriteCfg(svcs []vip) error { conf["priority"] = k.priority conf["useUnicast"] = k.useUnicast conf["vrid"] = k.vrid + conf["vrrpVersion"] = k.vrrpVersion if glog.V(2) { b, _ := json.Marshal(conf) diff --git a/keepalived-vip/keepalived.tmpl b/keepalived-vip/keepalived.tmpl old mode 100644 new mode 100755 index b16a506fc6..26aeaa3010 --- a/keepalived-vip/keepalived.tmpl +++ b/keepalived-vip/keepalived.tmpl @@ -1,7 +1,7 @@ {{ $iface := .iface }}{{ $netmask := .netmask }} global_defs { - vrrp_version 3 + vrrp_version {{ .vrrpVersion }} vrrp_iptables {{ .iptablesChain }} } diff --git a/keepalived-vip/main.go b/keepalived-vip/main.go old mode 100644 new mode 100755 index 226a786e39..f00ebd6ef8 --- a/keepalived-vip/main.go +++ b/keepalived-vip/main.go @@ -43,6 +43,8 @@ var ( useUnicast = flags.Bool("use-unicast", false, `use unicast instead of multicast for communication with other keepalived instances`) + vrrpVersion = flags.Int("vrrp-version", 3, `Which VRRP version to use (2 or 3)`) + configMapName = flags.String("services-configmap", "", `Name of the ConfigMap that contains the definition of the services to expose. The key in the map indicates the external IP to use. The value is the name of the @@ -122,7 +124,7 @@ func main() { if *useUnicast { glog.Info("keepalived will use unicast to sync the nodes") } - ipvsc := newIPVSController(kubeClient, namespace, *useUnicast, *configMapName, *vrid) + ipvsc := newIPVSController(kubeClient, namespace, *useUnicast, *configMapName, *vrid, *vrrpVersion) go ipvsc.epController.Run(wait.NeverStop) go ipvsc.svcController.Run(wait.NeverStop) diff --git a/keepalived-vip/vip-daemonset.yaml b/keepalived-vip/vip-daemonset.yaml old mode 100644 new mode 100755 index cf71b296ef..e0e199d0e1 --- a/keepalived-vip/vip-daemonset.yaml +++ b/keepalived-vip/vip-daemonset.yaml @@ -37,6 +37,8 @@ spec: # unicast uses the ip of the nodes instead of multicast # this is useful if running in cloud providers (like AWS) #- --use-unicast=true + # vrrp version can be set to 2. Default 3. + #- --vrrp-version=2 volumes: - name: modules hostPath: