From 54f99d08497578db895f69d1624bb483502f734b Mon Sep 17 00:00:00 2001 From: Arif Ali Date: Tue, 1 Apr 2014 16:16:14 +0100 Subject: [PATCH] defect 4033: fix device based routing in makeroutes --- xCAT-server/lib/xcat/plugins/route.pm | 123 ++++++++++++++++----- xCAT/postscripts/routeop | 151 ++++++++++++++++++++------ 2 files changed, 215 insertions(+), 59 deletions(-) diff --git a/xCAT-server/lib/xcat/plugins/route.pm b/xCAT-server/lib/xcat/plugins/route.pm index 8ec31df6c..1da3055f8 100644 --- a/xCAT-server/lib/xcat/plugins/route.pm +++ b/xCAT-server/lib/xcat/plugins/route.pm @@ -449,7 +449,7 @@ sub process_makeroutes { delete_route($callback, $route_hash->{net}, $route_hash->{mask}, $gw_ip, $gw_name, $route_hash->{ifname}); } else { - set_route($callback, $route_hash->{net}, $route_hash->{mask}, $gw_ip, $gw_name,$route_hash->{ifname}); + set_route($callback, $route_hash->{net}, $route_hash->{mask}, $gw_ip, $gw_name, $route_hash->{ifname}); } } } @@ -526,6 +526,7 @@ sub route_exists { my $mask = shift; my $gw_ip = shift; my $gw=shift; + my $ifname = shift; my $islinux=xCAT::Utils->isLinux(); @@ -557,7 +558,8 @@ sub route_exists { my $net1=$a[0]; my $mask1=$a[2]; my $gw1=$a[1]; - if (($net1 eq $net) && ($mask1 eq $mask) && (($gw1 eq $gw) || ($gw1 eq $gw_ip))) { + my $ifname1=$a[7]; + if (($net1 eq $net) && ($mask1 eq $mask) && (($gw1 eq $gw) || ($gw1 eq $gw_ip) || ($ifname1 eq $ifname))) { return 1; } } @@ -602,19 +604,27 @@ sub set_route { #print "set_route get called\n"; my $result; - if (!route_exists($net, $mask, $gw_ip, $gw)) { + if (!route_exists($net, $mask, $gw_ip, $gw, $ifname)) { #set temporay route my $cmd; # ipv6 network if ($net =~ /:/) { if (xCAT::Utils->isLinux()) { - $cmd="ip -6 route add $net/$mask via $gw_ip"; + if ( $gw_ip == "" || $gw_ip == "::" ) { + $cmd="ip -6 route add $net/$mask dev $ifname"; + } else { + $cmd="ip -6 route add $net/$mask via $gw_ip"; + } } else { # AIX TODO } } else { if (xCAT::Utils->isLinux()) { - $cmd="route add -net $net netmask $mask gw $gw_ip"; + if ( $gw_ip == "" || $gw_ip == "0.0.0.0" ) { + $cmd="route add -net $net netmask $mask dev $ifname"; + } else { + $cmd="route add -net $net netmask $mask gw $gw_ip"; + } } else { $cmd="route add -net $net -netmask $mask $gw_ip"; } @@ -676,18 +686,26 @@ sub delete_route { #print "delete_route get called\n"; my $result; - if (route_exists($net, $mask, $gw_ip, $gw)) { + if (route_exists($net, $mask, $gw_ip, $gw, $ifname)) { #delete route temporarily my $cmd; if ($net =~ /:/) { if (xCAT::Utils->isLinux()) { - $cmd = "ip -6 route delete $net/$mask via $gw_ip"; + if ( $gw_ip == "" || $gw_ip == "::" ) { + $cmd = "ip -6 route delete $net/$mask dev $ifname"; + } else { + $cmd = "ip -6 route delete $net/$mask via $gw_ip"; + } } else { # AIX TODO } } else { if (xCAT::Utils->isLinux()) { - $cmd="route delete -net $net netmask $mask gw $gw_ip"; + if ( $gw_ip == "" || $gw_ip == "0.0.0.0" ) { + $cmd="route delete -net $net netmask $mask dev $ifname"; + } else { + $cmd="route delete -net $net netmask $mask gw $gw_ip"; + } } else { $cmd="route delete -net $net -netmask $mask $gw_ip"; } @@ -827,14 +845,22 @@ sub addPersistentRoute_Sles { #print "old output=" . join("\n", @output) . "\n"; my $hasConfiged=0; if (@output && (@output > 0)) { - $hasConfiged=checkConfig_Sles($net, $mask, $gw_ip, $gw, \@output); + $hasConfiged=checkConfig_Sles($net, $mask, $gw_ip, $gw, $ifname, \@output); } #print "hasConfiged=$hasConfiged\n"; my $new_config; if ($net =~ /:/) { - $new_config = "$net/$mask $gw_ip - -\n"; + if ( $gw_ip == "" || $gw_ip == "::" ) { + $new_config = "$net/$mask :: - $ifname\n"; + } else { + $new_config = "$net/$mask $gw_ip - -\n"; + } } else { - $new_config="$net $gw_ip $mask $ifname\n"; + if ( $gw_ip == "" || $gw_ip == "0.0.0.0" ) { + $new_config="$net 0.0.0.0 $mask $ifname\n"; + } else { + $new_config="$net $gw_ip $mask $ifname\n"; + } } if (!$hasConfiged) { push(@output, $new_config); @@ -872,7 +898,7 @@ sub deletePersistentRoute_Sles { my @new_output=(); my $bigfound=0; foreach my $tmp_conf (@output) { - my $found = checkConfig_Sles($net, $mask, $gw_ip, $gw, [$tmp_conf]); + my $found = checkConfig_Sles($net, $mask, $gw_ip, $gw, $ifname, [$tmp_conf]); if (!$found) { push(@new_output, $tmp_conf); } else { @@ -909,13 +935,18 @@ sub checkConfig_Sles { my $mask = shift; my $gw_ip = shift; my $gw=shift; + my $ifname=shift; my $output=shift; + # Format: + # DESTINATION GATEWAY NETMASK INTERFACE + # DESTINATION/PREFIXLEN GATEWAY - INTERFACE + # ipv4 format: 192.168.0.0 207.68.156.51 255.255.0.0 eth1 # ipv6 format: fd59::/64 fd57:faaf:e1ab:336:21a:64ff:fe01:1 - - foreach my $line (@$output) { my @a=split(' ', $line); - my ($net1,$mask1,$gw1); + my ($net1,$mask1,$gw1,$ifname1); if ($net =~ /:/) { if (@a>0) { my $ipv6net = $a[0]; @@ -925,6 +956,10 @@ sub checkConfig_Sles { $gw1=$a[1]; if ($gw1 eq '-') { $gw1=$gw_ip; } } + if (@a>3) { + $ifname1=$a[3]; + if ($ifname1 eq '-') { $ifname1=$ifname;} + } } else { if (@a>0) { @@ -939,10 +974,14 @@ sub checkConfig_Sles { $mask1=$a[2]; if ($mask1 eq '-') { $mask1=$mask;} } + if (@a>3) { + $ifname1=$a[3]; + if ($ifname1 eq '-') { $ifname1=$ifname;} + } } - #print "net=$net1,$net mask=$mask1,$mask gw=$gw1,$gw_ip\n"; - if (($net1 && $net1 eq $net) && ($mask1 && $mask1 eq $mask) && (($gw1 && $gw1 eq $gw) || ($gw1 && $gw1 eq $gw_ip))) { + #print "net=$net1,$net mask=$mask1,$mask gw=$gw1,$gw_ip ifname=$ifname1\n"; + if (($net1 && $net1 eq $net) && ($mask1 && $mask1 eq $mask) && (($gw1 && $gw1 eq $gw) || ($gw1 && $gw1 eq $gw_ip) || ($ifname1 && $ifname1 eq $ifname))) { return 1; } } @@ -972,7 +1011,7 @@ sub addPersistentRoute_RH { #print "old output=" . join("\n", @output) . "\n"; my $hasConfiged=0; if (@output && (@output > 0)) { - $hasConfiged=checkConfig_RH($net, $mask, $gw_ip, $gw, \@output); + $hasConfiged=checkConfig_RH($net, $mask, $gw_ip, $gw, $ifname, \@output); } #print "hasConfiged=$hasConfiged\n"; my $new_config; @@ -987,7 +1026,11 @@ sub addPersistentRoute_RH { $new_config="$ifname $net/$mask $gw_ip"; } else { - $new_config="any net $net netmask $mask gw $gw_ip $ifname\n"; + if ( $gw_ip == "" || $gw_ip == "0.0.0.0" ) { + $new_config="any net $net netmask $mask dev $ifname\n"; + } else { + $new_config="any net $net netmask $mask gw $gw_ip\n"; + } } if (!$hasConfiged) { push(@output, $new_config); @@ -1031,7 +1074,7 @@ sub deletePersistentRoute_RH { my @new_output=(); my $bigfound=0; foreach my $tmp_conf (@output) { - my $found = checkConfig_RH($net, $mask, $gw_ip, $gw, [$tmp_conf]); + my $found = checkConfig_RH($net, $mask, $gw_ip, $gw, $ifname, [$tmp_conf]); if (!$found) { push(@new_output, $tmp_conf); } else { @@ -1065,14 +1108,16 @@ sub checkConfig_RH { my $mask = shift; my $gw_ip = shift; my $gw=shift; + my $ifname=shift; my $output=shift; foreach my $line (@$output) { my @a=split(' ', $line); #The format is: any net 172.16.0.0 netmask 255.240.0.0 gw 192.168.0.1 eth0 # ipv6 format: eth1 fd60::/64 fd57::214:5eff:fe15:1 - my ($net1,$mask1,$gw1); + my ($net1,$mask1,$gw1,$ifname1); if ($net =~ /:/) { + $ifname1 = $a[0]; if (@a>1) { my $ipv6net = $a[1]; ($net1,$mask1) = split("/",$ipv6net); @@ -1090,13 +1135,18 @@ sub checkConfig_RH { if ($mask1 eq '-') { $mask1=$mask;} } if (@a>6) { - $gw1=$a[6]; - if ($gw1 eq '-') { $gw1=$gw_ip; } + if ( $a[5] eq 'dev' ) { + $ifname1=$a[6]; + if ($ifname1 eq '-') { $ifname1=$ifname;} + } else { + $gw1=$a[6]; + if ($gw1 eq '-') { $gw1=$gw_ip; } + } } } - #print "net=$net1,$net mask=$mask1,$mask gw=$gw1,$gw_ip\n"; - if (($net1 && $net1 eq $net) && ($mask1 && $mask1 eq $mask) && (($gw1 && $gw1 eq $gw) || ($gw1 && $gw1 eq $gw_ip))) { + #print "net=$net1,$net mask=$mask1,$mask gw=$gw1,$gw_ip ifname=$ifname1,ifname\n"; + if (($net1 && $net1 eq $net) && ($mask1 && $mask1 eq $mask) && (($gw1 && $gw1 eq $gw) || ($gw1 && $gw1 eq $gw_ip) || ($ifname1 && $ifname1 eq $ifname))) { return 1; } } @@ -1120,12 +1170,21 @@ sub addPersistentRoute_Debian{ #ipv6 if ( $net =~ /:/){ - $cmd = "grep \"$net/$mask gw $gw_ip\" $conf_file"; - $route_conf = " up route -A inet6 add $net/$mask gw $gw_ip \n down route -A inet6 del $net/$mask gw $gw_ip \n"; + if ( $gw_ip == "" || $gw_ip == "::" ) { + $cmd = "grep \"$net/$mask dev $ifname\" $conf_file"; + $route_conf = " up route -A inet6 add $net/$mask dev $ifname \n down route -A inet6 del $net/$mask dev $ifname \n"; + } else { + $cmd = "grep \"$net/$mask gw $gw_ip\" $conf_file"; + $route_conf = " up route -A inet6 add $net/$mask gw $gw_ip \n down route -A inet6 del $net/$mask gw $gw_ip \n"; + } } else { #ipv4 $cmd = "grep \"-net $net netmask $mask gw $gw_ip\" $conf_file"; - $route_conf = " up route add -net $net netmask $mask gw $gw_ip \n down route del -net $net netmask $mask gw $gw_ip \n"; + if ( $gw_ip == "" || $gw_ip == "0.0.0.0" ) { + $route_conf = " up route add -net $net netmask $mask dev $ifname \n down route del -net $net netmask $mask dev $ifname \n"; + } else { + $route_conf = " up route add -net $net netmask $mask gw $gw_ip \n down route del -net $net netmask $mask gw $gw_ip\n"; + } } #fine the corresponding config in the config file @@ -1183,10 +1242,18 @@ sub deletePersistentRoute_Debian{ preParse_Debian(); #ipv6 if ( $net =~ /:/){ - $match = "$net/$mask gw $gw_ip"; + if ( $gw_ip == "" || $gw_ip == "::" ) { + $match = "$net/$mask dev $ifname"; + } else { + $match = "$net/$mask gw $gw_ip"; + } } else { - $match = "net $net netmask $mask gw $gw_ip"; + if ( $gw_ip == "" || $gw_ip == "0.0.0.0" ) { + $match = "net $net netmask $mask dev $ifname"; + } else { + $match = "net $net netmask $mask gw $gw_ip"; + } } open(FH, "<", $conf_file); diff --git a/xCAT/postscripts/routeop b/xCAT/postscripts/routeop index 7260a033a..2cf80a3f1 100755 --- a/xCAT/postscripts/routeop +++ b/xCAT/postscripts/routeop @@ -107,7 +107,8 @@ route_exists() net1=`echo $x|cut -d',' -f1` gw1=`echo $x|cut -d',' -f2` mask1=`echo $x|cut -d',' -f3` - if [ "$net" = "$net1" ] && [ "$mask" = "$mask1" ] && [ "$gw" = "$gw1" ]; then + ifname1=`echo $x|cut -d',' -f8` + if [ "$net" = "$net1" ] && [ "$mask" = "$mask1" ] && [ "$gw" = "$gw1" ] && [ "$ifname" = "$ifname1" ]; then ret=1 break fi @@ -174,11 +175,21 @@ add_persistent_route() filename="/etc/sysconfig/network/routes"; if echo $net | grep : 2>&1 1>/dev/null then - route="$net/$mask $gw - -" - route1="$net\/$mask $gw - -"; + if [ $gw_ip = "" -o $gw_ip = "::" ] ; then + route="$net/$mask :: - $ifname" + route1="$net\/$mask :: - $ifname"; + else + route="$net/$mask $gw - -" + route1="$net\/$mask $gw - -"; + fi else - route="$net $gw $mask $ifname"; - route1="$net $gw $mask $ifname"; + if [ $gw_ip = "" -o $gw_ip = "0.0.0.0" ] ; then + route="$net 0.0.0.0 $mask $ifname"; + route1="$net 0.0.0.0 $mask $ifname"; + else + route="$net $gw $mask $ifname"; + route1="$net $gw $mask $ifname"; + fi fi if [ -f $filename ]; then grep "$route" $filename 2>&1 1>/dev/null @@ -221,10 +232,18 @@ add_persistent_route() echo $net | grep : 2>&1 1>/dev/null #ipv6 if [ $? -eq 0 ];then - matchstr="$net/$mask gw $gw" + if [ "$gw" = "" -o "$gw" = "::" ] ; then + matchstr="$net/$mask dev $ifname" + else + matchstr="$net/$mask gw $gw" + fi v6flag=1 else - matchstr="net $net netmask $mask gw $gw" + if [ "$gw" = "" -o "$gw" = "0.0.0.0" ] ; then + matchstr="net $net netmask $mask dev $ifname" + else + matchstr="net $net netmask $mask gw $gw" + fi fi grep "$matchstr" $filename 2>&1 1>/dev/null @@ -237,11 +256,21 @@ add_persistent_route() if [ $? -eq 0 -a $foundflag -eq 1 ];then foundflag=0 if [ $v6flag -eq 1 ];then - echo " up route -A inet6 add $net/$mask gw $gw" >> $tempfile - echo " down route -A inet6 del $net/$mask gw $gw" >> $tempfile + if [ "$gw" = "" -o "$gw" = "::" ] ; then + echo " up route -A inet6 add $net/$mask dev $ifname" >> $tempfile + echo " down route -A inet6 del $net/$mask dev $ifname" >> $tempfile + else + echo " up route -A inet6 add $net/$mask gw $gw" >> $tempfile + echo " down route -A inet6 del $net/$mask gw $gw" >> $tempfile + fi else - echo " up route add -net $net netmask $mask gw $gw" >> $tempfile - echo " down route del -net $net netmask $mask gw $gw" >> $tempfile + if [ "$gw" = "" -o "$gw" = "0.0.0.0" ] ; then + echo " up route add -net $net netmask $mask dev $ifname" >> $tempfile + echo " down route del -net $net netmask $mask dev $ifname" >> $tempfile + else + echo " up route add -net $net netmask $mask gw $gw" >> $tempfile + echo " down route del -net $net netmask $mask gw $gw" >> $tempfile + fi fi fi echo $LINE | grep "iface $ifname " 2>&1 1>/dev/null @@ -255,11 +284,21 @@ add_persistent_route() #the insert place is the last line of the config file if [ $foundflag -eq 1 ];then if [ $v6flag -eq 1 ];then - echo " up route -A inet6 add $net/$mask gw $gw" >> $tempfile - echo " down route -A inet6 del $net/$mask gw $gw" >> $tempfile + if [ "$gw" = "" -o "$gw" = "::" ] ; then + echo " up route -A inet6 add $net/$mask dev $ifname" >> $tempfile + echo " down route -A inet6 del $net/$mask dev $ifname" >> $tempfile + else + echo " up route -A inet6 add $net/$mask gw $gw" >> $tempfile + echo " down route -A inet6 del $net/$mask gw $gw" >> $tempfile + fi else - echo " up route add -net $net netmask $mask gw $gw" >> $tempfile - echo " down route del -net $net netmask $mask gw $gw" >> $tempfile + if [ "$gw" = "" -o "$gw" = "0.0.0.0" ] ; then + echo " up route add -net $net netmask $mask dev $ifname" >> $tempfile + echo " down route del -net $net netmask $mask dev $ifname" >> $tempfile + else + echo " up route add -net $net netmask $mask gw $gw" >> $tempfile + echo " down route del -net $net netmask $mask gw $gw" >> $tempfile + fi fi fi mv -f $tempfile $filename @@ -273,14 +312,22 @@ add_persistent_route() # ipv6 net if echo $net | grep : 2>&1 1>/dev/null then + if [ "$gw" = "" ] ; then + $gw = "::"; + fi filename="/etc/sysconfig/static-routes-ipv6"; route="$ifname $net/$mask $gw"; # $net/mask does not work with sed cmd route1="$ifname $net\/$mask $gw"; else filename="/etc/sysconfig/static-routes"; - route="any net $net netmask $mask gw $gw $ifname"; - route1="any net $net netmask $mask gw $gw $ifname"; + if [ "$gw" = "" -o "$gw" = "0.0.0.0" ] ; then + route="any net $net netmask $mask dev $ifname"; + route1="any net $net netmask $mask dev $ifname"; + else + route="any net $net netmask $mask gw $gw $ifname"; + route1="any net $net netmask $mask gw $gw $ifname"; + fi fi if [ -f $filename ]; then grep "$route" $filename 2>&1 1>/dev/null @@ -340,15 +387,23 @@ rm_persistent_route() # ipv6 net if echo $net | grep : 2>&1 1>/dev/null then - route="$net/$mask $gw - -"; - route1="$net\/$mask $gw - -"; + if [ $gw = "" -o $gw = "::" ] ; then + route="$net/$mask :: - $ifname"; + route1="$net\/$mask :: - $ifname"; + else + route="$net/$mask $gw - -"; + route1="$net\/$mask $gw - -"; + fi else + if [ $gw = "" ] ; then + $gw = "0.0.0.0"; + fi if [ -n "$ifname" ]; then route="$net $gw $mask $ifname"; route1="$net $gw $mask $ifname"; else - route="$net $gw $mask"; - route1="$net $gw $mask"; + route="$net $gw $mask -"; + route1="$net $gw $mask -"; fi fi if [ -f $filename ]; then @@ -376,10 +431,18 @@ rm_persistent_route() echo $net | grep : 2>&1 1>/dev/null #ipv6 if [ $? -eq 0 ];then - matchstr="$net/$mask gw $gw" + if [ $gw = "" -o $gw = "::" ] ; then + matchstr="$net/$mask dev $ifname" + else + matchstr="$net/$mask gw $gw" + fi v6flag=1 else - matchstr="net $net netmask $mask gw $gw" + if [ $gw = "" -o $gw = "0.0.0.0" ] ; then + matchstr="net $net netmask $mask dev $ifname" + else + matchstr="net $net netmask $mask gw $gw" + fi fi grep "$matchstr" $filename @@ -397,12 +460,22 @@ rm_persistent_route() then filename="/etc/sysconfig/static-routes-ipv6"; # $net/$mask does not work with sed - route="$ifname $net\/$mask $gw" - route1="$ifname $net/$mask $gw" + if [ "$gw" = "" -o "$gw" = "::" ] ; then + route="$ifname $net\/$mask ::" + route1="$ifname $net/$mask ::" + else + route="$ifname $net\/$mask $gw" + route1="$ifname $net/$mask $gw" + fi else filename="/etc/sysconfig/static-routes"; - route="any net $net netmask $mask gw $gw $ifname"; - route1="any net $net netmask $mask gw $gw $ifname"; + if [ "$gw" = "" -o "$gw" = "0.0.0.0" ] ; then + route="any net $net netmask $mask dev $ifname"; + route1="any net $net netmask $mask dev $ifname"; + else + route="any net $net netmask $mask gw $gw $ifname"; + route1="any net $net netmask $mask gw $gw $ifname"; + fi fi if [ -f $filename ]; then grep "$route" $filename 2>&1 1>/dev/null @@ -431,14 +504,22 @@ if [ "$op" = "add" ]; then if echo $net | grep : 2>&1 1>/dev/null then if [ "$(uname -s)" = "Linux" ]; then - cmd="ip -6 route add $net/$mask via $gw" + if [ "$gw" = "" -o "$gw" = "::" ] ; then + cmd="ip -6 route add $net/$mask dev $ifname" + else + cmd="ip -6 route add $net/$mask via $gw" + fi else # AIX TODO cmd="ip -6 route add $net/$mask via $gw" fi else if [ "$(uname -s)" = "Linux" ]; then - cmd="route add -net $net netmask $mask gw $gw" + if [ "$gw" = "" -o "$gw" = "0.0.0.0" ] ; then + cmd="route add -net $net netmask $mask dev $ifname" + else + cmd="route add -net $net netmask $mask gw $gw" + fi else cmd="route add -net $net -netmask $mask $gw" fi @@ -472,14 +553,22 @@ elif [ "$op" = "delete" ]; then if echo $net | grep : 2>&1 1>/dev/null then if [ "$(uname -s)" = "Linux" ]; then - cmd="ip -6 route delete $net/$mask via $gw" + if [ "$gw" = "" -o "$gw" = "::" ] ; then + cmd="ip -6 route delete $net/$mask dev $ifname" + else + cmd="ip -6 route delete $net/$mask via $gw" + fi else # AIX TODO cmd="ip -6 route delete $net/$mask via $gw" fi else if [ "$(uname -s)" = "Linux" ]; then - cmd="route delete -net $net netmask $mask gw $gw" + if [ "$gw" = "" -o "$gw" = "0.0.0.0" ] ; then + cmd="route delete -net $net netmask $mask dev $ifname" + else + cmd="route delete -net $net netmask $mask gw $gw" + fi else cmd="route delete -net $net -netmask $mask $gw" fi