-Fix pping handling of FQDN-first /etc/hosts entries
-Have nodestat use nmap instead of fping/homegrown code -Require nmap instead of fping git-svn-id: https://svn.code.sf.net/p/xcat/code/xcat-core/trunk@3093 8638fb3e-16cb-4fca-ae20-7b5d299a9bcd
This commit is contained in:
		| @@ -86,10 +86,20 @@ foreach (@nodes) { | ||||
|     $deadnodes{$_}=1; | ||||
| } | ||||
| open (FPING, "nmap -sP ".join(' ',@nodes). " 2> /dev/null|") or die("Cannot open nmap pipe: $!"); | ||||
| my $node; | ||||
| while (<FPING>) { | ||||
|   if (/Host (.*) \(.*\) appears to be up/) { | ||||
|       print "$1: ping\n"; | ||||
|       delete $deadnodes{$1}; | ||||
|       $node=$1; | ||||
|       unless ($deadnodes{$node}) { | ||||
|           foreach (keys %deadnodes) { | ||||
|               if ($node =~ /^$_\./) { | ||||
|                   $node = $_; | ||||
|                   last; | ||||
|               } | ||||
|           } | ||||
|       } | ||||
|       delete $deadnodes{$node}; | ||||
|       print "$node: ping\n"; | ||||
|   } | ||||
| } | ||||
| foreach (sort keys %deadnodes) { | ||||
|   | ||||
| @@ -21,7 +21,7 @@ Provides: xCAT-client = %{version} | ||||
|  | ||||
| # fping is needed by pping (in case xCAT-client is installed by itself on a remote client) | ||||
| %ifos linux | ||||
| Requires: fping | ||||
| Requires: nmap | ||||
| %endif | ||||
|  | ||||
| %description | ||||
|   | ||||
| @@ -6,6 +6,7 @@ use Socket; | ||||
| use IO::Handle; | ||||
| use Getopt::Long; | ||||
| my $stat; | ||||
| my %portservices; | ||||
|  | ||||
| sub handled_commands { | ||||
|    return {  | ||||
| @@ -13,28 +14,6 @@ sub handled_commands { | ||||
|    }; | ||||
| } | ||||
|  | ||||
| sub pinghost { | ||||
|    my $node = shift; | ||||
|    my $rc = system("ping -q -n -c 1 -w 1 $node > /dev/null"); | ||||
|    if ($rc == 0) { | ||||
|       return 1; | ||||
|    } else { | ||||
|       return 0; | ||||
|    } | ||||
| } | ||||
|  | ||||
| sub nodesockopen { | ||||
|    my $node = shift; | ||||
|    my $port = shift; | ||||
|    my $socket; | ||||
|    my $addr = gethostbyname($node); | ||||
|    my $sin = sockaddr_in($port,$addr); | ||||
|    my $proto = getprotobyname('tcp'); | ||||
|    socket($socket,PF_INET,SOCK_STREAM,$proto) || return 0; | ||||
|    connect($socket,$sin) || return 0; | ||||
|    return 1; | ||||
| } | ||||
|  | ||||
| sub installer_query { | ||||
|    my $node = shift; | ||||
|    my $destport = 3001; | ||||
| @@ -128,40 +107,20 @@ sub preprocess_request | ||||
|          }  | ||||
|     } | ||||
|     return \@requests; | ||||
| } | ||||
|  | ||||
| sub interrogate_node { #Meant to run against confirmed up nodes | ||||
|     my $node=shift; | ||||
|     my $doreq=shift; | ||||
|     my $status = ""; | ||||
|     if (nodesockopen($node,15002)) { | ||||
|         $status.="pbs," | ||||
|     } | ||||
|     if (nodesockopen($node,8002)) { | ||||
|         $status.="xend," | ||||
|     } | ||||
|     if (nodesockopen($node,22)) { | ||||
|         $status.="sshd," | ||||
|     } | ||||
|     $status =~ s/,$//; | ||||
|     if ($status) { | ||||
|         return $status; | ||||
|     } | ||||
|     if ($status = installer_query($node)) { | ||||
|         return  $status; | ||||
|     } else { #pingable, but no *clue* as to what the state may be | ||||
|          $doreq->({command=>['nodeset'], | ||||
|                   node=>[$node], | ||||
|                   arg=>['stat']}, | ||||
|                   \&getstat); | ||||
|          return 'ping '.$stat; | ||||
|      } | ||||
|     return 0; | ||||
| } | ||||
|  | ||||
| sub process_request { | ||||
|    my $request = shift; | ||||
|    my $callback = shift; | ||||
|    my $doreq = shift; | ||||
|    %portservices = ( | ||||
|         '22' => 'ssh', | ||||
|         '15002' => 'pbs', | ||||
|         '8002' => 'xend', | ||||
|    ); | ||||
|    my @livenodes; | ||||
|    $statselect = new IO::Select; | ||||
|    my @nodes = @{$request->{node}}; | ||||
|    my %unknownnodes; | ||||
|    foreach (@nodes) { | ||||
| @@ -171,69 +130,66 @@ sub process_request { | ||||
|         if( !defined $packed_ip) { | ||||
|                 my %rsp; | ||||
|                 $rsp{name}=[$_]; | ||||
|                 $rsp{data} = [ "Please make sure $_ exists in /etc/hosts" ]; | ||||
|                 $rsp{data} = [ "Please make sure $_ exists in /etc/hosts or DNS" ]; | ||||
|                 $callback->({node=>[\%rsp]}); | ||||
|         } | ||||
|    } | ||||
|  | ||||
|    my $node; | ||||
|    my $fping; | ||||
|    open($fping,"fping ".join(' ',@nodes). " 2> /dev/null|") or die("Can't start fping: $!"); | ||||
|    while (<$fping>) { | ||||
|       my %rsp; | ||||
|       my $node=$_; | ||||
|       $node =~ s/ .*//; | ||||
|       chomp $node; | ||||
|        if (/ is alive/) { | ||||
|            $rsp{name}=[$node]; | ||||
|            $rsp{data} = [ interrogate_node($node,$doreq) ]; | ||||
|            $callback->({node=>[\%rsp]}); | ||||
|        } elsif (/is unreachable/) { | ||||
|          $rsp{name}=[$node]; | ||||
|          $rsp{data} = [ 'noping' ]; | ||||
|          $callback->({node=>[\%rsp]}); | ||||
|        } elsif (/ address not found/) { | ||||
|          $rsp{name}=[$node]; | ||||
|          $rsp{data} = [ 'nosuchhost' ]; | ||||
|          $callback->({node=>[\%rsp]}); | ||||
|        } | ||||
|     } | ||||
|     @nodes=(); | ||||
|    foreach $node (@nodes) { | ||||
|       my %rsp; | ||||
|       my $text=""; | ||||
|       $rsp{name}=[$node]; | ||||
|       unless (pinghost($node)) { | ||||
|          $rsp{data} = [ 'noping' ]; | ||||
|          $callback->({node=>[\%rsp]}); | ||||
|          next; | ||||
|       } | ||||
|       if (nodesockopen($node,15002)) { | ||||
|          $rsp{data} = [ 'pbs' ]; | ||||
|          $callback->({node=>[\%rsp]}); | ||||
|          next; | ||||
|       } elsif (nodesockopen($node,8002)) { | ||||
|          $rsp{data} = [ 'xend' ]; | ||||
|          $callback->({node=>[\%rsp]}); | ||||
|          next; | ||||
|       } elsif (nodesockopen($node,22)) { | ||||
|          $rsp{data} = [ 'sshd' ]; | ||||
|          $callback->({node=>[\%rsp]}); | ||||
|          next; | ||||
|       } elsif ($text = installer_query($node)) { | ||||
|          $rsp{data} = [ $text ]; | ||||
|          $callback->({node=>[\%rsp]}); | ||||
|          next; | ||||
|       } else { | ||||
|          $doreq->({command=>['nodeset'], | ||||
|                   node=>[$node], | ||||
|                   arg=>['stat']}, | ||||
|                   \&getstat); | ||||
|          $rsp{data} = [ 'ping '.$stat ]; | ||||
|          $callback->({node=>[\%rsp]}); | ||||
|          next; | ||||
|       } | ||||
|    my $ports = join ',',keys %portservices; | ||||
|    my %deadnodes; | ||||
|    foreach (@nodes) { | ||||
|        $deadnodes{$_}=1; | ||||
|    } | ||||
|    open($fping,"nmap -p $ports ".join(' ',@nodes). " 2> /dev/null|") or die("Can't start nmap: $!"); | ||||
|    my $currnode=''; | ||||
|    my $port; | ||||
|    my $state; | ||||
|    my %states; | ||||
|    my %rsp; | ||||
|    while (<$fping>) { | ||||
|       if (/Interesting ports on ([^ ]*) /) { | ||||
|           $currnode=$1; | ||||
|           unless ($deadnodes{$1}) { | ||||
|               foreach (keys %deadnodes) { | ||||
|                   if ($currnode =~ /^$_\./) { | ||||
|                       $currnode = $_; | ||||
|                       last; | ||||
|                   } | ||||
|               } | ||||
|           } | ||||
|           delete $deadnodes{$currnode}; | ||||
|       } elsif ($currnode) { | ||||
|           if (/^MAC/) { | ||||
|               $rsp{name}=[$currnode]; | ||||
|               my $status = join ',',sort keys %states ; | ||||
|               unless ($status or $status = installer_query($currnode)) { #pingable, but no *clue* as to what the state may be | ||||
|                  $doreq->({command=>['nodeset'], | ||||
|                       node=>[$currnode], | ||||
|                       arg=>['stat']}, | ||||
|                       \&getstat); | ||||
|                  $status= 'ping '.$stat; | ||||
|               } | ||||
|  | ||||
|               $rsp{data} = [ $status ]; | ||||
|               $callback->({node=>[\%rsp]}); | ||||
|               $currnode=""; | ||||
|               %states=(); | ||||
|               next; | ||||
|           } | ||||
|           if (/^PORT/) { next; } | ||||
|           ($port,$state) = split; | ||||
|           if ($port =~ /^(\d*)\// and $state eq 'open') { | ||||
|               $states{$portservices{$1}}=1; | ||||
|           } | ||||
|       }  | ||||
|     } | ||||
|     foreach $currnode (sort keys %deadnodes) { | ||||
|          $rsp{name}=[$currnode]; | ||||
|          $rsp{data} = [ 'noping' ]; | ||||
|          $callback->({node=>[\%rsp]}); | ||||
|     } | ||||
| } | ||||
| sub usage | ||||
| { | ||||
|   | ||||
| @@ -19,7 +19,7 @@ Requires: xCAT-server xCAT-client perl-DBD-SQLite | ||||
|  | ||||
| %ifos linux | ||||
| # yaboot-xcat is pulled in so any MN can manage ppc nodes | ||||
| Requires: atftp dhcp httpd nfs-utils expect fping bind perl-XML-Parser vsftpd yaboot-xcat | ||||
| Requires: atftp dhcp httpd nfs-utils expect nmap bind perl-XML-Parser vsftpd yaboot-xcat | ||||
| %ifarch s390x | ||||
| # No additional requires for zLinux right now | ||||
| %else | ||||
|   | ||||
| @@ -18,7 +18,7 @@ Requires: xCAT-server xCAT-client  perl-xCAT perl-XML-Parser | ||||
|  | ||||
| %ifos linux | ||||
| # yaboot-xcat is pulled in so any SN can manage ppc nodes | ||||
| Requires: atftp dhcp httpd nfs-utils expect fping bind yaboot-xcat | ||||
| Requires: atftp dhcp httpd nfs-utils expect nmap bind yaboot-xcat | ||||
| %ifarch s390x | ||||
| # No additional requires for zLinux right now | ||||
| %else | ||||
|   | ||||
		Reference in New Issue
	
	Block a user