通过 perl 的 open2 执行时,telnet 命令输出未完全打印
telnet command output not completely printed when executing through open2 of perl
我是 perl 的新手。
我的目标:执行 telnet 命令并捕获完整输出
我的代码:
use IPC::Open2;
open2(\*RDR, \*WTR, "telnet host_name 8000 2>&1") or die ("could not contact host_name");
print WTR "$command\n";
print WTR "quit\n";
foreach my $line (<RDR>)
{
print $line."\n";
}
close RDR;
问题:通过putty执行telnet命令时,打印了12行以上的输出。但是通过这个 perl 脚本只打印了 3 行
解析尝试:
我试过 Expect,Net::Telnet,IO::Pty。但是由于安全原因,这些模块没有安装在我的 blade 服务器中。
问题:那么,在不使用这些有用的魔法模块的情况下,如何使用 perl 获得任何 telnet 命令的完整输出?输出缓冲区中的字符数是否有限制?
你什么都没说 $command
,但这对我有用。
use warnings 'all';
use strict;
use IPC::Open2;
my $host = 'google.com';
my $pid = open2(\*RDR, \*WTR, "telnet $host 80 2>&1")
or die "Can't contact $host: $!";
print WTR "GET\n";
print WTR "quit\n";
while (my $line = <RDR>)
{
print $line if $. <= 10; # print only first 10 lines
}
close RDR;
waitpid($pid, 0);
my $child_exit_status = $? >> 8; # check how it went
这会打印整页(没有 if ...
)。为方便起见,打印限制为 10 行。
请仔细阅读文档IPC::Open2,因为所有这些都涉及到。
open2()
returns the process ID of the child process. [...]
open2()
does not wait for and reap the child process after it exits. [...]
This whole affair is quite dangerous, as you may block forever. [...]
另见 IPC::Open3. A well-regarded module is IPC::Run, if possible to have installed. Also excellent is Tiny::Capture, see a very similar problem with its use in 。两者都非常有名,所以也许您的管理员可以接受它们。
我建议切换到词法文件句柄
my $pid = open2 my $read_fh, my $write_fh, "telnet $host 80 2>&1"
or die "Can't contact $host: $!";
并在整个过程中更改 RDR
和 WTR
。
我不知道 Windows 环境如何影响上述内容。这些模块会给人一些信心,但我不确定 open2
票价如何。另一个可能的罪魁祸首可能是缓冲,即使我看不到它在您的代码中的表现。以防万一,你可以试试
use IO::Handle;
STDERR->autoflush(1);
STDOUT->autoflush(1);
默认加载 IO::Handle
,我认为是从 v5.16 开始的。
还有关于此 in perlfaq5 的讨论,以及进一步阅读的链接。
但是,如果您确实遇到缓冲问题,则很可能是在另一端,如果没有模块,则可能不容易解决。引用骆驼
As mentioned, the IO::Pty
and Expect
modules provide a pseudo-tty device, giving you line-buffering without needing to modify the program on the end of the pipe.
我是 perl 的新手。
我的目标:执行 telnet 命令并捕获完整输出
我的代码:
use IPC::Open2;
open2(\*RDR, \*WTR, "telnet host_name 8000 2>&1") or die ("could not contact host_name");
print WTR "$command\n";
print WTR "quit\n";
foreach my $line (<RDR>)
{
print $line."\n";
}
close RDR;
问题:通过putty执行telnet命令时,打印了12行以上的输出。但是通过这个 perl 脚本只打印了 3 行
解析尝试: 我试过 Expect,Net::Telnet,IO::Pty。但是由于安全原因,这些模块没有安装在我的 blade 服务器中。
问题:那么,在不使用这些有用的魔法模块的情况下,如何使用 perl 获得任何 telnet 命令的完整输出?输出缓冲区中的字符数是否有限制?
你什么都没说 $command
,但这对我有用。
use warnings 'all';
use strict;
use IPC::Open2;
my $host = 'google.com';
my $pid = open2(\*RDR, \*WTR, "telnet $host 80 2>&1")
or die "Can't contact $host: $!";
print WTR "GET\n";
print WTR "quit\n";
while (my $line = <RDR>)
{
print $line if $. <= 10; # print only first 10 lines
}
close RDR;
waitpid($pid, 0);
my $child_exit_status = $? >> 8; # check how it went
这会打印整页(没有 if ...
)。为方便起见,打印限制为 10 行。
请仔细阅读文档IPC::Open2,因为所有这些都涉及到。
open2()
returns the process ID of the child process. [...]
open2()
does not wait for and reap the child process after it exits. [...]
This whole affair is quite dangerous, as you may block forever. [...]
另见 IPC::Open3. A well-regarded module is IPC::Run, if possible to have installed. Also excellent is Tiny::Capture, see a very similar problem with its use in
我建议切换到词法文件句柄
my $pid = open2 my $read_fh, my $write_fh, "telnet $host 80 2>&1"
or die "Can't contact $host: $!";
并在整个过程中更改 RDR
和 WTR
。
我不知道 Windows 环境如何影响上述内容。这些模块会给人一些信心,但我不确定 open2
票价如何。另一个可能的罪魁祸首可能是缓冲,即使我看不到它在您的代码中的表现。以防万一,你可以试试
use IO::Handle;
STDERR->autoflush(1);
STDOUT->autoflush(1);
默认加载 IO::Handle
,我认为是从 v5.16 开始的。
还有关于此 in perlfaq5 的讨论,以及进一步阅读的链接。
但是,如果您确实遇到缓冲问题,则很可能是在另一端,如果没有模块,则可能不容易解决。引用骆驼
As mentioned, the
IO::Pty
andExpect
modules provide a pseudo-tty device, giving you line-buffering without needing to modify the program on the end of the pipe.