From 7e20228f4abf509e883093b79bf1f842b092f63b Mon Sep 17 00:00:00 2001 From: Peter Mikus Date: Wed, 9 May 2018 06:16:31 +0000 Subject: [PATCH] FIX: SSH connect issue error: [Errno 9] Bad file descriptor Change-Id: I4c5278d41e979f6af43054e3b5890fb154555494 Signed-off-by: Peter Mikus --- resources/libraries/python/VatExecutor.py | 11 +++++----- resources/libraries/python/ssh.py | 36 ++++++++++++------------------- 2 files changed, 19 insertions(+), 28 deletions(-) diff --git a/resources/libraries/python/VatExecutor.py b/resources/libraries/python/VatExecutor.py index d27e0677d3..8c3805c5c3 100644 --- a/resources/libraries/python/VatExecutor.py +++ b/resources/libraries/python/VatExecutor.py @@ -204,7 +204,6 @@ class VatTerminal(object): __LINUX_PROMPT = (":~$ ", "~]$ ", "~]# ") def __init__(self, node, json_param=True): - """TODO: Should we document this constructor can raise RuntimeError?""" json_text = ' json' if json_param else '' self.json = json_param self._node = node @@ -212,7 +211,7 @@ class VatTerminal(object): self._ssh.connect(self._node) try: self._tty = self._ssh.interactive_terminal_open() - except IOError: + except Exception: raise RuntimeError("Cannot open interactive terminal on node {0}". format(self._node)) @@ -222,7 +221,7 @@ class VatTerminal(object): self._tty, 'sudo -S {0}{1}'.format(Constants.VAT_BIN_NAME, json_text), self.__VAT_PROMPT) - except IOError: + except Exception: continue else: break @@ -254,9 +253,9 @@ class VatTerminal(object): """Execute command on the opened VAT terminal. :param cmd: Command to be executed. + :returns: Command output in python representation of JSON format or None if not in JSON mode. - :raise RuntimeError: If VAT command execution fails. """ VatHistory.add_to_vat_history(self._node, cmd) logger.debug("Executing command in VAT terminal: {0}".format(cmd)) @@ -264,7 +263,7 @@ class VatTerminal(object): out = self._ssh.interactive_terminal_exec_command(self._tty, cmd, self.__VAT_PROMPT) self.vat_stdout = out - except IOError: + except Exception: self._exec_failure = True vpp_pid = get_vpp_pid(self._node) if vpp_pid: @@ -346,4 +345,4 @@ class VatTerminal(object): for line_tmpl in cmd_template: vat_cmd = line_tmpl.format(**args) ret.append(self.vat_terminal_exec_cmd(vat_cmd.replace('\n', ''))) - return ret + return ret \ No newline at end of file diff --git a/resources/libraries/python/ssh.py b/resources/libraries/python/ssh.py index fe4404b053..5ff1b2d769 100644 --- a/resources/libraries/python/ssh.py +++ b/resources/libraries/python/ssh.py @@ -92,11 +92,11 @@ class SSH(object): format(self._ssh.get_transport().getpeername())) logger.debug('Connections: {0}'. format(str(SSH.__existing_connections))) - except RuntimeError as exc: + except: if attempts > 0: self._reconnect(attempts-1) else: - raise exc + raise def disconnect(self, node): """Close SSH connection to the node. @@ -236,8 +236,8 @@ class SSH(object): def interactive_terminal_open(self, time_out=30): """Open interactive terminal on a new channel on the connected Node. - FIXME: Convert or document other possible exceptions, such as - socket.error or SSHException. + :param time_out: Timeout in seconds. + :returns: SSH channel with opened terminal. .. warning:: Interruptingcow is used here, and it uses signal(SIGALRM) to let the operating system interrupt program @@ -245,10 +245,6 @@ class SSH(object): handlers only apply to the main thread, so you cannot use this from other threads. You must not use this in a program that uses SIGALRM itself (this includes certain profilers) - - :param time_out: Timeout in seconds. - :returns: SSH channel with opened terminal. - :raise IOError: If receive attempt results in socket.timeout. """ chan = self._ssh.get_transport().open_session() chan.get_pty() @@ -268,8 +264,7 @@ class SSH(object): break except socket.timeout: logger.error('Socket timeout: {0}'.format(buf)) - # TODO: Find out which exception would callers appreciate here. - raise IOError('Socket timeout: {0}'.format(buf)) + raise Exception('Socket timeout: {0}'.format(buf)) return chan def interactive_terminal_exec_command(self, chan, cmd, prompt): @@ -277,19 +272,18 @@ class SSH(object): interactive_terminal_open() method has to be called first! + :param chan: SSH channel with opened terminal. + :param cmd: Command to be executed. + :param prompt: Command prompt, sequence of characters used to + indicate readiness to accept commands. + :returns: Command output. + .. warning:: Interruptingcow is used here, and it uses signal(SIGALRM) to let the operating system interrupt program execution. This has the following limitations: Python signal handlers only apply to the main thread, so you cannot use this from other threads. You must not use this in a program that uses SIGALRM itself (this includes certain profilers) - - :param chan: SSH channel with opened terminal. - :param cmd: Command to be executed. - :param prompt: Command prompt, sequence of characters used to - indicate readiness to accept commands. - :returns: Command output. - :raise IOError: If receive attempt results in socket.timeout. """ chan.sendall('{c}\n'.format(c=cmd)) buf = '' @@ -305,9 +299,8 @@ class SSH(object): except socket.timeout: logger.error('Socket timeout during execution of command: ' '{0}\nBuffer content:\n{1}'.format(cmd, buf)) - # TODO: Find out which exception would callers appreciate here. - raise IOError('Socket timeout during execution of command: ' - '{0}\nBuffer content:\n{1}'.format(cmd, buf)) + raise Exception('Socket timeout during execution of command: ' + '{0}\nBuffer content:\n{1}'.format(cmd, buf)) tmp = buf.replace(cmd.replace('\n', ''), '') for item in prompt: tmp.replace(item, '') @@ -360,7 +353,6 @@ class SSH(object): def exec_cmd(node, cmd, timeout=600, sudo=False): """Convenience function to ssh/exec/return rc, out & err. - FIXME: Document :param, :type, :raise and similar. Returns (rc, stdout, stderr). """ if node is None: @@ -400,4 +392,4 @@ def exec_cmd_no_error(node, cmd, timeout=600, sudo=False): (ret_code, stdout, stderr) = exec_cmd(node, cmd, timeout=timeout, sudo=sudo) assert_equal(ret_code, 0, 'Command execution failed: "{}"\n{}'. format(cmd, stderr)) - return stdout, stderr + return stdout, stderr \ No newline at end of file -- 2.16.6