我有以下代码(较大脚本的一部分)
my $lsn = IO::Socket::INET->new(Listen => 1, LocalPort => 0); # just use any available port.
$port = $lsn->sockport();
我收到错误Can't call method "sockport" on an undefined value
。
IO::Socket::INET
的文档在这个问题上没有说太多:https://perldoc.perl.org/IO/Socket/INET.html(有没有更好看的地方?不太熟悉这个模块)。
奇怪的是,我最近更改了这个,在它传递了一个非零的,随机生成的端口号,并且当端口被使用时有时会中断。
我测试了在本地Windows机器上传递0
(再次,文档似乎没有提到如何选择要绑定的端口),这似乎使它'选择任何可用的port',这是我想要的,但也许它在Solaris上出现不同(发生此问题的地方)?
答案 0 :(得分:5)
IO::Socket::INET->new
与大多数Perl构造函数一样:它在成功时返回类的实例,在错误时返回false值。有一些侧面渠道来获取错误原因。究竟什么错误值是故意没有记录的,重要的是它是错误的。
这导致了一般模式my $obj = Class->new or die $reason;
。在IO :: Socket的情况下,您从$@
得到错误(这非常粗略)。
my $port = 999;
my $lsn = IO::Socket::INET->new(Listen => 1, LocalPort => $port)
or die "Couldn't listen on port $port: $@";
# Couldnt listen on port 999: Permission denied at -e line 1.
我测试了在我的本地Windows机器上传递0(再次,文档似乎没有提到如何让它选择要绑定的端口),这似乎使它'选择任何可用端口',是我想要的,但也许它在Solaris上出现不同(发生此问题的地方)?
是的,这是特定于实现的。 IO :: Socket :: INET只是Socket库周围的一个薄层,使用bind
。如果您通过bind
端口0,它将为您找到一个端口。对于所有现代实现,这通常都是正确的。
Windows bind
...
对于TCP / IP,如果端口指定为零,则服务提供商从动态客户端端口范围为应用程序分配唯一端口。在Windows Vista及更高版本中,动态客户端端口范围是介于49152和65535之间的值。这是对Windows Server 2003及更早版本的更改,其中动态客户端端口范围是介于1025和5000之间的值。
答案 1 :(得分:0)
是否尝试绑定到特权端口(在小于1024的Solaris上)?如果是这样,它可能是权限问题,并且需要root访问权限才能绑定。