ports/137865: [patch] heartbeat: correct dealing with cases, where are two or more (virtual) interfaces with an IP-address, but only one is up

Michael Leun michael.leun at arcor.net
Mon Aug 17 06:40:06 UTC 2009


>Number:         137865
>Category:       ports
>Synopsis:       [patch] heartbeat: correct dealing with cases, where are two or more (virtual) interfaces with an IP-address, but only one is up
>Confidential:   no
>Severity:       serious
>Priority:       medium
>Responsible:    freebsd-ports-bugs
>State:          open
>Quarter:        
>Keywords:       
>Date-Required:
>Class:          sw-bug
>Submitter-Id:   current-users
>Arrival-Date:   Mon Aug 17 06:40:05 UTC 2009
>Closed-Date:
>Last-Modified:
>Originator:     Michael Leun
>Release:        7.2
>Organization:
Vodafone AG & Co. KG
>Environment:
FreeBSD build72-64.tnd.arcor.net 7.2-RELEASE FreeBSD 7.2-RELEASE #0: Fri May  1 07:18:07 UTC 2009     root at driscoll.cse.buffalo.edu:/usr/obj/usr/src/sys/GENERIC  amd64

>Description:
Current implementation of function find_interface_bsd() in heartbeat-STABLE-1.2.4 used in port sysutils/heartbeat does not work correctly if there are multiple interfaces with the same IP address (where only one of is UP, the others are DOWN).

The attached patch replaces this function with one taking care of that.

It is implemented in perl and one might not be happy with that, but there is a depency to perl anyway.

The function was originally written by Michael Hofmann (mh at ubhofmann dot de). I modified his patch for the current port using the STABILE branch of heartbeat (it originally was created for heartbeat 1.2.5 used before).
>How-To-Repeat:
Create a configuration, where one IP address is configured on two or more (maybe virtual) interfaces and try to failover this address with heartbeat.
>Fix:
patch attached

Patch attached with submission follows:

--- resources/OCF/IPaddr.orig	2009-08-06 13:08:35.000000000 +0200
+++ resources/OCF/IPaddr	2009-08-06 13:12:35.000000000 +0200
@@ -298,9 +298,56 @@
   return $OCF_ERR_GENERIC
 }
 
+#
+#      Find out which alias serves the given IP address
+#      The argument is an IP address, and its output
+#      is an interface name (e.g., "em0").
+#
+#      parse the output of ifconfig and find the interface
+#      that holds ip address $ip (multiple may exist, but
+#      only one with flag UP)
+#      Try to find an interface with flag UP. If we don't find
+#      such an interface, try to find one with flag DOWN
+
 find_interface_bsd() {
-    #$IFCONFIG $IFCONFIG_A_OPT | grep "inet.*[: ]$OCF_RESKEY_ip "
-    $IFCONFIG | grep "$ipaddr" -B20 | grep "UP," | tail -n 1 | cut -d ":" -f 1
+
+    ipaddr="$1";
+
+    /sbin/ifconfig \
+       | /usr/bin/perl -w -e '
+
+            my $ip = $ARGV[0];
+
+            if (! $ip) {
+                exit(255);
+            }
+
+            my $if_name = "";
+            my $if_status = 0;
+
+            my $down_if_name = "";
+
+            while (<STDIN>) {
+                chomp();
+                if ( /^(\w+):\s+flags=/ ) {
+                    $if_name = $1;
+                    $if_status = ( /UP/ ) ? 1 : 0;
+                }
+                if ( /^\s+inet\s+${ip}/ ) {
+                    if ( $if_status ) {
+                        print $if_name;
+                        exit(0)
+                    } else {
+                        $down_if_name = $if_name;
+                    }
+                }
+            }
+
+            if ($down_if_name) {
+                print $down_if_name;
+            }
+
+         ' $ipaddr
 }
 
 #


>Release-Note:
>Audit-Trail:
>Unformatted:



More information about the freebsd-ports-bugs mailing list