加入收藏 | 设为首页 | 会员中心 | 我要投稿 李大同 (https://www.lidatong.com.cn/)- 科技、建站、经验、云计算、5G、大数据,站长网!
当前位置: 首页 > 大数据 > 正文

如果客户端不再连接,Perl不会关闭TCP套接字?

发布时间:2020-12-16 06:20:16 所属栏目:大数据 来源:网络整理
导读:该应用程序的目的是侦听特定的UDP多播,然后将数据转发到连接到服务器的任何TCP客户端.代码工作正常,但在TCP客户端断开连接后,我的套接字没有关闭.套接字实用程序实用程序显示套接字保持打开状态,并且所有UDP数据继续转发到客户端.我认为问题在于“if($write-
该应用程序的目的是侦听特定的UDP多播,然后将数据转发到连接到服务器的任何TCP客户端.代码工作正常,但在TCP客户端断开连接后,我的套接字没有关闭.套接字实用程序实用程序显示套接字保持打开状态,并且所有UDP数据继续转发到客户端.我认为问题在于“if($write-> connected())”块,因为它总是返回true,即使TCP客户端不再连接.我使用标准的 Windows Telnet连接到服务器并查看数据.当我关闭telnet时,TCP套接字假设在服务器上关闭.

为什么connected()显示连接是活动的,即使它们不是?另外,我应该使用什么替代品呢?

码:

#!/usr/bin/perl

use IO::Socket::Multicast;
use IO::Socket;
use IO::Select;

my $tcp_port = "4550";
my $tcp_socket = IO::Socket::INET->new(
                                       Listen    => SOMAXCONN,LocalAddr => '0.0.0.0',LocalPort => $tcp_port,Proto     => 'tcp',ReuseAddr => 1,);
use Socket qw(IPPROTO_TCP TCP_NODELAY);
setsockopt( $tcp_socket,IPPROTO_TCP,TCP_NODELAY,1);

use constant GROUP => '239.2.0.81';
use constant PORT  => '6550';
my $udp_socket= IO::Socket::Multicast->new(Proto=>'udp',LocalPort=>PORT);
$udp_socket->mcast_add(GROUP) || die "Couldn't set group: $!n";

my $read_select  = IO::Select->new();
my $write_select = IO::Select->new();

$read_select->add($tcp_socket);
$read_select->add($udp_socket);

## Loop forever,reading data from the UDP socket and writing it to the
## TCP socket(s).  
while (1) {

    ## No timeout specified (see docs for IO::Select).  This will block until a TCP
    ## client connects or we have data.
    my @read = $read_select->can_read();

    foreach my $read (@read) {

        if ($read == $tcp_socket) {

            ## Handle connect from TCP client.  Note that UDP connections are
            ## stateless (no accept necessary)...
            my $new_tcp = $read->accept();
            $write_select->add($new_tcp);

        }
        elsif ($read == $udp_socket) {

            ## Handle data received from UDP socket...
            my $recv_buffer;

            $udp_socket->recv($recv_buffer,1024,undef);

            ## Write the data read from UDP out to the TCP client(s).  Again,no
            ## timeout.  This will block until a TCP socket is writable.  
            my @write = $write_select->can_write();

            foreach my $write (@write) {

                ## Make sure the socket is still connected before writing.
        if ($write->connected()) {
                     $write->send($recv_buffer);
                   }
                else {
                    $write_select->remove($write);
                    close $write;

                }

            }

        }

    }

}

解决方法

我对perl或perl套接字一无所知,但我想不出一个套接字API,它提供了一种知道socket是否连接的方法.事实上,我很确定TCP实际上并没有像这样立即知道.这告诉我,connected()并没有告诉你你认为它告诉你什么. (我不知道,但我敢打赌,它告诉你你是否打电话给连接/接受)

通常套接字通过读取或写入零字节来告诉您它们已断开连接 – 您可能希望检查写入的返回值以查看它是否返回零

(编辑:李大同)

【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容!

    推荐文章
      热点阅读