[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