4

I'm using Net::SSH::Perl to connect to remote server and execute commands. The problem is that it doesn't get timed out even if the remote server doesn't respond for a long time. I don't find any timeout option in Net::SSH::Perl.

Any help to achieve timeout is appreciated.

Note: I don't have the rights to modify Net/SSH/Perl.pm

Hema
  • 167
  • 4
  • 15

3 Answers3

4

Use the ConnectTimeout option.

Sample:

use Net::SSH::Perl;

my %params = ( protocol => "2,1",
                identity_files => ["/home/user/.ssh/test_id_dsa"],
                options => [    "BatchMode yes",
                                "ConnectTimeout 3",
                                "StrictHostKeyChecking no"],
                debug => 'true'
);

Also see: Net::SSH::Perl ConnectTimeout (ssh -o option)

Chankey Pathak
  • 21,187
  • 12
  • 85
  • 133
  • As per the link given, the user is trying the ConnectTimeout option in Net::SSH::Perl and it's not working. So, the temporary solution is to add setsockopt in Perl.pm. As I don't have the rights to modify Perl.pm, I can't implement it. Anyway, is the ConnectTimeout option working for you? – Hema Aug 28 '14 at 07:45
  • 1
    I didn't test it so I don't know whether this works on my machine or not. I use Net::OpenSSH, you can try using that. Also see this: http://stackoverflow.com/a/2851593/257635 – Chankey Pathak Aug 28 '14 at 09:48
  • 1
    Even if this option had been implemented in Net::SSH::Perl, it wouldn't have helped the author. It defines a ConnectTimeout, e.g. the timeout for establishing a connection, and what the author wants is actually ServerAliveInterval, which is not implemented in Net::SSH::Perl also. – afenster Sep 03 '14 at 07:46
  • Or maybe I'm wrong and the author really needs to detect a connection timeout, not the keep-alive timeout. In such case ConnectTimeout would have helped of course (if Net::SSH::Perl supported it, but it doesn't). – afenster Sep 03 '14 at 07:57
2

As I see from your %params, you use the DSA key to authenticate on the remote server. Do you really need to use the native Perl SSH implementation that Net::SSH::Perl provides? It is useful in some cases where you cannot just wrap the regular ssh call (e.g. if you need to provide a clear-text password for connecting to the server), but it lacks so many useful SSH options—you've just found one of them.

I suggest that you try to use Net::SSH instead (which is a very simple wrapper to the system's ssh binary) and give it a ConnectTimeout and ServerAliveInterval options with -o, or Net::OpenSSH which is referred by @ChankeyPathak above and use its check_master method (as I understand from the description, it looks like what you need).

The ssh_config(1) manual has a good description of ConnectTimeout (which detects timeouts when establishing the connection) and TCPKeepAlive and ServerAliveInterval (which detect timeouts on the established connection).

For your reference: here is a complete list of options implemented in Net::SSH::Perl, grabbed from its Config.pm. If you do need to use any other option not listed here, use some other SSH module.

BindAddress
Host
BatchMode
ChallengeResponseAuthentication
Cipher
Ciphers
Compression
CompressionLevel
DSAAuthentication
GlobalKnownHostsFile
HostKeyAlgorithms
HostName
IdentityFile
NumberOfPasswordPrompts
PasswordAuthentication
PasswordPromptHost
PasswordPromptLogin
Port
Protocol
RhostsAuthentication
RhostsRSAAuthentication
RSAAuthentication
StrictHostKeyChecking
UsePrivilegedPort
User
UserKnownHostsFile
afenster
  • 3,468
  • 19
  • 26
1

I had a similar issue. I was executing a command that did not terminate for whatever reason. So I wrapped the call to $ssh->cmd in an eval with an alarm as documented in perldoc -f alarm. Not the nicest solution but the only option since I can't modify the command I was calling.