[linux-lvm] Re: do_apc_ms stomith

AJ Lewis lewis at sistina.com
Tue Jun 11 09:11:01 UTC 2002


I think this is probably good enough AFAIAC:
!!! ERROR DETECTED in /home/vortex/src/GFS/bin/do_apc_ms -h  !!!
 o Options out of order: -q  >= -p 
!!! END OF ERRORS !!!
!!! ERROR DETECTED in /home/vortex/src/GFS/bin/do_apc_ms -Z  !!!
 o invalid error message (line 1): Unknown option: Z

!!! END OF ERRORS !!!

Just the missing flag errors need to be changed other than that.

On Mon, Jun 10, 2002 at 05:29:02PM -0500, Adam Manthei wrote:
> Let me know how this does against your ruby script.
> 
> It's some what of an improvement... but things are starting to get real
> ugly.  
>  
> -- 
> Adam Manthei  <manthei at sistina.com>

> #!/usr/bin/perl
> 
> ###############################################################################
> ###############################################################################
> ##
> ##  Copyright (C) Sistina Software, Inc.  1997-2001  All rights reserved.
> ##
> ###############################################################################
> ###############################################################################
> 
> use Getopt::Std;
> use Net::Telnet ();
> 
> # WARNING!! Do not add code bewteen "#BEGIN_VERSION_GENERATION" and 
> # "#END_VERSION_GENERATION"  It is generated by the Makefile
> 
> #BEGIN_VERSION_GENERATION
> $GFS_RELEASE_NAME="";
> $SISTINA_COPYRIGHT="";
> $BUILD_DATE="";
> #END_VERSION_GENERATION
> 
> # Get the program name from $0 and strip directory names
> $_=$0;
> s/.*\///;
> my $pname = $_;
> 
> # Change these if the text returned by your equipment is different.
> # Test by running script with options -t -v and checking /tmp/apclog
> 
> my $immediate = 'immediate'; # Or 'delayed' - action string prefix on menu
> my $masterswitch = 'masterswitch plus '; # 'Device Manager' option to choose
> my $login_prompt = '/: /';
> my $cmd_prompt = '/> /';
> 
> my $max_open_tries = 1;     # How many telnet attempts to make
> my $open_wait = 5;           # Seconds to wait between each telnet attempt
> my $telnet_timeout = 20;     # Seconds to wait for matching telent response
> my $opt_o = 'reboot';        # Default fence action
> 
> sub fail
> {
>   ($msg)=@_;
>   print $msg."\n" unless defined $opt_q;
>   $t->close if defined $t;
>   exit 1;
> }
> 
> sub fail_usage
> {
>   ($msg)=@_;
>   printf stderr $msg."\n" if $msg;
>   print  stderr "Please use '-h' for usage.\n";
>   exit 1;
> }
> 
> 
> sub usage 
> {
>     print "Usage:\n";
>     print "\n";
>     print "$pname [options]\n";
>     print "\n";
>     print "Options:\n";
>     print "  -a <ip>          IP address or hostname of MasterSwitch\n";
>     print "  -h               usage\n";
>     print "  -l <name>        Login name\n";
>     print "  -n <num>         Outlet number to change: [<switch>:]<outlet> \n";
>     print "  -o <string>      Action: Reboot (default), Off or On\n";
>     print "  -q               quiet mode\n";
>     print "  -p <string>      Login password\n";
>     print "  -T               Test mode (cancels action)\n";
>     print "  -V               version\n";
>     print "  -v               Log to file /tmp/apclog\n";
> 
>     exit 0;
> }
> 
> sub version
> {
>   print "$pname $GFS_RELEASE_NAME $BUILD_DATE\n";
>   print "$SISTINA_COPYRIGHT\n" if ( $SISTINA_COPYRIGHT );
> 
>   exit 0;
> }
> 
> 
> if (@ARGV > 0) {
>    $opt_name = $pname;
>    getopts("a:hl:n:o:p:qTvV") || fail_usage ;
> 
>    usage if defined $opt_h;
>    version if defined $opt_V;
> 
>    fail_usage "too many parameters" if (@ARGV > 0);
> 
>    fail_usage "failed: $opt_name no IP address" unless defined $opt_a;
>    fail_usage "failed: $opt_name no plug number" unless defined $opt_n;
>    fail_usage "failed: $opt_name no login name" unless defined $opt_l;
>    fail_usage "failed: $opt_name no password" unless defined $opt_p;
>    fail_usage "failed: $opt_name unrecognised action: $opt_o"
>       unless $opt_o =~ /^(Off|On|Reboot)$/i;
> 
> } else {
>    get_options_stdin();
> 
>    fail "failed: $opt_name no IP address" unless defined $opt_a;
>    fail "failed: $opt_name no plug number" unless defined $opt_n;
>    fail "failed: $opt_name no login name" unless defined $opt_l;
>    fail "failed: $opt_name no password" unless defined $opt_p;
>    fail "failed: $opt_name unrecognised action: $opt_o"
>       unless $opt_o =~ /^(Off|On|Reboot)$/i;
> }
> 
> 
> if ( $opt_n =~ /(\d+):(\d+)/ ) {
> 	my $switchnum=($1);
> 	$opt_n = ($2);
> 	$masterswitch = $masterswitch . $switchnum;
> } else {
> 	$masterswitch = $masterswitch . "1";
> }
> 
> my $t = new Net::Telnet;
> $t->timeout($telnet_timeout);
> 
> $t->input_log('/tmp/apclog')
>   if $opt_v;
> 
> &login;
> &navigate;
> &action;
> 
> exit 0;
> 
> 
> sub login
> {
>   # Opt to return on failure and we'll retry
>   $t->errmode('return');  
> 
>   for (my $i=0; $i<$max_open_tries; $i++)
>   {
>     $t->open($opt_a);
>     ($_) = $t->waitfor($login_prompt);
>   
>     # Expect 'User Name : ' 
>     if (! /name/i) {
>       $t->close;
>       sleep($open_wait);
>       next;        
>     }
> 
>     $t->print($opt_l);
>     ($_) = $t->waitfor($login_prompt);
>   
>     # Expect 'Password  : ' 
>     if (! /password/i ) {
>       $t->close;
>       sleep($open_wait);
>       next;         
>     }
>   
>     # Send password
>     $t->print($opt_p);  
>     # No point retrying if we get this far e.g. if password is rejected
>     return;
>   }
>   fail "failed: $opt_name - telnet failed: ". $t->errmsg."\n" 
> }
> 
> 
> 
> # Navigate through menus to the appropriate outlet control menu.
> # Uses multi-line (mostly) case-insensitive matches to recognise menus
> # and works out what option number to select from each menu.
> 
> sub navigate
> {
>   # Abort on failure beyond here
>   $t->errmode(\&telnet_error);  
>   while(1)
>   {
>     # Get the new text from the menu
>     ($_) = $t->waitfor($cmd_prompt);
> 
>     # Identify next option 
>     if ( 
>           # "Control Console", "1- Device Manager"
>           /--\s*control console.*(\d+)\s*-\s*device manager/is  ||
> 
>           # "Device Manager", "1- MasterSwitch plus 1"
>           /--\s*device manager.*(\d+)\s*-\s*$masterswitch/is ||
> 
>           # "Device Manager", "1- Cluster Node 0   ON"
>           /--\s*(?:device manager|$masterswitch).*($opt_n)\s*-[^\n]*\s(?-i:ON|OFF)\*?\s/ism ||
> 
>           # "MasterSwitch plus 1", "1- Outlet 1:1  Outlet #1  ON"
>           /--\s*$masterswitch.*(\d+)\s*-\s*Outlet\s+$opt_n\s[^\n]*\s(?-i:ON|OFF)\*?\s/ism ||
> 
>           # Outlet Control
>           /(\d+)\s*-\s*((Control|Outlet)\s?){2}\s*(\d+:)?$opt_n\s/i 
>        ) {
>       $t->print($1);
>       next;
>     }
> 
>     # "Outlet Control X:N", "4- Immediate Reboot"
>     if ( /(\d+)\s*-\s*$immediate $opt_o/i ) {
>       $t->print($1);
>       last;
>     }
> 
>     #> $t->close;
>     fail "failed: $opt_name - unrecognised menu response\n";
>   }
> }
> 
> 
> sub action
> {
>   # "Enter 'YES' to continue or <ENTER> to cancel : "
>   ($_) = $t->waitfor('/: /');
>   if (! /$immediate $opt_o.*outlet $opt_n\s.*YES.*to continue/si ) {
>     fail "failed: $opt_name - unrecognised $opt_o response\n";
>     #> $t->close;
>   }
> 
>   # Test mode?
>   $t->print($opt_T?'NO':'YES');
> 
>   # "Success", "Press <ENTER> to continue..." 
>   ($_) = $t->waitfor('/continue/');
>   $t->print('');
> 
>   if (defined $opt_T) {
>     print "success: $opt_name test outlet $opt_n $opt_o\n" unless defined $opt_q; 
>     $t->close;
>     exit 0;
>   } elsif ( /Success/i ) {
>     print "success: $opt_name outlet $opt_n $opt_o\n" unless defined $opt_q; 
>     $t->close;
>     exit 0;
>   } 
> 
>   fail "failed: $opt_name - unrecognised action response\n";
> }
> 
> 
> sub get_options_stdin
> {
>     my $opt;
>     my $line = 0;
>     while(<>)
>     {
>         chomp;
> 
> 	# strip leading and trailing whitespace
>         s/^\s*//;
>         s/\s*$//;
> 
> 	# skip comments
> 	next if /^#/;
> 
>         $line+=1;
>         $opt=$_;
> 	next unless $opt;
>        
> 	($name,$val)=split /\s*=\s*/, $opt;
> 
> 	if ( $name eq "" )
> 	{
> 	   print stderr "parse error: $opt_name illegal name in option $line\n";
> 	   exit 2;
> 	} 
> 
> 	# "node:" specified information
> 	# TODO -- "sm" is depricated.  "fm" is the prefered method
> 	elsif ($name eq "sm" ) 
> 	{ 
> 	    (my $dummy,$opt_n) = split /\s+/,$val;
> 	# "node:" specified information
> 	} 
> 	elsif ($name eq "fm" ) 
> 	{
> 	    (my $dummy,$opt_n) = split /\s+/,$val;
> 	} 
> 
> 	# "fence:" or  "stomith:" specific info
> 	elsif ($name eq "ipaddr" ) 
> 	{
> 	    $opt_a = $val;
> 	} 
> 	elsif ($name eq "login" ) 
> 	{
> 	    $opt_l = $val;
>         } 
> 	elsif ($name eq "name" ) 
> 	{
>             $opt_name = $val;
> 	} 
> 	elsif ($name eq "option" ) 
> 	{
> 	    $opt_o = $val;
> 	} 
> 	elsif ($name eq "passwd" ) 
> 	{
> 	    $opt_p = $val;
> 	} 
> 	elsif ($name eq "test" ) 
> 	{
> 	    $opt_T = $val;
> 	} 
> 	elsif ($name eq "verbose" ) 
> 	{
> 	    $opt_v = $val;
> 	} 
> 
>         # DO NOTHING -- this field is used by fenced or stomithd
> 	elsif ($name eq "agent" ) 
> 	{
> 	} 
> 
> 	# FIXME should we do more error checking?  
> 	# Excess name/vals will be eaten for now
> 	else 
> 	{
> 	   print stderr "parse error: $opt_name unknown option: $opt\n";
> 	   #> exit 2;
> 	}
>     }
> }
> 
> 
> sub telnet_error
> {
>   fail "failed: $opt_name - telnet returned: ".$t->errmsg."\n";
> }
> 

-------------- next part --------------
A non-text attachment was scrubbed...
Name: not available
Type: application/pgp-signature
Size: 189 bytes
Desc: not available
URL: <http://listman.redhat.com/archives/linux-lvm/attachments/20020611/6ecef563/attachment.sig>


More information about the linux-lvm mailing list