Home | History | Annotate | Download | only in interconnect
      1 /*
      2  * CDDL HEADER START
      3  *
      4  * The contents of this file are subject to the terms of the
      5  * Common Development and Distribution License (the "License").
      6  * You may not use this file except in compliance with the License.
      7  *
      8  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
      9  * or http://www.opensolaris.org/os/licensing.
     10  * See the License for the specific language governing permissions
     11  * and limitations under the License.
     12  *
     13  * When distributing Covered Code, include this CDDL HEADER in each
     14  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
     15  * If applicable, add the following below this CDDL HEADER, with the
     16  * fields enclosed by brackets "[]" replaced with your own identifying
     17  * information: Portions Copyright [yyyy] [name of copyright owner]
     18  *
     19  * CDDL HEADER END
     20  */
     21 
     22 /*
     23  * Copyright 2008 Sun Microsystems, Inc.  All rights reserved.
     24  * Use is subject to license terms.
     25  *
     26  * ident	"@(#)SwitchLogic.java	1.43	08/10/16 SMI"
     27  */
     28 
     29 package com.sun.jist.interconnect;
     30 import com.sun.jist.JISTLogic;
     31 import com.sun.jist.interconnect.SwitchType;
     32 
     33 /**
     34  * JIST Switch Port Management.
     35  * <p>
     36  * This is used during fault injection to disable/enable/cycle/status on the
     37  * following switches:
     38  * <ul>
     39  * <li><a
     40  * href="http://apc.com/resource/include/techspec_index.cfm?base_sku=AP7921">
     41  *    APC Switched Rack PDU v2.7.0 and v3.3.4 firmware</a></li>
     42  * <li>Brocade 2Gb and 4Gb FC Switch Port(s)</li>
     43  * <li>Cisco 10Mb/100Mb/1Gb/10Gb Ethernet Switch Port(s)</li>
     44  * <li>Extreme 10Mb/100Mb/1Gb/10Gb Ethernet Switch Port(s)</li>
     45  * <li>McData 2Gb and 4Gb FC Switch Port(s)</li>
     46  * <li>QLogic 2Gb and 4Gb FC Switch Port(s)</li>
     47  * </ul>
     48  * <p>
     49  * The port number is specified as follows:
     50  * <ul>
     51  * <li>"0", "1", "2", etc... for Brocade, McData, & QLogic Switches.</li>
     52  * <li>"1/0/1", "1/0/2", "1/0/3", etc... for Cisco Switches.</li>
     53  * <li>"???", "???", "???", etc... for Extreme Switches.</li>
     54  * <li>"all" for all ports.</li>
     55  * </ul>
     56  * <p>
     57  * In order to establish communications with the Switch(es), the ISO-Latin
     58  * Character Set "ISO-8859-1" needs to be installed on the host executing
     59  * this class.
     60  * <p>
     61  * @author	Joel.Buckley (at) Sun.COM
     62  * @since	5.0
     63  */
     64 public class SwitchLogic extends JISTLogic {
     65 
     66 /** Declare & Initialize "public final static" Constants. */
     67 
     68 /** Declare "static" Class Variables. */
     69 
     70 /** Declare non-"static" Instance Variables. */
     71 
     72 /**
     73  * JIST Switch Logic Cycle Delay.
     74  * <p>
     75  * This is used to delay, in seconds, a port enable after a port disable is
     76  * run in cycle() method.
     77  * <p>
     78  * Set with Java Environment Parameter "cycleDelay=0".
     79  */
     80 public final int cycleDelay;
     81 
     82 /**
     83  * JIST Switch Logic Retry Delay.
     84  * <p>
     85  * This is used to delay, in seconds, a port status recheck after a check
     86  * for a status change fails in the ensure() method.
     87  * <p>
     88  * Set with Java Environment Parameter "retryDelay=3".
     89  */
     90 public final int retryDelay;
     91 
     92 /**
     93  * JIST Switch Logic Enable & Disable Max Retry.
     94  * <p>
     95  * This is used to determine the maximum number of times a failed port disable
     96  * or enable will be retried.
     97  * <p>
     98  * Set with Java Environment Parameter "retryMax=3".
     99  */
    100 public final int retryMax;
    101 
    102 /**
    103  * Switch Type (0)Unknown, (1)Brocade, (2)McData, (3)Qlogic, (4)Cisco,
    104  * (5)Extreme, or (6)APC.
    105  */
    106 private SwitchType switchType;
    107 
    108 /** Switch Hostname. */
    109 private final String host;
    110 
    111 /** Switch Command. */
    112 private final String command;
    113 
    114 /**
    115  * Switch Port.
    116  * <p>
    117  * For Brocade, McData, or QLogic Switches, port number is an integer such as
    118  * "0", "1", "2", etc.
    119  * <p>
    120  * For Cisco Switches, port number is a "#/#/#" sequence, such as "1/0/1",
    121  * "1/0/2", "1/0/3", etc.
    122  */
    123 private final String port;
    124 
    125 /** Switch loginid, default of "admin". */
    126 private final String user;
    127 
    128 /** Switch password, default of "password". */
    129 private final String pswd;
    130 
    131 /** Switch Type Command Prompt used throughout session. */
    132 private String switchPrompt;
    133 
    134 /** Initialize "static" Class Variables. */
    135 static {
    136         /** Booleans. */
    137 
    138         /** I/O Paths. */
    139 
    140         /** Test Settings. */
    141 
    142         /** Internal Variables - long. */
    143 
    144         /** Internal Variables - int. */
    145 
    146         /** Internal Variables - short. */
    147 
    148         /** Internal Variables - byte. */
    149 
    150         /** Internal Variables - Arrays. */
    151 
    152         /** Internal Variables - String. */
    153 
    154         /** Internal Variables - misc. */
    155 }
    156 
    157 /** Initialize non-"static" Instance Variables. */
    158 {
    159         /** Booleans. */
    160 
    161         /** I/O Paths. */
    162 
    163         /** Test Settings. */
    164 	cycleDelay = getIntProperty("cycleDelay", 0);
    165 	retryDelay = getIntProperty("retryDelay", 3);
    166 	retryMax = getIntProperty("retryMax", 3);
    167 	host = getStringProperty("host", UNSET);
    168 	command = getStringProperty("hostCommand", UNSET);
    169 	port = getStringProperty("hostPort", UNSET);
    170 	user = getStringProperty("hostUser", "admin");
    171 	pswd = getStringProperty("hostPassword", "password");
    172 
    173         /** Internal Variables - long. */
    174 
    175         /** Internal Variables - int. */
    176 
    177         /** Internal Variables - short. */
    178 
    179         /** Internal Variables - byte. */
    180 	switchType = null;
    181 
    182         /** Internal Variables - Arrays. */
    183 
    184         /** Internal Variables - String. */
    185 	setBranch("Switch Management");
    186 	loginPrompt = "SWITCH-NOT-LOGGED-IN-YET";
    187 	switchPrompt = "#";
    188 
    189         /** Internal Variables - misc. */
    190 }
    191 
    192 /**
    193  * Default Constructor.
    194  */
    195 public SwitchLogic() {}
    196 
    197 /**
    198  * Method used to detect offshoot Test Branches.
    199  * <p>
    200  * All methods with signature
    201  * "<FONT SIZE="-1"><CODE>public void test*(void)</CODE></FONT>" in this class
    202  * or this class' parent classes are automatically detected.
    203  * <p>
    204  * @see JISTLogic#getTree(String)
    205  * @see JISTLogic#getTree(String[])
    206  */
    207 public static String[] getTree() {
    208 	return (getTree("com.sun.jist.interconnect.SwitchLogic"));
    209 }
    210 
    211 /**
    212  * Method used before Test Case Execution.
    213  */
    214 public void setUp() {
    215 	super.setUp();
    216 
    217 	compare("Switch Hostname or IP Address", UNSET, "!=", host);
    218 	compare("Switch Command", UNSET, "!=", command);
    219 	compare("Switch Port", UNSET, "!=", port);
    220 }
    221 
    222 /**
    223  * Method used after Test Case Execution.
    224  */
    225 protected void tearDown() {
    226 	super.tearDown();
    227 }
    228 
    229 /**
    230  * Main method used to start {@link JISTLogic#execute Test Tree Execution}.
    231  * <p>
    232  * @see JISTLogic#getTree Test Tree Discovery.
    233  * @see JISTLogic#execute Test Tree Execution.
    234  * @param   args      Command Line Options.
    235  */
    236 public static void main(String[] args) {
    237 	switch (args.length) {
    238 	case(5):
    239 		System.setProperty("hostPassword", args[4]);
    240 		System.setProperty("hostUser", args[3]);
    241 		System.setProperty("hostPort", args[2]);
    242 		System.setProperty("hostCommand", args[1]);
    243 		System.setProperty("host", args[0]);
    244 		break;
    245 	case(3):
    246 		System.setProperty("hostPort", args[2]);
    247 		System.setProperty("hostCommand", args[1]);
    248 		System.setProperty("host", args[0]);
    249 		break;
    250 	default:
    251 		System.err.println(getMsg(510));
    252 		return;
    253 	}
    254 	execute("com.sun.jist.interconnect.SwitchLogic");
    255 }
    256 
    257 /**
    258  * Default test to handle executing switch management tests.
    259  */
    260 public void testDefault() {
    261 	setLeaf(getBranch(), "Generic Test");
    262 	if (login()) {
    263 		if (command.equals("status") && port.equals("all")) {
    264 			statusall();
    265 		} else if (command.equals("status")) {
    266 			status(port);
    267 		} else if (command.equals("disable") && port.equals("all")) {
    268 			tester.passfailBoolean = disableall();
    269 		} else if (command.equals("disable")) {
    270 			tester.passfailBoolean = disable(port);
    271 		} else if (command.equals("enable") && port.equals("all")) {
    272 			tester.passfailBoolean = enableall();
    273 		} else if (command.equals("enable")) {
    274 			tester.passfailBoolean = enable(port);
    275 		} else if (command.equals("cycle")) {
    276 			tester.passfailBoolean = cycle(port);
    277 		} else {
    278 			log(FAULT, "Invalid Command", command);
    279 			log(MILESTONE, "Correct Usage", getMsg(510));
    280 			tester.passfailBoolean = false;
    281 		}
    282 	}
    283 	logout();
    284 	assertTrue(passfailBoolean);
    285 }
    286 
    287 /**
    288  * Establish communications with the Fibre Channel Switch.
    289  * <p>
    290  * @return success Success of login process.
    291  */
    292 public final boolean login() {
    293 	String message;
    294 
    295 	log(MILESTONE, getMsg(532), getMsg(903));
    296 	if (!openCharSocket(this, host, 23)) {
    297 		close(this);
    298 		return (tester.passfailBoolean = false);
    299 	}
    300 
    301 	log(MILESTONE, getMsg(532), getMsg(533));
    302 	if ((message = seek("[(login)(Username)(User Name )(Password)]:"))
    303 	    == null) {
    304 		log(FAULT, getMsg(531), getMsg(989));
    305 		close(this);
    306 		return (tester.passfailBoolean = false);
    307 	} else if (message.indexOf("User Name :") >= 0) {
    308 		switchType = SwitchType.APCv2;
    309 	} else if (message.indexOf("Password:") >= 0) {
    310 		switchType = SwitchType.CISCO;
    311 	} else if (message.indexOf("Fabric OS") >= 0) {
    312 		switchType = SwitchType.BROCADE;
    313 	} else if (message.indexOf("Username:") >= 0) {
    314 		switchType = SwitchType.MCDATA;
    315 	} else if (message.matches("(?s).*[(Sanbox2)(switch)].*")) {
    316 		switchType = SwitchType.QLOGIC;
    317 	} else if (message.indexOf("Sorry") >= 0) {
    318 		log(FAULT, getMsg(532), getMsg(534));
    319 		close(this);
    320 		return (tester.passfailBoolean = false);
    321 	} else {
    322 		log(FAULT, getMsg(532), getMsg(535));
    323 		close(this);
    324 		return (tester.passfailBoolean = false);
    325 	}
    326 	log(PASS, getMsg(536) + switchType.toString(), message);
    327 
    328 	switchPrompt = switchType.getCommandPrompt();
    329 	loginPrompt = switchType.getLoginPrompt();
    330 	if (switchType != SwitchType.CISCO) {
    331 		write(user + newline);
    332 
    333 		log(MILESTONE, getMsg(532), getMsg(537));
    334 		seek("Password\\s*:");
    335 	}
    336 	write(pswd + newline);
    337 
    338 	log(MILESTONE, getMsg(532), getMsg(538));
    339 	if ((message = seek(switchPrompt)).matches(loginPrompt)) {
    340 		log(FAULT, getMsg(539), getMsg(902));
    341 		close(this);
    342 		return (tester.passfailBoolean = false);
    343 	} else if (switchType == SwitchType.APCv2 &&
    344 	    message.matches("(?s).*AOS\\s+v3.3.4.*")) {
    345 		switchType = SwitchType.APCv3;
    346 		log(PASS, getMsg(536) + switchType.toString(), message);
    347 	} else {
    348 		log(PASS, getMsg(532), message);
    349 	}
    350 
    351 	if (switchType == SwitchType.APCv3) {
    352 		log(MILESTONE, getMsg(532), getMsg(562));
    353 		write("1" + newline);
    354 		log(MILESTONE, getMsg(540), seek(switchPrompt));
    355 		log(MILESTONE, getMsg(532), getMsg(563));
    356 		write("2" + newline);
    357 		log(MILESTONE, getMsg(540), seek(switchPrompt));
    358 		write("1" + newline);
    359 		log(MILESTONE, getMsg(540), message = seek(switchPrompt));
    360 		if (message.contains("Press <ENTER> ")) {
    361 			write(newline);
    362 			log(MILESTONE, getMsg(540), seek(switchPrompt));
    363 		}
    364 	} else if (switchType == SwitchType.APCv2) {
    365 		log(MILESTONE, getMsg(532), getMsg(562));
    366 		write("1" + newline);
    367 		log(MILESTONE, getMsg(540), seek(switchPrompt));
    368 		log(MILESTONE, getMsg(532), getMsg(563));
    369 		write("3" + newline);
    370 		log(MILESTONE, getMsg(540), message = seek(switchPrompt));
    371 		if (message.contains("Press <ENTER> ")) {
    372 			write(newline);
    373 			log(MILESTONE, getMsg(540), seek(switchPrompt));
    374 		}
    375 	} else if (switchType == SwitchType.CISCO) {
    376 		log(MILESTONE, getMsg(532), getMsg(550));
    377 		write("enable" + newline);
    378 		switchPrompt = "#";
    379 		log(PASS, getMsg(550), message = seek("Password:"));
    380 		if (message.matches("(?s).*Password:.*")) {
    381 			write(pswd + newline);
    382 			log(PASS, getMsg(550), seek(switchPrompt));
    383 		}
    384 	} else if (switchType == SwitchType.QLOGIC) {
    385 		log(MILESTONE, getMsg(532), getMsg(540));
    386 		write("admin start" + newline);
    387 		log(PASS, getMsg(540), seek(switchPrompt));
    388 	}
    389 
    390 	log(MILESTONE, getMsg(532), getMsg(905));
    391 	return (true);
    392 }
    393 
    394 /** Cleanup communication resources with the Fibre Channel Switch. */
    395 public final void logout() {
    396 	log(MILESTONE, getMsg(541), getMsg(903));
    397 	if (switchType == SwitchType.APCv3) {
    398 		log(MILESTONE, getMsg(542), getMsg(573));
    399 		write("" + (char)0x01b);
    400 		log(MILESTONE, getMsg(542), seek(switchPrompt));
    401 		write("" + (char)0x01b);
    402 		log(MILESTONE, getMsg(542), seek(switchPrompt));
    403 		log(MILESTONE, getMsg(542), getMsg(574));
    404 		write("" + (char)0x01b);
    405 		log(MILESTONE, getMsg(542), seek(switchPrompt));
    406 		write(switchType.getLogoutCommand() + newline);
    407 	} else if (switchType == SwitchType.APCv2) {
    408 		log(MILESTONE, getMsg(542), getMsg(573));
    409 		write("" + (char)0x01b);
    410 		log(MILESTONE, getMsg(542), seek(switchPrompt));
    411 		log(MILESTONE, getMsg(542), getMsg(574));
    412 		write("" + (char)0x01b);
    413 		log(MILESTONE, getMsg(542), seek(switchPrompt));
    414 		write(switchType.getLogoutCommand() + newline);
    415 	} else if (switchType == SwitchType.CISCO) {
    416 		log(MILESTONE, getMsg(542), getMsg(561));
    417 		write("disable" + newline);
    418 		switchPrompt = host; // switchPrompt.getCommandPrompt();
    419 		log(PASS, getMsg(561), seek(switchPrompt));
    420 		write(switchType.getLogoutCommand() + newline);
    421 	} else if (switchType == SwitchType.QLOGIC) {
    422 		log(MILESTONE, getMsg(541), getMsg(542));
    423 		write("admin stop" + newline);
    424 		log(PASS, getMsg(542), seek(switchPrompt));
    425 		write(switchType.getLogoutCommand() + newline);
    426 	} else {
    427 		write(switchType.getLogoutCommand() + newline);
    428 	}
    429 	close(this);
    430 	log(MILESTONE, getMsg(541), getMsg(905));
    431 }
    432 
    433 /**
    434  * Cycle (Disable/Sleep/Enable) a specific port on the switch.
    435  * <p>
    436  * @param port Fibre Channel Switch Port.
    437  * @return report Report of port cycle.
    438  */
    439 public final boolean cycle(String port) {
    440 	log(MILESTONE, getMsg(543), getMsg(903));
    441 	if (!disable(port)) {
    442 		log(FAULT, getMsg(543), getMsg(902));
    443 		return (tester.passfailBoolean = false);
    444 	}
    445 	if (cycleDelay > 0) {
    446 		log(PASS, getMsg(544), cycleDelay + " sec.");
    447 		try {
    448 			Thread.currentThread().sleep(cycleDelay * 1000);
    449 		} catch (InterruptedException ie) {}
    450 	}
    451 	if (!enable(port)) {
    452 		log(FAULT, getMsg(543), getMsg(902));
    453 		return (tester.passfailBoolean = false);
    454 	}
    455 	log(MILESTONE, getMsg(543), getMsg(905));
    456 	return (true);
    457 }
    458 
    459 /**
    460  * Disable all ports on the switch.
    461  * <p>
    462  * @return report Report of port disable.
    463  */
    464 public final boolean disableall() {
    465 	String command = "";
    466 	log(MILESTONE, getMsg(545), getMsg(903));
    467 	if (switchType == SwitchType.BROCADE) {
    468 		command = "switchDisable\r";
    469 	} else {
    470 		log(FAULT, getMsg(535), switchType.toString());
    471 		return (tester.passfailBoolean = false);
    472 	}
    473 
    474 	if (!log(SENT, getMsg(545), command) ||
    475 	    !write(command) ||
    476 	    !log(MILESTONE, getMsg(545), seek(switchPrompt))) {
    477 		log(FAULT, getMsg(545), getMsg(902));
    478 		return (tester.passfailBoolean = false);
    479 	}
    480 	log(MILESTONE, getMsg(545), getMsg(905));
    481 	return (true);
    482 }
    483 
    484 /**
    485  * Enable all ports on the switch.
    486  * <p>
    487  * @return report Report of port disable.
    488  */
    489 public final boolean enableall() {
    490 	String command = "";
    491 	log(MILESTONE, getMsg(546), getMsg(903));
    492 	if (switchType == SwitchType.BROCADE) {
    493 		command = "switchEnable\r";
    494 	} else {
    495 		log(FAULT, getMsg(535), switchType.toString());
    496 		return (tester.passfailBoolean = false);
    497 	}
    498 
    499 	if (!log(SENT, getMsg(546), command) ||
    500 	    !write(command) ||
    501 	    !log(MILESTONE, getMsg(546), seek(switchPrompt))) {
    502 		log(FAULT, getMsg(546), getMsg(902));
    503 		return (tester.passfailBoolean = false);
    504 	}
    505 	log(MILESTONE, getMsg(546), getMsg(905));
    506 	return (true);
    507 }
    508 
    509 /**
    510  * Disable a specific port on the switch.
    511  * <p>
    512  * @param port Fibre Channel Switch Port.
    513  * @return report Report of port disable.
    514  */
    515 public final boolean disable(String port) {
    516 	String command = "";
    517 	log(MILESTONE, getMsg(545), getMsg(903));
    518 	if (switchType == SwitchType.APCv3 ||
    519 	    switchType == SwitchType.APCv2) {
    520 		write(port + newline);
    521 		log(MILESTONE, getMsg(564), seek(switchPrompt));
    522 		write("1" + newline);
    523 		log(MILESTONE, getMsg(565), seek(switchPrompt));
    524 		write("2" + newline);
    525 		log(MILESTONE, getMsg(566), seek("cancel"));
    526 		write("yes" + newline);
    527 		log(MILESTONE, getMsg(568), seek("continue"));
    528 		write(newline);
    529 		log(MILESTONE, getMsg(569), seek(switchPrompt));
    530 		write("" + (char)0x01b);
    531 		log(MILESTONE, getMsg(571), seek(switchPrompt));
    532 		if (switchType == SwitchType.APCv3) {
    533 			write("" + (char)0x01b);
    534 			log(MILESTONE, getMsg(571), seek(switchPrompt));
    535 		}
    536 		write("" + (char)0x01b);
    537 		log(MILESTONE, getMsg(572), command = seek(switchPrompt));
    538 		if (command.contains("Press <ENTER> ")) {
    539 			write(newline);
    540 			log(MILESTONE, getMsg(572), seek(switchPrompt));
    541 		}
    542 		return (ensure(port, switchType.getDisabled()));
    543 	} else if (switchType == SwitchType.CISCO) {
    544 		write("configure terminal" + newline);
    545 		log(MILESTONE, getMsg(551), seek("(config)#"));
    546 		write("interface Gi" + port + newline);
    547 		log(MILESTONE, getMsg(552), seek("(config-if)#"));
    548 		log(SENT, getMsg(545), "shutdown");
    549 		write("shutdown" + newline);
    550 		log(MILESTONE, getMsg(545), seek("(config-if)#"));
    551 		write("exit" + newline);
    552 		log(MILESTONE, getMsg(559), seek("(config)#"));
    553 		write("exit" + newline);
    554 		log(MILESTONE, getMsg(560), seek(switchPrompt));
    555 		return (ensure(port, switchType.getDisabled()));
    556 	} else if (switchType == SwitchType.QLOGIC) {
    557 		command = "set port " + port + " state down" + newline;
    558 	} else if (switchType == SwitchType.MCDATA) {
    559 		command = "config port blocked " + port + " true" + newline;
    560 	} else if (switchType == SwitchType.BROCADE) {
    561 		command = "portdisable " + port + "\r";
    562 	}
    563 	if (!log(SENT, getMsg(545), command) ||
    564 	    !write(command) ||
    565 	    !log(MILESTONE, getMsg(545), seek(switchPrompt)) ||
    566 	    !ensure(port, switchType.getDisabled())) {
    567 		log(FAULT, getMsg(545), getMsg(902));
    568 		return (tester.passfailBoolean = false);
    569 	}
    570 	log(MILESTONE, getMsg(545), getMsg(905));
    571 	return (true);
    572 }
    573 
    574 /**
    575  * Enable a specific port on the Fibre Channel Switch.
    576  * <p>
    577  * @param port Fibre Channel Switch Port.
    578  * @return report Report of port enable.
    579  */
    580 public final boolean enable(String port) {
    581 	String command = "";
    582 	log(MILESTONE, getMsg(546), getMsg(903));
    583 	if (switchType == SwitchType.APCv3 ||
    584 	    switchType == SwitchType.APCv2) {
    585 		write(port + newline);
    586 		log(MILESTONE, getMsg(564), seek(switchPrompt));
    587 		write("1" + newline);
    588 		log(MILESTONE, getMsg(565), seek(switchPrompt));
    589 		write("1" + newline);
    590 		log(MILESTONE, getMsg(567), seek("cancel"));
    591 		write("yes" + newline);
    592 		log(MILESTONE, getMsg(568), seek("continue"));
    593 		write(newline);
    594 		log(MILESTONE, getMsg(569), seek(switchPrompt));
    595 		write("" + (char)0x01b);
    596 		log(MILESTONE, getMsg(571), seek(switchPrompt));
    597 		if (switchType == SwitchType.APCv3) {
    598 			write("" + (char)0x01b);
    599 			log(MILESTONE, getMsg(571), seek(switchPrompt));
    600 		}
    601 		write("" + (char)0x01b);
    602 		log(MILESTONE, getMsg(572), command = seek(switchPrompt));
    603 		if (command.contains("Press <ENTER> ")) {
    604 			write(newline);
    605 			log(MILESTONE, getMsg(572), seek(switchPrompt));
    606 		}
    607 		return (ensure(port, switchType.getEnabled()));
    608 	} else if (switchType == SwitchType.CISCO) {
    609 		write("configure terminal" + newline);
    610 		log(MILESTONE, getMsg(551), seek("(config)#"));
    611 		write("interface Gi" + port + newline);
    612 		log(MILESTONE, getMsg(552), seek("(config-if)#"));
    613 		log(SENT, getMsg(546), "no shutdown");
    614 		write("no shutdown" + newline);
    615 		log(MILESTONE, getMsg(546), seek("(config-if)#"));
    616 		write("exit" + newline);
    617 		log(MILESTONE, getMsg(559), seek("(config)#"));
    618 		write("exit" + newline);
    619 		log(MILESTONE, getMsg(560), seek(switchPrompt));
    620 		return (ensure(port, switchType.getEnabled()));
    621 	} else if (switchType == SwitchType.QLOGIC) {
    622 		command = "set port " + port + " state online" + newline;
    623 	} else if (switchType == SwitchType.MCDATA) {
    624 		command = "config port blocked " + port + " false" + newline;
    625 	} else if (switchType == SwitchType.BROCADE) {
    626 		command = "portenable " + port + "\r";
    627 	}
    628 	if (!log(SENT, getMsg(546), command) ||
    629 	    !write(command) ||
    630 	    !log(MILESTONE, getMsg(546), seek(switchPrompt)) ||
    631 	    !ensure(port, switchType.getEnabled())) {
    632 		log(FAULT, getMsg(546), "Failed");
    633 		return (tester.passfailBoolean = false);
    634 	}
    635 	log(MILESTONE, getMsg(546), getMsg(905));
    636 	return (true);
    637 }
    638 
    639 /**
    640  * Ensure a specific port on the Fibre Channel Switch is disabled or enabled.
    641  * <p>
    642  * @param port Fibre Channel Switch Port.
    643  * @param ensureStatus Status to ensure.
    644  * @return report Report of port status check.
    645  */
    646 private final boolean ensure(String port, String ensureStatus) {
    647 	boolean success = false;
    648 	int retries = 0;
    649 	String statusNow;
    650 	while (running && retries <= retryMax) {
    651 		statusNow = status(port);
    652 		if (statusNow.matches(ensureStatus)) {
    653 			success = true;
    654 			break;
    655 		}
    656 		if (!log(MILESTONE, getMsg(547), "" + (++retries))) {
    657 			break;
    658 		}
    659 		if (retryDelay > 0) {
    660 			try {
    661 				Thread.currentThread().sleep(retryDelay * 1000);
    662 			} catch (InterruptedException ie) {
    663 			}
    664 		}
    665 	}
    666 	return (success);
    667 }
    668 
    669 /**
    670  * Status a specific port on the Fibre Channel Switch.
    671  * <p>
    672  * @param port Fibre Channel Switch Port.
    673  * @return report Report of port status.
    674  */
    675 public final String status(String port) {
    676 	String command = "", data = "";
    677 	log(MILESTONE, getMsg(548), getMsg(903));
    678 	if (switchType == SwitchType.APCv3 ||
    679 	    switchType == SwitchType.APCv2) {
    680 		command = port + newline;
    681 	} else if (switchType == SwitchType.CISCO) {
    682 		command = "show interface Gi" + port + " status" + newline;
    683 	} else if (switchType == SwitchType.QLOGIC) {
    684 		command = "show port " + port + newline;
    685 	} else if (switchType == SwitchType.MCDATA) {
    686 		command = "config port show " + port + newline;
    687 	} else if (switchType == SwitchType.BROCADE) {
    688 		command = "portshow " + port + "\r";
    689 	}
    690 	if (!log(SENT, getMsg(548), command) ||
    691 	    !write(command) ||
    692 	    !log(MILESTONE, getMsg(548), data = seek(switchPrompt))) {
    693 		log(FAULT, getMsg(548), getMsg(902));
    694 		tester.passfailBoolean = false;
    695 	} else {
    696 		log(MILESTONE, getMsg(548), getMsg(905));
    697 	}
    698 	if (switchType == SwitchType.APCv3 ||
    699 	    switchType == SwitchType.APCv2) {
    700 		write("" + (char)0x01b);
    701 		log(MILESTONE, getMsg(572), command = seek(switchPrompt));
    702 		if (command.contains("Press <ENTER> ")) {
    703 			write(newline);
    704 			log(MILESTONE, getMsg(572), seek(switchPrompt));
    705 		}
    706 	}
    707 	return (data);
    708 }
    709 
    710 /**
    711  * Status all ports on the Fibre Channel Switch.
    712  * <p>
    713  * @return report Report of all port status.
    714  */
    715 public final String statusall() {
    716 	String command = "", data = "";
    717 	log(MILESTONE, getMsg(549), getMsg(903));
    718 	if (switchType == SwitchType.APCv3 ||
    719 	    switchType == SwitchType.APCv2) {
    720 		command = newline;
    721 	} else if (switchType == SwitchType.QLOGIC) {
    722 		command = "show port" + newline;
    723 	} else if (switchType == SwitchType.MCDATA) {
    724 		command = "show port status" + newline;
    725 	} else if (switchType == SwitchType.BROCADE) {
    726 		command = "switchshow\r";
    727 	}
    728 	if (!log(SENT, getMsg(549), command) ||
    729 	    !write(command) ||
    730 	    !log(MILESTONE, getMsg(549), data = seek(switchPrompt))) {
    731 		log(FAULT, getMsg(549), getMsg(902));
    732 		tester.passfailBoolean = false;
    733 		return (data);
    734 	}
    735 	log(MILESTONE, getMsg(549), getMsg(905));
    736 	return (data);
    737 }
    738 
    739 } /* Class End */
    740