Beefy Boxes and Bandwidth Generously Provided by pair Networks
Perl: the Markov chain saw
 
PerlMonks  

Problem in connecting to remote unix host via Net::SSH2 from windows machine

by Perl_abcd_monk (Initiate)
on Jun 11, 2017 at 15:57 UTC ( [id://1192534]=perlquestion: print w/replies, xml ) Need Help??

Perl_abcd_monk has asked for the wisdom of the Perl Monks concerning the following question:

Hi Monks

I installed the Net::SSH2 module from PPM and trying to connect to remote unix host from windows OS. After running the below code i am getting Error "LINE : Error: "pwd" is not a recognized command"

Below is the code and also the test result once after running the script.I unable to judge weather the script actually succeeded in connecting the host and failed only in executing the the command which i have assigned for $cmd variable in script.Monks, please assist me to figuring out what is actually happening and correct me where i am doing wrong in the script.This is my first post, please ignore if i have not fallowed any posting standards here.
BEGIN { push(@INC,'C:\Perl64\site\lib'); } use warnings; use strict; use NET::SSH2; sub is_sshalive; my $host = "XXXX"; # use the ip host to connect my $user = "yyyy"; # your account my $pass = "zzzz"; # your password my $cmd; my $ssh2 = Net::SSH2->new(); $ssh2->debug(1); if ($ssh2->connect($host)) { if ($ssh2->auth_keyboard($user,$pass)) { print "\n Executing command...\n"; $cmd = "pwd"; print " ==> Running $cmd\n"; if(is_sshalive($ssh2) == 1) { print "\nSSH connection died"; exit 1; } else { run_testsuite($cmd, $ssh2); } } else { warn "ssh auth failed.\n"; exit 1; } } else { warn "Unable to connect Host $host \n"; exit 1; } print "test passed done 0\n"; sub run_testsuite { my $cmd = $_[0]; my $ssh2 = $_[1]; my $chan2 = $ssh2->channel(); $chan2->shell(); print $chan2 "$cmd \n"; print "LINE : $_" while <$chan2>; $chan2->close; return 0; } sub is_sshalive { my $ssh2 = $_[0]; if ($ssh2->poll(1000) == 0) { return 0; # passed } else { return 1; #failed } } Below is the partial test result where it is displaying Error Net::SSH2::Channel::read(size = 1, ext = 0) - read 1 bytes - read 1 total LINE : Error: "pwd" is not a recognized command Net::SSH2::poll: timeout = 250, array[1] - [0] = channel - [0] events 1 - libssh2_poll returned 1 - [0] revents 1 Net::SSH2::Channel::read(size = 1, ext = 0)
  • Comment on Problem in connecting to remote unix host via Net::SSH2 from windows machine
  • Download Code

Replies are listed 'Best First'.
Re: Problem in connecting to remote unix host via Net::SSH2 from windows machine
by syphilis (Archbishop) on Jun 12, 2017 at 01:31 UTC
    I unable to judge weather the script actually succeeded in connecting the host and failed only in executing the the command which I have assigned for $cmd.

    Yes, I think the connection has succeeded and the error is coming from the Linux host - though I doubt very much that "pwd" is in fact unknown to that host.

    On Windows, I'm apparently not set-up to use the auth_keyboard authentication to my remote Linux host - instead of auth_keyboard, I use auth_pubkey.
    Then, in order to get your script to work, I have to slightly alter your run_testsuite() sub to:
    sub run_testsuite { my $cmd = $_[0]; my $ssh2 = $_[1]; my $chan2 = $ssh2->channel(); #$chan2->blocking(0); $chan2->exec($cmd); print "LINE : $_" while <$chan2>; $chan2->close; return 0; }
    Update: Actually, your original sub works fine for me so long as I precede the call to $chan2->shell(); with $chan2->blocking(0); .

    With $ssh2->debug(0), that outputs (as expected):
    Executing command... ==> Running pwd LINE : /home/sisyphus test passed done 0


    Maybe give that approach a go instead - if only to verify that your remote Linux host does understand "pwd".

    With $ssh2->debug(1) it outputs:
    Executing command... ==> Running pwd Net::SSH2::poll: timeout = 1000, array[0] libssh2_channel_open_ex(ss->session, mandatory_type, strlen(mandatory_ +type), window_size, packet_size, ((void *)0) , 0 ) -> 0x2a6e3c4 Net::SSH2::Channel::getc(ext = 0) Net::SSH2::Channel::getc(ext = 0) Net::SSH2::Channel::getc(ext = 0) Net::SSH2::Channel::getc(ext = 0) Net::SSH2::Channel::getc(ext = 0) Net::SSH2::Channel::getc(ext = 0) Net::SSH2::Channel::getc(ext = 0) Net::SSH2::Channel::getc(ext = 0) Net::SSH2::Channel::getc(ext = 0) Net::SSH2::Channel::getc(ext = 0) Net::SSH2::Channel::getc(ext = 0) Net::SSH2::Channel::getc(ext = 0) Net::SSH2::Channel::getc(ext = 0) Net::SSH2::Channel::getc(ext = 0) Net::SSH2::Channel::getc(ext = 0) LINE : /home/sisyphus Net::SSH2::Channel::DESTROY test passed done 0 Net::SSH2::DESTROY object 0x297d73c
    which is also quite correct, but confusingly verbose.

    If I include $chan2->blocking(0); (presently commented out), the debugging output becomes a little less verbose:
    Executing command... ==> Running pwd Net::SSH2::poll: timeout = 1000, array[0] libssh2_channel_open_ex(ss->session, mandatory_type, strlen(mandatory_ +type), window_size, packet_size, ((void *)0) , 0 ) -> 0x29ce3c4 Net::SSH2::Channel::getc(ext = 0) Net::SSH2::Channel::DESTROY test passed done 0 Net::SSH2::DESTROY object 0x28dd73c
    For your script, you could try setting blocking(0) and blocking(1) to see if that makes any difference. You might also try replacing:
    print $chan2 "$cmd \n";
    with:
    print $chan2 "$cmd\n";
    And try anything else you can think of ;-)

    Cheers,
    Rob
      Actually, your original sub works fine for me so long as I precede the call to $chan2->shell(); with $chan2->blocking(0);

      Using non-blocking mode in that way is quite unreliable!

      The remote shell started by the shell method call runs a loop where it waits for new commands to be submitted and that's the reason why print "LINE : $_" while <$chan2> blocks; the remote shell is just waiting for a new command to arrive in order to execute it. It nevers sends the EOF which would terminate the while.

      Setting non-blocking mode causes <$chan2> to read data immediately available. So you depend on the remote command and the SSH talk on the network bringing its output faster than the perl script reading it.

      The right way to handle that is to look for the shell prompt to arrive (you have to ensure it can not appear in the command output), or to make the remote command generate its output in some way such that its end can be detected (i.e. appending some marker, preppending the length, using chunk-encoding, etc.).

        Using non-blocking mode in that way is quite unreliable!

        Thanks for pointing that out.
        The shell() method is something that I prefer to avoid and, in light of your explanation, I think I'll continue trying to avoid it.

        Cheers,
        Rob
Re: Problem in connecting to remote unix host via Net::SSH2 from windows machine
by kevbot (Vicar) on Jun 11, 2017 at 18:45 UTC
    Can you manually login to the remote system using shh and run pwd at the command prompt? Does it succeed, or do you get an error message?

Log In?
Username:
Password:

What's my password?
Create A New User
Domain Nodelet?
Node Status?
node history
Node Type: perlquestion [id://1192534]
Approved by davies
Front-paged by Corion
help
Chatterbox?
and the web crawler heard nothing...

How do I use this?Last hourOther CB clients
Other Users?
Others contemplating the Monastery: (4)
As of 2024-04-24 19:16 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?

    No recent polls found